皆さんこんにちわ、JavaScript のソース隠蔽について考えるコラムも今回で一応の結論を出そうと思います。
今回はもう既に色々出来上がっているので、無駄な前置きはググッと我慢して進めます。
それではこのミッションを遂行するための手持ち武器をまとめます。
- JavaScript による navigator.userAgent と navigator.platform のチェックで偽装を認めない認証
- Ajax による非同期なソース展開、送受信は POST とする事で URL 欄からの単純な攻撃を防ぐ
- 開発は通常通り JavaScriptファイル(.js)で行い、呼び出す時は PHP 内でファイルを読み込んで文字列のみ送信
- 認証を通らない時は何か画面に表示する
- JS を切られたらもうそれは無視する
こんな感じですね、それでは解説を交え早速実装して行きましょう。
取りあえずファイル構成はこんな感じで想定してます。
/index.html
/js/jquery.js
/js/hoge.js
/js/foo.js
/js/piyo.php
適当なディレクトリに上記構成でファイルを作成してください、foo.js が隠蔽したいファイルです。
条件を満たすと非同期に foo.js の中身が index.html に送信されるようにします。
まずは html 部分から、今回と言うか当 blog ではほぼ毎回 jQuery を使います、言うまでも無く色々と捗るので。
head 要素内に…
1 2 3 | <script src="./js/jquery.js" type="text/javascript"></script> <script src="./js/hoge.js" type="text/javascript"></script> <script id="moge" type="text/javascript"></script> |
jquery.js はご存知のライブラリ、まず呼び出しておきましょう。
hoge.js は判定文を書きます。
3行目は入れ子です、最終的に全て条件を満たすとこの中にソースを送信します。
次は hoge.js の中身です、前回の条件を踏まえて2つの condition を書いて上げましょう。
1 2 3 4 5 6 7 | $(function() { if(navigator.platform.indexOf('iPhone') != -1 && navigator.userAgent.indexOf('iPhone') != -1) { $('#hoge').load('./js/piyo.php', {mode:'hoge'}); } else { alert('error'); } }); |
iPhone シミュレータもハネたい場合は2行目を
1 | if(navigator.platform == 'iPhone' && navigator.userAgent.indexOf('iPhone') != -1) { |
にすれば良いかと思います。
navigator.userAgent も判定しているのは、将来的に webkit じゃないブラウザが出て来たら…と思うのですが iOS の仕様的にあり得ない気もするので無くても良いと思います。
最後に piyo.php の中身です、使い回しが効くように switch で書いてみました。
1 2 3 4 5 6 7 8 9 | switch($_POST['mode']) { case 'hoge': print(file_get_contents('./foo.js')); break; default: print('error'); break; } |
えーと、これでおしまいです。
今回前置きを書かなかったのは、このシンプルなコードを書くために計3回もの記事を消費した訳で。このコラム自体が壮大な前置きだったんだよ!!と言う事に気づいたからです。
いや、まぁ実際に検証してみるってのは大事な事だと思うので無駄では無い。ハズ。
気を取り直して解説、
- http request が来た
- hoge.js Line:2 で判定
- どちらも条件を満たした(次へ)
- どちらかの条件が満たせなかった(エラー出力などして終了)
- hoge.js Line:3 で id=hoge(script の入れ子)に piyo.php を呼び出す、mode と言うキーで hoge と言う文字列を POST する
- piyo.php はコールされると $_POST[‘mode’] を見て分岐処理を行う、何も渡されずに呼ばれたら error と言う文字列を返す
- piyo.php Line:3 にだけ書かれた foo.js のパスからファイルの内容をロードして print を実行、サーバサイドなのでブラウザからは解らない
- PHP でプリント(出力)されたものは POST 値としてブラウザに返される、jQuery の .load() の効果で index.html に書かれた入れ子の<script id="hoge">〜</script>の間に返された文字列が出力される
- 出力されると同時にその JS は勝手に実行される
こう言う動きになります、シンプルで良いですね。
切ない人の為に上記を実装したサンプルをこちらにアップしました、iPhone 以外からだときっと動かないハズ。
iPhone でアクセスするとやっつけ感満載のパズルゲームが始まると思います、何となく html5 の canvas 使ってみたくてサ。
そしてこれは下記環境下なら恐らく上手く隠蔽出来るハズ
- ソースの保存や Firebug 系のツールが無い環境
- JS の navigator.platform が偽装出来ない環境
あんまり調べてないからアレですけど、iOS 系なら大丈夫なんじゃなかろうか?どちらにせよ結構な手間をかけないとソースは見えないと思います。
いやー、長かったですね。お付き合い頂いた皆様、お疲れさまです。
今回良く解ったのは普通の Web ブラウザ上で JS のソースを完全に隠蔽するのは不可能、と言う事です。
完全に隠蔽した Web App を作りたいのなら、一旦素の状態で完成させた物をネイティブアプリの入れ子にリソースを全て埋め込んで、アプリの機能で html を表示して使うアプリをリリースする。と言う方法しか無いんじゃなかろうかと思います、何だか敗北感が凄いですがそう言うモノなんでしょうね。
では、最後に締めの言葉を。
デバイス限定だけど、そんなに手間をかけずに見え辛くするのは可能だよ!
やりたい人はやっても良いと思うよ!!
嗚呼、やはりこうなってしまうんですね。
今回の事は雑学として覚えておけば、妥協点のポイントとして役立つ時が来るかもしれません。
それではまた。
vividworks
最新記事 by vividworks (全て見る)
Tags: Ajax, JavaScript, jQuery, php, 非同期