
One Year of Nushell - rainworld
https://www.nushell.sh/blog/2020/08/23/year_of_nushell.html
======
ChrisSD
> It also turns out that getting a shell correct is a lot more experimentation
> and a lot less following what the textbooks say. In practice, things like
> ‘stdout’ and ‘stderr’ are used in a variety of ways, as are the exit codes
> output by programs. Our initial designs started with a stricter view of
> these ideas, and softened over time as we saw that the real world is a much
> fuzzier place than we realized.

Good point. Exit codes can be difficult. A non-zero error value may not be an
error; it could indicate a type of success or be a warning or a result of a
calculation or any number of things depending on the application.

~~~
adamch
In a redesigned shell, ideally there would be a richer way to describe the
result of a program. Maybe "return an integer and consult the manual to see
what it means" isn't the best way forward.

Personally, I think Result types from Rust/Haskell/Swift make a lot of sense
-- a program either succeeds with some output, or fails with an explanation of
why. By default, pipes stop piping if one command fails.

~~~
moonchild
> Personally, I think Result types make a lot of sense -- a program either
> succeeds with some output, or fails with an explanation of why

Usually, this _is_ what happens. Usually, the error-signalling return is
accompanied by a message (posted to stderr).

> By default, pipes stop piping if one command fails
    
    
      set -o pipefail

~~~
toastal
pipefail is not available to POSIX shells like dash

~~~
roryrjb
set -o pipefail is now part of POSIX[0] and I believe as soon as someone posts
a patch to dash to implement it, it will get included[1].

[0].
[https://www.austingroupbugs.net/view.php?id=789](https://www.austingroupbugs.net/view.php?id=789)

[1]. [https://lore.kernel.org/linux-
dash/20200701015226.GA6839@gon...](https://lore.kernel.org/linux-
dash/20200701015226.GA6839@gondor.apana.org.au/T/#t)

~~~
toastal
This is great! Thanks for posting it.

------
geophile
Marcel is another pipe-objects-instead-of-strings shell. It takes a different
approach to shell/language unification, compared to nushell and other modern
shells. Marcel exposes Python on the command line, e.g. to find files that
changed in the last day:

    
    
        ls -fr | select (f: now() - f.mtime < days(1))
    

ls pipes File objects to the select, and that's a Python function inside the
parens.

Scripting is done in Python, using marcel's shell commands as functions, by
importing the module marcel.api. So the examle above in Python would be:

    
    
        from marcel.api import *
    
        for file in (ls(file=True, recursive=True) |
                     select(lambda f: now() - f.mtime < days(1))):
    
        print(file)
    

So it's the same shell command (ls ... | select ...), but expressed as Python
functions, and the result is an iterator so that the command output can be
used inside a for loop.

For more info:
[https://www.marceltheshell.org](https://www.marceltheshell.org),
[https://github.com/geophile/marcel](https://github.com/geophile/marcel).

~~~
xfer
It's not a different approach though. It works exactly the same way in
powershell(just the host language is different).

~~~
geophile
Thanks, I wasn't aware of that. I believe my comment still applies to nushell
and a couple of others.

I like bash for simple commands, but hate the requirement to learn so many
sublanguages for more sophisticated usage, (as in sed, awk, find, and others).
I like Python for scripting, but the integration of shell commands is really
not very good. I built marcel to fix both of these problems.

~~~
vips7L
Powershell scripting is still done in the powershell language, but you can
import all of the .net/c# runtime to use.

I'd like to build the same but using the JVM/groovy as the runtime/scripting
language.

------
ridiculous_fish
Nushell is the only shell I know of (other than fish) which uses threads.
Threads are famously difficult in shells because of the fork/thread
interaction.

How is Nushell able to use threads? For example how are subshells implemented?

~~~
vlmutolo
Part of it could be due to using Rust as the implementation language. Rust has
good, cross-platform abstractions over things like threads and processes. The
language tends to make it harder to shoot yourself in the foot.

Would definitely like to hear from the authors of Nushell on how their
language choice has held up over the course of the project.

~~~
ridiculous_fish
A related issue is leaking fds into child processes. For example, Go locks
around fork() to prevent racing with creating new fds (e.g. from pipe) [1].
Rust doesn't have any synchronization between fork and creating fds; I wonder
whether/how this is addressed in nushell.

1:
[https://golang.org/src/syscall/exec_unix.go?s=7064:7143#L19](https://golang.org/src/syscall/exec_unix.go?s=7064:7143#L19)

------
eigenrick
One of my favorite, unexpected features of nushell so far is `$it` the
implicit "iteration" variable. It makes sense to have something like this in
conjunction with the 'each' command, which makes it very easy to loop over
lists or tables.

But $it is still useful in the absence of 'each'.

For instance:

dirname is a useful tool but you can't pipe to it (at least not the GNU
version), it expects a string parameter. We can still easily plug it into
nushell pipelines though, thanks to $it, which is this case is basically
turning stdin into a string.

Since dirname won't let us do

    
    
        which nu | get path | dirname 
    

we can instead do

    
    
        which nu | get path | dirname $it 
    
    

If I wanted to do this in bash, I'd have to go through some annoying (but
common) machinations in order to convert stdin into a text string to pass to
dirname.

~~~
nitroll
Like which nu | xargs dirname

------
laksdjfkasljdf
reading only this post, is nushell just an implicit awk after each pipe, that
already know the output format of a few common programs? or something more
than that?

~~~
algorithmsRcool
Think powershell, but built in rust, posix first and better at processing
data(xml, csv, json, ...)

~~~
xfer
I looked at the book, currently it is nowhere close to powershell.

As far as i can tell no way to define any function/commands(you have to write
plugins in another language, make an executable??). It supports pipeline, has
a large amounts of built-in operators/commands(probably enough to be usable as
a shell) and built-in parsers for a few formats(how does one write support for
another data format?). Maybe in future it will address these questions.

~~~
ChrisSD
The linked post is explicitly about that:

> Looking at Nu today, you can see some common parts of languages like `if` or
> `open`, but it doesn’t yet feel like there’s enough syntax to build up full
> programs. You can’t define your own commands, your own variables, and you
> can’t build out a project across multiple files. We’re working to address
> all of these limitations so that Nu can function not only for one-liners,
> but also for much more.

------
forbes
This seems very interesting. After a quick play I cannot find anything similar
to 'less' which I use very frequently. Is there a nushell equivalent?

~~~
eigenrick
The equivalent is called `textview` which is a built-in which tries to be a
bit more intelligent than `less` with regard to file-types.

The default viewer, which sort of runs at the end of every pipeline is called
`autoview`.

Now.. autoview _should_ be calling textview in the cases where the pipeline
detects a large text value. It is possible that you're not exactly running a
pipeline.

For instance: If you run:

    
    
        cat big.log
    

it is not running a pipeline, just an external command.

If you run:

    
    
        open big.log
    
     you're invoking nushell's mechanism for creating a pipeline sourced by the contents of big.log.  You should also notice that textview is invoked, because there should be a pager. 
    
    

Alternatively, you can choose to create a pipeline by pipe-ing the output of
cat big.log into something. If you pipe it to textview you should see the same
result:

    
    
        cat big.log | textview 
    

Hope that helps!

~~~
forbes
The command that I was trying to use was 'ls', which doesn't seem to play with
textview when I try it out 'ls | textview' (just no output at all). textview
does work for me with files, as in your example.

------
garciasn
Is it just me or does the lack of line continuation (i.e. \\) really ruin all
of the beauty the rest of this shell provides?

------
svnpenn
My issue is that NuShell has line hinting, with no way to disable it

~~~
forbes
What is line hinting?

~~~
svnpenn
if you type a letter, it fills the rest of the line with what it thinks you
want to type next

