0

I use this bash command often

find ~ -type f -name \*.smt -exec grep something {} /dev/null \;

so I am trying to turn it into a simple bash script that I would invoke like this

findgrep ~ something --mtime -12 --name \*.smt

However I get stuck with processing the command line options with GNU getopt like this:

if ! options=$(getopt -o abc: -l name:,blong,mtime: -- "$@")
then
    # something went wrong, getopt will put out an error message for us
    exit 1
fi

set -- $options

while [ $# -gt 0 ]

do
    case $1 in
    -t|--mtime) mtime=${2}   ; shift;;
    -n|--name|--iname) name="$2" ; shift;;

    (--) shift; break;;
    (-*) echo "$0: error - unrecognized option $1" 1>&2; exit 1;;
    (*) break;;
    esac
    shift
done

echo "done"
echo $@

if [ $# -eq 2 ]
then
    echo "2 args"
    dir="$1"
    str="$1"
elif [ $# -eq 1 ]
then
    dir="."
    str="$1"
    echo "1 arg"
else
    echo "need a search string"
fi


echo $dir
echo $str

echo $mtime
echo "${mtime%\'}"
echo "${mtime%\'}"

echo '--------------------'

mtime="${mtime%\'}"
mtime="${mtime#\'}"

dir="${dir%\'}"
dir="${dir#\'}"

echo $dir $mtime $name

# grep part not in yet
find $dir -type f -mtime $mtime -name $name

which does not seem to work - I suspect because the $name variable gets passed in quotes to find.

How do I fix that?

simone
  • 4,667
  • 4
  • 25
  • 47
  • Globs are not processed _by_ your script. They're processed _before your script starts_. When they're escaped, they're not processed at all (as long as you quote your expansions correctly), and that's appropriate and correct when you're going to pass them through to `find`. – Charles Duffy Mar 26 '22 at 20:50
  • `set -- $options` is just innately broken; don't do that _ever_. – Charles Duffy Mar 26 '22 at 20:52
  • (similarly, `getopt` is innately broken, and the BashFAQ advises unambiguously against its use under any circumstances whatsoever; see [BashFAQ #35](https://mywiki.wooledge.org/BashFAQ/035) describing various common and correct ways to parse command-line options, and [ComplexOptionParsing](https://mywiki.wooledge.org/ComplexOptionParsing) for discussion of those approaches -- like `getopt` -- that are _not_ recommended). – Charles Duffy Mar 26 '22 at 20:52
  • (also, note that util-linux is not a product of the GNU project) – Charles Duffy Mar 26 '22 at 20:56

1 Answers1

1
set -- $options

Is invalid (and it's not quoted). It's eval "set -- $options". Linux getopt outputs properly quoted string to be eval-ed.

mtime="${mtime%\'}"
mtime="${mtime#\'}"

dir="${dir%\'}"
dir="${dir#\'}"

Remove it. That's not how expansions work.

-name $name

It's not quoted. You have to quote it upon use.

-name "$name"

Check your scripts with shellcheck.

KamilCuk
  • 120,984
  • 8
  • 59
  • 111
  • "`getopt` outputs properly quoted string" -- depending on _whose_ `getopt`; it's not portable: the util-linux version is utterly unlike the one found on non-Linux platforms. Since the OP's question is not tagged Linux, providing a Linux-only answer is not necessarily optimal. – Charles Duffy Mar 26 '22 at 20:54
  • 1
    There's no such thing as GNU getopt. GNU doesn't make util-linux; it's built by the Linux kernel developers, not by GNU. – Charles Duffy Mar 26 '22 at 20:56