mirror of
https://github.com/fish-shell/fish-shell.git
synced 2026-05-11 02:51:15 -03:00
Compare commits
23 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
b2f791b577 | ||
|
|
61a637bcc5 | ||
|
|
86a736df57 | ||
|
|
22e6b3db16 | ||
|
|
727934c6b6 | ||
|
|
92d50414c4 | ||
|
|
1361a5f68c | ||
|
|
04af336843 | ||
|
|
670636885c | ||
|
|
62d8f7277b | ||
|
|
c18f293ae2 | ||
|
|
874fc439dd | ||
|
|
768a9b1fd3 | ||
|
|
866df31c9d | ||
|
|
c241b782e7 | ||
|
|
23518e7ad8 | ||
|
|
9f54c8d88b | ||
|
|
6c460f643c | ||
|
|
b8e7b6bcb0 | ||
|
|
aad64ccdc0 | ||
|
|
ba44c4242f | ||
|
|
210dda2c4c | ||
|
|
251fbc7260 |
@@ -1,3 +1,19 @@
|
||||
fish 3.3.1 (released July 6, 2021)
|
||||
==================================
|
||||
|
||||
This release of fish fixes the following problems identified in fish 3.3.0:
|
||||
|
||||
- The prompt and command line are redrawn correctly in response to universal variable changes (:issue:`8088`).
|
||||
- A superfluous error that was produced when setting the ``PATH`` or ``CDPATH`` environment variables to include colon-delimited components that do not exist was removed (:issue:`8095`).
|
||||
- The Vi mode indicator in the prompt is repainted correctly after :kbd:`Ctrl-C` cancels the current command (:issue:`8103`).
|
||||
- fish builds correctly on platforms that do not have a ``spawn.h`` header, such as old versions of OS X (:issue:`8097`).
|
||||
|
||||
A number of improvements to the documentation, and fixes for completions, are included as well.
|
||||
|
||||
If you are upgrading from version 3.2.2 or before, please also review the release notes for 3.3.0 (included below).
|
||||
|
||||
--------------
|
||||
|
||||
fish 3.3.0 (released June 28, 2021)
|
||||
===================================
|
||||
|
||||
|
||||
@@ -47,6 +47,10 @@ NOTARIZE_UUID=$(xcrun altool --notarize-app \
|
||||
test -z "$NOTARIZE_UUID" && cat "$LOGFILE" && die "Could not get RequestUUID"
|
||||
echo "RequestUUID: $NOTARIZE_UUID"
|
||||
|
||||
# notarization-info doesn't always know about our request immediately.
|
||||
echo "Giving notarization-info a chance to catch up..."
|
||||
sleep 15
|
||||
|
||||
success=0
|
||||
for i in $(seq 20); do
|
||||
echo "Checking progress..."
|
||||
|
||||
@@ -145,7 +145,7 @@ Note that fish has a default titlebar message, which will be used if the fish_ti
|
||||
|
||||
How do I run a command from history?
|
||||
------------------------------------
|
||||
Type some part of the command, and then hit the :kbd:`↑` (up) or :kbd:`↓` (down) arrow keys to navigate through history matches. Additional default key bindings include :kbd:`Control`\ +\ :kbd:`P` (up) and :kbd:`Control`\ +\ :kbd:`N` (down).
|
||||
Type some part of the command, and then hit the :kbd:`↑` (up) or :kbd:`↓` (down) arrow keys to navigate through history matches. Additional default key bindings include :kbd:`Control`\ +\ :kbd:`P` (up) and :kbd:`Control`\ +\ :kbd:`N` (down). See :ref:`Searchable command history <history-search>` for more information.
|
||||
|
||||
Why doesn't history substitution ("!$" etc.) work?
|
||||
--------------------------------------------------
|
||||
|
||||
@@ -523,7 +523,7 @@ After a command has been executed, it is remembered in the history list. Any dup
|
||||
|
||||
By pressing :kbd:`Alt`\ +\ :kbd:`↑` and :kbd:`Alt`\ +\ :kbd:`↓`, a history search is also performed, but instead of searching for a complete commandline, each commandline is broken into separate elements just like it would be before execution, and the history is searched for an element matching that under the cursor.
|
||||
|
||||
History searches are case-insensitive unless the search string contains an uppercase character, and they can be aborted by pressing the escape key.
|
||||
History searches are case-insensitive unless the search string contains an uppercase character. You can stop a search to edit your search string by pressing :kbd:`Esc` or :kbd:`Page Down`.
|
||||
|
||||
Prefixing the commandline with a space will prevent the entire line from being stored in the history.
|
||||
|
||||
|
||||
@@ -190,7 +190,6 @@ div.body a:hover {
|
||||
|
||||
tt, code, pre {
|
||||
font-family: monospace, sans-serif;
|
||||
font-size: 96.5%;
|
||||
/* Older sphinx versions set a color here, we need to inherit it from the outer div.highlight */
|
||||
background-color: inherit;
|
||||
}
|
||||
@@ -321,22 +320,22 @@ dl > dt span ~ em {
|
||||
|
||||
.sphinxsidebar ul.current > li.current { font-weight: bold }
|
||||
|
||||
.gray { color: #555555 }
|
||||
.purple { color: #551a8b }
|
||||
.red { color: #FF0000 }
|
||||
.gray { color: #777 }
|
||||
.purple { color: #551a8b; font-weight: bold; }
|
||||
.red { color: #FF0000; }
|
||||
|
||||
/* Color based on the Name.Function (.nf) class from pygments.css. */
|
||||
.command { color: #005fd7 }
|
||||
|
||||
/* Color based on the Name.Constant (.no) class from pygments.css. */
|
||||
.param { color: #00afff }
|
||||
.param { color: #00bfff }
|
||||
|
||||
/* Color based on the Name.Constant (.no) class from pygments.css. */
|
||||
/* Used for underlining file paths in interactive code examples. */
|
||||
.param-valid-path { color: #00afff; text-decoration: underline }
|
||||
|
||||
/* Color based on the Generic.Prompt (.gp) class from pygments.css. */
|
||||
.prompt { color: #8f5902 }
|
||||
.prompt { color: #8f7902 }
|
||||
|
||||
kbd {
|
||||
background-color: #f9f9f9;
|
||||
@@ -388,7 +387,7 @@ kbd {
|
||||
}
|
||||
|
||||
div.sphinxsidebar h3 a, div.related a, div.sphinxsidebar h3 {
|
||||
color: #AAA;
|
||||
color: #BBB;
|
||||
}
|
||||
.highlight {
|
||||
background: #000;
|
||||
@@ -408,12 +407,9 @@ kbd {
|
||||
}
|
||||
input {
|
||||
background-color: #222;
|
||||
color: #AAA;
|
||||
color: #BBB;
|
||||
}
|
||||
|
||||
div.body a {
|
||||
color: #2092da;
|
||||
}
|
||||
dt:target, span.highlighted {
|
||||
background-color: #404060;
|
||||
}
|
||||
@@ -424,4 +420,18 @@ kbd {
|
||||
table.docutils td, table.docutils th {
|
||||
border: 1px solid #222 !important;
|
||||
}
|
||||
div.body a {
|
||||
color: #2092fa;
|
||||
}
|
||||
div.footer a {
|
||||
color: #BBB;
|
||||
}
|
||||
|
||||
/* Color based on the Name.Function (.nf) class from pygments.css. */
|
||||
.command { color: #008fd7 }
|
||||
|
||||
/* The table background on fishfish Beta r1 */
|
||||
th, dl.field-list > dt {
|
||||
background-color: #121;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,28 +1,21 @@
|
||||
.highlight .hll { background-color: #ffffcc }
|
||||
.highlight { background: #f8f8f8; }
|
||||
.highlight .c { color: #8f5902; } /* Comment */
|
||||
.highlight .err { color: #a40000; border: 1px solid #ef2929 } /* Error */
|
||||
.highlight .g { color: #000000 } /* Generic */
|
||||
.highlight .k { color: #204a87; font-weight: bold } /* Keyword */
|
||||
.highlight .l { color: #000000 } /* Literal */
|
||||
.highlight .n { color: #000000 } /* Name */
|
||||
.highlight .o { color: #00a6b2; } /* Operator */
|
||||
.highlight .x { color: #000000 } /* Other */
|
||||
.highlight .p { color: #00afff; } /* Punctuation */
|
||||
.highlight .ch { color: #8f5902; font-style: italic } /* Comment.Hashbang */
|
||||
.highlight .cm { color: #8f5902; font-style: italic } /* Comment.Multiline */
|
||||
.highlight .cp { color: #8f5902; font-style: italic } /* Comment.Preproc */
|
||||
.highlight .cpf { color: #8f5902; font-style: italic } /* Comment.PreprocFile */
|
||||
.highlight .c1 { color: #8f5902; font-style: italic } /* Comment.Single */
|
||||
.highlight .cs { color: #8f5902; font-style: italic } /* Comment.Special */
|
||||
.highlight .p { color: #00bfff; } /* Punctuation */
|
||||
.highlight .c { color: #8f7902; } /* Comment */
|
||||
.highlight .ch { color: #8f7902; font-style: italic } /* Comment.Hashbang */
|
||||
.highlight .cm { color: #8f7902; font-style: italic } /* Comment.Multiline */
|
||||
.highlight .cp { color: #8f7902; font-style: italic } /* Comment.Preproc */
|
||||
.highlight .cpf { color: #8f7902; font-style: italic } /* Comment.PreprocFile */
|
||||
.highlight .c1 { color: #8f7902; font-style: italic } /* Comment.Single */
|
||||
.highlight .cs { color: #8f7902; font-style: italic } /* Comment.Special */
|
||||
.highlight .gd { color: #a40000 } /* Generic.Deleted */
|
||||
.highlight .ge { color: #000000; font-style: italic } /* Generic.Emph */
|
||||
.highlight .gr { color: #ef2929 } /* Generic.Error */
|
||||
.highlight .gh { color: #000080; font-weight: bold } /* Generic.Heading */
|
||||
.highlight .gi { color: #00A000 } /* Generic.Inserted */
|
||||
.highlight .go { color: #000000; font-style: italic } /* Generic.Output */
|
||||
.highlight .gp { color: #8f5902 } /* Generic.Prompt */
|
||||
.highlight .gs { color: #000000; font-weight: bold } /* Generic.Strong */
|
||||
.highlight .gp { color: #8f7902 } /* Generic.Prompt */
|
||||
.highlight .gu { color: #800080; font-weight: bold } /* Generic.Subheading */
|
||||
.highlight .gt { color: #a40000; font-weight: bold } /* Generic.Traceback */
|
||||
.highlight .kc { color: #204a87; font-weight: bold } /* Keyword.Constant */
|
||||
@@ -31,23 +24,17 @@
|
||||
.highlight .kp { color: #204a87; font-weight: bold } /* Keyword.Pseudo */
|
||||
.highlight .kr { color: #204a87; font-weight: bold } /* Keyword.Reserved */
|
||||
.highlight .kt { color: #204a87; font-weight: bold } /* Keyword.Type */
|
||||
.highlight .ld { color: #000000 } /* Literal.Date */
|
||||
.highlight .m { color: #0000cf; font-weight: bold } /* Literal.Number */
|
||||
.highlight .s { color: #4e9a06 } /* Literal.String */
|
||||
.highlight .na { color: #c4a000 } /* Name.Attribute */
|
||||
.highlight .nb { color: #204a87 } /* Name.Builtin */
|
||||
.highlight .nc { color: #000000 } /* Name.Class */
|
||||
.highlight .no { color: #00afff } /* Name.Constant */
|
||||
.highlight .no { color: #00bfff } /* Name.Constant */
|
||||
.highlight .nd { color: #5c35cc; font-weight: bold } /* Name.Decorator */
|
||||
.highlight .ni { color: #ce5c00 } /* Name.Entity */
|
||||
.highlight .ne { color: #cc0000; font-weight: bold } /* Name.Exception */
|
||||
.highlight .nf { color: #005fd7 } /* Name.Function */
|
||||
.highlight .nl { color: #f57900 } /* Name.Label */
|
||||
.highlight .nn { color: #000000 } /* Name.Namespace */
|
||||
.highlight .nx { color: #000000 } /* Name.Other */
|
||||
.highlight .py { color: #000000 } /* Name.Property */
|
||||
.highlight .nt { color: #204a87; font-weight: bold } /* Name.Tag */
|
||||
.highlight .nv { color: #000000 } /* Name.Variable */
|
||||
.highlight .ow { color: #204a87; font-weight: bold } /* Operator.Word */
|
||||
.highlight .w { color: #f8f8f8; } /* Text.Whitespace */
|
||||
.highlight .mb { color: #0000cf; font-weight: bold } /* Literal.Number.Bin */
|
||||
@@ -59,7 +46,7 @@
|
||||
.highlight .sb { color: #4e9a06 } /* Literal.String.Backtick */
|
||||
.highlight .sc { color: #4e9a06 } /* Literal.String.Char */
|
||||
.highlight .dl { color: #4e9a06 } /* Literal.String.Delimiter */
|
||||
.highlight .sd { color: #8f5902; font-style: italic } /* Literal.String.Doc */
|
||||
.highlight .sd { color: #8f7902; font-style: italic } /* Literal.String.Doc */
|
||||
.highlight .s2 { color: #999900 } /* Literal.String.Double */
|
||||
.highlight .se { color: #00a6b2 } /* Literal.String.Escape */
|
||||
.highlight .sh { color: #4e9a06 } /* Literal.String.Heredoc */
|
||||
@@ -69,9 +56,37 @@
|
||||
.highlight .s1 { color: #999900 } /* Literal.String.Single */
|
||||
.highlight .ss { color: #4e9a06 } /* Literal.String.Symbol */
|
||||
.highlight .bp { color: #3465a4 } /* Name.Builtin.Pseudo */
|
||||
.highlight .fm { color: #000000 } /* Name.Function.Magic */
|
||||
.highlight .vc { color: #000000 } /* Name.Variable.Class */
|
||||
.highlight .vg { color: #000000 } /* Name.Variable.Global */
|
||||
.highlight .vi { color: #000000 } /* Name.Variable.Instance */
|
||||
.highlight .vm { color: #000000 } /* Name.Variable.Magic */
|
||||
.highlight .il { color: #0000cf; font-weight: bold } /* Literal.Number.Integer.Long */
|
||||
|
||||
:root {
|
||||
--contrast: #000000;
|
||||
}
|
||||
|
||||
@media (prefers-color-scheme: dark) {
|
||||
:root {
|
||||
--contrast: #FFFFFF;
|
||||
}
|
||||
.highlight .k { color: #507a97; font-weight: bold } /* Keyword */
|
||||
.highlight .nf { color: #009fe7 } /* Name.Function */
|
||||
.highlight .c { color: #8fb902; } /* Comment */
|
||||
.highlight .nf { color: #008fd7 } /* Name.Function */
|
||||
.highlight .nb { color: #209a87 } /* Name.Builtin */
|
||||
}
|
||||
.highlight .g { color: var(--contrast) } /* Generic */
|
||||
.highlight .l { color: var(--contrast) } /* Literal */
|
||||
.highlight .n { color: var(--contrast) } /* Name */
|
||||
.highlight .x { color: var(--contrast) } /* Other */
|
||||
.highlight .ge { color: var(--contrast); font-style: italic } /* Generic.Emph */
|
||||
.highlight .go { color: var(--contrast); font-style: italic } /* Generic.Output */
|
||||
.highlight .gs { color: var(--contrast); font-weight: bold } /* Generic.Strong */
|
||||
.highlight .ld { color: var(--contrast) } /* Literal.Date */
|
||||
.highlight .nc { color: var(--contrast) } /* Name.Class */
|
||||
.highlight .nn { color: var(--contrast) } /* Name.Namespace */
|
||||
.highlight .nx { color: var(--contrast) } /* Name.Other */
|
||||
.highlight .py { color: var(--contrast) } /* Name.Property */
|
||||
.highlight .nv { color: var(--contrast) } /* Name.Variable */
|
||||
.highlight .fm { color: var(--contrast) } /* Name.Function.Magic */
|
||||
.highlight .vc { color: var(--contrast) } /* Name.Variable.Class */
|
||||
.highlight .vg { color: var(--contrast) } /* Name.Variable.Global */
|
||||
.highlight .vi { color: var(--contrast) } /* Name.Variable.Instance */
|
||||
.highlight .vm { color: var(--contrast) } /* Name.Variable.Magic */
|
||||
|
||||
@@ -53,6 +53,9 @@ complete -c bind -s K -l key-names -d 'Print names of available keys'
|
||||
complete -c bind -s M -l mode -d 'Specify the bind mode that the bind is used in' -xa '(bind -L)'
|
||||
complete -c bind -s m -l sets-mode -d 'Change current mode after bind is executed' -xa '(bind -L)'
|
||||
complete -c bind -s L -l list-modes -d 'Display a list of defined bind modes'
|
||||
complete -c bind -s s -l silent -d 'Operate silently'
|
||||
complete -c bind -l preset -d 'Operate on preset bindings'
|
||||
complete -c bind -l user -d 'Operate on user bindings'
|
||||
|
||||
complete -c bind -n __fish_bind_test1 -a '(bind --key-names)' -d 'Key name' -x
|
||||
complete -c bind -n __fish_bind_test2 -a '(bind --function-names)' -d 'Function name' -x
|
||||
|
||||
@@ -6,7 +6,7 @@ complete -c fish -s n -l no-execute -d "Only parse input, do not execute"
|
||||
complete -c fish -s i -l interactive -d "Run in interactive mode"
|
||||
complete -c fish -s l -l login -d "Run as a login shell"
|
||||
complete -c fish -s p -l profile -d "Output profiling information (excluding startup) to a file" -r
|
||||
complete -c fish -s p -l profile-startup -d "Output startup profiling information to a file" -r
|
||||
complete -c fish -l profile-startup -d "Output startup profiling information to a file" -r
|
||||
complete -c fish -s d -l debug -d "Specify debug categories" -x -a "(fish --print-debug-categories | string replace ' ' \t)"
|
||||
complete -c fish -s o -l debug-output -d "Where to direct debug output to" -rF
|
||||
complete -c fish -s D -l debug-stack-frames -d "Show specified # of frames with debug output" -x -a "(seq 128)\t\n"
|
||||
|
||||
@@ -965,7 +965,7 @@ complete -c git -n '__fish_git_using_command add' -l ignore-errors -d 'Ignore er
|
||||
complete -c git -n '__fish_git_using_command add' -l ignore-missing -d 'Check if any of the given files would be ignored'
|
||||
# Renames also show up as untracked + deleted, and to get git to show it as a rename _both_ need to be added.
|
||||
# However, we can't do that as it is two tokens, so we don't need renamed here.
|
||||
complete -f -c git -n '__fish_git_using_command add' -a '(__fish_git_files modified untracked deleted unmerged)'
|
||||
complete -f -c git -n '__fish_git_using_command add' -a '(__fish_git_files modified untracked deleted unmerged modified-staged-deleted)'
|
||||
# TODO options
|
||||
|
||||
### checkout
|
||||
@@ -976,7 +976,7 @@ complete -k -f -c git -n '__fish_git_using_command checkout; and not contains --
|
||||
complete -k -f -c git -n '__fish_git_using_command checkout; and not contains -- -- (commandline -opc)' -a '(__fish_git_branches)'
|
||||
complete -k -f -c git -n '__fish_git_using_command checkout; and not contains -- -- (commandline -opc)' -a '(__fish_git_unique_remote_branches)' -d 'Unique Remote Branch'
|
||||
complete -k -f -c git -n '__fish_git_using_command checkout; and not contains -- -- (commandline -opc)' -a '(__fish_git_recent_commits --all)'
|
||||
complete -k -f -c git -n '__fish_git_using_command checkout' -a '(__fish_git_files modified deleted)'
|
||||
complete -k -f -c git -n '__fish_git_using_command checkout' -a '(__fish_git_files modified deleted modified-staged-deleted)'
|
||||
complete -f -c git -n '__fish_git_using_command checkout' -s b -d 'Create a new branch'
|
||||
complete -f -c git -n '__fish_git_using_command checkout' -s t -l track -d 'Track a new branch'
|
||||
complete -f -c git -n '__fish_git_using_command checkout' -l theirs -d 'Keep staged changes'
|
||||
@@ -1104,7 +1104,11 @@ complete -c git -n '__fish_git_using_command diff' -s 1 -l base -d 'Compare the
|
||||
complete -c git -n '__fish_git_using_command diff' -s 2 -l ours -d 'Compare the working tree with the "our branch"'
|
||||
complete -c git -n '__fish_git_using_command diff' -s 3 -l theirs -d 'Compare the working tree with the "their branch"'
|
||||
complete -c git -n '__fish_git_using_command diff' -s 0 -d 'Omit diff output for unmerged entries and just show "Unmerged"'
|
||||
complete -c git -n '__fish_git_using_command diff; and not __fish_contains_opt cached staged' -a '(__fish_git_files modified deleted)'
|
||||
complete -c git -n '__fish_git_using_command diff; and not __fish_contains_opt cached staged' -a '(
|
||||
set -l kinds modified
|
||||
contains -- -- (commandline -opc) && set -a kinds deleted modified-staged-deleted
|
||||
__fish_git_files $kinds
|
||||
)'
|
||||
complete -c git -n '__fish_git_using_command diff; and __fish_contains_opt cached staged' -fa '(__fish_git_files all-staged)'
|
||||
|
||||
### Function to list available tools for git difftool and mergetool
|
||||
@@ -1119,9 +1123,13 @@ end
|
||||
|
||||
### difftool
|
||||
complete -c git -n __fish_git_needs_command -a difftool -d 'Open diffs in a visual tool'
|
||||
complete -c git -n '__fish_git_using_command difftool' -k -a '(__fish_git_ranges)'
|
||||
complete -c git -n '__fish_git_using_command difftool; and not contains -- -- (commandline -opc)' -k -a '(__fish_git_ranges)'
|
||||
complete -c git -n '__fish_git_using_command difftool' -l cached -d 'Visually show diff of changes in the index'
|
||||
complete -f -c git -n '__fish_git_using_command difftool' -a '(__fish_git_files modified deleted)'
|
||||
complete -f -c git -n '__fish_git_using_command difftool' -a '(
|
||||
set -l kinds modified
|
||||
contains -- -- (commandline -opc) && set -a kinds deleted modified-staged-deleted
|
||||
__fish_git_files $kinds
|
||||
)'
|
||||
complete -f -c git -n '__fish_git_using_command difftool' -s g -l gui -d 'Use `diff.guitool` instead of `diff.tool`'
|
||||
complete -f -c git -n '__fish_git_using_command difftool' -s d -l dir-diff -d 'Perform a full-directory diff'
|
||||
complete -c git -n '__fish_git_using_command difftool' -l prompt -d 'Prompt before each invocation of the diff tool'
|
||||
@@ -1573,7 +1581,7 @@ complete -f -c git -n '__fish_git_using_command restore' -l ignore-unmerged -d '
|
||||
complete -f -c git -n '__fish_git_using_command restore' -l ignore-skip-worktree-bits -d 'Ignore the sparse-checkout file and unconditionally restore any files in <pathspec>'
|
||||
complete -f -c git -n '__fish_git_using_command restore' -l overlay -d 'Never remove files when restoring'
|
||||
complete -f -c git -n '__fish_git_using_command restore' -l no-overlay -d 'Remove files when restoring (default)'
|
||||
complete -f -c git -n '__fish_git_using_command restore; and not contains -- --staged (commandline -opc)' -a '(__fish_git_files modified deleted unmerged)'
|
||||
complete -f -c git -n '__fish_git_using_command restore; and not contains -- --staged (commandline -opc)' -a '(__fish_git_files modified deleted modified-staged-deleted unmerged)'
|
||||
complete -f -c git -n '__fish_git_using_command restore; and contains -- --staged (commandline -opc)' -a '(__fish_git_files added modified-staged deleted-staged renamed copied)'
|
||||
complete -F -c git -n '__fish_git_using_command restore; and __fish_contains_opt -s s source'
|
||||
# switch options
|
||||
@@ -1582,7 +1590,7 @@ complete -k -f -c git -n '__fish_git_using_command switch' -a '(__fish_git_local
|
||||
complete -k -f -c git -n '__fish_git_using_command switch' -a '(__fish_git_unique_remote_branches)' -d 'Unique Remote Branch'
|
||||
complete -f -c git -n '__fish_git_using_command switch' -r -s c -l create -d 'Create a new branch'
|
||||
complete -f -c git -n '__fish_git_using_command switch' -r -s C -l force-create -d 'Force create a new branch'
|
||||
complete -f -c git -n '__fish_git_using_command switch' -s d -l detach -d 'Switch to a commit for inspection and discardable experiment'
|
||||
complete -f -c git -n '__fish_git_using_command switch' -s d -l detach -d 'Switch to a commit for inspection and discardable experiment' -k -ra '(__fish_git_refs)'
|
||||
complete -f -c git -n '__fish_git_using_command switch' -l guess -d 'Guess branch name from remote branch (default)'
|
||||
complete -f -c git -n '__fish_git_using_command switch' -l no-guess -d 'Do not guess branch name from remote branch'
|
||||
complete -f -c git -n '__fish_git_using_command switch' -s f -l force -l discard-changes -d 'Proceed even if the index or the working tree differs from HEAD'
|
||||
@@ -1708,7 +1716,7 @@ complete -f -c git -n '__fish_git_stash_using_command drop' -a '(__fish_git_comp
|
||||
complete -f -c git -n '__fish_git_stash_using_command pop' -a '(__fish_git_complete_stashes)'
|
||||
complete -f -c git -n '__fish_git_stash_using_command show' -a '(__fish_git_complete_stashes)'
|
||||
|
||||
complete -f -c git -n '__fish_git_stash_using_command push' -a '(__fish_git_files modified deleted)'
|
||||
complete -f -c git -n '__fish_git_stash_using_command push' -a '(__fish_git_files modified deleted modified-staged-deleted)'
|
||||
complete -f -c git -n '__fish_git_stash_using_command push' -s p -l patch -d 'Interactively select hunks'
|
||||
complete -f -c git -n '__fish_git_stash_using_command push' -s m -l message -d 'Add a description'
|
||||
|
||||
|
||||
@@ -75,7 +75,7 @@ function fish_vi_key_bindings --description 'vi-like key bindings for fish'
|
||||
|
||||
# Default (command) mode
|
||||
bind -s --preset :q exit
|
||||
bind -s --preset -m insert \cc cancel-commandline
|
||||
bind -s --preset -m insert \cc cancel-commandline repaint-mode
|
||||
bind -s --preset -M default h backward-char
|
||||
bind -s --preset -M default l forward-char
|
||||
bind -s --preset -m insert \n execute
|
||||
|
||||
@@ -77,9 +77,6 @@ static const struct woption long_options[] = {
|
||||
#define BUILTIN_SET_UVAR_ERR \
|
||||
_(L"%ls: Universal variable '%ls' is shadowed by the global variable of the same name.\n")
|
||||
|
||||
// Test if the specified variable should be subject to path validation.
|
||||
static int is_path_variable(const wcstring &env) { return env == L"PATH" || env == L"CDPATH"; }
|
||||
|
||||
static int parse_cmd_opts(set_cmd_opts_t &opts, int *optind, //!OCLINT(high ncss method)
|
||||
int argc, const wchar_t **argv, parser_t &parser, io_streams_t &streams) {
|
||||
const wchar_t *cmd = argv[0];
|
||||
@@ -247,64 +244,6 @@ static int check_global_scope_exists(const wchar_t *cmd, const set_cmd_opts_t &o
|
||||
return STATUS_CMD_OK;
|
||||
}
|
||||
|
||||
// Validate the given path `list`. If there are any entries referring to invalid directories which
|
||||
// contain a colon, then complain. Return true if any path element was valid, false if not.
|
||||
static bool validate_path_warning_on_colons(const wchar_t *cmd,
|
||||
const wcstring &key, //!OCLINT(npath complexity)
|
||||
const wcstring_list_t &list, io_streams_t &streams,
|
||||
const environment_t &vars) {
|
||||
// Always allow setting an empty value.
|
||||
if (list.empty()) return true;
|
||||
|
||||
bool any_success = false;
|
||||
|
||||
// Don't bother validating (or complaining about) values that are already present. When
|
||||
// determining already-present values, use ENV_DEFAULT instead of the passed-in scope because
|
||||
// in:
|
||||
//
|
||||
// set -l PATH stuff $PATH
|
||||
//
|
||||
// where we are temporarily shadowing a variable, we want to compare against the shadowed value,
|
||||
// not the (missing) local value. Also don't bother to complain about relative paths, which
|
||||
// don't start with /.
|
||||
const auto existing_variable = vars.get(key, ENV_DEFAULT);
|
||||
const wcstring_list_t &existing_values =
|
||||
existing_variable ? existing_variable->as_list() : wcstring_list_t{};
|
||||
|
||||
for (const wcstring &dir : list) {
|
||||
if (!string_prefixes_string(L"/", dir) || contains(existing_values, dir)) {
|
||||
any_success = true;
|
||||
continue;
|
||||
}
|
||||
|
||||
const wchar_t *colon = std::wcschr(dir.c_str(), L':');
|
||||
bool looks_like_colon_sep = colon && colon[1];
|
||||
if (!looks_like_colon_sep && any_success) {
|
||||
// Once we have one valid entry, skip the remaining ones unless we might warn.
|
||||
continue;
|
||||
}
|
||||
struct stat buff;
|
||||
bool valid = true;
|
||||
if (wstat(dir, &buff) == -1) {
|
||||
valid = false;
|
||||
} else if (!S_ISDIR(buff.st_mode)) {
|
||||
errno = ENOTDIR;
|
||||
valid = false;
|
||||
} else if (waccess(dir, X_OK) == -1) {
|
||||
valid = false;
|
||||
}
|
||||
if (valid) {
|
||||
any_success = true;
|
||||
} else if (looks_like_colon_sep) {
|
||||
streams.err.append_format(BUILTIN_SET_PATH_ERROR, cmd, key.c_str(), dir.c_str(),
|
||||
std::strerror(errno));
|
||||
streams.err.append_format(BUILTIN_SET_PATH_HINT, cmd, key.c_str(), key.c_str(),
|
||||
std::wcschr(dir.c_str(), L':') + 1);
|
||||
}
|
||||
}
|
||||
return any_success;
|
||||
}
|
||||
|
||||
static void handle_env_return(int retval, const wchar_t *cmd, const wcstring &key,
|
||||
io_streams_t &streams) {
|
||||
switch (retval) {
|
||||
@@ -344,10 +283,6 @@ static void handle_env_return(int retval, const wchar_t *cmd, const wcstring &ke
|
||||
static int env_set_reporting_errors(const wchar_t *cmd, const wcstring &key, int scope,
|
||||
wcstring_list_t list, io_streams_t &streams, env_stack_t &vars,
|
||||
std::vector<event_t> *evts) {
|
||||
if (is_path_variable(key) && !validate_path_warning_on_colons(cmd, key, list, streams, vars)) {
|
||||
return STATUS_CMD_ERROR;
|
||||
}
|
||||
|
||||
int retval = vars.set(key, scope | ENV_USER, std::move(list), evts);
|
||||
handle_env_return(retval, cmd, key, streams);
|
||||
|
||||
|
||||
@@ -428,7 +428,7 @@ void event_print(io_streams_t &streams, const wcstring &type_filter) {
|
||||
}
|
||||
switch (d1.type) {
|
||||
case event_type_t::signal:
|
||||
return d1.signal < d2.signal;
|
||||
return d1.param1.signal < d2.param1.signal;
|
||||
case event_type_t::process_exit:
|
||||
return d1.param1.pid < d2.param1.pid;
|
||||
case event_type_t::job_exit:
|
||||
|
||||
@@ -57,7 +57,7 @@ enum {
|
||||
};
|
||||
using readb_result_t = int;
|
||||
|
||||
static readb_result_t readb(int in_fd, bool queue_is_empty) {
|
||||
static readb_result_t readb(int in_fd) {
|
||||
assert(in_fd >= 0 && "Invalid in fd");
|
||||
universal_notifier_t& notifier = universal_notifier_t::default_notifier();
|
||||
select_wrapper_t fdset;
|
||||
@@ -98,7 +98,7 @@ static readb_result_t readb(int in_fd, bool queue_is_empty) {
|
||||
// This may come about through readability, or through a call to poll().
|
||||
if ((fdset.test(notifier_fd) && notifier.notification_fd_became_readable(notifier_fd)) ||
|
||||
notifier.poll()) {
|
||||
if (env_universal_barrier() && !queue_is_empty) {
|
||||
if (env_universal_barrier()) {
|
||||
return readb_uvar_notified;
|
||||
}
|
||||
}
|
||||
@@ -169,7 +169,7 @@ char_event_t input_event_queue_t::readch() {
|
||||
return mevt.acquire();
|
||||
}
|
||||
|
||||
readb_result_t rr = readb(in_, queue_.empty());
|
||||
readb_result_t rr = readb(in_);
|
||||
switch (rr) {
|
||||
case readb_eof:
|
||||
return char_event_type_t::eof;
|
||||
@@ -180,6 +180,7 @@ char_event_t input_event_queue_t::readch() {
|
||||
break;
|
||||
|
||||
case readb_uvar_notified:
|
||||
env_universal_barrier();
|
||||
break;
|
||||
|
||||
case readb_ioport_notified:
|
||||
|
||||
@@ -10,7 +10,7 @@
|
||||
|
||||
#include <cstring>
|
||||
#include <memory>
|
||||
#ifdef FISH_USE_POSIX_SPAWN
|
||||
#ifdef HAVE_SPAWN_H
|
||||
#include <spawn.h>
|
||||
#endif
|
||||
#include <cwchar>
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
#include <unistd.h>
|
||||
|
||||
#include "maybe.h"
|
||||
#if HAVE_SPAWN_H
|
||||
#ifdef HAVE_SPAWN_H
|
||||
#include <spawn.h>
|
||||
#endif
|
||||
#ifndef FISH_USE_POSIX_SPAWN
|
||||
@@ -53,7 +53,7 @@ pid_t execute_fork();
|
||||
void safe_report_exec_error(int err, const char *actual_cmd, const char *const *argv,
|
||||
const char *const *envv);
|
||||
|
||||
#ifdef FISH_USE_POSIX_SPAWN
|
||||
#if FISH_USE_POSIX_SPAWN
|
||||
/// A RAII type which wraps up posix_spawn's data structures.
|
||||
class posix_spawner_t {
|
||||
public:
|
||||
|
||||
@@ -715,3 +715,13 @@ set --show ""
|
||||
#CHECKERR: set --show ""
|
||||
#CHECKERR: ^
|
||||
#CHECKERR: (Type 'help set' for related documentation)
|
||||
|
||||
# Test path splitting
|
||||
begin
|
||||
set -l PATH /usr/local/bin:/usr/bin
|
||||
echo $PATH
|
||||
# CHECK: /usr/local/bin /usr/bin
|
||||
set -l CDPATH .:/usr
|
||||
echo $CDPATH
|
||||
# CHECK: . /usr
|
||||
end
|
||||
|
||||
44
tests/checks/tmux-prompt.fish
Normal file
44
tests/checks/tmux-prompt.fish
Normal file
@@ -0,0 +1,44 @@
|
||||
#RUN: %fish -C 'set -g fish %fish' %s
|
||||
#REQUIRES: command -v tmux
|
||||
|
||||
# Isolated tmux.
|
||||
# Note $XDG_CONFIG_HOME typically has a leading double-dot,
|
||||
# so our uvars file will leak across runs; therefore
|
||||
# descend more deeply into the tmpdir.
|
||||
set -g tmpdir (mktemp -d)/inner1/inner2/
|
||||
mkdir -p $tmpdir
|
||||
|
||||
set -g tmux tmux -S $tmpdir/.tmux-socket -f /dev/null
|
||||
|
||||
set -g sleep sleep .1
|
||||
set -q CI && set sleep sleep 1
|
||||
|
||||
set fish (builtin realpath $fish)
|
||||
cd $tmpdir
|
||||
|
||||
while set -e prompt_var
|
||||
end
|
||||
|
||||
$tmux new-session -x 80 -y 10 -d $fish -C '
|
||||
# This is similar to "tests/interactive.config".
|
||||
function fish_greeting; end
|
||||
function fish_prompt; printf "prompt $status_generation> <$prompt_var> "; end
|
||||
# No autosuggestion from older history.
|
||||
set fish_history ""
|
||||
function on_prompt_var --on-variable prompt_var
|
||||
commandline -f repaint
|
||||
end
|
||||
'
|
||||
|
||||
$sleep # Let fish draw a prompt.
|
||||
|
||||
$tmux capture-pane -p
|
||||
# CHECK: prompt 0> <>
|
||||
|
||||
set -U prompt_var changed
|
||||
$sleep
|
||||
$tmux capture-pane -p
|
||||
# CHECK: prompt 0> <changed>
|
||||
|
||||
$tmux kill-server
|
||||
rm -r $tmpdir
|
||||
Reference in New Issue
Block a user