Chrome拡張でページのグローバル変数にアクセスしたい

Chromeで動くユーザースクリプトの一種である、Chrome拡張。非常に便利で、ページに様々な追加機能を付加することができるのだが、残念なことに、そのページのグローバル空間(window)にアクセスすることができない。Chrome拡張の中からwindowにアクセスしても、それはChrome拡張内のグローバル空間であり、ページのそれとは共有されない。

Chrome拡張から、ページのDOMにアクセスすることはできる。content_scriptに任意のJSファイルを指定し、そのファイル内で普通にDOM操作をするだけだ。

http://dev.screw-axis.com/doc/chrome_extensions/guide/content_script/

しかし、windowからDOMへのアクセスは可能(window.document)である一方、DOMからwindowへのアクセスはできない。

ならば、DOM操作によってJS文を直接、親切のscriptタグに書き込めばいいのではないかと考えた。結論から言えば、これもダメだ。DOM内のscriptタグにconsole.log(window)を記述しても、コンソールに表示されるのは、Chrome拡張のグローバル空間なのである。

var s$ = $("<script />");
s$.text("console.log(window);"); // コードをテキストとして埋め込むとか鬼畜い
$("head").append(s$);

ではどうするか。下記のサイトを見ると、「location.hrefに、JSコードを与えてやれば、ページのグローバル空間内でスクリプトが実行されるよ!」と書かれている。

クッキー加速装置
http://yubais.net/chrome-ext/cookie-acceleration/
 

これはもう試すしかない。実際にやってみると、たしかにスクリプトが実行されているようだ。

location.href = "javascript: console.log(window); ";

となれば、任意の関数をJSファイル内で定義し、それをtoString()で文字列化したものをこれに食わせれば、任意の挙動をさせることができるではないか。

var run = function(script){
  location.href = "javascript: setTimeout(" + script.toString() + ", 10);"; // Function.toString()は、"function(){"から始まる文字列になるので、 //setTimeoutなどで呼び出しをラップする } var func = function(){   console.log("test", window); } run(func);

しかし、しかしである。これはいくらなんでもどうなんだろうか。やってることは「文字列で与えたコードを、evalよろしく実行する」という行為であり、いや別にXSSとかが関わる場所じゃないんだし、問題はないだろうけど、正直あまり「美しい」とは言いがたい。

また、この方法では、任意のJSライブラリを読み込んで使うことができない。ACAOが返ってくるサイトに置いてあるものなら大丈夫だが、Chrome拡張のcontent_scriptに指定したファイルなどを読み込むことはできない。非常に残念である。

何か他にいい手はないのだろうか。確かに、無闇矢鱈にページのwindowにアクセスされて、その情報を任意のサーバーに送られてしまっては問題があるのはわかるが、上記のlocation.href方式を使えば結局送信できてしまうわけで、もっとシンプルにアクセスする方法があるなら、ぜひとも知りたいところである。

※ 以下、記事無し

ここから先は

0字

¥ 100

この記事が気に入ったらサポートをしてみませんか?