如今越學下去,便越以爲基礎非常重要,對於底層的東西更是須要弄懂。
php
SESSION和COOKIE web
這兩個東西通常是用來標識客戶端身份的固然也可用來存儲全局變量。redis
先說說session,照個人理解,它是從服務器端產生的內存標記。就是腳本啓動session後,經過瀏覽器發出請求,此時,服務器端便會自動生成一個獨有的session id,便經過響應,以Set-Cookie:PHPSESSID=********,的形式傳回到瀏覽器,其後,每一次瀏覽器的請求中,都會在請求頭中以 Cookie: PHPSESSID=*******,格式發送到服務器,而後服務端會根據客戶端傳送的PHPSESSID與自身存在的PHPSESSID進行匹配,從而獲取與該ID相對應的信息。這就是一個會話機制的工做流程。數據庫
session有多種存儲方式,能夠存放在內存、數據庫、或是文件中,固然,存放到數據庫和文件實際上都是存放到硬盤裏,可是,獲取硬盤信息是經過I/O,O操做的效率是遠遠低於操做內存的數據,因此這個能夠次級考慮。而內存的讀取速度是遠高於硬盤的,因此能夠優先考慮,其實現方式能夠經過,redis或memcached來解決。編程
而cookie,以前個人不求甚解,對其想法就僅僅停留在cookie是保存在瀏覽器的這麼一個說法。如今看來,cookie和session是一個依賴的關係,這個能夠從上面的會話機制的工做流程能夠看出來。因爲cookie是由瀏覽器來進行管理的(並非由編程語言直接操做,而是經過瀏覽器),因此一旦瀏覽器禁用cookie,那麼session就不能正常工做了。在此,有兩個解決方案:
瀏覽器
一、URL重寫,便是把PHPSESSID經過url傳輸到服務端,這個有安全隱患問題,應加密處理髮送。
安全
二、經過表單隱藏發送,這個天然也是有必定的操做難度,不怎麼建議使用。
服務器
不管是session和cookie,都是因爲http無狀態的產物,下面摘自於網咯的一些說法;
cookie
網絡
HTTP的無狀態是由其歷史使命而決定的。但隨着網絡技術的蓬勃發展,人們不再知足於死板乏味的靜態HTML,他們但願web應用能動起來,因而客戶端出現了腳本和DOM技術,HTML裏增長了表單,而服務端出現了CGI等等動態技術。而正是這種web動態化的需求,給HTTP協議提出了一個難題:一個無狀態的協議怎樣才能關聯兩次連續的請求呢?也就是說無狀態的協議怎樣才能知足有狀態的需求呢?
此時有狀態是必然趨勢而協議的無狀態性也是木已成舟,所以咱們須要一些方案來解決這個矛盾,來保持HTTP鏈接狀態,因而出現了cookie和session。
對於此部份內容,讀者或許會有一些疑問,筆者在此先談兩點:
1. 無狀態性和長鏈接
可能有人會問,如今被普遍使用的HTTP1.1默認使用長鏈接,它仍是無狀態的嗎?
鏈接方式和有無狀態是徹底沒有關係的兩回事。由於狀態從某種意義上來說就是數據,而鏈接方式只是決定了數據的傳輸方式,而不能決定數據。長鏈接是隨着計算機性能的提升和網絡環境的改善所採起的一種合理的性能上的優化,通常狀況下,web服務器會對長鏈接的數量進行限制,以避免資源的過分消耗。
2. 無狀態性和session
Session是有狀態的,而HTTP協議是無狀態的,兩者是否矛盾呢?
Session和HTTP協議屬於不一樣層面的事物,後者屬於ISO七層模型的最高層應用層,前者不屬於後者,前者是具體的動態頁面技術來實現的,但同時它又是基於後者的。在下文中筆者會分析Servlet/Jsp技術中的session機制,這會使你對此有更深入的理解;
上 面提到解決HTTP協議自身無狀態的方式有cookie和session。兩者都能記錄狀態,前者是將狀態數據保存在客戶端,後者則保存在服務端。
SESSION在php.ini配置的一些說明:(來自網絡)
[服務端]
session.save_handler = files
默認爲file,定義session在服務端的保存方式,file意爲把sesion保存到一個臨時文件裏,若是咱們想自定義別的方式保存(好比用數據庫),則須要把該項設置爲user;
session.save_path = "D:/APMServ5.2.0/PHP/sessiondata/"
定義服務端存儲session的臨時文件的位置。
session.auto_start = 0
如置1,則不用在每一個文件裏寫session_start(); session自動start :)
session.gc_probability = 1
session.gc_divisor = 100
session.gc_maxlifetime = 1440
這三個配置組合構建服務端session的垃圾回收機制
session.gc_probability與session.gc_divisor構成執行session清理的機率,理論上的解釋爲服務端按期有必定的機率調用gc函數來對session進行清理,清理的機率爲:gc_probability/gc_divisor 好比:1/100 表示每個新會話初始化時,有1%的機率會啓動垃圾回收程序,清理的標準爲session.gc_maxlifetime定義的時間。
[客戶端]
session.use_cookies = 1
sessionid在客戶端採用的存儲方式,置1表明使用cookie記錄客戶端的sessionid,同時,$_COOKIE變量裏纔會有$_COOKIE[‘PHPSESSIONID’]這個元素存在;
session.use_only_cookies = 1
也是定義sessionid在客戶端採用的存儲方式,置1表明僅僅使用 cookie 來存放會話 ID。通常來講,如今客戶端都會支持cookie,因此建議設置成1,這樣能夠防止有關經過 URL 傳遞會話 ID 的攻擊。
session.use_trans_sid = 0
相對應於上面那個設置,這裏若是置1,則表明容許sessionid經過url參數傳遞,同理,建議設置成0;
session.referer_check =
這個設置在session.use_trans_sid = 1的時候纔會生效,目的是檢查HTTP頭中的"Referer"以判斷包含於URL中的會話id是否有效,HTTP_REFERER必須包含這個參數指定的字符串,不然URL中的會話id將被視爲無效。因此通常默認爲空,即不檢查。
session.name = PHPSESSID
定義sessionid的名稱,即變量名,因此經過瀏覽器http工具看到的http頭文件裏的PHPSESSID=##############;
session.hash_function = 0
選擇session_name的加密方式,0表明md5加密,1表明sha1加密,默認是0,可是聽說用sha1方式加密,安全性更高;
session.hash_bits_per_character = 4
指定在session_name字符串中的每一個字符內保存多少位二進制數,這些二進制數是hash函數的運算結果。
4 bits: 0-9, a-f
5 bits: 0-9, a-v
6 bits: 0-9, a-z, A-Z, "-", ","
url_rewriter.tags = "a=href,area=href,frame=src,input=src,form=,fieldset="
指定重寫哪些HTML標籤來包含sid(session_id)(僅在"session.use_trans_sid"打開的狀況下有效),URL重寫器將添加一個隱藏的"<input>",它包含了本應當額外追加到URL上的信息。
session.cookie_lifetime = 0
保存sessionid的cookie文件的生命週期,如置0,表明會話結束,則sessionid就自動消失,常見的強行關閉瀏覽器,就會丟失上一次的sessionid;
session.cookie_path = /
保存sessionid的cookie文件在客戶端的位置;
session.cookie_domain = /
保存sessionid的cookie的域名設置,這跟cookie容許的域名的訪問權限設置有關,通常來講想讓本身網站全部的目錄都能訪問到客戶端的cookie,就應該設置成「/」如須要詳細瞭解,能夠看下setcookie()函數的domain參數相關設置和使用方法;
session.bug_compat_42 = 1
session.bug_compat_warn = 1
這兩個能夠說幾乎是快要被廢棄的設置,是爲了老版本的php服務的,主要是針對 session_register函數,由於php5的register_global默認是關閉狀態,因此在php5里根本用不到 session_register這個函數;而且php6就要廢除這個設置,直接定義爲關閉,因此不必研究這兩個了;