① php 怎麼使用session
PHP session用法其實很簡單它可以把用戶提交的數據以全局變數形式保存在一個session中並且會生成一個唯一的session_id,這樣就是為了多了不會產生混亂了,並且session中同一瀏覽器同一站點只能有一個session_id,下面我們一起來看看關於session使用方法。
如何使用session,凡是與session有關的,之前必須調用函數session_start();
為session賦值很簡單,如:
<?php
Session_start();
$Name = "這是一個Session例子";
Session_Register("Name");//注意,不要寫成:Session_Register("$Name");
Echo $_SESSION["Name"];
//之後$_SESSION["Name"]為"這是一個Session例子"
?>
在php4.2之後,可以為session直接賦值:
復制代碼 代碼如下:
<?PHP
Session_Start();
$_SESSION["name"]="value";
?>
② php中$_session[]是什麼意思
使用php應用session時,將session中的數據存儲在伺服器上,然後通過客戶端傳來的sessionid識別客戶端的信息,並提取信息。
php中的session的常用操作:session的寫入、讀取、注冊與刪除。
session的開始
標記session使用開始的函數是session_start,session_start函數用於初始化session變數。語法如下:
session_start();
返回值為true。
session的寫入和讀取
在php中,session的使用是通過預定義數組$_session的調用和讀取來完成。
在網站的頁面中,在注冊頁面對$_session數組進行賦值,在其他的頁面中對$_session數組進行讀取。
注冊頁面中的session,例如:
?php
session_start();
$_session['keyword']=
"php";
?
其他頁面中的session,例如:
?php
session_start();
echo
$_session['keyword'];
?
依次運行,結果是:
php
③ PHP中SESSION的問題
Session 和 Cookie 有什麼關系
Cookie 也是由於 HTTP 無狀態的特點而產生的技術。也被用於保存訪問者的身份標示和一些數據。每次客戶端發起 HTTP 請求時,會將 Cookie 數據加到 HTTP header 中,提交給服務端。這樣服務端就可以根據 Cookie 的內容知道訪問者的信息了。 可以說,Session 和 Cookie 做著相似的事情,只是 Session 是將數據保存在服務端,通過客戶端提交來的 session_id 來獲取對應的數據;而 Cookie 是將數據保存在客戶端,每次發起請求時將數據提交給服務端的。
上面提到,session_id 可以通過 URL 或 cookie 來傳遞,由於 URL 的方式比 cookie 的方式更加不安全且使用不方便,所以一般是採用 cookie 來傳遞 session_id。
服務端生成 session_id,通過 HTTP 報文發送給客戶端(比如瀏覽器),客戶端收到後按指示創建保存著 session_id 的 cookie。cookie 是以 key/value 形式保存的,看上去大概就這個樣子的:PHPSESSID=e4tqo2ajfbqqia9prm8t83b1f2。在 PHP 中,保存 session_id 的 cookie 名稱默認叫作 PHPSESSID,這個名稱可以通過 php.ini 中 session.name 來修改,也可以通過函數 session_name() 來修改。
為什麼不推薦使用 PHP 自帶的 files 型 Session 處理器
在 PHP 中,默認的 Session 處理器是 files,處理器可以用戶自己實現(參見:自定義會話管理器)。我知道的成熟的 Session 處理器還有很多:Redis、Memcached、MongoDB……
為什麼不推薦使用 PHP 自帶的 files 類型處理器,PHP 官方手冊中給出過這樣一段 Note:
無論是通過調用函數 session_start() 手動開啟會話, 還是使用配置項 session.auto_start 自動開啟會話, 對於基於文件的會話數據保存(PHP 的默認行為)而言, 在會話開始的時候都會給會話數據文件加鎖, 直到 PHP 腳本執行完畢或者顯式調用 session_write_close() 來保存會話數據。 在此期間,其他腳本不可以訪問同一個會話數據文件。
上述引用參見:Session 的基本用法
為了證明這段話,我們創建一下 2 個文件: 文件:session1.php
<?php
session_start();
sleep(5);
var_mp($_SESSION);
?>
文件:session2.php
<?php
session_start();
var_mp($_SESSION);
?>
在同一個瀏覽器中,先訪問 http://127.0.0.1/session1.php,然後在當前瀏覽器新的標簽頁立刻訪問 http://127.0.0.1/session2.php。實驗發現,session1.php 等了 5 秒鍾才有輸出,而 session2.php 也等到了將近 5 秒才有輸出。而單獨訪問 session2.php 是秒開的。在一個瀏覽器中訪問 session1.php,然後立刻在另外一個瀏覽器中訪問 session2.php。結果是 session1.php 等待 5 秒鍾有輸出,而 session2.php 是秒開的。
分析一下造成這個現象的原因:上面例子中,默認使用 Cookie 來傳遞 session_id,而且 Cookie 的作用域是相同。這樣,在同一個瀏覽器中訪問這 2 個地址,提交給伺服器的 session_id 就是相同的(這樣才能標記訪問者,這是我們期望的效果)。當訪問 session1.php 時,PHP 根據提交的 session_id,在伺服器保存 Session 文件的路徑(默認為 /tmp,通過 php.ini 中的 session.save_path 或者函數 session_save_path() 來修改)中找到了對應的 Session 文件,並對其加鎖。如果不顯式調用 session_write_close(),那麼直到當前 PHP 腳本執行完畢才會釋放文件鎖。如果在腳本中有比較耗時的操作(比如例子中的 sleep(5)),那麼另一個持有相同 session_id 的請求由於文件被鎖,所以只能被迫等待,於是就發生了請求阻塞的情況。
既然如此,在使用完 Session 後,立刻顯示調用 session_write_close() 是不是就解決問題了哩?比如上面例子中,在 sleep(5) 前面調用 session_write_close()。
確實,這樣 session2.php 就不會被 session1.php 所阻塞。但是,顯示調用了 session_write_close() 就意味著將數據寫到文件中並結束當前會話。那麼,在後面代碼中要使用 Session 時,必須重新調用 session_start()。
例如:
<?php
session_start();
$_SESSION['name'] = 'Jing';
var_mp($_SESSION);
session_write_close();
sleep(5);
session_start();
$_SESSION['name'] = 'Mr.Jing';
var_mp($_SESSION);
?>
官方給出的方案:
對於大量使用 Ajax 或者並發請求的網站而言,這可能是一個嚴重的問題。 解決這個問題最簡單的做法是如果修改了會話中的變數, 那麼應該盡快調用 session_write_close() 來保存會話數據並釋放文件鎖。 還有一種選擇就是使用支持並發操作的會話保存管理器來替代文件會話保存管理器。
我推薦的方式是使用 Redis 作為 Session 的處理器。
拓展閱讀:
為什麼不能用 memcached 存儲 Session
如何使用 Redis 作為 PHP Session handler
Session 數據是什麼時候被刪除的
這是一道經常被面試官問起的問題。
先看看官方手冊中的說明:
session.gc_maxlifetime 指定過了多少秒之後數據就會被視為"垃圾"並被清除。 垃圾搜集可能會在 session 啟動的時候開始( 取決於 session.gc_probability 和 session.gc_divisor)。 session.gc_probability 與 session.gc_divisor 合起來用來管理 gc(garbage collection 垃圾回收)進程啟動的概率。此概率用 gc_probability/gc_divisor 計算得來。例如 1/100 意味著在每個請求中有 1% 的概率啟動 gc 進程。session.gc_probability 默認為 1,session.gc_divisor 默認為 100。
繼續用我上面那個不太恰當的比方吧:如果我們把物品放在超市的儲物箱中而不取走,過了很久(比如一個月),那麼保安就要清理這些儲物箱中的物品了。當然並不是超過期限了保安就一定會來清理,也許他懶,又或者他壓根就沒有想起來這件事情。
再看看兩段手冊的引用:
如果使用默認的基於文件的會話處理器,則文件系統必須保持跟蹤訪問時間(atime)。Windows FAT 文件系統不行,因此如果必須使用 FAT 文件系統或者其他不能跟蹤 atime 的文件系統,那就不得不想別的辦法來處理會話數據的垃圾回收。自 PHP 4.2.3 起用 mtime(修改時間)來代替了 atime。因此對於不能跟蹤 atime 的文件系統也沒問題了。
GC 的運行時機並不是精準的,帶有一定的或然性,所以這個設置項並不能確保舊的會話數據被刪除。某些會話存儲處理模塊不使用此設置項。
對於這種刪除機制,我是存疑的。
比如 gc_probability/gc_divisor 設置得比較大,或者網站的請求量比較大,那麼 GC 進程啟動就會比較頻繁。
還有,GC 進程啟動後都需要遍歷 Session 文件列表,對比文件的修改時間和服務端的當前時間,判斷文件是否過期而決定是否刪除文件。
這也是我覺得不應該使用 PHP 自帶的 files 型 Session 處理器的原因。而 Redis 或 Memcached 天生就支持 key/value 過期機制的,用於作為會話處理器很合適。或者自己實現一個基於文件的處理器,當根據 session_id 獲取對應的單個 Session 文件時判斷文件是否過期。
為什麼重啟瀏覽器後 Session 數據就取不到了
session.cookie_lifetime 以秒數指定了發送到瀏覽器的 cookie 的生命周期。值為 0 表示"直到關閉瀏覽器"。默認為 0。
其實,並不是 Session 數據被刪除(也有可能是,概率比較小,參見上一節)。只是關閉瀏覽器時,保存 session_id 的 Cookie 沒有了。也就是你弄丟了打開超市儲物箱的鑰匙(session_id)。
同理,瀏覽器 Cookie 被手動清除或者其他軟體清除也會造成這個結果。
為什麼瀏覽器開著,我很久沒有操作就被登出了
這個是稱為「防呆」,為了保護用戶賬戶安全的。
這個小節放進來,是因為這個功能的實現可能和 Session 的刪除機制有關(之所以說是可能,是因為這個功能不一定要借住 Session 實現,用 Cookie 也同樣可以實現)。 說簡單一點,就是長時間沒有操作,服務端的 Session 文件過期被刪除了。
一個有意思的事情
在我試驗的過程中,發現了小有意思的事情:我把 GC 啟動的概率設置為 100%。如果只有一個訪問者請求,該訪問者即使過了很久(超過了過期時間)後才發起第二次請求,那麼 Session 數據也還是存在的('session.save_path' 目錄下面的 Session 文件存在)。是的,明明就超過了過期時間,卻沒有被 GC 刪除。這時,我用另外一個瀏覽器訪問時(相對於另一個訪問者),這次請求生成了新的 Session 文件,而上一個瀏覽器請求生成的那個 Session 文件終於沒有了(之前那個 Session 文件在 'session.save_path' 目錄下面的消失了)。
還有,發現 Session 文件被刪除後,再次請求,還是會生成和之前文件名相同的 Session 文件(因為瀏覽器並沒有關閉,再次請求發送的 session_id 是相同的,所以重新生成的 Session 文件的文件名還是一樣的)。但是,我不理解的是:這個重新出現的文件的創建時間竟然是第一次的那個創建時間,難道它是從回收站中回來的?(確實,我做這個試驗時是在 window 下進行的)
我猜測的原因是這樣:當啟動會話後,PHP 根據 session_id 找到並打開了對應的 Session 文件,然後才啟動 GC 進程。GC 進程就只檢查除了當前這個 Session 文件外的其他文件,發現過期的就幹掉。所有,即使當前這個 Session 文件已經過期了,GC 也沒有刪除它。
我認為這個不合理的。
由於發生這種情況影響也不大(畢竟線上請求很多,當前請求的過期文件被其他請求喚起的 GC 幹掉的可能性是比較大的) + 我沒有信心去看 PHP 源代碼 + 我並不在線上使用 PHP 自帶的 files 型 Session 處理器。所以,這個問題我就沒有深入研究了。請諒解。
<?php
// 過期時間設置為 30 秒
ini_set('session.gc_maxlifetime', '30');
// GC 啟動概率設置為 100%
ini_set('session.gc_probability', '100');
ini_set('session.gc_divisor', '100');
session_start();
$_SESSION['name'] = 'Jing';
var_mp($_SESSION);
?>
④ php的session 有什麼用
session是什麼,剛開始我也不明白,非專業詞典翻譯為會議,會議期。直到接觸asp後才知道session是干什麼的,有什麼用。
作個不太恰當的比喻吧(雖然不恰當,但意義卻是一樣的),session就好象你和你女友(或妻子)之間的感情似的,session是你和網站之間的感情。
session在WEB技術中佔有非常重要的份量。由於網頁是一種無狀態的連接程序,因此你無法得知用戶的瀏覽狀態。因此我們必須
通過session記錄用戶的有關信息,以供用戶再次以此身份對web伺服器提供要求時作確認,例如,我們在某些網站中常常要求用戶登錄,
但我們怎麼知道用戶已經登錄了呢,如果沒有session的話,登錄信息是無法保留的,那豈不要讓用戶在每一頁網頁中都要提供
用戶名和密碼。
當然,session不光用於用戶身份認證功能,還可能用於其它方面,以後我們會提到的。
session用中文來解釋就是會話期。一個會話期開始於用戶輸入一個站點的網址時,結束於他離開這個站點時。
session最早出現在動態腳本語言Active Server Pages中,它的功能之強大,是一句話無法說清楚的。
當php還在3.0版本時,session是它永遠的痛。雖然php具有執行速度快,使用靈活,功能強大等優點,但因為session的問題,使很多站點的開發放棄了php,至少我的老闆是這樣認為的。當時有很多php免費函數庫提供在php3上實現session的方案,但都讓人感覺不正宗。
就好象你花好幾千大洋買的手機卻配置一個很粗糙的草作的袋子一樣,雖然功能是一樣的,但總讓人覺得別扭。php4的出現讓php在session問題上
有了翻身的機會。雖然它的session實現還不是很理想(主要是效率問題),但畢竟是它自己實現的,而且可以實際使用了。
那我們用session干什麼呢,你說了半天,我用不上的話,你豈不有賣紙張之嫌。OK,我們來看看session有什麼用:作過網站的人都有這樣的體會,在一頁頁面中的變數(在本章都指伺服器端變數,下同)是不能在下一頁中用的,雖然有一些辦法可以實現,比如用form,urlstring等等
但有些對於用戶來說是不方便的,即使讓form自動提交,但其中的延時在現今的網路狀況下足以讓人窒息,而這兩種方法都明顯加大程序員的負擔。如果你正在開發一個大型項目,那這些額外的負擔是不能忽略的。而有了session就好辦了,session中注冊的變數可以作為全局變數使用。什麼,全局變數?
好極了。這樣一來,你知道有什麼用了吧:最主要的用於用戶身份認證,程序狀態記錄,頁面之間參數傳遞。
說了它這么半天的好處,你已經動心了吧,先別高興,它還有缺點呢:它是用文件保存的變數(當然效率不高了,雖然可以用別的方式,但
很麻煩的),不能保存對象。與之相對的是,asp中的session可以保存對象變數,用內存變數來保存session變數。但為什麼我們還選用php呢,呵呵,
為什麼,你能從本書的開始看到這章,想必你也應該明白了吧,你還不明白,Faint,你再從頭看起吧,我保證你成為PHP專家^_^。
session是怎樣實現的呢?呵呵,你一定以為很高深吧,我來告訴你它的秘密。如果說只保存變數的話,很多讀者都明白,這是很簡單的,
但前面我們說過,http協議是一種無狀態的連接,你怎麼知道那個變數是誰的,這個變數又是誰的呢?在session實現中用cookie實現的。cookie
存在於客戶端,也就是用戶的機器中,裡面保存著用戶的session ID,也就是session號碼,當用戶的瀏覽器請求伺服器時把session ID也一起送到
伺服器,這樣伺服器就可以識別你是誰,也就可以把變數識別開了。這樣我們就不難理解了,為什麼有時session會失效了。不信的話,你可以試試:
在IE的"工具"菜單上有"Internet選項"菜單,打開後再選"安全"->"自定義級別",將安全設置中的"允許使用每個對話cookies"設為禁用,再看看
session能不能用。這下明白了吧!不過php4在linux/unix平台上可以自動檢查cookies狀態,當cookies 不可用時,自動會把session ID
附帶在url上進行傳遞。這是它在session方面比asp多的唯一的優點了。
⑤ php session 的原理機制是什麼
首先說一下在php中如何操作session
session_start(); //使用該函數打開session功能
$_SESSION //使用預定義全局變數操作數據
$_SESSION['user'] = 'php'; //定義一個session
echo $_SESSION['user']; //輸出session
使用unset($_SESSION['user']) //銷毀一個session的值
簡單地操作,一切都是由伺服器實現;由於處理在後台,一切看起來也很安全。但是session採用什麼樣機制,又是怎樣被實現,並且如何來保持會話的狀態的呢?
下面我們了解一下session實現與工作原理
瀏覽器和伺服器採用http無狀態的通訊,為了保持客戶端的狀態,使用session來達到這個目的。然而服務端是怎麼樣標示不同的客戶端或用戶呢?
這里我們可以使用生活中的一個例子,假如你參加一個晚會,認識了很多人,你會採取什麼方式來區分不同的人呢!你可能根據臉型,也有可能根據用戶的名字,
或者人的身份證,即採用一個獨一無二的標示。在session機制中,也採用了這樣的一個唯一的session_id來標示不同的用戶,不同的是:瀏覽器每次請求都會帶上
由伺服器為它生成的session_id.
簡單介紹一下流程:當客戶端訪問伺服器時,伺服器根據需求設置session,將會話信息保存在伺服器上,同時將標示session的session_id傳遞給客戶端瀏覽器,
瀏覽器將這個session_id保存在內存中(還有其他的存儲方式,例如寫在url中),我們稱之為無過期時間的cookie。瀏覽器關閉後,這個cookie就清掉了,它不會存在用戶的cookie臨時文件。
以後瀏覽器每次請求都會額外加上這個參數值,再伺服器根據這個session_id,就能取得客戶端的數據狀態。
如果客戶端瀏覽器意外關閉,伺服器保存的session數據不是立即釋放,此時數據還會存在,只要我們知道那個session_id,就可以繼續通過請求獲得此session的信息;但是這個時候後台的session還存在,但是session的保存有一個過期時間,一旦超過規定時間沒有客戶端請求時,他就會清除這個session。
⑥ php中如何使用SESSION
1、在php中使用session,首先要啟動session會話,啟動session會話要使用php內置函數session_start(),如圖所示。
⑦ PHP中$_session是什麼意思怎麼用
1.session.save_handler = files
* 1. session_start()
1. session_start()是session機制的開始,它有一定概率開啟垃圾回收,因為session是存放在文件中,
PHP自身的垃圾回收是無效的,SESSION的回收是要刪文件的,這個概率是根據php.ini的配置決定的,
但是有的系統是 session.gc_probability = 0,這也就是說概率是0,而是通過cron腳本來實現垃圾回收。
session.gc_probability = 1
session.gc_divisor = 1000
session.gc_maxlifetime = 1440//過期時間 默認24分鍾
//概率是 session.gc_probability/session.gc_divisor 結果 1/1000,
//不建議設置過小,因為session的垃圾回收,是需要檢查每個文件是否過期的。
session.save_path = //好像不同的系統默認不一樣,有一種設置是 "N;/path"
//這是隨機分級存儲,這個樣的話,垃圾回收將不起作用,需要自己寫腳本
2. session會判斷當前是否有$_COOKIE[session_name()];session_name()返回保存session_id的COOKIE鍵值,
這個值可以從php.ini找到
session.name = PHPSESSID //默認值PHPSESSID
3. 如果不存在會生成一個session_id,然後把生成的session_id作為COOKIE的值傳遞到客戶端.
相當於執行了下面COOKIE 操作,注意的是,這一步執行了setcookie()操作,COOKIE是在header頭中發送的,
這之前是不能有輸出的,PHP有另外一個函數 session_regenerate_id() 如果使用這個函數,這之前也是不能有輸出的。
setcookie(session_name(),
session_id(),
session.cookie_lifetime,//默認0
session.cookie_path,//默認'/'當前程序跟目錄下都有效
session.cookie_domain,//默認為空
)
4. 如果存在那麼session_id = $_COOKIE[session_name];
然後去session.save_path指定的文件夾里去找名字為'SESS_' . session_id()的文件.
讀取文件的內容反序列化,然後放到$_SESSION中
* 2. 為$_SESSION賦值
比如新添加一個值$_SESSION['test'] = 'blah'; 那麼這個$_SESSION只會維護在內存中,當腳本執行結束的時候,
用把$_SESSION的值寫入到session_id指定的文件夾中,然後關閉相關資源. 這個階段有可能執行更改session_id的操作,
比如銷毀一個舊的的session_id,生成一個全新的session_id.一半用在自定義 session操作,角色的轉換上,
比如Drupal.Drupal的匿名用戶有一個SESSION的,當它登錄後需要換用新的session_id
if (isset($_COOKIE[session_name()])) {
setcookie(session_name(), '', time() - 42000, '/');//舊session cookie過期
}
session_regenerate_id();//這一步會生成新的session_id
//session_id()返回的是新的值
3.寫入SESSION操作
在腳本結束的時候會執行SESSION寫入操作,把$_SESSION中值寫入到session_id命名的文件中,可能已經存在,
可能需要創建新的文件。
* 4. 銷毀SESSION
SESSION發出去的COOKIE一般屬於即時COOKIE,保存在內存中,當瀏覽器關閉後,才會過期,假如需要人為強制過期,
比如 退出登錄,而不是關閉瀏覽器,那麼就需要在代碼里銷毀SESSION,方法有很多,
o 1. setcookie(session_name(), session_id(), time() - 8000000, ..);//退出登錄前執行
o 2. usset($_SESSION);//這會刪除所有的$_SESSION數據,刷新後,有COOKIE傳過來,但是沒有數據。
o 3. session_destroy();//這個作用更徹底,刪除$_SESSION 刪除session文件,和session_id
當不關閉瀏覽器的情況下,再次刷新,2和3都會有COOKIE傳過來,但是找不到數據
2.session.save_handler = user
用戶自定義session處理機制,更加直觀
* session_set_save_handler('open', 'close', 'read', 'write', 'destroy', 'gc');
1.session_start(),
執行open($save_path, $session_name)打開session操作句柄
$save_path 在session.save_handler = files的情況下它就是session.save_path,
但是如果用戶自定的話,這個兩個參數都用不上,直接返回TRUE
執行read($id)從中讀取數據.//這個參數是自動傳遞的就是session_id(),可以通過這個值進行操作。
* 2.腳本執行結束
執行write($id, $sess_data) //兩個參數,很簡單
* 3.假如用戶需要session_destroy()
先執行destroy.在執行第2步
一個實際例子:
//SESSION初始化的時候調用
function open($save_path, $session_name)
{
global $sess_save_path;
$sess_save_path = $save_path;
return(true);
}
//關閉的時候調用
function close()
{
return(true);
}
function read($id)
{
global $sess_save_path;
$sess_file = "$sess_save_path/sess_$id";
return (string) @file_get_contents($sess_file);
}
//腳本執行結束之前,執行寫入操作
function write($id, $sess_data)
{
echo "sdfsf";
global $sess_save_path;
$sess_file = "$sess_save_path/sess_$id";
if ($fp = @fopen($sess_file, "w")) {
$return = fwrite($fp, $sess_data);
fclose($fp);
return $return;
} else {
return(false);
}
}
function destroy($id)
{
global $sess_save_path;
$sess_file = "$sess_save_path/sess_$id";
return(@unlink($sess_file));
}
function gc($maxlifetime)
{
global $sess_save_path;
foreach (glob("$sess_save_path/sess_*") as $filename) {
if (filemtime($filename) + $maxlifetime < time()) {
@unlink($filename);
}
}
return true;
}
⑧ php中session_destroy()的作用
Session_destroy()銷毀當前會話中的所有數據,但不重置與當前會話關聯的全局變數,也不重置會話cookie。如果需要再次使用會話變數,則必須再次調用session_start()函數。
為了完全銷毀會話,例如當用戶注銷時,必須同時重置會話ID。如果會話ID是由cookie傳遞的,那麼還會調用setcookie()函數來刪除客戶機的會話cookie。
使用方法:
1.要在PHP中使用會話,首先需要啟動會話。要啟動會話,您需要使用PHP的內置函數session_start(),如圖所示。
⑨ php中session的用法
在使用上是為了能夠在伺服器端保存一個能夠跨頁面使用的變數
//直接在index頁面使用,並給出變數名
$_SESSION['username']='張三';//將張三保存到名為username的session中
//在你的userInfo直接輸出
echo$_SESSION['username'];//輸出名為username的session
在沒有使用框架的時候請在頁首加上session_start()