problem with perl from apache

N

NishantModak.

hello,
i have a program like this

____________________________________________________________________________________
#!/usr/bin/perl


use CGI;

use am_common;


$CGI::pOST_MAX = 512 * 1024; # half meg is max size


$pvars = CGI::new();





# get directories if passed in otherwise get them from the .cfg file


my $dir_work = $pvars->param("DIRW");


my $dir_conf = $pvars->param("DIRC");


my $dir_ast = $pvars->param("DIRA");


if (!$dir_work)


{


$dir_work = get_cfg_value("dir_work");


}


if (!$dir_conf)


{


$dir_conf = get_cfg_value("dir_conf");


}


if (!$dir_ast)


{


$dir_ast = get_cfg_value("dir_ast");


}


my $page = "Content-type: text/html\n\n";


$page .= "<HTML><HEAD><TITLE>Asterisk Management
System</TITLE></HEAD><BODY>";


$page .= "<FONT SIZE=-1><B><A
HREF=\"am-help.pl?DIRW=$dir_work&DIRC=$dir_conf&DIRA=$dir_ast&HT=help-main\">HELP</A></B>";


$page .= "<CENTER><FONT SIZE=+3><B>Asterisk Management
System</B></FONT><BR>";


$page .= "<HR>";


$page .= "<BR><A
HREF=\"config.pl?DIRW=$dir_work&DIRC=$dir_conf&DIRA=$dir_ast\">Configuration</A>";


$page .= "<BR><A
HREF=\"admin.pl?DIRW=$dir_work&DIRC=$dir_conf&DIRA=$dir_ast\">Administration</A></CENTER>";


$page .= "</BODY></HTML>";





print $page;


exit(0);



_____________________________________________________________________________


this works well when i run it through the shell..
but when i try to execute it from the browser .. an empty screen turns
up.

HELP HELP HELP........
 
S

Scott Bryce

NishantModak. said:
#!/usr/bin/perl

use strict;
use warnings;
use CGI;

use am_common;

am_common is not used in this script, but I'll assume your complete
script needs it. I had to comment that line out to run your script.

$CGI::pOST_MAX = 512 * 1024; # half meg is max size
$pvars = CGI::new();

my $pvars = CGI::new();
# get directories if passed in otherwise get them from the .cfg file


my $dir_work = $pvars->param("DIRW");


my $dir_conf = $pvars->param("DIRC");


my $dir_ast = $pvars->param("DIRA");

Since I don't know what is in your get_cfg_value subroutine, I'll
rewrite the above:

my $dir_work = $pvars->param('DIRW') || 'some_dir_w';
my $dir_conf = $pvars->param('DIRC') || 'some_dir_c';
my $dir_ast = $pvars->param('DIRA') || 'some_dir_a';

<code calling get_cfg_value snipped>

my $page = "Content-type: text/html\n\n";


$page .= "<HTML><HEAD><TITLE>Asterisk Management System</TITLE></HEAD><BODY>";


$page .= "<FONT SIZE=-1><B><A HREF=\"am-help.pl?DIRW=$dir_work&DIRC=$dir_conf&DIRA=$dir_ast&HT=help-main\">HELP</A></B>";


$page .= "<CENTER><FONT SIZE=+3><B>Asterisk Management System</B></FONT><BR>";


$page .= "<HR>";


$page .= "<BR><A HREF=\"config.pl?DIRW=$dir_work&DIRC=$dir_conf&DIRA=$dir_ast\">Configuration</A>";


$page .= "<BR><A HREF=\"admin.pl?DIRW=$dir_work&DIRC=$dir_conf&DIRA=$dir_ast\">Administration</A></CENTER>";


$page .= "</BODY></HTML>";
print $page;


exit(0);

exit(0) is not necessary here. The script will exit anyway.
this works well when i run it through the shell..
but when i try to execute it from the browser .. an empty screen turns
up.

I don't get an empty screen after making the changes indicated above.

before making the changes, I get an Internal Server Error. The Perl
error is Can't locate am_common.pm in @INC

Perhaps there is something in your get_cfg_value subroutine that is
messing up your HTML? Since I can't see it, I can't help you with it.

To get the best possible help here, please post a complete script that
we can run by cutting it and pasting it into a text editor.
 
A

A. Sinan Unur

i have a program like this

Please format the source code properly before pasting. There is just too
much vertical space in your post which makes it harder to follow the
code.
#!/usr/bin/perl

use strict;
use warnings;

missing.

Also,

$| = 1 # see perldoc perlvar

would be useful for CGI.
use CGI;

use am_common;

This prevents us from being able to run your code without additional
work. Please read the posting guidelines for this group to learn how to
compose an effective message.
$CGI::pOST_MAX = 512 * 1024; # half meg is max size

Right margin comments explaining the obvious are not useful. They also
have the nasty habit of wrapping to the next line.
$pvars = CGI::new();

I doubt it makes a difference, but, for consistency with the OO style, I
would use

my $pvars = CGI->new;
my $dir_work = $pvars->param("DIRW");
my $dir_conf = $pvars->param("DIRC");
my $dir_ast = $pvars->param("DIRA");

You should check if DIRW, DIRC, and DIRA are acceptable. At this point,
you would be allowing access to any directory on the server by this CGI
script. Not good.

You could, for example, do (untested code):

use File::Spec::Functions 'catfile';

my $dir_root = '/some/specific/path';

....

my $dir_work;
if (defined (my $dir = $pvars->param('DIRW')) ) {
if ( $dir =~ m{ \A (\w+) \z }x ) {
$dir = catfile $dir_root, $dir;
$dir_work = $dir if -d $dir;
}
}

unless (defined $dir_work) {
$dir_work = get_cfg_value('dir_work');
}

Of course, I would use a hash to hold the directory variables, factor
the validation code above to a subroutine, and call it for each of the
directories.

### still untested ###

use File::Spec::Functions qw( catfile );

my %dirs = map { $_ => undef } qw(work conf ast);

sub validate_dir {
my ($root, $name, $value) = @_;

my $ret;

if (defined (my $dir = $value) ) {
if ( $dir =~ m{ \A (\w+) \z }x ) {
$dir = catfile $root, $1;
$ret = $dir if -d $dir;
}
}

$ret = get_cfg_value($name) unless defined $ret;
}

for my $d (keys %dirs) {
$dirs{$d} = validate_dir('/some/path', $d => $pvars->param($d));
}
my $page = "Content-type: text/html\n\n";

You are using CGI.pm so why not use it.
$page .= "<HTML><HEAD><TITLE>Asterisk Management
System</TITLE></HEAD><BODY>";

Tedious. Have you heard of HERE docs?

Also:
<FONT SIZE=-1><B><A HREF=\"am-help.pl?DIRW=$dir_work&DIRC=
$dir_conf&DIRA=$dir_ast&HT=help-main\">HELP</A></B>";

See http://validator.w3.org/docs/help.html#faq-ampersand

<a href="am-help.pl?DIRW=$dir_work;DIRC=$dir_conf;DIRA=$dir_ast"> ...
etc

CGI.pm will parse this correctly. (Also, the name $pvars implies and a
512MB POST_MAX you are expecting input via POST, but this is GET.)

Anyway:

my $page = <<END_OF_HTML;
<HTML><HEAD><TITLE>Asterisk Management System</TITLE></HEAD>

<BODY>

<FONT SIZE=-1>
<B>
<A HREF="am-help.pl?DIRW=$dir_work;DIRC=$dir_conf;DIRA=$dir_ast;HT=help-
main">HELP</A>
</B>
<CENTER>
<FONT SIZE=+3><B>Asterisk Management System</B></FONT>

<BR>
<HR>
<BR>

<A HREF="config.pl?DIRW=$dir_work;DIRC=$dir_conf;DIRA=$dir_ast">
Configuration</A>

<BR>

<A HREF="admin.pl?DIRW=$dir_work&DIRC=$dir_conf&DIRA=$dir_ast">
Administration</A>

</CENTER>

</BODY>
</HTML>
END_OF_HTML

print $cgi->header, $page;
this works well when i run it through the shell..
but when i try to execute it from the browser .. an empty screen turns
up.

HELP HELP HELP........

Your HTML reminds me of 1995. You might be able to avoid future problems
by separating the HTML from the script by using HTML::Template, and
designing the HTML separately and in a standards compliant manner.

Sinan
 
N

NishantModak.

The get_cfg_value subroutine is like : --
_______________________________________
sub get_cfg_value {
my $n = @_[0];
my $l = "";
my @a;

open IH, "am.cfg"; // some conf file from where i read the
contents
while(<IH>)
{
$l = $_;
@a = split(/=/, $l);
$l = $a[0];
$l =~ s/^\s+//;
$l =~ s/\s+$//;
if ($l eq $n)
{
$a[1] =~ s/^\s+//;
$a[1] =~ s/\s+$//;
close(IH);
return($a[1]);
}
}
close(IH);
return("");
}
___________________________________
any clues now ?
 
A

Anno Siegel

NishantModak. said:
The get_cfg_value subroutine is like : --
_______________________________________
sub get_cfg_value {
my $n = @_[0];
my $l = "";
my @a;

open IH, "am.cfg"; // some conf file from where i read the contents

That doesn't compile. "//" doesn't introduce a comment in Perl. Please
post real code, not something made-up.

Anno
 
A

A. Sinan Unur

The get_cfg_value subroutine is like : --

Seriously, consider one of the many excellent config file parsers on
CPAN. For example, I have used Config::properties and Config::Tiny in
the past.
sub get_cfg_value {
my $n = @_[0];

It looks like you do not have warnings enabled.
my $l = "";
my @a;

open IH, "am.cfg"; // some conf file from where i read the
contents

Please post code in a way others can copy and paste without jumping
through hoops.

1. So, you open & close the config file each time this sub is invoked.
Does not sound like a great idea to me. I would read and cache the
config variables on the first call if there is any chance this routine
can be called many times.

2. Always, yes, *always* check the return value of open. E.g.:

open my $config_fh, '<', 'am.cfg' or return;
while(<IH>)
{
$l = $_;

while (my $l = said:
@a = split(/=/, $l);
$l = $a[0];
$l =~ s/^\s+//;
$l =~ s/\s+$//;

*arrgh!*

if (m{ \A (\w+) \s* = \s* (\w+) \s* \z}x) {
my ($key, $val) = ($1, $2);
if ($l eq $n)

Use descriptive names for variables. Don't use the same variable for
more than one purpose.
{
$a[1] =~ s/^\s+//;
$a[1] =~ s/\s+$//;
close(IH);
return($a[1]);
}

With the above, all of this can be reduced to:

return $val if $key eq $name;
}
close(IH);
return("");

The return value above will evaluate to true in list context, possibly
causing hard to track bugs. You are better off with a plain return.

Here is how I would change this (*warning* untested code):

package MyConfig;

use strict;
use warnings;

use Carp;

use constant CONFIG_FILENAME => 'am.cfg';

my $config_read;
my %config;

sub get_cfg_value {
my ($name) = @_;
read_cfg_file(CONFIG_FILENAME, \%config) unless $config_read;
if (exists $config{$name}) {
return $config{$name};
} else {
return;
}
}

sub read_cfg_file {
my ($file, $config) = @_;

open my $fh, '<', $file;
unless ( $fh ) {
carp "Cannot open '$file': $!";
return;
}

while ( <$fh> ) {
if (m{ \A (\w+) \s* = \s* (\w+) \s* \z}x) {
$config->{$1} = $2;
}
}

return $config_read = 1;
}

1;
__END__

On the other hand, there are tested modules on CPAN.

Sinan
 
P

Proud_to_b_indian

i thought u ppl could understand it ...
BUT NO HOPES>.........

i have the same code that i posted it here.
i had put the "//" just for the sake of readers to understand it,,
but seems to b of no use.. as people here are just trying to get away
from answers..and post somethings irrelevant..

does anybody have a solution ?

Anno said:
NishantModak. said:
The get_cfg_value subroutine is like : --
_______________________________________
sub get_cfg_value {
my $n = @_[0];
my $l = "";
my @a;

open IH, "am.cfg"; // some conf file from where i read the contents

That doesn't compile. "//" doesn't introduce a comment in Perl. Please
post real code, not something made-up.

Anno
--
If you want to post a followup via groups.google.com, don't use
the broken "Reply" link at the bottom of the article. Click on
"show options" at the top of the article, then click on the
"Reply" at the bottom of the article headers.
 
A

A. Sinan Unur

Anno said:
NishantModak. said:
The get_cfg_value subroutine is like : --
_______________________________________
sub get_cfg_value {
my $n = @_[0];
my $l = "";
my @a;

open IH, "am.cfg"; // some conf file from where i read the
contents

That doesn't compile. "//" doesn't introduce a comment in Perl.
Please post real code, not something made-up.

Anno
--
If you want to post a followup via groups.google.com, don't use
the broken "Reply" link at the bottom of the article. Click on
"show options" at the top of the article, then click on the
"Reply" at the bottom of the article headers.

Please do not quote signatures and please do not top-post.
i thought u ppl could understand it ...

Baby talk is not a good way to communicate.

BUT NO HOPES>.........

Insulting people whose help you want is not a good idea either.

I hear Python is a much better language than Perl. Maybe you can try it?
i have the same code that i posted it here.
i had put the "//" just for the sake of readers to understand it,,
but seems to b of no use.. as people here are just trying to get away
from answers..and post somethings irrelevant..

There are many things in your code and that you regard as irrelevant, but
make it hard for someone else (who is not on your machine, and who is not
seeing what you are seeing) to decide what the problem and the solution
are.
does anybody have a solution ?

Please read the posting guidelines for this group. The guidelines contain
invaluable tips on how to help yourself, and help others help you.

For example, the fact that you do not check whether open succeeded in
get_cfg_value introduces uncertainty.

The fact that you build your HTML using string concatenation with a whole
bunch of escapes discourages me from even looking at it.

The fact that you have not posted a script that we can easily copy,
paste, and run, discourages me from trying to run your code.

Hope this helps.

Sinan
 
U

Uri Guttman

Ptbi> i thought u ppl could understand it ...
Ptbi> BUT NO HOPES>.........

even if that code would compile it is very hard to read as you picked
useless single letter names and don't explain any of what it is trying
to do.

Ptbi> i have the same code that i posted it here.
Ptbi> i had put the "//" just for the sake of readers to understand it,,
Ptbi> but seems to b of no use.. as people here are just trying to get away
Ptbi> from answers..and post somethings irrelevant..

how about you asking a relevant question? explain what you think your
code should be doing? show some code that is compilable. if you comment
use proper *perl* comments (which is # and not //) so we could cut/paste
the code and run it without editing. it is your responsibility to make
it easy for us to help you. this is a free newsgroup where we choose to
discuss perl. please read the (frequently posted) guidelines on how to
best get help here.

uri
 
U

Uri Guttman

ASU> sub get_cfg_value {
ASU> my ($name) = @_;
ASU> read_cfg_file(CONFIG_FILENAME, \%config) unless $config_read;
ASU> if (exists $config{$name}) {
ASU> return $config{$name};
ASU> } else {
ASU> return;

you could just return $config{$name} and not do the check. a config key
can't have an undef value from the file so if it doesn't exist you would
get the same return value. yes, it would have different results in a
list context but that shouldn't be called like that.

ASU> sub read_cfg_file {
ASU> my ($file, $config) = @_;

ASU> open my $fh, '<', $file;
ASU> unless ( $fh ) {
ASU> carp "Cannot open '$file': $!";
ASU> return;
ASU> }

ASU> while ( <$fh> ) {
ASU> if (m{ \A (\w+) \s* = \s* (\w+) \s* \z}x) {
ASU> $config->{$1} = $2;
ASU> }
ASU> }

ASU> return $config_read = 1;
ASU> }

you could reduce that to (untested):

use File::Slurp ;

....

%{$config} = read_file( $file ) =~
m{ ^ (\w+) \s* = \s* (\w+) \s* $ }xm ;


for basic key=value config files, that is the fastest and easiest way to
load them. the regex could be written with ([^=])+ to extract the key if
blanks aren't allowed.

uri
 
J

Jürgen Exner

Proud_to_b_indian said:
i thought u ppl could understand it ...

Sorry, my brain fails to parse this sentence.
What on earth does a Private Pilot Licence have to do with Perl?
Would you mind translating it into English?
does anybody have a solution ?

For what problem?

jue
 
E

Eric Schwartz

NishantModak. said:
The get_cfg_value subroutine is like : --
_______________________________________

use warnings;
use strict;
sub get_cfg_value {
my $n = @_[0];
my $l = "";
my @a;

Please pick more descriptive variable names. I can't figure out what
any of these variable names are supposed to mean. Also, you don't
need $l or @a to be declared here, since you don't use them until
inside the while loop. Refrain from declaring variables until you
need them.
open IH, "am.cfg"; // some conf file from where i read the
contents

This doesn't compile-- if you post code that people can just cut and
paste, then it's easy for people to help you. You are not exactly
going out of your way to get people to help you.

You should also check the result of any open() calls, as otherwise you
may be reading from a closed filehandle. You should also prefer the
3-arg open in general, though when just reading from a file, I often
don't bother. But most importantly for this line, you should use a
scalar variable:

open my $ih, '<', 'am.cfg' or die "Can't open am.cfg: $!";
while(<IH>)
{
$l = $_;

This is a waste-- first you assign a line to $_, then to $l. Why not
just

while ( my $l = <$ih> )
{

?
@a = split(/=/, $l);

Okay, it appears that you have a file that is in "key=value" format,
and you want to return the value for a given key. This would have
been really nice to know-- I like it much better when I know up-front
what code is supposed to do, instead of having to puzzle it out as I
read.

@a is a terrible name for a variable here; you don't really make it
obvious what @a is supposed to mean, and anyway, an array is not the
most obvious data structure. I would prefer to write this as:

my ($key, $value) = split(/=/, $l);

And poof, you don't have to remember anything about $a[0] or $a[1], or
any of that. You can read $key and know that its contents are a key,
and $value and know that it's a value. See how much easier that is
than $a[0]?
$l = $a[0];

Above, $l was meant to be a line-- now it's the key of a key/value
pair. This doesn't make sense. Don't overload the meaning of a
single variable like that-- instead, declare a new one that means what
you are using the variable to mean.
$l =~ s/^\s+//;
$l =~ s/\s+$//;

If I didn't know better, I'd think you read the FAQ.
if ($l eq $n)
{
$a[1] =~ s/^\s+//;
$a[1] =~ s/\s+$//;
close(IH);
return($a[1]);
}

See how much more confusing it is to use $a[1] here instead of $value?

Anyway, all you need to do here is create a variable outside the while
loop (I like to use $rv or $retval, depending principally on my mood),
and then you can:

if ($key eq $n) # is $n meant to be $name? If so, use $name
{
$value =~ s/^\s+//;
$value =~ s/\s+$//;
$retval = $value;
last;
}

Then at the end, just:

close($ih);
return $retval;

instead of repeating the same thing twice.
}
close(IH);
return("");
}
___________________________________
any clues now ?

Well, let's see:

1) You didn't explain what this function was supposed to do.
2) You didn't provide it in a cut-and-paste-able fashion, requiring
me to spend too much time reading it to understand what it was
meant to do.
3) You didn't explain what this function did when you used it.
4) You didn't explain how that was different from what you expected
it to do.
5) You didn't provide a self-contained example, so even once we fix
your relatively minor syntax error, we don't know how it's intended
to be used.

So no, I think we still need several more clues, at least.

-=Eric
 
A

Anno Siegel

Proud_to_b_indian said:
i thought u ppl could understand it ...
BUT NO HOPES>.........

i have the same code that i posted it here.
i had put the "//" just for the sake of readers to understand it,,
but seems to b of no use.. as people here are just trying to get away
from answers..and post somethings irrelevant..

Please use complete English words.

Oh really? So we hang around here reading posts, but we're too lazy to
give real answers and rather post drivel? That is an insult to the
people who spend their spare time to make this newsgroup work.
does anybody have a solution ?

Do you have a problem? You haven't stated one.

Anno
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,780
Messages
2,569,611
Members
45,265
Latest member
TodLarocca

Latest Threads

Top