mod_perl2 start one script twice
mod_perl2 start one script twice
am 22.10.2008 11:35:02 von CthuMP
I have follow simple script:
!#/usr/bin/perl
print "Content-Type: text/html\n\n";
print "Counter: " . (++$counter) . "\n";
print time(), "\n";
sleep(20);
print time(), "\n";
Starting that script twice in two different browser windows gives me same
results. In second window I start script after some period (about 10
seconds) after first script started. First and Second scripts ends at the
same time.
So, I misunderrstand, why results are same?
As I see it, apache must give work to second child processes for second
request (because first busy). And scripts must end works in different time
(first script in 10 seconds before second) and give different results (same
counter result, but different times).
Even if script runs sequentially for each request, results will difference
and second script ends after 30 seconds (10 remained for 1st script and 20
for 2nd). But it is not!
If I copy script and run two same scripts with different names it works
fine.
Second question about childs. I not fully understand, how childs work. One
child can handle only one script? It's important, because if one child can
handle different scripts, than module global variables saves their values
between different script calls.
For example, if script1 and script2 uses module My::TestPackage, first
script sets $My::TestPackage::variable = 123, then script2, after it
request, will see in $My::TestPackage::variable value 123, but I haven't
seen mention about that situation in official documentations.
--
View this message in context: http://www.nabble.com/mod_perl2-start-one-script-twice-tp201 07113p20107113.html
Sent from the mod_perl - General mailing list archive at Nabble.com.
Re: mod_perl2 start one script twice
am 22.10.2008 16:16:10 von CthuMP
CthuMP wrote:
>
> Starting that script twice in two different browser windows gives me same
> results. In second window I start script after some period (about 10
> seconds) after first script started. First and Second scripts ends at the
> same time.
>
I have solved that problem.
If someone interesting, it was an opera cache. Starting in different
browsers gives me correct results.
--
View this message in context: http://www.nabble.com/mod_perl2-start-one-script-twice-tp201 07113p20111625.html
Sent from the mod_perl - General mailing list archive at Nabble.com.
Re: mod_perl2 start one script twice
am 22.10.2008 16:28:20 von Adam Prime
CthuMP wrote:
> I have follow simple script:
> !#/usr/bin/perl
>
> print "Content-Type: text/html\n\n";
>
> print "Counter: " . (++$counter) . "\n";
> print time(), "\n";
>
> sleep(20);
>
> print time(), "\n";
>
> Starting that script twice in two different browser windows gives me same
> results. In second window I start script after some period (about 10
> seconds) after first script started. First and Second scripts ends at the
> same time.
> So, I misunderrstand, why results are same?
>
If you're actually seeing the same results from the 'print time()'
calls, something weird is going on. A proxy server between you and the
server might cause that i suppose, or something the browser is doing
with caching, but that shouldn't really happen at the server end i don't
think (unless there is some sort of caching mechanism going on there too.
> As I see it, apache must give work to second child processes for second
> request (because first busy). And scripts must end works in different time
> (first script in 10 seconds before second) and give different results (same
> counter result, but different times).
>
That sounds accurate to me
> Even if script runs sequentially for each request, results will difference
> and second script ends after 30 seconds (10 remained for 1st script and 20
> for 2nd). But it is not!
> If I copy script and run two same scripts with different names it works
> fine.
>
>
> Second question about childs. I not fully understand, how childs work. One
> child can handle only one script? It's important, because if one child can
> handle different scripts, than module global variables saves their values
> between different script calls.
> For example, if script1 and script2 uses module My::TestPackage, first
> script sets $My::TestPackage::variable = 123, then script2, after it
> request, will see in $My::TestPackage::variable value 123, but I haven't
> seen mention about that situation in official documentations.
>
Each apache child will handle any and all scripts. You can't reliably
share global variables like that for exactly the reason you mention.
Generally, if you're running code under mod_perl you should be running
it under 'use strict' (which would break your original example).
Adam
Re: mod_perl2 start one script twice
am 22.10.2008 16:57:04 von aw
CthuMP wrote:
>
> CthuMP wrote:
>> Starting that script twice in two different browser windows gives me same
>> results. In second window I start script after some period (about 10
>> seconds) after first script started. First and Second scripts ends at the
>> same time.
>>
>
> I have solved that problem.
> If someone interesting, it was an opera cache. Starting in different
> browsers gives me correct results.
If you want to avoid this, there are HTTP headers that you can set for
the response of the server, that will tell the browser not to cache this
page.
But since you are obviously starting with this, I don't want to spoil
your fun. You will find this around lesson 17 or so..
Better to do one thing at a time.
;-)
Re: mod_perl2 start one script twice
am 22.10.2008 17:03:24 von Foo JH
It's quite simple really. You're running 2 instances of the script. To
retain the value of $counter, read up the mod_perl documentation for tips.
CthuMP wrote:
> I have follow simple script:
> !#/usr/bin/perl
>
> print "Content-Type: text/html\n\n";
>
> print "Counter: " . (++$counter) . "\n";
> print time(), "\n";
>
> sleep(20);
>
> print time(), "\n";
>
> Starting that script twice in two different browser windows gives me same
> results. In second window I start script after some period (about 10
> seconds) after first script started. First and Second scripts ends at the
> same time.
> So, I misunderrstand, why results are same?
> As I see it, apache must give work to second child processes for second
> request (because first busy). And scripts must end works in different time
> (first script in 10 seconds before second) and give different results (same
> counter result, but different times).
> Even if script runs sequentially for each request, results will difference
> and second script ends after 30 seconds (10 remained for 1st script and 20
> for 2nd). But it is not!
> If I copy script and run two same scripts with different names it works
> fine.
>
>
> Second question about childs. I not fully understand, how childs work. One
> child can handle only one script? It's important, because if one child can
> handle different scripts, than module global variables saves their values
> between different script calls.
> For example, if script1 and script2 uses module My::TestPackage, first
> script sets $My::TestPackage::variable = 123, then script2, after it
> request, will see in $My::TestPackage::variable value 123, but I haven't
> seen mention about that situation in official documentations.
Re: mod_perl2 start one script twice
am 22.10.2008 17:49:01 von aw
>>
>> Second question about childs. I not fully understand, how childs work.
In a little bit more details :
When you start Apache, one single process is started.
That's what you can call the "main" Apache.
It reads and checks the configuration, and bombs out if anything is wrong.
If nothing is wrong, it will then "fork" a number of "children" Apache.
That initial number is set in your configuration file.
The "main" Apache continues to live, and it is that one that is
"listening" on port 80.
Each of the children is identical, and they can all handle any request.
Each child contains the full configuration of Apache, all the add-on
modules etc..
If you are using mod_perl, then each of these children also contains its
own copy of mod_perl and of the perl interpreter. Don't forget this.
When a request comes into Apache (the main one), it looks to see which
of his children has nothing to do at the moment, and gives the request
to that one for processing.
If there are no children free, the main Apache may decide to start a new
one. That is also defined in the configuration (MaxChild). If there
are too many free children, the main Apache may decide to kill some (to
save memory etc..).
In other words, the main Apache does not handle requests, it just gives
work to his children and controls what they are doing and how long they
live. It's terrible and immoral, but that's the way it works.
Each child may handle many requests. How many before it dies, depends
on another configuration parameter : MaxRequestsPerChild. If this is
set to 0, it stays alive "forever" (or until the main Apache decides to
kill it). Which specific requests a child will handle, is rather
unpredictable : it depends on which child the main Apache gives the next
request. (This is not entirely true, but we'll leave that for later).
Now the one selected child handle this one request that he received from
his main Apache "papa".
If it is a request that involves mod_perl, you have to be careful,
because the perl interpreter that is started by mod_perl in this child,
remains "alive" as long as this child itself lives, and it does
"remember" some things from one request to the next.
For example, that's what makes it fast : the first time it runs one
cgi-bin script, it will compile it and keep the resulting compiled code
in memory. The next time a request comes to this same Apache child for
the same script, it will not need to compile it again, but it will
re-use the compiled version.
If the request goes to another child, then that one will also compile
the script and keep it in memory, because it does not know about the
other child.
For example, if the script is big, and if there are 15 Apache children,
and you call the same script 20 times, it is possible that the first 15
calls will be slow, and then the last 5 times it will be very fast.
That is because each child may get one request, and they all have to
first compile the script. But at the second time, they don't have to
anymore.
There is a danger to this : for some types of variables in your script,
perl will remember the last value you put in it, and the next time the
script runs in the same child, it will start with that same value.
So make sure that all variables that you use, are initialised properly
when you start the script.
In other words, write :
my $var = 0;
instead of
my $var;
Note : each Apache child is a totally separate process, and each of
these processes has its own memory and its own perl interpreter. So you
can in principle NOT "communicate" between one cgi-bin script and the
other (or between two consecutive runs of the same script), because you
never know in which Apache child your next request is going to run.
And variables are NOT shared between different requests, even of the
same script, except as indicated above.
Now, if you are very careful, and if you know exactly what you are
doing, and if you know exactly how to do it, you might be able, within
the same Apache child, to initialise a variable once, and leave it to
that same value so that the next time a script runs in the same Apache
child, it will find that same value already initialised.
But re-read the previous paragraph 3 times, making sure you understand
all the if's. Because if you do this without understanding all those
ifs, you will create errors that are very nasty and very difficult to find.
All the above is clearly explained in the mod_perl on-line
documentation, but it never hurts to repeat it.