JJ004 has asked for the wisdom of the Perl Monks concerning the following question:

I am in the midst of building my own message board one piece at a time. in this problem there is a message board with one link to a subject. The script opens the text file to be searched, stores it in an array, and searches the array for the section to be displayed on the new page. At the momment this code is not finding the search string, and thus displays nothing, except when you put an identical print statement between the if and while statements. Here we go:
#!/usr/bin/perl print "Content-type:text/html\n\n"; #http://xxrainxx.tripod.com/cgi-bin/mboard.html test page #http://xxrainxx.tripod.com/cgi-bin/postall.txt text file open (INF,"postall.txt") or dienice("Couldn't open postall.txt for re +ading: $!"); $subject = $ENV{'QUERY_STRING'}; $subject =~ s/%([a-fA-F0-9][a-fA-F0-9])/pack("C",hex($1))/eg; $subject =~ tr/_/ /; @b = <INF>; close (INF); print <<"EndHTML"; <html><head><title>$subject</title></head> <body bgcolor="#000000" text="#DDFFDD" face="Verdana,Helvetica,Arial"> +\n $ENV{'QUERY_STRING'}\n<br> $subject\n<br> <br> <blockquote> Here's the message:\n<br>\n<br>\n EndHTML print "$subject this is what I'm looking for<br>\n"; for ($x=1;$x < scalar @b;$x++) { if($b[$x]=="***Begin $subject"){ while ($b[$x]!="***Begin Here***\n"){ print "$b[$x]<br>\n"; $x = $x + 1; } } } #foreach $line (@b){ # chomp($line); # print "$line<br>\n"; #} # I removed a section of html when posting because last time closing t +he textarea broke the preview text field. sub dienice { my($msg) = @_; print "<h2>Error</h2>\n"; print "$msg;\n"; }

Replies are listed 'Best First'.
Re: searching a text file
by Zaxo (Archbishop) on Oct 23, 2001 at 08:31 UTC

    Update: Does "***Begin $subject" in the equality test need to be "***Begin $subject\n"?

    So much to do here.

    1. #!/usr/bin/perl -w Warnings on.
    2. use strict; aid in debugging.
    3. use CGI; You'll get toasted for parsing $QUERY_STRING
    4. $| = 1; Let through whatever gets printed right away.
    &dienice does nothing that use CGI::Carp qw(fatalsToBrowser); can't do better.

    Consider reading the file like this:

    my $cgi = new CGI; my $subject = $cgi->param('subject'); my @b; { local $/="***Begin Here***\n"; open INF, "< /full/path/to/postall.txt" or die $!; @b = grep { chomp; # remove "***Begin Here***\n", then # remove marker and return true to grep if match s/^\*\*\*Begin \Q$subject\E//; } <INF>; close INF or die $!; } # lines go by for (@b) { s/\n/<br\/>\n/g; } print @b;

    Update2: Added chomp, positional ^, and comments to grep code, a litle text cleanup.

    After Compline,
    Zaxo

Re: searching a text file
by Zecho (Hermit) on Oct 23, 2001 at 11:17 UTC
    On behalf of JJ004 I will mention that, through conversation in the chatterbox, we found that his webhost (tripod.com) does not provide the warnings or carp modules.

    The file he is searching uses the following format:
    ***Begin Con Quéso? 21/Oct/2001 7:26:51 -4h = EST Joel Demelira Con_Quéso? 21/Oct/2001 07:26:51 -4h = EST Del Maré Cujo van Ouaiden! ***Begin Here*** ***End Con Quéso? 21/Oct/2001 7:26:51 -4h = EST
    The ***Begin Here*** line starts a list of replies to the post. I visited the site, and noticed that no matter what you search for, it comes back with the previous post as its search result. (which also happens to be the first in the file.)

    My suggestions would include using a better format for the data file, perhaps using a DBM file or _insert_your _favorite_here. Also, knowing that this is for a hand-rolled message board, I would suggest he read up on perlfunc:flock as well. A broad suggestion would be that he find some other examples of small message boards and see just how they were implementd.
Re: searching a text file
by the_0ne (Pilgrim) on Oct 23, 2001 at 08:14 UTC
    Not sure if this is your problem altogether since I haven't tested the code, but the lines...
    if($b[$x]=="***Begin $subject"){ while ($b[$x]!="***Begin Here***\n"){
    s/b
    if($b[$x] eq "***Begin $subject"){ while ($b[$x] ne "***Begin Here***\n"){
    When you are comparing strings, eq and ne are the operators. Numeric operators are == and !=.

    Again, I'm not totally sure this is your full problem, but I know when searching strings, == and != will give you unpredictable results.

    Also, if your line will not always be the exact same string... ***Begin $subject Then you might want to try a regex...
    if($b[$x] =~ /\*\*\*Begin $subject/){
    Good luck.
      alas no I implemented the changes you suggested, and although good, I still get no output on the new page, in between the sentences "this is what I'm looking for" and "all done" But I greatly appreciate the effort