Nushell 0.87.0
Nushell, or Nu for short, is a new shell that takes a modern, structured approach to your command line. It works seamlessly with the data from your filesystem, operating system, and a growing number of file formats to make it easy to build powerful command line pipelines.
Today, we're releasing version 0.87.0 of Nu. This release focussed heavily on improving internals, fills a few gaps in our command set and completion handling, and starts work on an integrated LSP language server.
Where to get it
Nu 0.87.0 is available as pre-built binaries or from crates.io. If you have Rust installed you can install it using cargo install nu.
Note
The optional dataframe functionality is available by cargo install nu --features=dataframe.
As part of this release, we also publish a set of optional plugins you can install and use with Nu. To install, use cargo install nu_plugin_<plugin name>.
Table of content
- Themes of this release / New features
- Hall of fame
- LSP is coming to Nushell
- Living in the terminal: completions and hints
- Handling exotic paths
- Improving the
matchcommand - Pipeline redirections
- Some work on the standard library
- New allowed operands to the modulo operator
- Disallowing invalid table definitions and manipulations
- The documentation becomes better
- Some progress in the "dataframe" department
- Our set of commands is evolving
- Breaking changes
- Full changelog
Themes of this release / New features [toc]
Hall of fame [toc]
Bug fixes [toc]
Thanks to all the contributors below for helping us solve issues and bugs 🙏
| author | description | url |
|---|---|---|
| @hustcer | Fix winget release submission error | #10757 |
| @sophiajt | fix the flag type on release-pkg.nu | #10762 |
| @fdncred | update release-pkg.nu with updated manual instructions | #10759 |
| @amtoine | remove the last mention to let-env | #10718 |
| @hustcer | Update Nushell version to v0.86 for release script | #10797 |
| @stfacc | Do not use white text in the default light theme | #10796 |
| @sholderbach | Revert "Bump regex from 1.9.6 to 1.10.2" | #10818 |
| @fdncred | fix main not building due to errors later found in describe | #10821 |
| @hudclark | fix: Ensure consistent vals and cols when parsing with --flexible | #10814 |
| @gaetschwartz | Fix describe -d for lazy records | #10836 |
| @fdncred | updated NU_LIB_DIRS delimiter for command line | #10837 |
| @WindSoilder | redirection: fix internal commands error with o+e> redirection | #10816 |
| @amtoine | sync $env.config.filesize.metric | #10277 |
| @michel-slm | [nu-cmd-base] add missing LICENSE text | #10855 |
| @amtoine | use to_lowercase in str downcase | #10850 |
| @lavafroth | fix: preserve path when completing intermediate directory | #10831 |
| @CAD97 | Improve case insensitivity consistency | #10884 |
| @stfacc | Add "shape_keyword" to default config | #10922 |
| @KAAtheWiseGit | Fix issues with error make refactor | #10950 |
| @hustcer | Fix alpine docker file | #10992 |
| @gaetschwartz | Fix tests for cargo.exe check command | #11022 |
| @FMotalleb | Fix (http) get HTTP_PROXY from $env | #11026 |
| @fdncred | allow items to properly evaluate block settings | #10980 |
| @WindSoilder | fix custom command's default value | #11043 |
Enhancing the documentation [toc]
Thanks to all the contributors below for helping us making the documentation of Nushell commands better 🙏
| author | description | url |
|---|---|---|
| @Hofer-Julian | Add long options for misc and network | #10753 |
| @Hofer-Julian | Add long options for generators and math | #10752 |
| @Hofer-Julian | Add long options for platform and random | #10776 |
| @Hofer-Julian | Add long options for path | #10775 |
| @Hofer-Julian | Use long options for string | #10777 |
| @Hofer-Julian | Add long options for viewers | #10787 |
| @KAAtheWiseGit | Change category of scope commands to core | #10892 |
| @dzorya | better help message for MissingPositional error | #10949 |
| @drbrain | Show plugin extra usage and search terms | #10952 |
| @drbrain | Update description and error types for split-by | #10865 |
| @fdncred | update items example to send data through the pipeline | #10976 |
| @sholderbach | Spell out our platform support policy | #10778 |
Changes to the internals of Nushell [toc]
Thanks to all the contributors below for helping us making the source base of Nushell better and helping with the general development process of the project 🙏
| author | description | url |
|---|---|---|
| @WindSoilder | Refactor: simplify lex_item impl | #10744 |
| @WindSoilder | Refactor: remove duplicate code to simplify lite_parsing logic. | #10735 |
| @lavafroth | Extract common logic for setting error in parse_short_flags | #10709 |
| @amtoine | add toolkit run to run a Nushell revision | #10687 |
| @CAD97 | Remove registry clean_string hack | #10804 |
| @sholderbach | Convert more examples and tests to record! macro | #10840 |
| @sholderbach | Add common map-like API to nu_protocol::Record | #10841 |
| @sholderbach | Add Record::remove/retain/retain_mut | #10876 |
| @sholderbach | Convert "pure" macros to pure fn in config.rs | #10893 |
| @IanManske | Reuse Closure type in Value::Closure | #10894 |
| @WindSoilder | Refactor: introduce a gen_save_call function to reduce duplicate code | #10852 |
| @IanManske | Make FromValue take owned Values | #10900 |
| @sholderbach | Use Record APIs in nu-protocol/nu-engine | #10917 |
| @IanManske | Reduce element shifting in Record::retain_mut | #10915 |
| @fdncred | remove unwraps in registry_query command | #10936 |
| @drbrain | Restore test_config tests | #10954 |
| @fdncred | updates trash dependency to 3.1.2 | #10965 |
| @fdncred | remove unnecessary files | #10966 |
| @drbrain | Convert ShellError::UnsupportedInput to named fields | #10971 |
| @IanManske | Use Vec for Closure captures | #10940 |
| @sholderbach | Refactor find in terms of clean Record API | #10929 |
| @sholderbach | Refactor table cmd and nu-table with Record API | #10930 |
| @drbrain | Convert ShellError::DatetimeParseError to named fields | #10991 |
| @sholderbach | Use Record's public API in a bunch of places | #10927 |
| @sholderbach | Refactor and fix Config<->Value mechanism | #10896 |
| @IanManske | Use Record::get instead of Value functions | #10925 |
| @sholderbach | Add Record::drain to take out elements by range | #11002 |
| @sholderbach | Use record API in more parts of nu-protocol | #10928 |
| @IanManske | Refactor env conversion to eliminate Value::follow_cell_path_not_from_user_input | #10926 |
| @sholderbach | Add Record::truncate for trimming based on len | #11004 |
| @IanManske | Refactor drop columns to fix issues | #10903 |
| @drbrain | Match toolkit clippy settings to CI clippy settings | #10984 |
| @IanManske | Refactor flatten command | #11017 |
| @IanManske | Implement Display for CellPath | #11023 |
| @CAD97 | Limit run-external --redirect-combine sh test to not(Windows) | #10905 |
| @KAAtheWiseGit | Add special error case for alias | #10975 |
LSP is coming to Nushell [toc]
IDE support has been and still is one of the big goals for Nushell 1.0: a modern language needs to have proper language support to unlock pleasant and fast development with it 😄
In #10990, @fdncred made the shell integration with VS Code better.
Warning
The rest of this section is in the early stages of its development. It will require time to mature and be fully featured, but we're happy to ship it with Nushell as of now.
Thanks to @schrieveslaach and #10723, LSP is now coming to Nushell!
As Cargo comes with Rust, we want Nushell to embed its language support one way or another. The goal is to make nu fully featured and capable of handling LSP, formatting, and testing without any extra installation by default.
#10723 integrates a Language Server Protocol (LSP) implementation directly inside Nushell. Running
nu --lspwill start the language server.
When properly configured in an IDE, the server can be run and then a client can attach to it and query things like diagnostics, completions, and more in the future.
A very incomplete example, just to give you an idea, could be the following to setup nu --lsp as a language server in Neovim:
configs.nulsp = {
default_config = {
cmd = { "nu", "--lsp" },
filetypes = { "nu" },
root_dir = function(fname)
...
end
},
}Living in the terminal: completions and hints [toc]
Thanks to @lavafroth in #10898 Nushell will now fall back to the builtin default completer when external completers are defined but return no results for the current command.
Note
The following example is fictitious, carapace-bin should be able to complete it 😉
Let's say you have Carapace setup as an external completer but it is not able to autocomplete git comm<TAB>, then Nushell will try to do it.
Because most commands make sense only in the directory they were run in, @p00f wrote #10780 which will make hints aware of the current directory.
Note
Hints are the shadowed incomplete completions that appear when you start typing commands, e.g. if you were to run echo foo bar baz, pressing echo would then show foo bar baz in a dimmed font: this is a hint.
Handling exotic paths [toc]
As can be seen in #10571 , #10364 , #10211 , #9558, #9310 and probably more related issues and duplicates, handling exotic filenames and filesystem paths, e.g. containing globbing characters or looking like command options, is a non-trivial problem to solve.
As part of this new release, @lavafroth and @bobhy have worked in the direction of making this experience better in Nushell:
- files that look like command options, i.e. starting with
-or--will be correctly escaped in completions with #10721 - with #10694 commands such as
cp,rm, ormvwill first look at files from the input paths as the literal string and then, only if the literal file does not exist, they will expand the globbing and work on the resulting found files
e.g. let's say I created a bunch of files, one of them containing an obvious globbing pattern
touch *.txt foo.txt bar.txt baz.txt- running
rm *.txtonce will only remove*.txtand leave the three{foo,bar,baz}.txtfiles - running
rm *.txta second time will remove all the other files
Tips
The first time *.txt is interpreted as a literal and the *.txt file is found and removed. The second time *.txt is not found as a literal filename. rm searches for *.txt as a glob pattern; finds foo.txt, bar.txt, and baz.txt; and removes them.
Improving the match command [toc]
Can we all agree for one moment that match is a great command?
def work-on-list []: any -> string {
match $in {
[$x, ..] if $x == 1 => { 'good list' },
[..] => { 'not a very good list' },
_ => { 'not a list at all' }
}
}> [1, 2, 3] | work-on-list
good list
> [2, 1, 3] | work-on-list
not a very good list
> "ehe i'm not a list" | work-on-list
not a list at allHowever, it had a pretty big flaw: it was not able to work on null values 😮
> match null { null => "success", _ => "failure" }
failureIn #10829, thanks to @hudclark, the match command is now able to work properly on null values.
> match null { null => "success", _ => "failure" }
successPipeline redirections [toc]
Once again @WindSoilder has been working on pipeline redirections. Because they need to be given a target path to properly function, i.e.
echo aaa o> | ignoredoes not make sense in itself, #10835 makes commands such as the one just above throw a nice error:
Error: nu::parser::parse_mismatch
× Parse mismatch during operation.
╭─[entry #1:1:1]
1 │ echo aaa o> | ignore
· ─┬
· ╰── expected redirection target
╰────The following will still function as expected:
echo aaa o> foo.txt | ignoreSome work on the standard library [toc]
@amtoine made the use of std 'path add' better in #10710. Now this command that allows adding paths to the $env.PATH environment variable will (1) expand all the input paths to get only absolute paths and (2) split $env.PATH on : to make sure the command runs properly the first time it runs in the configuration.
Note
If Bash is still your login shell, the value of $env.PATH in env.nu might be a :-separated list of system paths. This change to std 'path add' should help prevent the final $env.PATH from containing this original :-separated list of paths.
A new candidate to the standard library, null-stream, has been added by @Hullabaloo-and-Howdy-Do in nushell/nu_scripts#649
New allowed operands to the modulo operator [toc]
When doing maths, modulo is a ubiquitous operator, e.g.
> (11 + 5) mod 7
2> (123 * 456) mod 13
6However, this operation was only possible on int and float values. As durations are so similar to integers and real numbers, i.e. they are just numbers with a simple unit, @gaetschwartz implemented the mod operator of Nushell for durations in #10745.
Thanks to their work, Nushell will now allow the following command:
> (2min + 31sec) mod 20sec
11secDisallowing invalid table definitions and manipulations [toc]
As can be seen in #11020 and #10875, Nushell will let you define or manipulate tables that have columns called the same. Starting the effort to fix these unexpected and error-prone behaviors, @sholderbach disallowed the definition of table literals with duplicated columns in #10875.
Trying to define the following ill-defined table
[[a a]; [1 2]]will result in an error from now onwards.
Error: nu::shell::column_defined_twice
× Record field or table column used twice
╭─[entry #2:1:1]
1 │ [[a a]; [1 2]]
· ┬ ┬
· │ ╰── field redefined here
· ╰── field first defined here
╰────The documentation becomes better [toc]
This section sheds some light on some of the contributions from Enhancing the documentation.
PluginSignature test 1 for plugin. Returns Value::Nothing
Extra usage for nu-example-1
Search terms: example
Usage:
> nu-example-1 {flags} <a> <b> (opt) ...(rest)
Flags:
-h, --help - Display the help message for this command
-f, --flag - a flag for the signature
-n, --named <String> - named string
Parameters:
a <int>: required integer value
b <string>: required string value
opt <int>: Optional number (optional)
...rest <string>: rest value string
Examples:
running example with an int value and string value
> nu-example-1 3 bbSome progress in the "dataframe" department [toc]
Thanks again to @ayax79 who has been working on the dataframes.
- dataframes will now support small int types with #10828
- with #10943, dataframes will now be able to read Polars structs, such as JSONL or PARQUET files that contain rows with structured data
Our set of commands is evolving [toc]
As usual, new release rhymes with changes to commands!
New commands [toc]
whoamiusing uutils by @tertsdiepraam in #10488umkdirusing uutils by @KAAtheWiseGit in #10785- In an upcoming release we intend to replace our existing
mkdircommand with this uutils implementation
- In an upcoming release we intend to replace our existing
execfor Windows by @IanManske in #11001
Changes to existing commands [toc]
- the
ansi linkcommand has been put back to the default set of commands of Nushell by @hustcer in #10801. It should be available without any extra steps with this release. - @Tiggax added
--ignore-errortoreject#10737 - in #10795 @gaetschwartz added a
--detailedoption todescribe --updatehas been added back tocpby @ludwig-austermann in #10824- empty lists are now allowed as input to
group-byand will return an empty record thanks to @0scvr in #10730 - @CAD97 has improved the return types of
registry valuein #10806 - @gaetschwartz has made the
debug infocommand lazy in #10728 group-bynow returns a table instead of a record if you pass it the new flag--to-tablethanks to @drbrain and #10848.- with the changes from @fdncred in #10870 and #10912,
sort-byis now allowed to work with records andcompactwith empty strings input listwill now returnnullwhen no choice has been selected, see the contribution of @KAAtheWiseGit in #10913- thanks to @KAAtheWiseGit
error makehas been refactored in #10923 and will now take a$.label.spanand a$.help
error make {
msg: "Message"
label: {
text: "Label text"
span: (metadata $var).span
}
}- with #11013 and thanks to @sholderbach
transposehas been refactored and should now be much faster - in #11024 @WindSoilder allowed
rejectto take lists as selector values - the
--prettyoption has been removed fromto xmlin favor of--indentby @Hofer-Julian in #10668
Deprecated commands [toc]
extern-wrappedin favor ofdef --wrappedby @amtoine in #10716def-envin favor ofdef --envby @amtoine in #10715unfoldin favor ofgenerateby @fdncred and @amtoine in #10770 and #10771sizein favor ofstr statsby @amtoine and @hustcer in #10772 and #10798glob --notin favor ofglob --excludeby @amtoine in #10827
Removed commands [toc]
- the
$nothingvariable by @amtoine in #10567 random integerby @amtoine in #10568 in favor ofrandom intprofileby @kubouch in #10807
Breaking changes [toc]
- #10884 Improve case insensitivity consistency
- #10923 Refactor
error make - #10913 Change
input listto return null - #10875 Disallow duplicated columns in table literals
- #10806 Improve
registry valuereturn types - #10807 Finish removing
profilecommand and related data - #10568 remove
random integerin favor ofrandom int - #10668 Remove
to xml --pretty - #10567 remove the
$nothingvariable
Full changelog [toc]
Nushell
- WindSoilder created
- fix custom command's default value
- make reject support list input directly
- Refactor: introduce a
gen_save_callfunction to reduce duplicate code - redirection: fix internal commands error with
o+e>redirection - redirect should have a target
- Refactor: remove duplicate code to simplify
lite_parsinglogic. - Refactor: simplify lex_item impl
- sholderbach created
- Bump
rustixpatch versions - Revert "add color-backtrace crate (#10942)"
- Refactor
transposeand improve perf - Add
Record::truncatefor trimming based on len - Use record API in more parts of
nu-protocol - Add
Record::drainto take out elements by range - Refactor and fix
Config<->Valuemechanism - Use
Record's public API in a bunch of places - Refactor
tablecmd andnu-tablewith Record API - Refactor
findin terms of cleanRecordAPI - Use Record APIs in
nu-protocol/nu-engine - Disallow duplicated columns in table literals
- Convert "pure" macros to pure fn in
config.rs - Add
Record::remove/retain/retain_mut - Add common map-like API to
nu_protocol::Record - Convert more examples and tests to
record!macro - Revert "Bump regex from 1.9.6 to 1.10.2"
- Spell out our platform support policy
- Bump version to
0.86.1
- Bump
- app/dependabot created
- Bump crate-ci/typos from 1.16.22 to 1.16.23
- Bump indexmap from 2.0.2 to 2.1.0
- Bump crate-ci/typos from 1.16.21 to 1.16.22
- Bump hustcer/setup-nu from 3.7 to 3.8
- Bump hustcer/setup-nu from 3.6 to 3.7
- Bump rust-ini from 0.19.0 to 0.20.0
- Bump scraper from 0.17.1 to 0.18.1
- Bump crate-ci/typos from 1.16.20 to 1.16.21
- Bump which from 4.4.2 to 5.0.0
- Bump uuid from 1.4.1 to 1.5.0
- Bump regex from 1.9.6 to 1.10.2
- Bump crate-ci/typos from 1.16.19 to 1.16.20
- Bump csv from 1.2.2 to 1.3.0
- Bump lru from 0.11.1 to 0.12.0
- Bump rustix from 0.36.15 to 0.36.16
- FMotalleb created
- gaetschwartz created
- IanManske created
- Implement
DisplayforCellPath - Refactor
flattencommand - Refactor
drop columnsto fix issues - Refactor env conversion to eliminate
Value::follow_cell_path_not_from_user_input - Add
execcommand for Windows - Use
Record::getinstead ofValuefunctions - Use
VecforClosurecaptures - Reduce element shifting in
Record::retain_mut - Make
FromValuetake ownedValues - Reuse
Closuretype inValue::Closure
- Implement
- ayax79 created
- drbrain created
- Match toolkit clippy settings to CI clippy settings
- Convert ShellError::DatetimeParseError to named fields
- Convert ShellError::UnsupportedInput to named fields
- Update description and error types for
split-by - Restore test_config tests
- Show plugin extra usage and search terms
group-bynow returns a table instead of a record
- CAD97 created
- KAAtheWiseGit created
- hustcer created
- fdncred created
- allow vscode-specific ansi escape sequence to set path
- allow
itemsto properly evaluate block settings - update
itemsexample to send data through the pipeline - add color-backtrace crate for more intuitive backtraces
- remove unnecessary files
- updates
trashdependency to 3.1.2 - remove unwraps in registry_query command
- allow
compactto also compact empty strings - allow
sort-byto work with records - updated NU_LIB_DIRS delimiter for command line
- fix main not building due to errors later found in describe
- rename
unfoldtogenerate - update release-pkg.nu with updated manual instructions
- dzorya created
- stfacc created
- schrieveslaach created
- lavafroth created
- michel-slm created
- amtoine created
- use
to_lowercaseinstr downcase - deprecate
glob --notin favor ofglob --exclude - expand paths and split PATH in
std path add - sync
$env.config.filesize.metric - add
toolkit runto run a Nushell revision - deprecate
sizetostr size - add
unfoldback with a deprecation warning - remove
random integerin favor ofrandom int - remove the
$nothingvariable - deprecate
def-envandexport def-env - deprecate
extern-wrappedandexport extern-wrapped - remove the last mention to
let-env
- use
- tertsdiepraam created
- ludwig-austermann created
- hudclark created
- kubouch created
- Hofer-Julian created
- p00f created
- 0scvr created
- Tiggax created
- sophiajt created
- bobhy created
Extension
- EmilyGraceSeville7cf created
- Yakiyo created
- fdncred created
Documentation
- WindSoilder created
- Traister101 created
- MarikaChlebowska created
- amtoine created
- cosineblast created
- wanesty created
- noverby created
- stfacc created
- xBLACKICEx created
- Roba1993 created
- CBenoit created
- sholderbach created
- rukai created
- Stromberg90 created
- hustcer created
- hatunike created
- 0scvr created
Nu_Scripts
- sholderbach created
- Abdillah created
- fj0r created
- amtoine created
- fix the TOC of the release note template
- fix the indentation of the comments in the release note template...
- add a command to get last release date in the release note template
- complete the release note template
- add a few enhancements to the
create-prscript for releases - make
list-merged-prsa module and add template example - update the
nu-themesreadme - make hooks a module
- make the themes a module
- fix removed commands
- fnuttens created
- fdncred created
- Hullabaloo-and-Howdy-Do created
- AntoineSebert created
- drbrain created
Reedline
- Hofer-Julian created
- p00f created
- ClementNerma created
- LevitatingBusinessMan created
- fdncred created
- stfacc created
- sunfishcode created