From 0ebd41eb9ff22109d497f325648c5bd8eeb4a871 Mon Sep 17 00:00:00 2001 From: Johannes Altmanninger Date: Fri, 29 Aug 2025 11:40:42 +0200 Subject: [PATCH] Extract function for calling mktemp BSD mktemp doesn't support GNU mktemp's -t or --tmpdir option, so when we want a named temporary file, we need to compute ${TMPDIR:-/tmp} ourselves, see 5accc7c6c5b (Fix funced's tmpfile generation on OSX, 2016-05-23). While at it, use template like "fish.XXXXXX"; seems like a good idea? Take care to have edit_command_buffer use a pretty filename. --- share/completions/scp.fish | 2 +- share/functions/__fish_mktemp_relative.fish | 22 ++++++++++++++++++++ share/functions/edit_command_buffer.fish | 18 ++++++++-------- share/functions/fish_config.fish | 2 +- share/functions/fish_update_completions.fish | 2 +- share/functions/funced.fish | 9 +++----- share/functions/help.fish | 4 +--- share/functions/psub.fish | 10 +++------ 8 files changed, 41 insertions(+), 28 deletions(-) create mode 100644 share/functions/__fish_mktemp_relative.fish diff --git a/share/completions/scp.fish b/share/completions/scp.fish index 219c674dc..0e01063cd 100644 --- a/share/completions/scp.fish +++ b/share/completions/scp.fish @@ -47,7 +47,7 @@ complete -c scp -d "Local Path" -n "not string match @ -- (commandline -ct)" complete -c scp -d "Remote Path" -f -n "commandline -ct | string match -e ':'" -a ' (__scp_remote_target):( if not set -q __fish_scp_sftp - set -l tmp (mktemp) + set -l tmp (__fish_mktemp fish-scp) if scp -P(__scp2ssh_port_number) -o "BatchMode yes" -q -O $tmp (__scp_remote_target):/dev/null set -g __fish_scp_sftp true else diff --git a/share/functions/__fish_mktemp_relative.fish b/share/functions/__fish_mktemp_relative.fish new file mode 100644 index 000000000..ed50268f8 --- /dev/null +++ b/share/functions/__fish_mktemp_relative.fish @@ -0,0 +1,22 @@ +function __fish_mktemp_relative + # OSX mktemp is rather restricted - no suffix, no way to automatically use TMPDIR + if not set -q TMPDIR[1] + set -f TMPDIR /tmp + end + # TODO use "argparse --move-unknown" + set -l mktemp_args + set -l found_positional false + for arg in $argv + switch $arg + case '-*' + set -a mktemp_args $arg + case '*' + set -a mktemp_args $TMPDIR/$arg.XXXXXX + set found_positional true + end + end + if not $found_positional + set -a mktemp_args $TMPDIR/fish.XXXXXX + end + mktemp $mktemp_args +end diff --git a/share/functions/edit_command_buffer.fish b/share/functions/edit_command_buffer.fish index 5de7b41af..f6a2ab4f7 100644 --- a/share/functions/edit_command_buffer.fish +++ b/share/functions/edit_command_buffer.fish @@ -1,9 +1,9 @@ function edit_command_buffer --description 'Edit the command buffer in an external editor' - set -l f (mktemp) + set -l tmpdir (__fish_mktemp_relative -d fish) or return 1 - if set -q f[1] - command mv $f $f.fish - set f $f.fish + set -l f + if set -q tmpdir[1] + set f $tmpdir/command-line.fish else # We should never execute this block but better to be paranoid. if set -q TMPDIR @@ -11,9 +11,9 @@ function edit_command_buffer --description 'Edit the command buffer in an extern else set f /tmp/fish.$fish_pid.fish end - command touch $f - or return 1 end + command touch $f + or return 1 set -l editor (__fish_anyeditor) or return 1 @@ -52,13 +52,13 @@ function edit_command_buffer --description 'Edit the command buffer in an extern set found true break end - set cursor_from_editor (mktemp) + set cursor_from_editor (__fish_mktemp_relative fish-edit_command_buffer) set -a editor +$line "+norm! $col|" $f \ '+au VimLeave * ++once call writefile([printf("%s %s %s", shellescape(bufname()), line("."), col("."))], "'$cursor_from_editor'")' case emacs emacsclient gedit set -a editor +$line:$col $f case kak - set cursor_from_editor (mktemp) + set cursor_from_editor (__fish_mktemp_relative fish-edit_command_buffer) set -a editor +$line:$col $f -e " hook -always -once global ClientClose %val{client} %{ echo -to-file $cursor_from_editor -quoting shell \ @@ -117,7 +117,7 @@ function edit_command_buffer --description 'Edit the command buffer in an extern end command rm $cursor_from_editor end - command rm $f + command rm -r (path dirname $f) # We've probably opened something that messed with the screen. # A repaint seems in order. commandline -f repaint diff --git a/share/functions/fish_config.fish b/share/functions/fish_config.fish index e368f9a8f..3271a779e 100644 --- a/share/functions/fish_config.fish +++ b/share/functions/fish_config.fish @@ -26,7 +26,7 @@ function fish_config --description "Launch fish's web based configuration" echo "Cannot find web configuration tool. Please check your fish installation." return 1 end - set -l temp (mktemp -d) + set -l temp (__fish_mktemp_relative -d fish_config) for dir in (status list-files tools/web_config | path dirname | path sort -u) mkdir -p $temp/$dir or return diff --git a/share/functions/fish_update_completions.fish b/share/functions/fish_update_completions.fish index 86231793c..6bedc2e5f 100644 --- a/share/functions/fish_update_completions.fish +++ b/share/functions/fish_update_completions.fish @@ -11,7 +11,7 @@ function fish_update_completions --description "Update man-page based completion echo "Cannot find man page completion generator. Please check your fish installation." return 1 end - set -l temp (mktemp -d) + set -l temp (__fish_mktemp_relative -d fish_update_completions) for file in create_manpage_completions.py deroff.py status get-file tools/$file >$temp/$file or return diff --git a/share/functions/funced.fish b/share/functions/funced.fish index 32e767ce1..355e10724 100644 --- a/share/functions/funced.fish +++ b/share/functions/funced.fish @@ -58,12 +58,9 @@ function funced --description 'Edit function definition' return 0 end - # OS X (macOS) `mktemp` is rather restricted - no suffix, no way to automatically use TMPDIR. - # Create a directory so we can use a ".fish" suffix for the file - makes editors pick up that - # it's a fish file. - set -q TMPDIR - or set -l TMPDIR /tmp - set -l tmpdir (mktemp -d $TMPDIR/fish.XXXXXX) + # Create a directory so we can use a ".fish" suffix for the file - + # makes editors pick up that it's a fish file. + set -l tmpdir (__fish_mktemp_relative -d fish-funced) or return 1 set -l tmpname $tmpdir/$funcname.fish diff --git a/share/functions/help.fish b/share/functions/help.fish index 11647355a..8596c9881 100644 --- a/share/functions/help.fish +++ b/share/functions/help.fish @@ -226,9 +226,7 @@ function help --description 'Show help for the fish shell' # trampoline (they're only needed if there's a fragment in the path) if set -l clean_url (string match -re '#' $page_url) # Write a temporary file that will redirect where we want. - set -q TMPDIR - or set -l TMPDIR /tmp - set -l tmpdir (mktemp -d $TMPDIR/help.XXXXXX) + set -l tmpdir (__fish_mktemp_relative -d fish-help) or return 1 set -l tmpname $tmpdir/help.html echo '' >$tmpname diff --git a/share/functions/psub.fish b/share/functions/psub.fish index 0f0e280dc..01ad567b5 100644 --- a/share/functions/psub.fish +++ b/share/functions/psub.fish @@ -17,15 +17,11 @@ function psub --description "Read from stdin into a file and output the filename return 1 end - set -l tmpdir /tmp - set -q TMPDIR - and set tmpdir $TMPDIR - if set -q _flag_fifo # Write output to pipe. This needs to be done in the background so # that the command substitution exits without needing to wait for # all the commands to exit. - set dirname (mktemp -d $tmpdir/.psub.XXXXXXXXXX) + set dirname (__fish_mktemp_relative -d .psub) or return 1 set filename $dirname/psub.fifo"$_flag_suffix" command mkfifo $filename @@ -34,11 +30,11 @@ function psub --description "Read from stdin into a file and output the filename # after the fork. command tee $filename >/dev/null & else if test -z "$_flag_suffix" - set filename (mktemp $tmpdir/.psub.XXXXXXXXXX) + set filename (__fish_mktemp_relative .psub) or return 1 command cat >$filename else - set dirname (mktemp -d $tmpdir/.psub.XXXXXXXXXX) + set dirname (__fish_mktemp_relative -d .psub) or return 1 set filename "$dirname/psub$_flag_suffix" command cat >$filename