2011-09-22 1 views
5

J'écris deux fichiers, un journal en utilisant une fonction Log_message et l'autre dans ma fonction file_write en écrivant OUT et je veux l'écrire ligne par ligne et ne pas être tamponné afin qu'il écrit ligne par ligne et pas tout en un aller à la fin du script.

J'ai lu au sujet de la mise en mémoire tampon et de rendre le handle de dossier chaud mais ne peut pas faire fonctionner mon code.

Dans cet exemple j'ai ajouté le $|=1; juste avant la boucle foreach mais il écrit toujours en une fois. Est-ce que je fais quelque chose de vraiment bête?

J'ai inclus tout mon script plus bas si cela peut vous aider.

#----------------------------------------------- 
    sub file_write { 
    #----------------------------------------------- 
    open OUT, ">>$OUT" or Log_message ("\n$DATE - $TIME - ERROR - Could not create filelist.doc \t"); 
    Log_message ("\n$DATE - $TIME - INFO - Opened the output file"); 
    my $total = scalar keys %{ $doc->{ resource } }; 
    Log_message ("\n$DATE - $TIME - INFO - Found: " . $total . " resources"); 
    #printf "resources: %s\n", scalar keys %{ $doc->{ resource } }; 

    $|=1; 

    #And I have also tried: 

    #use IO::Handle; 
    #STDOUT->autoflush(1); 

    foreach (keys %{ $doc->{ resource } }) { 
     #print OUT $doc->{ resource }->{ $_ }->{ id }, "\n"; 
     my $ID = $doc->{ resource }->{ $_ }->{ id }, "\n"; 
     Log_message ("\n$DATE - $TIME - INFO - Found: " . $ID); 
     my $testurl = "http://dronlineservices.letterpart.com/web/content.xql?action=doc_html&lang=en&pub=" . $pubId . "&docid=" . $ID; 
     print OUT "$testurl\n"; 
     sleep 1; 

    } 

Et le script entier

# !c:/Perl/bin/Perl.exe 


#----------------------------------------------- 
#Modules 
#----------------------------------------------- 
use XML::Simple; 
use LWP; 
use Data::Dumper; 
$Data::Dumper::Indent = 1; 
$Data::Dumper::Sortkeys = 1; 
use strict; 
use warnings; 

#----------------------------------------------- 
#Declare variables 
#----------------------------------------------- 
    my $script = "LiveContent Auto Cache Script"; # Name of the script 
    my $version = "Version 0.1"; 
    #my $pubId = "COMP-20110922XXXX"; 
    my $pubId = "LiveContentDoc";  
    my $OUT = "output.txt"; 
    my $LOG = "cacher-log.log";  # Location of log file 
    my $DATE;             # Date in form 2001-sep-01 
    my $DATENR;            # Date in form 2001-01-09 
    my $TIME;            # Time in form 12:04:03 
    my $txtmesg = ""; 
    my $resource; 
    my $xs; 
    my $doc; 

#################################### 
########### Main Program ########### 
#################################### 
error_logger();        # Open Log file and time stamp it 
request_url(); #Open the xml url and read it in 
file_write(); #write the contents of the xml url to a file 


#----------------------------------------------- 
sub request_url { 
#----------------------------------------------- 
my $useragent = LWP::UserAgent->new; 
my $request = HTTP::Request->new(GET => "http://digitalessence.net/resource.xml"); 
#my $request = HTTP::Request->new(GET => "http://dronlineservices.letterpart.com/web/content.xql?action=index&lang=en&pub=" . $pubId); 
$resource = $useragent->request($request); 
$xs   = XML::Simple->new(); 
$doc  = $xs->XMLin($resource->content); 

} 


#----------------------------------------------- 
sub file_write { 
#----------------------------------------------- 
open OUT, ">>$OUT" or Log_message ("\n$DATE - $TIME - ERROR - Could not create filelist.doc \t"); 
Log_message ("\n$DATE - $TIME - INFO - Opened the output file"); 
my $total = scalar keys %{ $doc->{ resource } }; 
Log_message ("\n$DATE - $TIME - INFO - Found: " . $total . " resources"); 
#printf "resources: %s\n", scalar keys %{ $doc->{ resource } }; 



use IO::Handle; 
STDOUT->autoflush(1); 

foreach (keys %{ $doc->{ resource } }) { 
    #print OUT $doc->{ resource }->{ $_ }->{ id }, "\n"; 
    my $ID = $doc->{ resource }->{ $_ }->{ id }, "\n"; 
    Log_message ("\n$DATE - $TIME - INFO - Found: " . $ID); 


    my $testurl = "http://dronlineservices.letterpart.com/web/content.xql?action=doc_html&lang=en&pub=" . $pubId . "&docid=" . $ID; 
    print OUT "$testurl\n"; 


     # my $browser = LWP::UserAgent->new; 
     # $browser->timeout(240); 
     # $browser->env_proxy; 
     # $browser->agent('Mozilla/5.0 (compatible; Googlebot/2.1; +http://www.google.com/bot.html)'); 

      # my $response = $browser->get($testurl); 

     # if ($response->is_success) { 
      #  print "\n############################\n"; 
      #  print "$testurl\n"; 
      #  print "\n############################\n"; 
       # print $response->decoded_content; # print the response out 
      # } 
      # else { 
      # my $error = $response->status_line; 
      #  Log_message ("\n$DATE - $TIME - WARN - Can't load $ID because: $error"); 
      # die $response->status_line; 

     # } 



    #my $loadrequest = $ua->get('http://dronlineservices.letterpart.com/web/content.xql?action=doc_html&lang=en&pub=" . $pubId . "&docid=" . $ID'); 
    sleep 1; 

} 


Log_message ("\n$DATE - $TIME - INFO - Written the output file"); 
#close(OUT) or Log_message ("\n$DATE - $TIME - WARN - Failed to close the Output file"); 
Log_message ("\n$DATE - $TIME - INFO - Closed the output file"); 
} 
#----------------------------------------------- 
sub error_logger { 
#----------------------------------------------- 
    time_stamp();                                # Run Time stamp sub 
    open LOG, ">>$LOG" or die ("could not open log file <$LOG>");        # Open Log File 
    Log_message ("\n$DATE - $TIME - -----------------------------------------\ \t"); 
     Log_message ("\n$DATE - $TIME - INFO - Start of Application\ \t"); 
     Log_message ("\n$DATE - $TIME - INFO - $script\ \t"); 
     Log_message ("\n$DATE - $TIME - INFO - $version\ \t"); 
     Log_message ("\n$DATE - $TIME - -----------------------------------------\ \t"); 

} 
#------------------------------------------------------------- 
sub Log_message { 
#------------------------------------------------------------- 
    time_stamp();     # Run time_stamp every time the log is written to 
    my($mesg) = @_; 
    print LOG $mesg if $LOG; # Print to log file 
    print $mesg;    # Print to Screen 
    $txtmesg = $mesg; 
    #print "\nLOGGING: $txtmesg\n"; 
} 
#----------------------------------------------- 
sub time_stamp { 
#----------------------------------------------- 
    my($Sec,$Min,$Hour,$Day,$MonthNr,$Year) = localtime(time()); 
    my $Month=("Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec")[$MonthNr]; 
    $Sec = sprintf("%02d",$Sec); 
    $Min = sprintf("%02d",$Min); 
    $Day = sprintf("%02d",$Day); 
    $MonthNr = sprintf("%02d",++$MonthNr); 
    $Year = 1900 + $Year; 
    $DATE = "$Year-$Month-$Day"; 
    $DATENR = "$Year-$MonthNr-$Day"; 
    $TIME = "$Hour:$Min:$Sec"; 
} # end sub 

Répondre

16

Vous avez oublié de sélectionner la poignée d'abord.

select((select(OUT), $| = 1)[0]); 
+4

Afin d'obtenir quelques explications sur cette ligne de code, une bonne lecture est la documentation ('perldoc perlvar'): _Si paramétré sur non nul, force le flush immédiatement et après chaque écriture ou impression ** sur le canal de sortie ** actuellement sélectionné. –

+0

Merci beaucoup. Maintenant, pour lire les docs pour en avoir plus de sens! –

+9

utilisez IO :: Handle; OUT-> autoflush (1); est beaucoup plus lisible –

11
use IO::Handle; 
OUT->autoflush(1); 

Mais il est préférable d'utiliser des descripteurs de fichier lexical:

use IO::Handle; 
open my $outfh, ">>", $OUT or Log_message ("\n$DATE - $TIME - ERROR - Could not create filelist.doc \t"); 
$outfh->autoflush(1); 
+1

thatsawfullyhardtoreadwithoutanyparens. De plus, la question posée sur la façon d'utiliser '$ |' correctement. Votre réponse ne répond pas à cela. Enfin, vous dites le handle de fichier lexical mais vous ne le pensez pas. Vous voulez dire des poignées autovivrées. – tchrist

+3

@tchrist, Bien sûr que oui. La bonne façon d'utiliser '$ |' est de ne pas l'utiliser via 'autoflush'. – ikegami

+0

@ikegami C'est un sens plutôt idiot de "correct". Le '$ |' n'est pas déprécié, et personne n'a intérêt à le prétendre. – tchrist

Questions connexes