6.7 クッキーとローカルストレージ

(1/1)
クッキーのイラスト
6.5 ファイル・アクセス、同期・非同期、JSON - ファイル・アクセスとセキュリティ」において、JavaScriptではクライアントPCのストレージ(ローカル・ドライブ)にあるファイル・アクセス制限が厳しいと書いた。一方で、作業用のデータを一時的にストレージする方法として、クッキー(Cookie)とローカルストレージ(LocalStrage)が用意されている。
今回は、クッキーローカルストレージの利用方法を説明する。

目次

サンプル・プログラム

圧縮ファイルの内容
cookie.htmlクッキーを使う
localStorage.htmlローカルストレージを使う
cookie.html 更新履歴
バージョン 更新日 内容
1.1.0 2023/08/16 コメント追加
1.0 2021/09/18
localStorage.html 更新履歴
バージョン 更新日 内容
1.1.0 2023/08/16 ファイル名変更,コメント追加
1.0 2021/09/18 初版

クッキーとは

クッキー(Cookie)はJavaScript専用の仕組みではなく、サーバと簡単なデータの受け渡しを行うためにHTTP通信に規定されたプロトコルだ。
たとえば、次のような使い方が考えられる。
  1. クライアントAがサーバαにアクセスする。このときクッキーは空。
  2. サーバαはアクセス日時をクッキーのキーlastaccessに代入してクライアントAに返す。
  3. クライアントAはlastaccessを受け取り保管する。サーバ側で保管期日を設定したり、ブラウザ終了後に廃棄するという設定もできる。
JavaScriptスクリプト内でクッキーの参照や保管ができる。

ただし、セキュリティ保持の観点から、サーバαとやり取りしているクッキーの内容と、別のサーバβとのやり取りで参照したり保管することはできない。サーバαとサーバβの識別はドメイン名で行っている。
また、サーバ通信(HTTP通信)ではクッキーの内容が平文でやり取りされる。データを秘匿したいのであれば、暗号化通信(HTTPS通信)を利用しなければならない。
クッキーを使う

クッキーの値を取得する

  38: /**
  39:  * クッキーの値を取得する
  40:  * @param   String key クッキー名
  41:  * @return  String 値/null:値がない
  42: */
  43: function getCookie(key) {
  44:     let val = null;
  45:     let cookies = document.cookie.split(';');   //全てのクッキー
  46:     console.log(cookies);
  47: 
  48:     //keyに合致する値を取り出す
  49:     for (let i = 0i < cookies.lengthi++) {
  50:         let arr = cookies[i].split('=');
  51:         if (arr[0].trim() === key) {
  52:             val = arr[1];
  53:             break;
  54:         }
  55:     }
  56: 
  57:     return val;
  58: }

JavaScriptには プロパティが用意されており、下記のように、そのサーバ(ドメイン)との通信で交わされる全てのクッキーが格納されている。
a=123; b=456; c=789
ユーザー関数 getCookie では、split メソッドと配列を使い、1つ1つのキーに分離する。
指定したキーが無い場合は null を返す。

クッキーに値を設定する

  60: /**
  61:  * クッキーに値を設定する
  62:  * @param   String key クッキー名
  63:  * @param   String val 値
  64:  * @return  なし
  65: */
  66: function setCookie(key, val) {
  67:     document.cookie = key + '=' + val + ';';
  68: }

クッキーに値を設定するには、cookie プロパティに代入すればよい。他のクッキーには影響を与えない。

与えられた日時と現在日時の差を求める

  70: /**
  71:  * 与えられた日時と現在日時の差を求める
  72:  * @param   String dt 日時(文字列)
  73:  * @param   Number 差(秒)/NaN:dtが不正
  74:  * @return  なし
  75: */
  76: function diffDateTime(dt) {
  77:     let dt0 = new Date();
  78:     let dt1 = new Date(dt);
  79:     if (isNaN(dt1))     return NaN;
  80:     let diff = Math.round((dt0.getTime() - dt1.getTime()) / 1000);
  81: 
  82:     return diff;
  83: }

与えられた日時と現在日時の差(秒)を求めるユーザー関数 diffDateTime を用意した。

クッキーを使う

  95:     //クッキー対応可否チェック
  96:     if (typeof document.cookie === 'undefined') {
  97:         document.getElementById('error').innerHTML = 'エラー:クッキーが利用できません.';
  98:         return;
  99:     }
 100:     //クッキーから値を取得
 101:     let val = getCookie(COOKIE_KEY);
 102:     //値がない
 103:     if (val == null) {
 104:         document.getElementById('val').innerHTML = '未登録';
 105:     //値がある
 106:     } else {
 107:         document.getElementById('val').innerHTML = COOKIE_KEY + '=' + val;
 108:         let diff = diffDateTime(val);
 109:         if (! isNaN(diff)) {
 110:             document.getElementById('diff').innerHTML = diff;
 111:         }
 112:     }
 113: 
 114:     //現在日時をクッキーに保存
 115:     let dt = new Date();
 116:     setCookie(COOKIE_KEY, dt.toISOString());
 117: }

メインプログラムでは、まず cookieプロパティ を使ってクッキーに対応しているかどうかチェックする。
対応していれば、クッキーから値を取得し、それを表示する。
最後に、現在日時をクッキーに保存する。

ローカルストレージとは

ローカルストレージもJavaScript専用の仕組みではなく、HTML5 で規格化されたWeb Storage の一種である。
Web Storage には、localStoragesessionStorage の2種類があり、それぞれの特徴を下表に示す。
名称 特 徴
sessionStorage 一時的にデータを保存する。
ウィンドウを閉じるタイミングで消える。
同じページを複数のウィンドウで開いた場合、別々に保存される。
localStorage 明示的に消去しない限り、データをローカル環境に保持し続ける。
Web Storage生成元(オリジン)ごとに分離して保存される。生成元とは、プロトコル、ドメイン、ポート番号の3つ組みである。
つまり、プロトコル、ドメイン、ポート番号のいずれかが異なれば、キー情報が同じでも異なるデータ格納領域となる。"https://www.pahoo.org/e-soul/webtech/js01/program/birthgame.html" と "https://www.pahoo.org/index.html" は同じオリジンである。
また、オリジンが異なるデータ領域へのアクセスをさせないことで、セキュリティを保っている。

クッキー はHTTP通信の時に必ずやり取りされるデータであったのに対し、Web Storage は通信しない、つまり、純粋にクライアントPCに保存するための仕組みである。
なお、キャッシュ は余計な通信を減らすための手段で、データを保存を目的とするものではない。明示的にキャッシュにアクセスするための手段も用意されていない。
ローカルストレージを使う

ローカルストレージを使う

  63:     //ローカルストレージ対応可否チェック
  64:     if (typeof localStorage === 'undefined') {
  65:         document.getElementById('error').innerHTML = 'エラー:ローカルストレージが利用できません.';
  66:         return;
  67:     }
  68: 
  69:     //ローカルストレージから値を取得
  70:     let val = localStorage.getItem(LOCALSTRAGE_KEY);
  71:     //値がない
  72:     if (val == null) {
  73:         document.getElementById('val').innerHTML = '未登録';
  74:     //値がある
  75:     } else {
  76:         document.getElementById('val').innerHTML = LOCALSTRAGE_KEY + '=' + val;
  77:         let diff = diffDateTime(val);
  78:         if (! isNaN(diff)) {
  79:             document.getElementById('diff').innerHTML = diff;
  80:         }
  81:     }
  82: 
  83:     //現在日時をローカルストレージに保存
  84:     let dt = new Date();
  85:     localStorage.setItem(LOCALSTRAGE_KEY, dt.toISOString());
  86: }

メインプログラムでは、まず localStorageプロパティ を使ってローカルストレージに対応しているかどうかチェックする。
対応していれば、ローカルストレージから値を取得し、それを表示する。
最後に、現在日時をローカルストレージに保存する。

コラム:ブラウザによる挙動の違い

http(s):// プロトコルと file:// プトロコルとで、クッキーやローカルストレージの動作がブラウザによって違うので、一覧に整理しておく。
  クッキー ローカルストレージ
http(s):// file:// http(s):// file://
IE ×
Edge ×
Chrome ×
Firefox
Safari × ×
(この項おわり)
header