ChromeExtensionのBrowser actions作ってみてはまったこと

#概要

ブラウザの右上に表示するタイプのChrome拡張を作ろうとして、デバッグしづらくていろいろハマったのでメモ

#前置き

読者としてはこれからChrome拡張作ってみよう、もしくは作り出してみたけど動かない！って方を想定
開発の基礎はあまり説明しないので各自調べて下さい。
http://liginc.co.jp/web/tool/browser/163575


##環境
Chrome バージョン 50.0.2661.75 (64-bit)
Mac OS X 10.11.1

#Browser actionsでJSが動かない

###Browser actionsって…？

ブラウザのタブ右上に出る各Extensionのアイコンメニューのこと
<img width="336" alt="スクリーンショット_2016-04-19_21_33_13_.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/99683/b75a993e-6b96-1c0d-2895-3095e416fd38.jpeg">

manifest.jsonというファイルでbrowser_actionを指定すると表示できます

#JSの読み込み方
\<script\>タグで読み込みするのですが、下記の書き方はエラーでJS動きませんでした

動かないパターン1

```html
<script>
    alert('hoge');
</script>
```

動かないパターン2

```html
<script src="popup.js"/>
```

動かないパターン1はcontent security policyにひっかかるそうです。
参考 : http://oxynotes.com/?p=8895
Chrome ExtensionにおいてはインラインJavaScriptは一切動きません。
とりあえず動かそうと思ったら全く動かず、browser_actionはconsoleにエラー吐いたりもしないのでなかなか分からなかったです
動かないパターン2はなんでだか分かりません。動くやつと動かないやつ比べたらこれが原因でした

これなら動く

```html
<script src="popup.js"></script>
```

#JSのデバッグができない

これいまだに解決できてないんですが、browser_actionのdefault_popup(右上に出る各Extensionのアイコンメニュー押した時出るhtml)から読み込んだJSは、console.logがそのままだとどこにも出力されません。
なのでsyntax error等起こっているとJSが全く動かずエラーも出ません。

###解決法1

default_popup上で右クリック→検証でdev toolsを開き、consoleを見る
操作がめんどい

###解決法2

alertは動くのでconsole.logの代わりに使う
alert仕込むのがめんどい

###解決法3

上記のめんどくささを解決する方法知ってる方いたらコメント頂けるとありがたいです

#値の保存ができない

右上メニュー(browser_action)とそれ以外(例：content_scripts:Webページに対する拡張、各ページ読み込み時に表示を変えたりするやつ)との連携は基本chrome.extension.sendMessageなどを使いやりとりします。

簡易的なデータの保存が自分が調べた結果ではなかったです。
下記ダメだった手順

###localStorage
参考:http://ota42y.com/blog/2014/08/17/local-storage/

manifest.jsonに

```json
"permissions": [
    "storage",
    "unlimitedStorage"
  ]
```

とかを足して、

```js
var localStorage['data'] = 'aaa'; //データ保存
var data = localStorage['data']; //データ取得
```

browser_action内default_popup内で保存したデータをcontent_scriptsに設定しているindex.js(webページ読み込み時に呼ばれるやつ)から取得しようとしたりしたけど、取得できない

###localStorageの仕様
>Content Script(insert_hello.js)内でもwindow.localStorageにアクセスできます。しかし、設定画面で設定した値は、そこにはありません。
>window.localStorageは、各ページ毎に持たれるものだからです。
>extension全体で共通のwindow.localStrageは、Background Pageにあるものになります。

引用 : http://memememomo.hatenablog.com/entry/20100519/1274220602
なので値はBackground Pageで管理する必要が出てきます。

###File API
公式サンプル : https://github.com/GoogleChrome/chrome-app-samples/tree/master/samples/filesystem-access
File APIを使うにはmanifest.jsonで

```json:manifest.jsonの一部
"permissions": [
    {"fileSystem": ["write", "retainEntries", "directory"]},
    "storage"
  ],
```

fileSystemパーミッションが必要
fileSystemのパーミッションを取得するには

```json:manifest.jsonの一部
"app": {
    "background": {
      "scripts": ["background.js"]
    }
  },
```
のように"app"として宣言が必要。
appはChromeでそれ用に別windowを開くものなので今回の目的にそぐわないものでした。
また、"app"キーの宣言と"browser_action","content_scripts"の宣言は競合するので、どちらかしか指定できません

###ダメだった書き方

```json:manifest.jsonの一部
"permissions": [
    {"fileSystem": ["write", "retainEntries", "directory"]},
    "storage"
  ],
"browser_action": {
    "default_icon": "l_2573424_12101819053e50d7315fd8917905ce46.png"
    ,"default_title": "SpeedCapture"
    ,"default_popup": "popup.html"
  }
```

appとして宣言してないと下記のようなエラーが出ます
`'fileSystem' is only allowed for packaged apps, but this is a extension.`

以上