Problem with a script

Hi everyone,
I got a problem with a script. What it's supposed to do is:

  • to take as arguments a directory name <dir> and a dimension (in byte) <dim>;
  • if <dir> exists, to write name and dimension of every regular file within it that sizes lesser than <dim> in regFileList.

Nothing happens when I run it, and digiting later "echo $?" result is 0.

Here's the code:

#!/bin/bash 

if [ $# -ne 2 ]
then
    echo "script use: bash prova <dir> <dim>"
else
    if [ -d $1 ]
    then
        for file in `ls $1`
        do
          if [ -f $file ]
          then
              a=`ls -o | awk '/$file/ {print $4}'`
              if [ $a -lt $2 ]
              then
                  ls -o | awk '/$file/ { print $3 " " $4 }' >> regFileList
              fi
          fi
        done
    else
        echo "$1 is not a directory or it does not exist"
    fi
fi

Where do I make a mistake?

Also, since I'm learning, I'd like any tips on my coding.

Thanks.

a=`ls -o | awk '/$file/ {print $4}'

$file is within the shell single quotes and is not substituted.
There is only one filename in the loop so we only need to look at the directory for the one file.

a=`ls -o $file| awk '{print $4}'`

ls -o $file | awk '{print $3 " " $4 }' >> regFileList
1 Like

Right, but still not working.

Please post the current version of the script and any output. (When I ran the original script I got loads of errors from "test" and "awk").
What happens with the corrected version?

Wow, my terminal reports nothing when I run it, even if surely there's something wrong; maybe this depends on my terminal version or what?

I simply corrected it with your lines:

#!/bin/bash

if [ $# -ne 2 ]
then
    echo "script use: bash prova <dir> <dim>"
else
    if [ -d $1 ]
    then
        for file in `ls $1`
        do
          if [ -f $file ]
          then
              a=`ls -o $file | awk '{ print $4 }'`
              if [ $a -lt $2 ]
              then
                  ls -o $file | awk '{ print $3 " " $4 }' >> regFileList
              fi
          fi
        done
    else
        echo "$1 is not a directory or it does not exist"
    fi
fi

There's no output.

EDIT: Maybe my code is not good at all? Would you post a version of yours?

Just ran yours on a directory containing some files which were smaller than the second parameter value. No errors.

The output is in the file called regFileList.

To read the output.

more regFileList

I should add that your script will misbehave if the directory name or the files contain space characters.
The main task is to answer your original post.

Ok it works, I just didn't use it properly. :slight_smile:

My latest version is:

#!/bin/bash

if [ $# -ne 2 ]
then
    echo "script use: bash prova <dir> <dim>"
else
    if [ -d $1 ]
    then
        for file in `ls $1`
        do
          if [ -f $file ] && [ $(ls -o $file | awk '{ print $4 }') -lt $2 ]
          then
              ls -o $file | awk '{ print $3 " " $4 }' >> regFileList
          fi
        done
    else
        echo "$1 is not a directory or it does not exist"
    fi
fi

Thanks for the awk tip. Problem is solved.

What should be done in this case?

Use a "while" loop not a "for" loop. In the "for" loop a filename with a space character becomes two parameters. Within the "while" loop preserve spaces by placing double quotes round the variable.

#!/bin/bash

if [ $# -ne 2 ]
then
    echo "script use: bash prova <dir> <dim>"
else
    if [ -d $1 ]
    then
        ls -1|while read file
        do
          if [ -f "$file" ] && [ $(ls -o "$file" | awk '{ print $4 }') -lt $2 ]
          then
              ls -o "$file" | awk '{ print $3,$4,$9 }' >> regFileList
          fi
        done
    else
        echo "$1 is not a directory or it does not exist"
    fi
fi

BTW. Until first looking at this board I had never seen "ls" in a "for" line ever. Yet we see daily here. It must be mentioned in a popular shell book.

1 Like

Thanks man, I learned something new! :cool:

Just because I'm new to scripting languages and like to experiment.

If you find this kind of stuff somewhere, please link me.

The FAQ section of this site is worth a read.
A quick search of this site for "bash tutorial" turned up this post:

http://www.unix.com/shell-programming-scripting/81073-understand-bash-scripting-encryption.html

It is important to realise early on that there is a huge variety of Linux and unix out in the field. Beware of blindly copying shell script without working what it will actually do on your system.

ls -o output it�s little different, envitonment like LANG and so on change the output. This ex. has done using my ls -o result format:
-rw-r--r-- 1 owner 45 2010-03-29 18:43 filename

#!/bin/bash or ksh93 or ...

[ $# -ne 2 ] && echo "usage:$0 <dir> <dim>" >&2  && exit 1

dir="$1"
dim="$2"

[ ! -d "$dir" ] && echo "$dir is not a directory or it does not exist" >&2 && exit 2

cd "$dir"
ls -o | while read filedata
do
        values=($filedata)
        owner=${values[2]}
        size=${values[3]}
        date=${values[4]}
        # filename can include spaces, empty other flds, rest is filename
        for f in 0 1 2 3 4 5
        do
               values[$f]=""
        done
        name=${values[*]}

        if [ -f "$name" -a "$size" -lt "$dim" ] ; then
          echo "$name $size $date"
        fi
done
chmod a+rx prova
./prova somedir 100 > regFileList