FTP search ,grep using perl

Need assistance on a Perl script.

I have a list of file names in a file and would like to search/grep the same names in the list of files on the ftp server and output to a file. Any help is appreciable

Below is the script that can give me the list of files,size of file, Modified date on the FTP server

#!/usr/bin/perl -w
use Net::FTP;

$ftp = Net::FTP->new("hostname");
$ftp->login('user', 'pass');
$ftp->cwd("path");
$ftp->binary;
#$flag=$ftp->mdtm($_);

my @filenames=$ftp->ls();
print " Total files:", $#filenames + 1, "\n";
foreach (@filenames)
{
 print $_, " Size:[", $ftp->size($_), "]", " Mtime ", scalar(localtime($ftp->mdtm($_))), "\n";
}
$ftp->quit();

grep as in what? regex match? literal filename match? case sensitive or insensitive?

Not case sensitive . Example below

File name on the server ftp 471560-99999-2013.op.gz

search for 471560 and get the result

Okay, so a simple substring match, you can do that with index() in perl. If it returns -1, the string is not found. If it returns anything else, it is found.

#!/usr/bin/perl -w
use Net::FTP;

my @str;

while($line=<STDIN>)
{
        chomp($line); # Remove newline from end of string
        push(@str, $line); # Add string to end of @str array
}

$ftp = Net::FTP->new("hostname");
$ftp->login('user', 'pass');
$ftp->cwd("path");
$ftp->binary;
#$flag=$ftp->mdtm($_);

my @filenames=$ftp->ls();
print " Total files:", $#filenames + 1, "\n";
foreach (@filenames)
{
        $name=$_;
        print $name, " Size:[", $ftp->size($name), "]", " Mtime ", scalar(localtime($ftp->mdtm($name))), "\n";
        foreach(@str)
        {
                if(index($line,$_) >= 0)
                {
                        print $name, " matches ", $_, "\n";
                        $ftp->get($name);
                        break;
                }
        }
}

$ftp->quit();

run it like

./myscript.pl < listfile

I get an error below. Can you please help me on this

Use of uninitialized value in index at ./test.pl line 26, <STDIN> line 2.
Use of uninitialized value in index at ./test.pl line 26, <STDIN> line 2.

Oh, you're using strict, so I have to declare every last variable.

I think. I don't have an easy FTP setup to test this with.

#!/usr/bin/perl -w
use Net::FTP;

my @str;
my $name;
my $line;

while($line=<STDIN>)
{
        chomp($line); # Remove newline from end of string
        push(@str, $line); # Add string to end of @str array
}

$ftp = Net::FTP->new("hostname");
$ftp->login('user', 'pass');
$ftp->cwd("path");
$ftp->binary;
#$flag=$ftp->mdtm($_);

my @filenames=$ftp->ls();
print " Total files:", $#filenames + 1, "\n";
foreach (@filenames)
{
        $name=$_;
        print $name, " Size:[", $ftp->size($name), "]", " Mtime ", scalar(localtime($ftp->mdtm($name))), "\n";
        foreach(@str)
        {
                if(index($line,$_) >= 0)
                {
                        print $name, " matches ", $_, "\n";
                        $ftp->get($name);
                        break;
                }
        }
}

$ftp->quit();

When i run the script I get the below output

bash-3.00$ ./test.pl < files.txt
Unquoted string "break" may clash with future reserved word at ./perltest1.pl line 31.
Useless use of a constant in void context at ./perltest1.pl line 31

.

Use of uninitialized value in index at ./perltest1.pl line 27, <STDIN> line 2.
Use of uninitialized value in index at ./perltest1.pl line 27, <STDIN> line 2.
bash-3.00$ more files.txt
450070
766133

OK, I found an FTP to test with.

#!/usr/bin/perl -w
use Net::FTP;

my @str, $line, $ftp;

while($line=<STDIN>)
{
        chomp($line); # Remove newline from end of string
        push(@str, $line); # Add string to end of @str array
}

$ftp = Net::FTP->new("localhost");
$ftp->login('user', 'pass');
$ftp->cwd("path");
$ftp->binary;
#$flag=$ftp->mdtm($_);

my @filenames=$ftp->ls();
print " Total files:", $#filenames + 1, "\n";
foreach (@filenames)
{
        print $_, " Size:[", $ftp->size($_), "]", " Mtime ", scalar(localtime($ftp->mdtm($_))), "\n";

        for my $s(@str)
        {
                if(index($_, $s) >= 0)
                {
                        print $_, " matches ", $s, "\n";
                        $ftp->get($_);
                }
        }
}

$ftp->quit();

My FTP doesn't seem to have mdtm. I suspect many don't. FTP is very simple and stupid, you only get what it gives you, and that is very inconsistent.

This script couldnt match the pattern i have in the file.

It did the same thing as before.

mdtm is part of Net::FTP. So it will work on any server as long as Net::FTP module was installed.

And what pattern was that?

This is not hypothetical. Your script throws tons of errors about mdtm on my system -- my ftp server doesn't have that.

The output of ls looks different on different FTP servers. Some show mtime -- some don't.

What ls in FTP is supposed to look like has no standard at all. FTP is very simple, stupid, and messy... That's why a perl module like this is such a blessing, it deals with that mess for you and gives you a straightforward list.

But it can't invent an mdtm out of nothing. If the other end doesn't list that, you don't get it.

The only thing you can depend on getting is the filename. You only get sizes and dates if you're lucky.

Sample File name on the FTP server is 471560-99999-2013.op.gz and there are 13000 files. first 6 digits of the file name are listed in my text file. I would like to search the numerical pattern and get that list into an output file.

Below file.txt has 2 filenames.

bash-3.00$ more files.txt
450070
766133

Thank you for explaining about FTP process.

It works fine here. When I put an 471560-99999-2013.op.gz in my FTP and an 471560 in the list, then run

./ftp.pl < list

...it grabs 471560-99999-2013.op.gz, putting it in the same folder I ran the script in.

Please show me more details if it doesn't work, including actual sample content from your list file and the manner in which you are running the program and program output.

I already presented in my previous scrap .

when i run the script . I dont get any output except the number of files on the server .

I commented out the below step.

I wanted an output to a file once it matches the pattern .

 print $_, " Size:[", $ftp->size($_), "]", " Mtime ", scalar(localtime($ftp->mdtm($_))), "\n";
$./test.pl < files.txt
Total files:10556

$ more files.txt
450070
766133

I don't see that either of those strings would match 471560 . Were you expecting a range match?

Yes!!! :o

Okay, that changes things, when you just want a first and last number instead of a bunch of individual filenames. Working on it.

This is what my initial posting was .Sorry if the message was not conveyed properly .

I have a list of file names in a file and would like to search/grep the same names in the list of files on the ftp server and output to a file.

Let me brief it again .

my file.txt has few numbers

Ftp server has list of 13000 files.

based on my list which has 10 or 100 names of the file names and i want to see if those 10 or 100 files present on the FTP server and output to the file

That's just confusing the matter even more...

What do these numbers in files.txt actually mean if you're not actually looking for their literal strings? Are they ordered in ranges, first \n last \n first \n last \n first \n last \n ? Or what?

Let me tell you in Unix

$ ls -l |grep 471560-99999-2013.op.gz
-rw-r-----   1 ara2wj   nagp           0 Apr 23 14:23 471560-99999-2013.op.gz
(example files on the ftp server )

$ ls -l |grep 471560
-rw-r-----   1 ara2wj   nagp           0 Apr 23 14:23 471560-99999-2013.op.gz
(in my file i have 471560)

My file.txt has list of partial name of the files that are present ftp server, I need to search/grep on the ftp server to see if they are present and get the result to an output saying that they are there on the server

So you don't want a range match now? You do want literal strings?

The program as given works here... Perhaps you're in the wrong directory, perhaps you're not looking for where your files are appearing, perhaps you don't have permissions to write to the current folder, perhaps you don't have permissions to retrieve the files, or perhaps your search strings contain garbage you didn't intend (carriage returns?)