WWW::Mechanize::Firefox wait until images are loaded - perl

Using this Perl module, how would I wait for the page to load all the images? (I am trying to screenshot image which is part of the age)
I tried $agent->success and this only checks if the page is loaded (doesn't check the images).

I don't think there is a wait method in the module but you can check if the element is visible yet and loop through and wait for it to be visible.
FOO: {while(1){
if($gent->is_visible($element)){
print "Image Downloaded\n";
last FOO;
}
else{
print "Downloading image...\n"; #This might print until image is downloaded
sleep(10);
}
}}

Related

Qt Save form take 3-4 second to open

i'm using this on push button click in Qt:
QString fileName = QFileDialog::getSaveFileName(this, tr("Save file"),
QString(),
tr("(*.csv));
it take 3-4 second to open the save Form. why? how i can improve speed?
Try to connect this slot to a QPushButton:
void MainWindow::openFD(){
QTime myopentime=QTime::currentTime();
for (int i=0;i<1000000;i++) ;//comment out this line for the real test
QString fileName = QFileDialog::getSaveFileName(this,QString(),QString(myopentime.toString("m.s.zzz")+" "+QTime::currentTime().toString("m.s.zzz"))
,tr("*.csv") );
}
Then try to run it with and without the count part.
You will see, that the count part adds some ms... without it there is not even ms (mili-second) of difference in the time shown in filename place.
So, you have to search somewhere else in your code or give us a better example.
PS:
1) You will need :
#include <QTime>
2) The line that counting is there to show you that my method works (since you will see some difference when uncomment)
Result and Answer: The problem is not on QFileDialog if this test will not give you differences but somewhere else in your code or possibly in the Window manager of your OS.

Is there a way to get screen to return a session id or pid?

Is there a way to get screen to echo back the session id when it creates a new window?
I am working on script in perl and I need screen to return the session id or the PID to me so I record it in an array or a hash.
What is your purpose for gathering these pids? It can be a little tricky in perl. Something like Unix::PID might help ( http://metacpan.org/pod/Unix::PID ) but I have the suspicion that your question does not address the actual problem you are trying to solve.
Since you are using screen -dmS <somename> you can do this:
my %screens;
for( $i = 0; $i < 10; $i++) {
system("screen -dmS server$i");
}
open(my $fh, "screen -list|");
while (<$fh>){
if (/Detached/) {
/\s*(\d*)\.(.*?)\s/;
my ($pid, $name) = ($1, $2);
$screens{$name} = $pid;
}
};
Check for the environment variable $ENV{'STY'} within any programs running inside screen.
On my MacOS X 10.6 system at least, it contains the session ID, e.g.:
29379.ttys000.hostname
and where the first field is the PID.
From outside screen, you can run:
screen -list
to get a list of all of your sessions.
Failing that, it's unclear how you're actually starting screen from within your script, but if you use a standard fork / exec model then the child PID available after the call to fork will be the required PID. See man perlipc for more details on how to fork a child program and interact with it.

POE complains that POE::Kernel's run method was never called when I fork

This is my code:
if ($DAEMON) {
my $pid = fork();
if (not defined $pid) {
print "Unable to start daemon.\n";
exit(1);
}
elsif ($pid == 0) {
open STDOUT, '>', '/dev/null';
open STDERR, '>', '/dev/null';
_create_sessions($self, $settings);
$poe_kernel->run;
}
else { print "Script forked to background with PID $pid\n"; }
}
else {
_create_sessions($self, $settings);
$poe_kernel->run;
}
When $DAEMON = 1, it complains that POE::Kernel's run() method was never called, but as you can see in the above code, I did that already. The script works perfectly fine when in daemon mode, but I can't get rid of that warning or understand why it says that. I also tried calling $poe_kernel->has_forked() and that didn't make a difference either.
I'm out of ideas. Any suggestions?
Updated to add: Maybe I wasn't clear enough. The code below creates the session and runs the kernel.
_create_sessions($self, $settings);
$poe_kernel->run;
It works perfectly fine. It's only when the same code is run inside a fork'd child so I can send the script to the background, that it says POE::Kernel's run method wasn't called. The script does go into the background and works like it should which means the kernel is indeed running. I'm only looking to get rid of that annoying warning.
ysth is right. The warning happens because POE::Session instances are created in the parent process but they haven't been given an opportunity to run.
% perl -wle 'use POE; POE::Session->create(inline_states=>{_start => sub {}})'
40023: Sessions were started, but POE::Kernel's run() method was never
40023: called to execute them. This usually happens because an error
40023: occurred before POE::Kernel->run() could be called. Please fix
40023: any errors above this notice, and be sure that POE::Kernel->run()
40023: is called. See documentation for POE::Kernel's run() method for
40023: another way to disable this warning.
In the above example, 40023 is the process ID where the problem was detected.
It's similar to Perl's warning about exiting with active threads:
% perl -wle 'use threads; threads->create(sub { sleep 3600 }); '
Perl exited with active threads:
1 running and unjoined
0 finished and unjoined
0 running and detached
While your code snippet shows sessions are created and run in the child process, I suspect sessions are created before or afterward. The parent process doesn't exit in your snippet, so there's no telling where execution goes afterward?
You should also call POE::Kernel->has_forked() in the child process. I can't tell whether that's happening in your code snippet.
The correct solution is to move all session instantiation into the child process when daemonizing. A passable workaround is to call POE::Kernel->run() just after using POE::Kernel and before any sessions are actually created. run() will return immediately because no sessions exist, but the call satisfies the condition you're being warned about. It's a way of saying "yes, yes, but I know what I'm doing".
From the doc, POE::Kernel's run is normally called as a class method; what is $poe_kernel?
Somewhere, you seem to be starting a session but don't end up calling POE::Kernel->run();
Update: since the message you see is output with warn, and you are throwing away STDERR in the child, I'm guessing it is the parent giving the warning. Something you are doing (in the code you don't show that loads POE and sets $poe_kernel?) is in fact creating a session, apparently unintentionally.
Try to reduce your code to a short, yet runnable example and you will either find the problem yourself or enable others to help you find it.

Mechanize::Firefox gets stuck

I'm using WWW::Mechanize::Firefox to crawl pages that load some JavaScript after they have been loaded.
My code regarding this problem:
my ($firemech) = WWW::Mechanize::Firefox->new(tab => 'current', );
$firemech->get($url);
die "Cannot connect to $url\n" if !$firemech->success();
print "I'm connected!\n";
my ($retries) = 10;
while ($retries-- and ! $firemech->is_visible( xpath => '//*[#class="areaMapC"]' )) {
sleep 1;
}
die "Timeout" unless $retries;
my ($content) = $firemech->content();
Everything goes fine for the first page, it loads the page and recognizes the class that loads later. Then, it changes to the second page correctly (I see Firefox changing it), but it never gets to the "I'm connected!" print.
I checked the URL and that the wanted class is there, the code it's the same for both the pages (except some IDs which I want to extract). I really have no clue what's going wrong.
A page of this kind is HERE.
I solved this one by simply using
my ($firemech) = WWW::Mechanize::Firefox->new();
Instead of what I used before. It still keeps the content in one tab so it works perfectly with my needs.

Why are my shared variables getting cleared out between PerlChildInitHandler and PerlResponseHandler in mod_perl?

I am trying to load a configuration file into a hash during my PerlChildInitHandler and then access the values from PerlResponseHandler. However, even though the process number is the same, it seems that variables changed during the child_init() call revert back to their default values when handler() gets called.
The basic scenario is:
package StartupLog;
# the variable I'm testing
my $sticky = 0;
sub child_init {
$sticky = 1;
return 0;
}
sub handler {
warn __PACKAGE__ . " sticky = $sticky\n"; ### always says "0" but should say "1"
return 0;
}
1;
This was never answered, so eventually I moved on to using the PerlPostConfigHandler, which seemed to work acceptably. I can only assume it's something about the forking that happens in the PerlChildInitiHandler but, sorry to say, I gave up. Hope this helps someone in the future.
Generally, if you want to load something at childinit time, and access it in the response phase, you'd stuff it into a package global (like $My::variable = 'lols'). I've never tried to do it the way you are here. Did you try using our instead of my maybe?.