Vielä kerran rautalankaa tarvitaan:
Jos A.php tiedoston alussa on includetettu tiedosto (B.php), jossa on ensimmäisenä session_start(), niin tarvitseeko se olla kuitenkin myös A.php alussa?
Esitin kysymyksen tähän liittyvän oppaan kommenttiosiossa, mutta sitä varmaan luetaan varsin satunnaisesti...
Eiköhän se riitä, että se on asetettu vain kerran, kunhan se on vain
a) ennen minkään sortin ruudulle tulostamista (echo, html-merkkaus, tyhjät välilyönnit yms.)
ja
b) ennen sessio-muuttujien käsittelyä.
Lebe80 kirjoitti:
Eiköhän se riitä, että se on asetettu vain kerran, kunhan se on vain
Ei nyt näinkään. Funktioita ei koskaan pidä kutsua huvin vuoksi ja siellä täällä. Session_start() heittää noticen, jos sitä kutsutaan väärässä paikassa. Tästä yksinkertaisesta syystä asia olisi selvinnyt ihan kokeilemallakin.
niin siis en sanonutkaan ihan noin, että sen voi heittää mihin tahansa, vaan vastasin Turson kysymykseen, joka kysyi pitääkö se olla molemmissa tiedostoissa.
Tietenkin näin jälkikäteen luettuna sen voi ymmärtää myös noin, varsinkin jos ei lue ensimmäistä viestiä, ja kun jätin vielä lainauksenkin lisäämättä tekstiini.
Sanoit itse "kunhan se vain on", ts. ei niin väliä että onko kerran vai onko muutaman, "kunhan se vain on". Kysyjä oli jo nyt epävarma siitä, minne kaikkialle se pitää laittaa, joten hän olisi voinut alkaa pelata "varman päälle" ja ripotella session avauksia vähän joka paikkaan.
Niin, mutta eikö se riitä, että se on vain kerran, jos A.php -tiedostossa ekana includetaan B.php, jonka alussa on session_start() ?
edit:
Turso kirjoitti:
Jos A.php tiedoston alussa on includetettu tiedosto (B.php), jossa on ensimmäisenä session_start(), niin tarvitseeko se olla kuitenkin myös A.php alussa?
Lebe80 kirjoitti:
Eiköhän se riitä, että se on asetettu vain kerran, kunhan se on vain
a) ennen minkään sortin ruudulle tulostamista (echo, html-merkkaus, tyhjät välilyönnit yms.)
ja
b) ennen sessio-muuttujien käsittelyä.
Eli en ala laittelemaan ihan kaikkia mahdollisia tapauksia, vaan noi yleisimmät, eli ei tulostuksia, ja "alussa" ei aina ole tarkoittanut ihan ensimmäisenä, vaan osalla ohjelmoijista se saattanut tarkoittaa "jossain siellä alkupuolella". Eli en tajua miksi tästä asiasta pitää tehdä nyt näinkin monen viestin mittainen väittely, jossa me kuitenkin molemmat puhutaan samasta asiasta ja alkuperäinen viestin kirjoittaja on jo asian saanut selville.
Alchemist ilmeisesti luuli että lauseesi loppuu siihen "kunhan se vain on", vaikka todellisuudessa kirjoitit "kunhan se vain on a) ... ja b) ..."
Mainittakoon, että tämän hetkisessä ratkaisussa session_start() on nyt ripoteltu kaikkiin mahdollisiin tiedostoihin. (Taitaa muuten heittää jonkun noticen juuri siitä, että sessio aloitetaan "uudelleen".) Tähän asti en ole tästä välittänyt, koska homma toimii. Kysymys olikin juuri periaatteellinen, mikä olisi oikea tapa? Tulostusten huomioiminen on selvä asia.
Kun includetat PHP-tiedoston toiseen, on kuin sinulla olisi vain yksi tiedosto. Joten session_start() vain kerran, ei joka tiedostoon.
Kiitän, Merri, kaivattu rautalanka!
Auttaisiko asiaa session käsittelyn kääriminen luokan sisään, joka huolehtisi session_start()-kutsuista ja muista tarvittavista asioista? Tässä yksi staattinen malli jonka käyttöönoton pitäisi olla helppoa. Myös singleton-pattern voisi olla tässä sopiva tai muu vastaava malli, joka takaa ettei useampia sessioita käynnistellä päällekäin.
abstract class Session { private static $started = false; final private function __construct() { throw new LogicException("This constructor should not get called"); } public static function start() { if(self::$started === true) { return; } session_start(); self::$started = true; } public static function get($key, $default = null) { self::start(); if(array_key_exists($key, $_SESSION)) { return $_SESSION[$key]; } return $default; } public static function set($key, $value) { if($key === null || is_array($key) || is_object($key) || is_resource($key)) { throw new InvalidArgumentException("Invalid key type: ".gettype($key)); } self::start(); $_SESSION[$key] = $value; } } // Usage example Session::set('a', 1); $a = Session::get('a');
Aihe on jo aika vanha, joten et voi enää vastata siihen.