Muistelin, että luin jostain, että php-tiedoston suoritus loppuu jos selaimesta painaa peruuta tai latausen lopetusta. Joten kysyn onko tämä totta?
Ja jos tämä on totta, niin pysähtyykö php-koodin suoritus juuri siihen mihin se peruutuksen sattuessa on ehtinyt suorittaa, vai suorittaako se mahdollisen silmukan loppuun ensiksi?
Ja varsinainen kysymykseni: Mikäli tuhon ensimmäiseen vastaukseen on myönteinen vastaus ja ollaan luotu oli jossa on __destruct() functio, niin suoritetaanko tämä functio silti. Sillä mikäli jos olen ymmärtänyt __destruct():n oikein se suoritetaan aina kun olio "tuhoutuu". Eli käytännössä silloin, kun tiedoston käsittely loppuu?
Näitähän voi toki testailla itse kukin. Mielenkiintoisia kysymyksiä, ja varsinkin mielenkiintoisia tuloksia sain testaillessani:
-Apassi ajoi asetuksista huolimatta tiedostoa aina niin pitkään kunnes oltiin saavutettu ajon aikarajoitus.
-Olion __destruct metodia ei kutsuta ilman sen rekisteröimistä shutdown-funkkariksi.
-Ilmeisesti tuota silmukkaa ei suoriteta loppuun.
-sleep ja usleep ohittavat aikarajoituksen.
Jotain vähän haeskelinkin Intternetsistä, ja siellä lausuttihin: PHP ei tiedä käyttäjän lopettaneen suorituksen ennen kuin se yrittää tulostaa jotain.
Tässäpä koodi, jolla testailin
<?php class Test { // koska shutdownissa cwdir vaihtuu serverroottiin const ABSOLUTE_LOGPATH = 'C:/Apache/htdocs/'; ### // muokkaile näitä mahdollisesti erilaisten tulosten saavuttamiseksi const IGNORE_ABORT = false; const REGISTER_SHUTDOWN = true; const OB_ON = true; const TIME_LIMIT = 6; // s const NAPTIME = 1000000; // µs ('mikrosekunneissa', jos mikromerkki ei näy oikein) const LONGNAP = 6; // s, muokkaile lyhemmäksi kuin TIME_LIMIT jos tahdot looppailla ### private $_round; private $_timer; public function __construct() { ignore_user_abort( self::IGNORE_ABORT ); // ilman tätä tuota tuhoamisfunkkaria ei jostakin syystä kutsuta.. hmm if ( self::REGISTER_SHUTDOWN ) register_shutdown_function( array( &$this, '__destruct' ) ); echo 'Test instance initialized!<br />'; $this->_round = -1; $this->_timer = microtime( true ); } public function run() { file_put_contents( 'test.log', '' ); set_time_limit( self::TIME_LIMIT ); if ( self::OB_ON ) ob_start(); while( true ): $this->_round += 2; $str = ' this is round ' . $this->_round . ' in the loop'; echo '(Looping) ', $str, '<br />'; if ( self::OB_ON ) ob_flush(); file_put_contents( 'test.log', '(Archiving)' . $str . "\n", FILE_APPEND ); usleep( self::NAPTIME ); $round = $this->_round; $this->_round = 'Roundcounter is sleepy +_+'; usleep( self::LONGNAP ); $this->_round = $round - 1; endwhile; } public function __destruct() { if ( self::OB_ON ) ob_end_clean(); $msg = '(Destructing) Ran through ' . $this->_round . ' loops' . "\n"; $msg .= '(Execution time) ' . ( microtime( true ) - $this->_timer ); file_put_contents( self::ABSOLUTE_LOGPATH . 'test.log', $msg, FILE_APPEND ); echo 'Destroying Test instance!'; } } $test = new Test(); $test->run(); ?>
Kiitoksia tää selvensi asioita.
Aihe on jo aika vanha, joten et voi enää vastata siihen.