> [!Note] > > - <font color=red>Red</font>: Higher priority then the other items within its section. Things that affect user experience negatively or make maintenance and development harder. > - <font color=yellow>Yellow</font>: Doesn't need immediate attention, but has to be handled at some point. > - <font color=lightgreen>Green</font>: Wishlist / nice to have ## Documentation > [!Caution] Outdated Documentation > > nushell.sh docs can lag behind a lot > - "Custom command attributes" were merged in February and they still aren't in the docs > [!Warning] Search > > - The online docs are the first place newcomers will look. It should be easy to navigate for those who aren't familiar with nushell > - Web search should work at least as good as `help -f` > [!Tip] Builtin Docs / Tutor > > - `tutor` integrated with `explore` for a truly interactive experience > [!Tip] Extra Formats > > - Offline: pdf, epub, static html, manpages? > - https://devdocs.io/nushell/ (last updated at 0.85) ## Globbing > [!Warning] Multiple Globbing Implementations with Non-compatible Syntax > > Currently we have `nu-glob` and `wax` > #### `nu-glob` > - consistent between platforms > - has its own syntax shape > - 😞 limited functionality > #### `wax` > - more functionality > - 😞 some problems on windows > [!Important] Devyn's `glob_experiment` hopefully will replace both > [!Tip] Explicit Syntax > > - Common expectation is using backticks: > ``` > ls `crates/*/Cargo.toml` > ``` > - Could allow glob interpolation before we get into the whole bare-word pit: > ``` > $NU_PLUGIN_DIRS | each {|dir| ls $`($dir)/nu_*` } > ``` > [!Note] Set Operations on Globs - Unconventional 🤔 > > - We have a lot of commands that use globs, but only two of them support an `--exclude` flag, `glob` and `du` > - Most commands have `...rest: glob` (cp, mv, rm, ...) which works nicely, but some like ~~`watch` can't have that due to having a closure as its last parameter~~ (streaming `watch` 🥳) > - It would be really nice if we had a way to combine globs better than the brace/alternation syntax (`{abc,def}`), and a way to exclude patterns without adding another parameter to all commands that interact with globs > > Performing set operations on glob values (using operators or commands) could be really useful: > ``` > # difference > ls (`**/tsconfig.json` - `**/node_modules/**`) > > # union > watch ./ -g (`grammar.js` + `src/parser.c`) > ``` > > Checking if a path matches a glob: > ``` > if $file in $glob { ... } > ``` ## Completions > [!Warning] We have 3 separate apis for custom completions :worried: > > ### External completer > ```nushell > $env.config.completions.external.completer = {|spans: list<string>| ... } > ``` > For a commandline like this: > ```nushell > preceeding ... | pipeline ... | command we want to complete --ma > ``` > The completer closure receives a ***list*** of strings: > ```nushell > let spans = ["command", "we", "want", "to", "complete", "--ma"] > ``` > And is expected to return a list of suggestions: > ```nushell > list< > # let's call this type `suggestion` > oneof< > string, > record< > value: string > description?: string > style?: oneof<string, record> > > > > > > > ``` > > ### Custom command parameter completions > ```nushell > def "nu-complete foo" [context: string, position: int] { ... } > > def foo [ param: any@"nu-complete foo" ] { ... } > ``` > For a commandline like this: > ```nushell > preceeding ... | pipeline ... | command we want to complete --ma > ``` > The completer command receives a: > ```nushell > let context = "command we want to complete --ma" > let position = 65 # relative to *whole* commandline, not context > ``` > And is expected to return: > ```nushell > oneof< > list<suggestion>, > record< > options: record<case_sensitive, completion_algorithm, sort>, > completions: list<suggestion> > > > > > ``` > Custom command parameter completions can affect completion settings 😃, but using the context requires manually parsing it 😢 > > ### Custom menu source > ```nushell > $env.config.menus.0.source = {|buffer, position| ... } > ``` > Assuming `only_buffer_difference: false`, for a commandline like this: > ```nushell > preceeding ... | pipeline ... | command we want to complete --ma > ``` > The completer command receives a: > ```nushell > let context = "preceeding ... | pipeline ... | command we want to complete --ma" > let position = 65 > ``` > And is expected to return: > ```nushell > list< > record< > # The value that will be inserted in the buffer > value: any > # Optional. Description that will be displayed with the selected value > description: string > # Optional. Span indicating what section of the string > # will be replaced by the value > span: { start: int, end: int } > # Optional. A list of strings that will be displayed with the selected value. > # Only works with a description menu > extra: [string] > > > > > ``` > > ### What to do? > > #### Unify completer input: > - `spans: list<string>`: Same as current external completion, last pipeline element as tokens > - `context: string`: Whole commandline, including *after* the cursor. Kind of unnecessary, as it can be grabbed with `commandline`. Including it makes implementations easier to test. > - `pipeline_element/command: record<start: int, end: int>` (:bike::hut:) Span of the pipeline element the cursor is on. > - `cursor`: Cursor position. > - `on`: Position the completion was invoked. > > These should cover all existing use cases and allow new ones. :::success ### Whole command completion is implemented :tada: ::: ## `nu-table`/`tabled`/`explore` > [!caution] Maintenance > > ==@zhiburt== is more or less ***the*** maintainer. At least a few people in the core team should be familiar enough to deal with bugs when they pop up. > > If we want any new features or improvements, we should be familiar enough to experiment or at the very least have enough understanding to know what's feasible. We can't request new features without knowing what its implementation could entail. > [!Tip] explore > - `reedline` > - `input list` like multiple selection > - fuzzy selection? > - we can just offload this if we have a command that handles fuzzy sorting-filtering. It would be helpful for custom menus too. > Switch to `try` mode, write `fuzzy ...`, and you have it! ## Parser (current & new) ## Package Management > [!Warning] Package Sources > > - Don't couple too tightly to github or *even git* > - For git: support shallow and sparse checkouts, installing packages from monorepos that contain multiple packages shouldn't eat up more storage than necessary > - File system paths should not only be possible to use, but treated similarly to "external" sources, ie support updating, versioning etc > This would make it possible to use more exotic sources through file system mounts without modification to the package manager > - Support dependencies. Possibly include non nu dependencies: > [!Note] Ideas: > > - https://packspec.org/spec.html ## Terminal Event Hooks for Reedline > [!Warning] Problem > `term query` is very neat, but: > - it's blocking, and cant be run in a background job > - it cant cancel after a defined timeout > - it cant *react* to events it hasn't initiated itself reedline handles all IO in the repl including responding to terminal events like resizing. The basic idea - we can define a new type of hook for reacting to terminal events/requests - reedline handles the actual detection of these events - hooks can subscribe to specific events - maybe even to all `csi`/`osc` events like the neovim example below - hooks receive the terminal response as a `binary` ~~value~~ **stream** (see kitty's ambitious protocol extensions like advanced clipboard (binary data, mimetype, large size), tty file transfer etc) ### Inspiration from Neovim Neovim has two events that can be used handle terminal events: - `TermResponse`: This for handling events/responses neovim receives from the host terminal - `TermRequest`: This is for handling requests neovim's embedded terminal receives from child processes ```lua -- Query the terminal palette for the RGB value of color 1 -- (red) using OSC 4 vim.api.nvim_create_autocmd('TermResponse', { once = true, callback = function(args) local resp = args.data.sequence local r, g, b = resp:match("\027%]4;1;rgb:(%w+)/(%w+)/(%w+)") end, }) io.stdout:write("\027]4;1;?\027\\") ``` ## Advanced Stream Handling > [!Caution] TODO > Move over the post from `drawing-board` ## Stabilization :(