Cookies czyli ciasteczka były początkowo znane pod nazwą "Magic cookies".
Do czego w ogóle służą ciasteczka? Właściwie jak by nie patrzeć to ciasteczka służą do tego by je zjeść =). Nie - nie chodzi o takie ciasteczka.
W terminologii komputerowej ciasteczka służą do przechowywania przez przeglądarkę pewnych małych kawałków informacji. Takie dane mogą być wykorzystane do różnych celów (np. do zaliczania odwiedzin, przekazywania informacji między stronami itp.). Niestety muszę was zasmucić - raczej nie nadają się do spałaszowania :(.
Po utworzeniu pojedynczego Cookie tylko server który je utworzył może odczytywać zeń dane, zapewniając w ten sposób prywatność użytkownika. Cookie to nic innego jak tylko zwykły plik tekstowy przechowywany na dysku osoby odwiedzającej stronę. Tak więc poprzez cookie - wbrew krążącym legendom - nie można sprawdzić zawartości dysku czy przesłać jakiegoś fikuśnego programu (czy to trojana czy to wirusa).
Każde ciasteczko ma postać:
CookieNazwa=cookieWartosc; expires=datawygasniecia; domain=domenaStrony; path=sciezkaURL; secure
Jak widać na przykładzie powyżej pierwszą część składni ciasteczka zajmuje nazwa ciasteczka oraz jego wartość. Są to jedyne wymagane parametry ciasteczka. Jeśli przeglądarka nie znajdzie cookie o danej nazwie w aktualnej domenie/ścieżce, utworzy nowe (choć nie znaczy to, że zapisze do pliku). Jeśli ciasteczko o podanej nazwie już istnieje, jego stara wartość zostanie zastąpiona przez nową.
Wartość ciasteczka musi być podawana jako ciąg bez spacji. Jeżeli chcielibyśmy użyć spacji w wartości ciasteczka wówczas taką wartość musielibyśmy przekształcić za pomocą funkcji escape(), która przekonwertuje spacje na zapis %20. Przy odczycie takiej wartości musimy odwrócić naszą zamianę, korzystając przy tym z funkcji unescape() (zastosujemy to przy przykładowej funkcji służącej do odczytu wartości cookie).
Przykładowe zastosowanie funkcji escape i unescape:
var NazwaCookie = "Przedmiot doskonały nie wiadomo jakiego pochodzenia"; Document.write(escape(NazwaCookie)); //wypisze się Przedmiot%20doskonały%20nie%20wiadomo... Document.write(unescape(NazwaCookie)); //wypisze się Przedmiot doskonały nie wiadomo...
Parametr EXPIRES określa datę wygaśnięcia. W ciasteczkowym pliku data wygaśnięcia jest przechowywana w sekundach, jednakże my w celu jej ustalenia musimy ją podawać w formacie GTM. Po upływie daty wygaśnięcia ciasteczko zostaje usunięte z systemu. Jeżeli nie podamy tego parametru, wówczas ciasteczko zostanie utworzone do czasu trwania sesji czyli do póty, do póki będzie włączona przeglądarka. Gdy przeglądarka zostanie zamknięta wówczas ciasteczka bez parametru expires zostaną usunięte. Gdy podasz datę wygaśnięcia ciasteczka na wcześniejszą od aktualnej - wówczas takie ciasteczko zostanie usunięte.
Parametr DOMAIN określa domenę ciasteczka. Jeżeli nie ustawisz tego parametru, wówczas przeglądarka ustawi go jako nazwę servera skąd zostało utworzone ciasteczko. Jeżeli będziesz chciał wyświetlić wszystkie ciasteczka z dokumentu cookie wówczas zostaną ci wyświetlone tylko te ciasteczka, które mają parametr domain taki jak dokument z którego wysyłasz żądanie wyświetlenia ciasteczek. Adresy domeny możesz podawać na różne sposoby - jest tylko jedno zastrzeżenie - adres taki musi zawierać przynajmniej 2 kropki np.
.pckurier.pl
.digimer.pl
Możesz też podać cały URL (<http://taka.sobie.domena/ścieżka>).
Ostatnim parametrem ciasteczka jest parametr PATH który ustawia ścieżkę skąd zostało utworzone ciasteczko. Najlepszym rozwiązaniem jest tutaj pozostawienie domyślnej wartości czyli "/".
Kolejny parametr ciasteczka to SECURE. Jeśli pominiesz ten parametr, przeglądarka automatycznie przyjmuje, że cookie dostępne jest dla każdej domeny lub programu CGI, jeśli tylko zgadzają się odpowiednie własności. Powinno się raczej pomijać ten parametr.
Aby utworzyć ciasteczko korzystamy z poniższej konstrukcji:
document.cookie = nazwa_cokie + "=" + wartosc_cookie + "; expires=" + data_Wygasniecia
Możemy utworzyć funkcję służącą do tworzenia ciasteczek. Przykładowo może mieć ona następującą postać:
function ustawCookie(nazwa, wartosc, expire) {
document.cookie = nazwa + "=" + escape(wartosc) + ((expire==null)?"" : ("; expires=" + expire.toGMTString()))
}
Funkcję wywołujemy z parametrem nazwa, wartość oraz expire. Następnie ustawiamy ciasteczko (document.cookie) o nazwie nazwa, escapowanej wartości oraz o czasie wygaśnięcia podanym w parametrze expires. Sprawdzamy czy parametr expires nie jest pusty. Jeżeli sprawdzenie wykaże że parametr ten jest pusty (null) wówczas pomijamy wstawianie do ciasteczka parametru expires (czyli wstawiamy pusty ciąg znaków).
Aby powyższa funkcja działała, powinniśmy przekazywać parametr expire w postaci daty:
var waznosc = new Date()
waznosc.setMonth(waznosc.getMonth()+6) //ustawiamy czas na 6 miesięcy do przodu
ustawCookie('mail_autora', wartosc_z_pola_mail, waznosc) //dzieki temu nasze ciasteczko będzie zapamiętane przez 6 miesięcy
Odczytane ciasteczko to jeden długi ciąg znaków którym zawarta jest para nazwa=wartość. Pomimo, iż możemy ustawić pozostałe parametry ciasteczka, to nie możemy ich odczytać. Kolejne cookie są oddzielone od siebie znakami "; ". Zauważ, że po średniku jest spacja. Przykładowo documen.cookie (zawierający nasze ciasteczka) może mięć wartość:
nazwacookie1=wartosccookie1; nazwacookie2=wartosccookie2; nazwacookie3=wartosccookie3;
Kolejne cookie są oddzielone od siebie za pomocą znaków "; ". Aby wydzielić poszczególne cookie do zmiennej tablicowej toCookie korzystamy z funkcji split.
toCookie = document.cookie.split("; ")
Jeżeli przykładowo wydrukujemy teraz toCookie[1] to wyświetli nam się 2 ciasteczko w systemie (jeżeli takowe jest) czyli np. nazwacookie2=wartoscookie2. Korzystamy ponownie z metody split aby wydzielić nazwę i wartość ciasteczka. I tak Split("=")[0] to nazwa ciasteczka, a Split("=")[1] to wartość ciasteczka.
document.write(toCookie[0]) //wypisze nazwacookie1=wartosccookie1
//jest równoznaczne z
document.write( toCookie[0].split("=")[0] + "=" + toCookie[0].split("=")[1] )
Możemy oczywiście odczytywać wartości poszczególnych ciasteczek jak to jest pokazane wyżej - czyli za pomocą indeksów (toCookie[0], toCookie[1]). Jednakże nie jest to najlepsza metoda. Przypuśćmy, że ustawiamy ciasteczko o nazwie "Przedmiot" i wartości "Skakanka". Gdybyśmy chcieli odczytać wartość tego ciasteczka posługując się indeksami, doszlibyśmy do wniosku, że nie wiemy którym z kolei ciastkiem jest ciastko o nazwie "Przedmiot".
Napiszmy funkcję, która wymagać będzie w parametrze nazwę ciastka, a zwracać będzie jego wartość (jeżeli takowe ciastko istnieje):
function pokazCookie(nazwa) { //1
if (document.cookie!="") { //2
var toCookie=document.cookie.split("; "); //3
for (i=0; i<toCookie.length; i++) { //4
var nazwaCookie=toCookie[i].split("=")[0]; //5
var wartoscCookie=toCookie[i].split("=")[1]; //6
if (nazwaCookie==nazwa) return unescape(wartoscCookie) //7
}
}
}
Tworzymy funkcje z parametrem nazwa (1). Jeżeli istnieją cookie działamy dalej (2)... Tworzymy tablice toCookie, rozdzielając document.cookie na kawałki (toCookie[1], toCookie[2]) za pomoca meotdy split("; "). Każdy element ma postać NazwaCookie=WartoscCookie (3). Wykonujemy pętle dla elementów tablicy toCookie (4). W każdym obiegu pętli rozdzielamy kolejny element tablicy toCookie i pod zmienna nazwaCookie przypisujemy pierwsza cześć rozdzielonego elementu (czyli NazwaCookie) (5). To samo robimy dla wartoscCookie - przypisujemy druga cześć podzielonego elementu czyli wartość cookie (6). Jeżeli nazwaCookie jest taka sama jak podana w parametrze przy wywołaniu funkcji to zwracamy unescapowaną wartość ciasteczka (//7).
Aby odczytać przy pomocy wyżej przedstawionej funkcji wartość cookie wywołujemy ja z nazwa cookie np. pokazCookie("Przedmiot"). Funkcja zwróci wówczas wartość ciasteczka "Przedmiot" czyli dla naszego przykładu wartość Skakanka.
Aby usunąć dane ciasteczko musimy ustawić jego parametr expires na wcześniejszy od aktualnej daty. Możemy to zrobić korzystając np. z poniższej funkcji służącej do usuwania ciastek.
function usunCookie(nazwa) {
var dzis = new Date()
if (document.cookie!="") {
var toCookie=document.cookie.split("; ");
for (i=0; i<toCookie.length; i++) {
var nazwaCookie=toCookie[i].split("=")[0];
var wartoscCookie=toCookie[i].split("=")[1];
if (nazwaCookie==nazwa) document.cookie=nazwaCookie+"=;expires="+dzis.getMonth()-1
}
}
}
Jak widać powyższa funkcja przypomina swoim wyglądem nieco funkcję pokazCookie(). Jej działanie jest podobne. Różnica polega na tym, że tamta funkcja zwracała wartość ciasteczka którego nazwa została podana w parametrze, ta natomiast ustawia parametr expires takiego ciasteczka na jeden miesiąc przed aktualną datą (co powoduje usunięcie danego ciasteczka). Zauważ, że tworzone na nowo ciasteczko nie zawiera wartości a tylko nazwę i czas ważności:
document.cookie=nazwaCookie+"=;expires="+dzis.getMonth()-1
Wartość ciasteczka nie jest nam potrzebna gdyż i tak za moment ów ciastko zostanie skasowane.
Możemy oczywiście chcieć usunąć wszystkie ciasteczka naraz. Jako że potrafimy już wydzielić kolejne ciasteczka do tablicy za pomocą metody split(), to usunięcie ich wszystkich nie jest zadaniem trudnym.
function usunAllCookie() {
if (document.cookie!="") {
var toCookie=document.cookie.split("; ");
var dataWygasniecia=new Date;
dataWygasniecia.setDate(dataWygasniecia.getDate()-1)
for (i=0; i<toCookie.length; i++) {
var nazwaCookie=toCookie[i].split("=")[0];
var document.cookie=nazwaCookie + ";expires=" + dataWygasniecia.toGMTString()
}
}
}
W powyższej funkcji wykonujemy pętlę po wszystkich elementach tablicy toCookie. Pobieramy nazwę ciasteczka, po czym tworzymy nowe ciasteczko o takiej samej nazwie (czyli ciasteczko zostaje nadpisane) i ważności równej zmiennej dataWygasniecia (czyli o dacie mniejszej o 1 rok od bieżącej - ciasteczko zostaje więc skasowane). W ten sposób kasujemy wszystkie ciastka (czyli hmm... zjadamy je)
Załóżmy, że na chcemy odczytać od użytkownika jakieś dane - np. jego imię i nazwisko żeby móc potem z nich korzystać na innych stronach. Tworzymy więc odpowiedni formularz:
<form name="formularz"> <fieldset> Podaj imie: <input name="imie" type="text" maxlength="20" length="20"><br> Podaj nazwisko: <input name="nazwisko" type="text" maxlength="20" length="20"><br> <input type="button" id="zapisz" value="Zapisz"> </fieldset> </form>
Następnie tworzymy odpowiedni skrypt, który utworzy nam nasze ciasteczka (1 dla imienia i 2 dla nazwiska):
<script type="text/javascript">
function upieczCiacho() {
var imie = document.formularz.imie.value;
var nazwisko = document.formularz.nazwisko.value;
//ponizej sprawdzamy czy uzytkownik wpisal dane
if ((imie!="") && (nazwisko!="")) {
document.cookie="imie=" + escape(imie);
document.cookie="nazwisko=" + escape(nazwisko);
} else {
alert("Wypelnij wszystkie pola")
}
}
document.getElementById('zapisz').onClick = upieczCiacho;
</script>
W skrypcie sprawdzamy czy użytkownik wpisał imię i nazwisko (wypełnił wszystkie pola), a następnie jeżeli sprawdzenie to powiodło się tworzymy odpowiednie ciasteczka o nazwie "imie" i "nazwisko" i wartościach pobranych z pól "imie" i "nazwisko" naszego formularza (przy okazji traktując je funkcją escape) . Niby nie ma imienia ze spacjami, ale nie wiadomo co użytkownik sobie wymyśli tam wpisać ;] (można też po prostu wcześniej zweryfikować takie pole).
Mamy więc utworzone dwa ciasteczka - jedno o nazwie imie i wartości pochodzącej z pola imie, o raz drugie o nazwie nazwisko i wartości pochodzącej z pola o nazwie nazwisko.
Teraz tworzymy nową stronę na której pobierzemy dane z ciasteczek. Korzystamy przy tym z wcześniej napisanej funkcji służącej do pobierania wartości z ciastek.
<html>
<head><title>pobieramy dane z ciastek</title></head>
<script type="text/javascript">
function pokazCookie(nazwa) {
if (document.cookie!="") {
var toCookie=document.cookie.split("; ");
for (i=0; i<toCookie.length; i++) {
var nazwaCookie=toCookie[i].split("=")[0];
var wartoscCookie=toCookie[i].split("=")[1];
if (nazwaCookie==nazwa) return unescape(wartoscCookie)
}
}
}
</script>
<body>
Witaj użytkowniku o imieniu:
<script type="text/javascript">
document.write(pokazCookie("imie"));
</script>
I nazwisku:
<script type="text/javascript">
document.write(pokazCookie("nazwisko"));
</script>
</body>
</html>
Oczywiście powinniśmy odpowiednio zmodyfikować naszą stronę, tak aby sprawdzała czy istnieją nasze ciasteczka i w razie czego wypisywała stosowny komunikat (typu "Witaj użytkowniku kimkolwiek jesteś ;)..."), lecz tutaj tego nie robimy, żeby nie zagmatwać kodu.
Na sam koniec warto wspomnieć o kilu sprawach. Stosowanie ciasteczek może być bardzo użyteczne przy tworzeniu liczników odwiedzin (ale tylko dla jednej osoby - dla wielu osób stosuje się skrypty po stronie servera).
Za pomocą ciasteczek możemy na przykład pobrać od użytkownika jego imię, a podczas następnych wizyt za pomocą wartości ciasteczka ustawionego na pewien czas (za pomocą expires) od razu je wypisywać na naszej stronie. Ciasteczka możemy stosować do przechowywania unikalnych kodów które będą przydzielane podczas logowania a następnie będą sprawdzane na kolejnych stronach naszej witryny (czyli tak zwane numery sesji w PHP).
Zastosowanie ciasteczek ma ogromne możliwości. Jednakże jest jeszcze małe "ale" (nie mylić z piwem). Przeglądarka użytkownika może mieć wyłączoną obsługę ciasteczek, lub też po prostu ich nie obsługiwać. Dlatego też musimy ostrożnie postępować z zastosowaniem ciasteczek i uważać by za bardzo nie uzależniać od nich naszych witryn.
Poniżej wypisuje wszystkie cookie (jeżeli w ogóle są):
if (document.cookie!="") { //jeżeli istnieją w ogóle cookie
toCookie = document.cookie.split("; "); //tworzymy talblice toCookie z ciasteczkami
document.write("Ilosc cookie: <strong>" +toCookie.length+ "</strong><BR>"); //wypisujemy ilosc cookie (czyli wielkosc toCookie)
for (i=0; i<toCookie.length; i++) { //rozpoczyanmy petle po toCookie
document.write("Nazwa cookie " +i+ ": <strong>" +toCookie[i].split("=")[0]+ "</strong><BR>"); //wypisujemy nazwe aktualnego cookie...
document.write("Wartość cookie " +i+ ": <strong>" +toCookie[i].split("=")[1]+ "</strong><BR>"); //i jego wartosc
}
} else {
document.write('Nie ma żadnych cookie');
}