Closed qwertimer closed 3 years ago
The problem is with they way we are checking the number of arguments. After our shift, $#
will always be zero. We need to change the qualifier for the if statement on line 12.
I started working on this earlier this morning, but had to stop to log onto work. I'll keep playing with it as I have free time.
For now I changed line 12 from >
to =
so the script will import the text in the snippet file. However, the email example Rob reviewed yesterday won't work.
"After our shift, $# will always be zero"
This is actually only true if we don't pass anything else in the command. For example, snip nameemail
and snip foo
will both have $#
equal to zero. If we passed additional arguments, i.e. snip nameemail Mike Mike@mike.com
, then our $# > 0
would be TRUE.
However, when we use VI Magic and pass data into the script, the shell still only recognizes snip nameemail
. Our update will need to get the data passed to the script (maybe by using STDIN) and apply logic there.
Sorry for the additional details, but I wanted to spell this out in case it helps anyone else who is following along.
I think this works. I'll need to play around on how to do a PR (if needed). Let me know what you think.
#!/usr/bin/bash
[[ -z $SNIPPETS ]] && echo "SNIPPETS directory undefined" && exit 1
snip() {
local name="$1"
shift
local path="$SNIPPETS/$name"
if [[ -r $path ]]; then
local buf="$(<$path)"
local in="$(</dev/stdin)"
if [[ $# = 0 && -z $in ]]; then
echo "$buf"
return
fi
if [[ $# > 0 ]]; then
local -i n=1
for arg in $@; do
buf=${buf//\{$n\}/$arg}
((n++))
done
echo "$buf"
else
while IFS=$'\n' read -r argline; do
if [[ -n $argline ]]; then
IFS=" " snip $name $argline
fi
done
fi
fi
}
snip "$@"
I found a bug when there is no STDIN. Fixed code is below:
#!/usr/bin/bash
[[ -z $SNIPPETS ]] && echo "SNIPPETS directory undefined" && exit 1
snip() {
local name="$1"
shift
local path="$SNIPPETS/$name"
if [[ -r $path ]]; then
local buf="$(<$path)"
if [[ -s /dev/stdin ]]; then
local in="$(</dev/stdin)"
else
local in=""
fi
if [[ $# = 0 && -z $in ]]; then
echo "$buf"
return
fi
if [[ $# > 0 ]]; then
local -i n=1
for arg in $@; do
buf=${buf//\{$n\}/$arg}
((n++))
done
echo "$buf"
else
while IFS=$'\n' read -r argline; do
if [[ -n $argline ]]; then
IFS=" " snip $name $argline
fi
done
fi
fi
}
snip "$@"
Looks like it works. I was able to add a snippet into an empty buffer in vim. It also outputs to the terminal if i run the snip tool in the terminal.
The snip tool works as expected for everything except if i have an empty line and wish to place a snippet on this line. The snippet fails to place anything down. Not sure whether you wish to support this. I thought i figured out how to fix it but it breaks the multiline parsing. If we add -ge 0 rather than > 0 we can place a snippet on an empty line.