0

Why do I get these errors:

-bash: [: missing `]'
grep: ): No such file or directory
grep: ]: No such file or directory

when I run this in sh or bash:

if [ \( lsusb -t | grep -q 'qmi_wwan' \) ]; then
    echo 'yes'
else
    echo 'no'
fi
A6EE
  • 141
  • 1
  • 8
  • 1
    Don't you need to escape the | as well? – Jerry Jeremiah Nov 22 '21 at 00:23
  • True, forgot about `|`. Now I'm getting this: `-bash: [: ')' expected, found -t` – A6EE Nov 22 '21 at 00:25
  • 2
    `[` is a command (an alternate name for the command also called `test`), not shell syntax, and it only performs a limited number of operations; `lsusb` is not one of them. See its documentation at https://pubs.opengroup.org/onlinepubs/9699919799/utilities/test.html – Charles Duffy Nov 22 '21 at 00:54
  • 2
    ...also, `|` behaves the same way in the presence of `[` as it behaves in any other context: it ends one simple command and starts a new one, with the stdout of the command on its left connected to the stdin of the command on its right. So you're running `[ '(' usb -t` as one command, and `grep -q 'qmi_wwan' ')' ']'` as a second command. Neither of those is useful. – Charles Duffy Nov 22 '21 at 00:57
  • 2
    Now, you _could_ run `[ "$(lsusb -t | grep qmi_wwan)" ]`, and _that_ would be useful -- inefficient compared to just `lsusb -t | grep -q qmi_wwan`, but useful. (When you pass `[` a single argument other than the expected terminating `]`, as that does, it tests whether that argument is empty; `[ "string" ]` is identical to `[ -n "string" ]`, `test "string"`, or `test -n "string"` -- removing the `-q` was necessary because when it's present, the stdout from `grep` is _always_ empty, so the test result would always be false). – Charles Duffy Nov 22 '21 at 00:59

1 Answers1

0

If you want to check the exit code of the grep command, use it instead of the [ command:

if lsusb -t | grep -q 'qmi_wwan'
then
  echo "Yes"
fi
that other guy
  • 116,971
  • 11
  • 170
  • 194
  • I didn't post the full if statement which includes logical operators and other statements. But this subset of statements returns the same error, so I didn't include the rest to minimize the confusion. – A6EE Nov 22 '21 at 00:30
  • 2
    Do you mean "I'm not sure how to apply this solution because I don't know how to use logical operators outside of `[`?" You can use `!`, `||` and `&&` for not/or/and with other commands, including `[` – that other guy Nov 22 '21 at 00:35
  • I checked the command without `[` before and it works fine, but I wanted to check why it didn't work with `[`. – A6EE Nov 22 '21 at 00:47
  • 1
    Because you aren't running the command anymore; you're running `[` with the *text* of the command as its arguments. – chepner Nov 22 '21 at 18:40