Yönlendirmeden sonra PHP oturumu kaybedildi


132

PHP'de yeniden yönlendirmeden sonra bir oturumu kaybetme sorununu nasıl çözebilirim?

Son zamanlarda, yeniden yönlendirmeden sonra oturumu kaybetme konusunda çok yaygın bir sorunla karşılaştım. Ve (her ne kadar hala hiçbir çözüm bulabiliriz bu web sitesi aracılığıyla arama yaptıktan sonra bu yakın geldi).

Güncelleme

Cevabı buldum ve aynı sorunu yaşayan herkese yardımcı olmak için buraya göndermeyi düşündüm.


1
Soru, PHP'de bir yeniden yönlendirmeden sonra bir oturumu kaybetme sorununun nasıl çözüleceğidir. Cevabı çoktan buldum, sadece başkalarının bilmesini sağlamak için buraya gönderdim. Çünkü benim çözümüm StackOverflow'da değil.
dayuloli

2
Sorun değil, ancak bu bir QA sitesidir. Lütfen sorunuzu soru haline getirin.
jeremy

Senden olduğunu fark etmedim. Yine de bu site sorular içindir, zaten bildiğiniz soruların cevapları için değil.
Aris


21
@Aris Bu doğru değil, insanlar kodlamayla ilgili bir soruları olduğunda, yardım için StackOverflow'a geliyorlar. Mevcut cevap yoksa ihtiyaç duydukları yardımı alamazlar. Bu cevabı vermeye çalışıyorum.
dayuloli

Yanıtlar:


209

İlk önce şu olağan kontrolleri yapın:

  1. session_start();Herhangi bir seans çağrılmadan önce arandığından emin olun . Bu nedenle, güvenli bir bahis, sayfanızın başına, açılış <?phpbildiriminin hemen sonrasına, her şeyden önce koymaktır . Ayrıca açılış <?phpbildiriminden önce boşluk / sekme olmadığından emin olun .
  2. headerYönlendirmeden sonra, mevcut komut dosyasını kullanarak sonlandırın exit();(Diğerleri de önerdi session_write_close();ve session_regenerate_id(true)bunları da deneyebilirsiniz, ancak kullanırım exit();)
  3. Test etmek için kullandığınız tarayıcıda çerezlerin etkinleştirildiğinden emin olun.
  4. register_globalsKapalı olduğundan emin olun , bunu php.inidosyada ve kullanarak da kontrol edebilirsiniz phpinfo(). Bakın bu onu nasıl kapatılacağı konusunda.
  5. Oturumu silmediğinizden veya boşaltmadığınızdan emin olun
  6. $_SESSIONSüper küresel dizinizdeki anahtarın hiçbir yerde üzerine yazılmadığından emin olun
  7. Aynı alan adına yönlendirdiğinizden emin olun. Yani bir diğerine yönlendirme www.yourdomain.comiçin yourdomain.comileriye oturumu taşımaz.
  8. Dosya uzantınızın olduğundan emin olun .php(olur!)

Şimdi, bunlar en yaygın hatalardır, ancak hile yapmazlarsa, sorun büyük olasılıkla hosting şirketinizle ilgilidir. Her şey çalışıyorsa localhostancak uzak / test sunucunuzda çalışmıyorsa, büyük olasılıkla suçlu budur. Bu nedenle, barındırma sağlayıcınızın bilgi tabanını kontrol edin (ayrıca forumlarını vb. Deneyin). FatCow ve iPage gibi şirketler için belirtmeniz gerekir session_save_path. Bunun gibi:

session_save_path('"your home directory path"/cgi-bin/tmp');
session_start();

("ana dizini yolunuzu" gerçek ana dizin yolunuzla değiştirin. Bu genellikle kontrol panelinizdedir (veya eşdeğeridir), ancak test.phpkök dizininizde bir dosya da oluşturabilir ve şunu yazabilirsiniz:

<?php echo $_SERVER['SCRIPT_FILENAME']; ?>

'Test.php'den önceki bit, ana dizin yolunuzdur. Ve elbette, klasörün kök dizininizde gerçekten var olduğundan emin olun. (Bazı programlar senkronizasyon sırasında boş klasörler yüklemiyor)


8
Çok iyi yazılmış +1, eğer hepsi başarısız olursa, sadece çerezleri kullanın (rastgele bir dize oluşturun ve veritabanında saklayın ve bunu çerez değeriniz olarak kullanın).
Dave Chen

2
http ve n https arasında geçiş yapmak da bir sorun olabilir stackoverflow.com/questions/441496/…
dev.e.loper

4
Php 5.4.0 itibariyle register_globals kaldırıldı, bu yüzden artık bir soruna neden olmayacak
anthonygore

2
Web sunucusu hata günlüğünü de kontrol edin; benim durumumda, "Oturum verileri (dosyalar) yazılamadı. Lütfen geçerli session.save_path ayarının doğru olduğunu doğrulayın" hatası oluştu. Save_path dizinindeki izinler yanlıştı.
timbonicus

Seanslarımın session.save_path dışında bir yerde saklanmasının bir nedeni var mı?
Justin

26

başlık çağrısından sonra "çıkış" kullanmalısınız

header('Location: http://www.example.com/?blabla=blubb');
exit;

Gecko için bir hata var (örn. Waterfox, Firefox, SeaMonkey) burada herhangi bir veri çıkışı (örn. echo ' ';) Veya herhangi bir tür boşluk varsa, konum başlığını tamamen yok sayacaktır.
John

18

Olası tüm çözümleri denedim ama hiçbiri benim için işe yaramadı! Tabii ki, paylaşılan bir barındırma hizmeti kullanıyorum.

Sonunda, yönlendirme başlığının içinde 'göreli url' kullanarak sorunu çözdüm!

header("location: http://example.com/index.php")

oturum çerezlerini geçersiz kıldı

header("location: index.php")

bir cazibe gibi çalıştı!


7

Ben de aynı sorunu yaşadım. Üzerinde birkaç saat çalıştım ve bu beni çılgına çevirdi.

Benim durumumda sorun, yalnızca Chrome ve Firefox'taki eksik favicon.ico nedeniyle çağrılan bir 404 idi . Diğer gezginler iyi çalıştı.


Sadece bu cevap için teşekkür etmek istedim, 404 resim isteğinin Varnish tarafından PHP'ye çerezsiz iletildiğini ve bu nedenle sürekli yeni oturumlar oluşturulduğunu fark ettim. Sensiz asla anlayamayabilirim.
Pascal Zajac

Aynı sorunu yaşadım, favicon.ico'm yeniden yönlendiriliyordu (alt etki alanından ana etki alanına 302 yönlendirmesi) ve böylece her seferinde yeni bir oturum oluşturdu. Çok teşekkürler!
simdrouin

4

Header () işlevinde göreli yolu "dir / file.php" ile kullandığımda benim için çalışıyor. Tam url'yi kullanarak yeniden yönlendirdiğinizde oturumun herhangi bir nedenle kaydedilmediğini düşünüyorum ...

//Does retain the session info for some reason
header("Location: dir");

//Does not retain the session for some reason
header("Location: https://mywebz.com/dir")

3

Bu beni uzun süre şaşırttı (ve bu yazıyı bulmak harikaydı!) Ama yine de sayfa yönlendirmeleri arasında oturum açamayan başka biri için çalışmak ... php.ini dosyasına gitmem ve çerezleri açmam gerekiyordu :

session.use_cookies = 1 

Seansların çerezler olmadan çalıştığını sanıyordum ... aslında BUNLARINIZ GEREKTİĞİNİ biliyorum ... ama bu en azından büyük resimde neler olup bittiğini anlayana kadar sorunumu çözdü.


Seansların çerezler olmadan çalışabileceğini bilmiyordum! Her gün yeni bir şeyler öğrenin! programmerinterview.com/index.php/php-questions/…
dayuloli

elbette çerezler olmadan çalışabilirler, yapılandırmanıza bağlıdır. Ama ne yaptığını bilmelisin. Ve bunu yapmak için iyi bir nedeniniz var. Çünkü daha az güvenli. ve her ne sebeple olursa olsun çerezler olmadan çalışmanız gerektiğinde. En azından ini_set'i yapılandırmalısınız ('session.use_strict_mode', '1'); ve genellikle kısa bir oturum süresine sahiptir ve kullanıcı oturum açtıktan sonra session_regenerate_id () kullanın. Ancak, bazı kullanıcılar bir forumda sunucunuzdaki bir siteye bir bağlantı gönderirse, bu bağlantıyı gerçekten tıklayanlar oturumu devralacaktır. Belki ipi kontrol etmek de iyi bir fikirdir.
Michael

3

Bağlamım biraz farklı olsa da benzer bir sorun yaşadım. Ana bilgisayar adı windowsve IP adresi olan bir makinede yerel geliştirme kurulumum vardı 192.168.56.2.

Sisteme şunlardan birini kullanarak erişebilirim:

Giriş yaptıktan sonra, PHP kodum şunu kullanarak yeniden yönlendirecek:

header('http://windows/');

Sisteme erişmek için kullanılan önceki alan adı olmasaydı windows, oturum verileri kaybolacaktı. Bunu kodu şu şekilde değiştirerek çözdüm:

header('http://'.$_SERVER['HTTP_HOST'].'/');

Artık, kullanıcının hangi yerel etki alanı adını veya IP adresini koyduğuna bakılmaksızın çalışır.

Umarım bu birisi için yararlı olabilir.


3

Bu konuyla belirli bir sayfada karşılaştım. Yönlendirmeden hemen önce diğer sayfalarda $ _SESSION değerlerini ayarlıyordum ve her şey yolunda gidiyordu. Ancak bu belirli sayfa çalışmıyordu.

Sonunda, bu belirli sayfada, sayfanın başında oturumu bozduğumu ancak bir daha başlatmadığımı fark ettim. Yani yok etme işlevim şu şekilde değişti

function sessionKill(){

    session_destroy();

}

için:

function sessionKill(){

    session_destroy();
    session_start();

}

Ve her şey çalıştı!


3

Ben de aynı sorunu yaşıyordum. Birdenbire, oturum değişkenlerimden BAZILARI sonraki sayfada kalmıyordu. Sorun çıktı (php7.1'de) başlık konumunuzda WWW olmamalı, örn. Https: // mysite . tamam, https: //www.mysite . o sayfaların oturum değişkenlerini kaybedecek. Hepsi değil, sadece o sayfa.


Bunun nedeni ya da www.mysite.comtamamen farklı bir alan adı olarak görülmesiblog.mysite.commysite.com
dayuloli

2

Günlerdir bununla mücadele ediyorum, tüm çözümleri kontrol ediyorum / deniyorum, ancak sorunum session_start();yeniden yönlendirmeden sonra tekrar aramamış olmamdı. Sadece seansın "hala hayatta" olduğunu varsaydım.

Yani bunu unutma!


Evet! bu benim de sorunumdu. Bir PHP oturumu başlatmanın tüm evi aydınlatmak gibi olduğunu düşündüm. Girdiğiniz her oda için düğmeyi çevirmeniz gerektiğini fark etmemiştim.
Dale Thompson

1

Aynı sorunu yaşadım ve en kolay yolu buldum. Sadece 1 satır JS ile bir yönlendirme .html'ye yönlendirildim

<!DOCTYPE html>
<html>
<script type="text/javascript">
<!--
window.location = "admin_index.php";
//–>
</script>
</html>

PHP yerine

header_remove();
header('Location: admin_login.php');
die;

Umarım bu yardımcı olur.

Aşk Gram


1

Eğer kullanıyorsanız session_set_cookie_params(), dördüncü parametreyi $secureolarak geçip geçmediğinizi kontrol etmek isteyebilirsiniz true. Eğer öyleyseniz, url'ye https kullanarak erişmeniz gerekir.

$secureParam gerçek araçlarla olmak Oturumu güvenli bir istek içinde kullanılabilir. Bu sizi yerel olarak sahne veya üretim ortamlarından daha fazla etkileyebilir.

Bahsetmek çünkü bugünün çoğunu bu sorunu bulmaya harcadım ve bu benim için çözdü. Bu projeye yeni eklendim ve hiç kimse bunun https gerektirdiğinden bahsetmedi.

Yani yerel olarak https kullanabilir veya $secureparametresi olarak ayarlayıp FALSEhttp'yi yerel olarak kullanabilirsiniz. Değişikliklerinizi yukarı ittiğinizde bunu doğru olarak ayarladığınızdan emin olun.

Yerel sunucunuza bağlı olarak, yerel URL'nize https sunulması için sunucunun DocumentRootiçinde düzenleme yapmanız gerekebilir httpd-ssl.conf.


1

Başka bir olası neden:

Bu benim sunucu depolama alanım. Sunucu disk alanım doldu. Bu yüzden sunucumdaki birkaç dosya ve klasörü kaldırdım ve denedim.

Çalıştı !!!

Oturumumu AWS Dynamo DB'ye kaydediyorum, ancak yine de sunucumda oturumu işlemek için biraz alan bekliyor. Emin değilim neden!!!


1

Laravel kullanıyorsanız ve bu sorunu yaşıyorsanız, ihtiyacınız olan şey yeniden yönlendirmeden önce oturum verilerinizi kaydetmektir.

session()->save();
// Redirect the user to the authorization URL.
header('Location: ' . $authorizationUrl);
exit;

0

Yönlendirme çalışmadığında da aynı sorunu yaşadım ve bulabildiğim tüm çözümleri denedim, başlık yönlendirmem bir formda kullanılıyordu.

Bunu, başlık yönlendirmesini farklı bir php sayfasına 'signin_action.php' koyarak ve değişken parametrelerini url parametrelerinde istediğimden geçirerek ve ardından 'signin_action.php' formunda yeniden atayarak çözdüm.

signin.php

if($stmt->num_rows>0) {
$_SESSION['username'] = $_POST['username'];
echo '<script>window.location.href = "http://'.$root.'/includes/functions/signin_action.php?username='.$_SESSION['username'].'";</script>';
error_reporting(E_ALL);

signin_action.php

<?php
require('../../config/init.php');
$_SESSION['username'] = $_GET['username'];
if ($_SESSION['username']) {

echo '<script>window.location.href = "http://'.$root.'/user/index.php";</script>';
exit();
} else {
echo 'Session not set';
}

?>

Güzel bir çözüm değil ama işe yaradı.


0

Benim için hata, oturumda serileştirilemeyen bir nesneyi kaydetmeye çalışmamdı, böylece oturumu yazmaya çalışırken bir istisna atılmıştı. Ancak tüm hata işleme kodum zaten herhangi bir işlemi durdurduğundan, hatayı hiç görmedim.

Yine de Apache hata günlüklerinde bulabilirim.


0

Sadece kayıt için ... Bu problemi yaşadım ve birkaç saat boyunca her şeyi denedikten sonra sorun diskin dolu olması ve php oturumlarının tmp dizinine yazılamamasıydı ... bu yüzden bu problemle karşılaşırsanız şunu kontrol edin çok...


Bu cevap benim için çalıştı. Nginx ile bir Amazon Machine Image çalıştırıyoruz. Oturum klasörünün (bizim durumumuzda www) doğru kullanıcıya ait olmadığı bir hata var gibi görünüyor, bu nedenle chown -R www.wwwoturumlar klasöründe performans göstermek sorunu çözüyor.
Joshua

0

Benim için Firefox, oturum kimliğini (PHPSESSID) bir çerezde sakladı, ancak Google Chrome GET veya POST parametresini kullandı. Bu nedenle, yalnızca geri dönen betiğin (benim için: paypal ödeme) url veya POST parametresinde PHPSESSID işlediğinden emin olmalısınız.


0

Burada SO ve diğer bloglarda birçok çözümü denedikten sonra ... benim için işe yarayan şey web sitemin köküne .htaccess eklemekti.

RewriteEngine on
RewriteCond %{HTTP_HOST} ^yoursitename.com$
RewriteRule ^.*$ "http\:\/\/www\.yoursitename\.com" [R=301,L]

0

Wordpress kullanıyorsanız, bu kancayı eklemem ve oturumu init'te başlatmam gerekiyordu:

function register_my_session() {
    if (!session_id()) {
        session_start();
    }
}
add_action('init', 'register_my_session');

0

Benim için hiçbir şey işe yaramadı ama soruna neyin neden olduğunu buldum (ve çözdüm):

Tarayıcınızın tanımlama bilgilerini kontrol edin ve farklı alt alan adlarında (" www.website.com " ve " web sitesi.com " için bir tane gibi) php oturum tanımlama bilgilerinin bulunmadığından emin olun .

Bunun nedeni, çerezleri ayarlamak ve sayfaları iç çerçevelerde açmak için alt etki alanını yanlış bir şekilde kullanan bir javascript idi.


0

Her şeyden session_start()önce, $_SESSIONdeğişkeni kullanmadan önce aradığınızdan emin olun .

Hata raporlamayı devre dışı bıraktıysanız, açmayı deneyin ve sonucu görün.

ini_set('display_errors', 1);
ini_set('display_startup_errors', 1);
error_reporting(E_ALL);

@ Dayuloli'nin cevabında bahsedilmeyen en yaygın nedenler:

  1. Disk alanı sorunu. Disk alanınızın dolu olmadığından emin olun, oturum dosyalarını depolamak için biraz alana ihtiyacınız vardır.

  2. Oturum dizini yazılabilir olmayabilir. İle kontrol edebilirsinizis_writable(session_save_path())


0

Ben de aynı sorunu yaşıyordum ve cevabı için kodumda arama yapmaktan çıldırdım. Sonunda, barındırma hizmetimin kısa süre önce sunucumdaki PHP sürümünü güncellediğini ve session_save_pathparametreyi php.inidosyada doğru şekilde ayarlamadığını buldum .

Bu nedenle, birisi bunu okursa, lütfen php.iniher şeyden önce yapılandırmayı kontrol edin .


0

Seansınızı ayarlarken ve session_write_closearasında çağrılmadığından emin olun session_start().

session_start();

[...]

session_write_close();

[...]

$_SESSION['name']='Bob'; //<-- won't save

0

Artık GDPR bir şey olduğuna göre, bu soruyu ziyaret eden kişiler muhtemelen bir çerez komut dosyası kullanıyor. Bu senaryo benim için soruna neden oldu. Görünüşe göre PHP PHPSESSID, oturumu izlemek için adı verilen bir çerez kullanıyor . Bu komut dosyası onu silerse, verilerinizi kaybedersiniz.

Ben kullanılan bu çerez komut . "Temel" çerezleri etkinleştirme seçeneği vardır. PHPSESSIDListeye ekledim , komut dosyası çerezi silmeyi bıraktı ve her şey yeniden çalışmaya başladı.

Muhtemelen kullanmaktan kaçınmak için bazı PHP ayarı etkinleştirmek olabilir PHPSESSID, ancak çerez komut sorunun nedeni ise, neden düzeltemez o .


0

Bu sorunu günlerce hata ayıkladıktan sonra düzelttim ve bunun nedeni PayPal Ekspres Satın Alma'dan gelen iade URL'mde 'www' olmamasıydı. Chrome, alan adlarının aynı şekilde ele alınması gerektiğini fark etti, ancak diğer tarayıcılar bazen bunu yapmadı. Oturumları / çerezleri ve mutlak yolları kullanırken, "www" yu unutmayın!


0

PHP'nin oturum dosyalarını depoladığı yola grup yazma izinleri vererek düzelttim. Oturum yolunu session_save_path () işlevi ile bulabilirsiniz.


0

Bugün bir projede bu sorunu yaşadım ve bu parametreyi yanlış olarak değiştirmek zorunda kaldım (veya satırları kaldırmak, varsayılan olarak devre dışıdır):

ini_set( 'session.cookie_secure', 1 );

Bunun nedeni gerçek projenin yalnızca https üzerinden değil http üzerinden çalışmasıdır. Http://php.net/manual/en/session.security.ini.php belgelerinde daha fazla bilgi bulabilirsiniz


0
ini_set('session.save_path',realpath(dirname($_SERVER['DOCUMENT_ROOT']) . '/../session'));
session_start();

Cevap vermek için çok geç ama bu benim için çalıştı


0

Bana göre bu bir izin hatasıydı ve bu sorunu çözdü:

chown -R nginx: nginx / var / opt / remi / php73 / lib / php / session

PHP üzerinde birkaç saat test ettim ve yaptığım son test, session1.php ve session2.php olmak üzere iki dosya oluşturmamdı.

session1.php:

session_start();

$_SESSION["user"] = 123;

header("Location: session2.php");

session2.php:

session_start();

print_r($_SESSION);

ve boş bir dizi yazdırıyordu.

Bu noktada bunun bir sunucu sorunu olabileceğini düşündüm ve aslında öyleydi.

Umarım bu birine yardımcı olur.


1
Chown, paket güncellemesinde varsayılan değere geri döneceği için KÖTÜ bir çözümdür. Varsayılan havuz yapılandırmasındaki yorumlara bakın (www.conf). Apache dizininden başka bir dizin kullanılıyorsa doğru yol (örn: / var / lib / php / nginx / session)
Remi Collet

Haklısın. paket güncellemesi ilk etapta sorunumun sebebiydi. Ama bu şekilde yapıldığı ve bunun yardımcı olduğu hızlı bir çözüme ihtiyacım olduğu için. SYS yöneticim çözdü, Linux konusunda pek iyi değilim.
temo
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.