2

What I'm trying to do is the get the user input and search through the file, If it match it will show the result, else it will echo $keyword not found.

But my scrip is always return fault.

       read -p "Enter keyword: " keyword
       if search="$(cat ./records | grep '$keyword')"
       then
       echo "$search"
       else
        echo "$keyword not found!"
       fi ;;
Rui F Ribeiro
  • 56,709
  • 26
  • 150
  • 232
  • the error is that you are using '$keyword'. within single quotes the variable is not expanded and treated as text. use "$keyword" instead. – John Smith Sep 27 '17 at 06:40

2 Answers2

5
read -r -p 'Enter pattern: ' pattern

result=$( grep -e "$pattern" records )

if [ -n "$result" ]; then
    printf '%s\n' "$result"
else
    printf 'No match found for pattern "%s"\n' "$pattern"
fi
  • The assignment to search (result in my code) is best done outside of the if statement.

  • Test with -n ("is this string non-empty?") on the result.

  • Don't single-quote the variable (it will prevent the shell from expanding its value). Double quote it instead.

  • Notice "pattern" rather than "keyword". The way you use grep here will use the user-supplied string as a regular expression (a pattern, such as cat.*dog), not necessarily as a plain fixed string.

  • cat should be used to concatenate files, in most other cases it's more or less useless.

  • Use read -r to allow the user to enter backslashes.


Alternatively:

read -r -p 'Enter pattern: ' pattern

if ! grep -e "$pattern" records; then printf 'No match found for pattern "%s"\n' "$pattern" fi

This avoids storing a potentially huge amount of data in a shell variable and instead relies on the exit status of grep to tell whether the pattern may be found in the file or not. If the pattern is found, the matching lines will be printed (and nothing more has to be done).

Regarding the use of printf in place of echo: Why is printf better than echo?


Shorter, using a short-circuit OR.

read -r -p 'Enter pattern: '

grep -e "$REPLY" records || printf 'No match found for pattern "%s"\n' "$REPLY"

Kusalananda
  • 333,661
1

See below:

read -p "Enter keyword: " keyword

if search=$(grep "$keyword" ./records)
        then
                echo "$search"
        else
                echo "$keyword not found!"
        fi
  1. Don't use quotting with $() as @jasonwryan was noted above
  2. Not nesessary to use cat piping with grep. Use grep <pattern> file instead
  3. Delete ;; after fi