dimo414 / bash-cache

Transparent caching layer for bash functions; particularly useful for functions invoked as part of your prompt.
GNU General Public License v3.0
73 stars 4 forks source link

/bin/sh: error importing function definition for `bc::cache'.... #15

Closed dimo414 closed 5 years ago

dimo414 commented 5 years ago

Original report by Anonymous.


When I try to use this on osx I get this on stderr:

/bin/sh: error importing function definition for `bc::cache'
/bin/sh: error importing function definition for `bc::off'
/bin/sh: error importing function definition for `bc::_modtime'
/bin/sh: error importing function definition for `bc::_now'
/bin/sh: error importing function definition for `bc::copy_function'
/bin/sh: error importing function definition for `bc::_cleanup'
/bin/sh: error importing function definition for `bc::_read_input'
/bin/sh: error importing function definition for `bc::on'
/bin/sh: error importing function definition for `bc::_time'
/bin/sh: error importing function definition for `bc::_newer_than'
/bin/sh: error importing function definition for `bc::benchmark'
/bin/sh: error importing function definition for `bc::_write_cache'
/bin/sh: error importing function definition for `bc::locked_cache'
/bin/sh: error importing function definition for `bc::_hash'
/bin/sh: error importing function definition for `bc::_ensure_dir_exists'
/bin/sh: error importing function definition for `bc::cache'
/bin/sh: error importing function definition for `bc::off'
/bin/sh: error importing function definition for `bc::_modtime'
/bin/sh: error importing function definition for `bc::_now'
/bin/sh: error importing function definition for `bc::copy_function'
/bin/sh: error importing function definition for `bc::_cleanup'
/bin/sh: error importing function definition for `bc::_read_input'
/bin/sh: error importing function definition for `bc::on'
/bin/sh: error importing function definition for `bc::_time'
/bin/sh: error importing function definition for `bc::_newer_than'
/bin/sh: error importing function definition for `bc::benchmark'
/bin/sh: error importing function definition for `bc::_write_cache'
/bin/sh: error importing function definition for `bc::locked_cache'
/bin/sh: error importing function definition for `bc::_hash'
/bin/sh: error importing function definition for `bc::_ensure_dir_exists'
/bin/sh: error importing function definition for `bc::cache'
/bin/sh: error importing function definition for `bc::off'
/bin/sh: error importing function definition for `bc::_modtime'
/bin/sh: error importing function definition for `bc::_now'
/bin/sh: error importing function definition for `bc::copy_function'
/bin/sh: error importing function definition for `bc::_cleanup'
/bin/sh: error importing function definition for `bc::_read_input'
/bin/sh: error importing function definition for `bc::on'
/bin/sh: error importing function definition for `bc::_time'
/bin/sh: error importing function definition for `bc::_newer_than'
/bin/sh: error importing function definition for `bc::benchmark'
/bin/sh: error importing function definition for `bc::_write_cache'
/bin/sh: error importing function definition for `bc::locked_cache'
/bin/sh: error importing function definition for `bc::_hash'
/bin/sh: error importing function definition for `bc::_ensure_dir_exists'

Are there any restrictions on command/syntax/etc for the cached function?

❯ bash --version
GNU bash, version 5.0.7(1)-release (x86_64-apple-darwin18.5.0)
Copyright (C) 2019 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>

This is free software; you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

I'm using bash, so I don't understand the /bin/sh ... errors.

dimo414 commented 5 years ago

Original comment by Michael Diamond (Bitbucket: dimo414).


Thanks for the report; can you share exact reproduction steps? I use OSX regularly and have not seen this behavior. I'm able to get a similar error by explicitly dropping into a sh shell:

$ sh
sh-3.2$ source bash-cache.sh
sh: `bc::_ensure_dir_exists': not a valid identifier
sh: `bc::_hash': not a valid identifier
sh: `bc::_modtime': not a valid identifier
sh: `bc::_now': not a valid identifier
sh: `bc::_newer_than': not a valid identifier
sh: `bc::_read_input': not a valid identifier
sh: `bc::copy_function': not a valid identifier
sh: `bc::on': not a valid identifier
sh: `bc::off': not a valid identifier
sh: `bc::_write_cache': not a valid identifier
sh: `bc::_cleanup': not a valid identifier
sh: `bc::cache': not a valid identifier
sh: `bc::locked_cache': not a valid identifier
sh: `bc::_time': not a valid identifier
sh: `bc::benchmark': not a valid identifier

Which makes me suspect you're source-ing Bash Cache from a sh script. Do you perhaps have a #!/bin/sh shebang somewhere?

dimo414 commented 5 years ago

Original comment by Bruce Edge (Bitbucket: bedge, GitHub: bedge).


I refactored and the above problem went away. Different issue now.

I have a file that I source in my shell to provide convenience functions


#!/bin/bash
[ "${DEBUG}" ] && echo "aliases.tam"
set -a

BC_CACHE_DIR=/tmp/bash.cache
BC=./bash-cache.sh
[ -r ${BC} ] && source ${BC}

function asg-info() {
  stack=$1
  asg_str=$2
  filter=$3
  additional=$4
  for t in $(slave_types) ; do
    if [ "$asg_str" = "$t" ] ; then
      found=1
      break
    fi
  done
  if ! set-stack $stack ; then
    return 1
  fi

  aws autoscaling describe-auto-scaling-groups --query \
    "AutoScalingGroups[] \
    |[?starts_with(AutoScalingGroupName, 'tam') || starts_with(AutoScalingGroupName, 'fsm')] \
    |[?contains(AutoScalingGroupName, '${stack}') || contains(AutoScalingGroupName, '${stack/prd/prod}')] \
    |[?contains(AutoScalingGroupName, '${asg_str}')]$filter" $additional

} && bc::cache asg-info PWD

More functions below

With the above code, if I source that file in a shell, none of the functions below the decorated one are added to the shell.

It’s like the “ bc::cache asg-info PWD “ decorator terminates the import of the file.

dimo414 commented 5 years ago

Original comment by Michael Diamond (Bitbucket: dimo414).


And to confirm, you don't see any error messages? Is it possible you have set -e set somewhere? If bc::cache asg-info PWD failed with set -e that would cause the script to exit (though I'm not sure why that function would fail silently).

Could you try sourcing it with set -x? Or in a pristine shell (like env -i bash --noprofile --norc)?

The [ -r ${BC} ] && source ${BC} line seems a little suspect too; that would silently not source bash-cache.sh if it doesn't exist, which would then cause all usages of the bc functions to fail. Generally source "${BC}" || return would be safer - source will print an error if it can't source the file.

dimo414 commented 5 years ago

Original comment by Bruce Edge (Bitbucket: bedge, GitHub: bedge).


Using a clean shell fixes the problem and it works fine.

Now I just need to find out why my default shell config (zsh + gobs of extras) fails.

It never returns from the “ bc::cache asg-info PWD”

It’s so damn verbose with set -x as to be borderline useless.

Thanks for the help. Really nice bit of shell coding.

dimo414 commented 5 years ago

Original comment by Bruce Edge (Bitbucket: bedge, GitHub: bedge).


Actually, zsh aborts parsing the source after the

bc::cache asg-info PWD 

even with no config loaded at all. Something in bash-cache.sh is not zsh compatible.

dimo414 commented 5 years ago

Original comment by Bruce Edge (Bitbucket: bedge, GitHub: bedge).


I added some instrumentation to bash-cache.sh to see where it was failing.

eg:

bc::copy_function() {

echo copy 1
local function="${1:?Missing function}"
local new_name="${2:?Missing new function name}"
echo copy 2
set -x
declare -F "$function" &> /dev/null || {
echo "No such function ${function}" >&2; return 1
}
echo copy 3
eval "$(printf "%s()" "$new_name"; declare -f "$function" | tail -n +2)"
echo copy 4
}

(sorry, the code formatting block function here is stripping newlines)

From a clean shell:

(p3.7) USROMBEDGE01% . ~/.aliases.tam
copy 1
copy 2
+bc::copy_function:7> declare -F asg-info

If I remove the >&2 /dev/null after the declare, I see:

+bc::copy_function:8> declare -F asg-info
bc::copy_function:declare:8: not valid in this context: asg-info

I know it says “bash” cache, but would be nice if zsh worked too.

This looks like the problem: https://stackoverflow.com/questions/10194861/bash-zsh-declare-oh-my

dimo414 commented 5 years ago

Original comment by Michael Diamond (Bitbucket: dimo414).


Ok yeah, I don't use zsh so I've not tried to make it work for any shells other than Bash (hence the name, as you note 🙂).

I'd be open to expanding this to support other shells like zsh, but it'd probably require contributions from an interested user. It's not a priority for me.

I'm going to close this, but I'll file a separate bug for zsh support.