まとめ
Safari: Apple謹製だけど機能少ない
Chrome: なぜか異常に充実
Firefox: ほぼ何もできない
表
気が向いたときにちょっとずつ更新中
Safari | Chrome | Firefox | |
---|---|---|---|
参照 | Application( "Safari" ) | Application( "Chrome" ) | Application( "Firefox" ) |
ウィンドウ (全て) |
app.windows() | app.windows() | app.windows() |
ウィンドウ (最前面) |
app.windows[0] | app.windows[0] | app.windows[0] |
ウィンドウ 作成 |
app .Document().make() | app .Window().make() | - |
タブ (全て) |
win.tabs() | win.tabs() | - |
タブ (表示中) |
win .currentTab() | win .activeTab() | - |
タブ 切り替え |
win .currentTab = tab | win .activeTabIndex = index | - |
URL移動 | tab.url = "http://qiita.com" | tab.url = "http://qiita.com" | - |
JS実行 | app .doJavaScript("alert('hi.'),{in: tab}) | app .execute(tab, {javascript:"alert('hi.')"}) | - |
ページ更新 | tab.url = tab.url() | tab.reload() | - |
読込中止 | - | tab.stop() | - |
戻る & 進む | (やろうと思えばdoJavaScriptで) | tab.goBack(); tab.goForward(); |
- |
ブックマーク | - | 参照可(長いので省略) | - |
履歴 | - | - | - |
Chromeの新規ウィンドウ作成は戻り値でそのままWindowを得られる。
SafariはDocumentが返ってくるからURL移動したいときとか困る。
(app.Window().make()
できればいいのに・・・)
Windowを得る場合は以下のようにするといいのかもしれない・・・
var Safari = Application("Safari");
var doc = Safari.Document().make();
var win = Safari.windows[doc.name()];
//URL移動
win.currentTab.url = "http://qiita.com"
使ってみる
以下の記事と同じことをするコードを書いてみました。
JXAを知らない方はこちら。
やること
下準備
- 待ち秒数を指定 (DELAY)
- アプリケーションの参照を取得
- 最前面のウィンドウを取得
ループ
- タブを切り替えてDELAY秒だけ待つ
- ページを更新してDELAY秒だけ待つ
試すには30秒は長いので3秒にしました。
Safari
const DELAY = 3;
var Safari = Application("Safari");
var window = Safari.windows[0]; //最前面のウィンドウを取得
while(window.exists()) { //無限ループ (ウィンドウが開いてなければ実行しない)
window.tabs().forEach(function(tab){
// タブ切り替え
window.currentTab = tab;
delay(DELAY);
// 更新
tab.url = tab.url();
delay(DELAY);
});
};
ウィンドウから全タブを取得できます。
タブの切り替えは現在のタブ(currentTab
)に任意のタブをセットすることで行います。
Safariには表示中のページを更新する関数がありません。
ページの更新は表示中のurlをタブのurl
プロパティに再セットすることで可能です。
またはdoJavaScript
によってページ内でJavaScriptを実行して更新します。
Safari.doJavaScript("location.reload()", {in:tab});
doJavaScript
はページ内での実行結果を戻り値として返します。
ページから簡単に情報を得たい場合に便利かもです。
同じJavaScriptで書けますし。
メモ:
ブックマークにアクセスすることが出来ません。
ブックマークを整理するスクリプト書きたかったのに無理でした・・・。
リーディングリストに追加する機能はあるのですが、その一覧を取得する機能も無いです。
ビビりました。
Chrome
const DELAY = 3;
var Chrome = Application("Google Chrome");
var window = Chrome.windows[0]; //最前面のウィンドウを取得
while(window.exists()){ //無限ループ (ウィンドウが開いてなければ実行しない)
window.tabs().forEach(function(tab, i){
// タブ切り替え
window.activeTabIndex = i + 1;
delay(DELAY);
// 更新
tab.reload();
delay(DELAY);
});
};
ウィンドウから全タブを取得できます。
タブの切り替えはウィンドウのactiveTabIndex
にインデックスをセットすることで行います。
インデックスは1から始まることに注意。
タブからはインデックスを取得できません。
そのためforEachのカウンタを利用する必要があります。
アクティブなタブを取得する関数は.activeTab()
です。
これは読み取り専用なのでSafariのように他のタブをセットすることはできません。
Chromeには表示中のページを更新する機能(.reload()
)があります。
更新キャンセルや「進む」「戻る」の機能もあります。
もちろんページ内でJavaScriptを実行することも可能です。
Chrome.execute(tab, {javascript:"location.reload()"});
Safariと同じようにexecute
もページ内での実行結果が戻り値になります。
メモ:
今回のブラウザの中で、スクリプト向けに用意された機能はChromeがダントツで充実してました!
ブックマークにアクセスすることもできます。
ブックマークを整理するスクリプトを書くことも可能でしょう。
やってませんが。
Firefox
const DELAY = 3;
var Firefox = Application("Firefox");
var window = Firefox.windows[0]; //最前面のウィンドウを取得
SystemEvents = Application("System Events");
while(window.exists()){ //無限ループ (ウィンドウが開いてなければ実行しない)
// タブ切り替え
Firefox.activate();
delay(0.3); //アクティブになるまで少し待つ
SystemEvents.keystroke("]", {using:["command down", "shift down"]});
delay(DELAY);
// 更新
Firefox.activate();
delay(0.3); //アクティブになるまで少し待つ
SystemEvents.keystroke("r", {using:"command down"});
delay(DELAY);
};
ウィンドウからタブを取得できません。
ってことはApplication.documents()
でページの内容を見れるのかな?
>> Firefox = Application("Firefox")
=> Application("Firefox")
>> Firefox.windows.length
=> 10
>> Firefox.documents()
=> []
>>
!?
空の配列が返ってきました。
どうやら用語説明はテンプレそのまま使っていて、機能は何もなさそうです。多分。
ウィンドウを取得する以外、ほぼ何も出来なさそうです。
こういう場合はSystem Events
からキーボードを押したりして操作するしかありません。
キーボードやマウス操作をする方法はこちらに書きました。
Application("Firefox")
の部分を変えるだけでSafariでもChromeでも動きます。
いちいち.activate()
する必要があるので他の作業中に動作させるのは無理です。
メモ:
ページの内容すら取得できないんじゃ・・・?
スクリプトで操作するなら別のブラウザを使いましょう。
追記:
windowにもdocumentプロパティがあることに気付きましたが、nullでした。
varFirefox = Application("Firefox");
Firefox.windows[0].document();
//=> undefined
Firefox.windows[0].properties();
//=> {"document":null, "closeable":true, "zoomed":true, "class":"window", "index":1, "visible":true, "name":"Yahoo! JAPAN", "modal":false, "miniaturizable":true, "titled":true, "id":6188, "miniaturized":false, "floating":false, "resizable":true, "bounds":{"x":0, "y":23, "width":1280, "height":709}, "zoomable":true}
ウィンドウからページのタイトルだけ取得できるようです。
上の例だとYahooを開いていることがname
プロパティで分かります。
ページ内容を取得する方法が存在するなら、知ってる方教えてください。
蛇足
ぜんぜん関係ないけど、Terminalでシェルスクリプトを実行するdoScript
もSafariのdoJavaScript
と同じ構文
ただし戻り値はタブの参照です。タブを指定しない場合は新しいウィンドウを開くので。
var Terminal = Application("Terminal");
var tab = Terminal.windows[0].selectedTab(); // SafariはcurrentTab。名前統一してくれ
Terminal.doScript("echo 'hi.'", {in:tab});
var newTab = Terminal.doScript("echo 'hi new window.'");
コマンド実行の戻り値を得たい場合はdoShellScript
を使います
これはTerminalじゃなくても使えます
var app = Application.currentApplication();
app.includeStandardAdditions = true;
var date = app.doShellScript("date");