Home > Back-end >  how to move a file after grep command when there is no return result
how to move a file after grep command when there is no return result

Time:11-13

I wanna move a file after the grep command but as I execute my script, I noticed that there are no results coming back. regardless of that, I want to move the file/s to another directory.

this is what I've been doing:

for file in *.sup
do 
   grep -iq "$file" '' /desktop/list/varlogs.txt || mv "$file" /desktop/first;
done

but I am getting this error:

mv: 0653-401 Cannot rename first /desktop/first/first

suggestions would be very helpful

CodePudding user response:

I am not sure what the two single quotes are for in between ..."$file" '' /desktop.... With them there, grep is looking also for $file in a file called '', so grep will throw the grep: : No such file or directory error with that there.

Also pay attention to the behavior change of adding the -q or --quiet flags, as it affects the returned value of grep and will impact whether the command to the || is run or not (see man grep for more).

I can't make out exactly what you are trying to do, but you can add a couple statements to help figure out what is going on. You could run your script with bash -x ./myscript.sh to display everything that runs as it runs, or add set -x before and set x after the for loop in the script to show what is happening.

I added some debugging to your script and changed th || to an if/then statement to expose what is happening. Try this and see if you can find where things are going awry.

echo -e "============\nBEFORE:\n============"
echo -e "\n## The files in current dir '$(pwd)' are: ##\n$(ls)"
echo -e "\n## The files in '/desktop/first' are: ##\n$(ls /desktop/first)"

echo -e "\n## Looking for '.sup' files in '$(pwd)' ##"

for file in *.sup; do
  echo -e "\n## == look for '${file}' in '/desktop/list/varlogs.txt' == ##"

  # let's change this to an if/else
  # the || means try the left command for success, or try the right one
  # grep -iq "$file" '' /desktop/list/varlogs.txt || mv -v "$file" /desktop/first

  # based on `man grep`:  EXIT STATUS
  #   Normally the exit status is 0 if a line is selected,
  #   1 if no lines were selected, and 2 if an error occurred.
  #   However, if the -q or --quiet or --silent is used and a line
  #   is selected, the exit status is 0 even if an error occurred.

  # note that --ignore-case and --quiet are long versions of -i and -q/ -iq
  if grep --ignore-case --quiet "${file}" '' /desktop/list/varlogs.txt; then
    echo -e "\n'${file}' found in '/desktop/list/varlogs.txt'"
  else
    echo -e "\n'${file}' not found in '/desktop/list/varlogs.txt'"
    echo -e "\nmove '${file}' to '/desktop/first'"
    mv --verbose "${file}" /desktop/first
  fi
done

echo -e "\n============\nAFTER:\n============"
echo -e "\n## The files in current dir '$(pwd)' are: ##\n$(ls)"
echo -e "\n## The files in '/desktop/first' are: ##\n$(ls /desktop/first)"
  • || means try the first command, and if it is not successful (i.e. does not return 0), then do the next command. In your case, it appears you are looking in /desktop/list/varlogs.txt to see if any .sup files in the current directory match any in the varlogs file and if not, then move them to the /desktop/first/ directory. If matches were found, leave them in the current dir. (according to the logic you have currently)
  • mv --verbose explain what is being done
  • echo -e enables interpretation of backslash escapes
  • set -x shows the commands that are being run/ debugging

Please respond and clarify if anything is different. I am trying to raise in the ranks to be more helpful so I would appreciate comments, and upvotes if this was helpful.

CodePudding user response:

Suggesting to avoid repeated scans of /desktop/list/varlogs.txt, and remove duplicats:

mv $(grep -o -f <<<$(ls -1 *.sup) /desktop/list/varlogs.txt|sort|uniq) /desktop/first 

Suggesting to test step 1. in explanation below to list the files to be moved.

Explanation

1. grep -o -f <<<$(ls -1 *.sup) /desktop/list/varlogs.txt| sort| uniq

List all the files selected in ls -1 *.sup mentioned in /desktop/list/varlogs.txt in a single scan.

-o list only matched filenames.

<<<$(ls -1 *.sup) prepare a temporary redirected input file containing all the pattern match strings. From the output of ls -1 *.sup

|sort|uniq Than, sort the list and remove duplicates (we can move the file only once).

2. mv <files-list-output-from-step-1> /desktop/first

Move all the files found in step 1 to directory /desktop/first

  • Related