electron@5.0.0でkeytar@4.6.0をWindowsで使う2020年版
新しいPC環境にElectron + Keytar(もしくはsqlite3など)のネイティブモジュールを利用するようなアプリを作ろうとした時、毎回引っかかるのが、この問題。keytarは資格情報マネージャの読み書きをする大変優れたモジュールなのですが、利用する為にはネイティブモジュールをコンパイルする環境がなければなりません。
しかし、electronやnode.jsをインストールしただけでは構築ができないのです。また、最新版ではコンパイル出来ないといったケースもあります(もともとkeytar自体がElectronで使うことを想定していないので、Node.jsでは素直に使えても、Electronで動かないというケースが多い)
そこで今回改めて、Electron 5.0.0とKeytar4.6.0、Python 3.x、node-gyp 6.1.0にてWindows用の環境構築を検証しまとめてみました(Windows10 64bitで検証)。
※2020/12/9時点、keytar最新版の6.0.1を同じ環境でビルドしてみたら使えました
今回必要とするもの
- Node.js - v12.16.1
- electron - v5.0.0
- Windows-Build-Tools
- Visual C++ Build Tools
- electron-rebuild - 1.10.1
- node-gyp - 6.1.0
- Python 3.x
- keytar - v4.6.0
最新版v7.4.0について
Keytarの最新版である7.4.0では最新のNode.jsおよびElectronに対してネイティブ対応したので、以下の面倒なリビルド作業関係は不要になりました。npmのための環境変数の設定等は必要ですが、Node.js v14.16.0およびElectron 12.0.1にて難なくKyetarが動かせるようになっています。
下記のエントリーも合わせて御覧ください。
インストール
Node.jsのインストール
これは非常に簡単です。Node.jsのサイトから今回は64bit版のLTSと書かれたリンクをクリックすることでインストーラが手に入ります。素直にダウンロードして、インストーラを起動し、そのまま全てインストールを実行しましょう。今回は、12.6.1を指定してるので、対象のバージョンのインストーラを手に入れます。
インストール後
- コマンドプロンプトを起動する
- cd Documentsでドキュメントフォルダに移動
- mkdir testmanにてtestmanというフォルダを作ってみる
- cd testmanでそのフォルダに入る
- npm init -yにてpackage.jsonを作成する
で、プロジェクトの作成準備が完了します。
electronのインストール
今回は相性検証済みのelectronのv5.0.0をインストール(最新版だとkeytar4.6.1はリビルドしても駄目でした)。
- コマンドプロンプトを起動する
- npm i -g electron@5.0.0を実行する
- インストールが完了したら、electron -vでバージョンを調べる事が可能です。
Windows Build Toolsのインストール
Python2.7などのビルドに必要な一連のコマンド類をインストールする事が可能です。こちらはPowerShellの管理者権限でインストールが必要です。
- PowerShellを管理者権限で起動する
- npm install -g windows-build-toolsを実行してインストールする。環境によっては結構時間がかかる
- Successfullyという文字が出たら完了です。Enterキーを押します。
- これでPython2.7等がインストール完了。
- こちらのスレでelectron-rebuildでエラーがでる場合、「[Environment]::SetEnvironmentVariable("VCTargetsPath", "C:\Program Files (x86)\Microsoft Visual Studio\2017\Professional\Common7\IDE\VC\VCTargets\", "Machine")」をPowerShellの管理者権限で実行すればOKだよとありましたが、自分は効果なかった。
VisualC++ Build Toolsをインストール
Microsoftが提供してるコマンドラインビルドツールです。Visual Studio 2017と2019が現在インストール可能になっています。
- ファイルをダウンロードする
- インストーラを実行する
- 続行ボタンをクリック
- ダウンロードが始まるのでしばらく待つ
- インストールをクリックする
- 完了すると下のスクショのような画面になる
図:インストール完了画面
electron-rebuildをインストールする
ここが結構厄介なところ。旧式のやり方を自分は使っていて使えているのでそちらの方法を。
- コマンドプロンプトを起動する
- npm install -g electron-rebuildを実行してグローバルインストールする(公式サイトは現在、npm install --save-dev electron-rebuildとして記述)
- インストールが完了したら終了。
- ただ、自分の場合、新旧どちらのケースでもエラーが出てelectron-rebuild --versionでバージョン表記が出なかった
- エラーは設定がきちんと通っていない事が原因。次項で修正する
1 2 3 4 5 6 7 |
An unhandled error occurred inside electron-rebuild Unable to find parent node_modules directory, specify it via --module-dir, E.g. "--module-dir ." for the current directory Error: Unable to find parent node_modules directory, specify it via --module-dir, E.g. "--module-dir ." for the current directory at C:\Users\ユーザ名\AppData\Roaming\npm\node_modules\electron-rebuild\lib\src\cli.js:99:23 at Generator.next (<anonymous>) at fulfilled (C:\Users\ユーザ名\AppData\Roaming\npm\node_modules\electron-rebuild\lib\src\cli.js:6:58) |
図:上記のようなエラーが出て止まる・・・
Python 3.xをインストールする
2020/1/1ついに、Python 2.x系サポートが終了した為、今後Node.jsでNative BuildするにもPython 2.x系に頼るのはどうかと思う。既にnode-gypが3.x系に対応済みであるので、上記のツール類で2.x系がインストールされてしまうが、別途3.xをインストールし、2.x系はアンインストールすると良いでしょう。自分のOSのbit数に応じたPython3を入れましょう。今回は64bit版で進めます。
- ホームからインストーラをダウンロードする
- 実行する。Add Python 3.x to PATHにはチェックを入れておく
- そのままインストールを完了する。
- コマンドプロンプトから、python --versionで3.xが出ればOK。2.x系が出る場合には、コントロールパネルのプログラムと機能からpython 2.x系を削除しておく(環境変数いじっても可)
※3.x系インストールしてから、2.x系削除をすると環境変数を削除されてしまうので、先に2.x系をアンインストールしてから3.xを入れるとGood
図:WindowsユーザはPATHの追加をチェックしておこう
環境変数の設定
インストールが完了したら次に環境変数の手動変更です。ここが本作業の中で一番面倒な場所かもしれません。上記のインストールが完了したらまずは再起動して本作業を始めましょう。
electron-rebuildの場所を調べる
前項でelectron-rebuildをインストール後--versionでバージョンを調べてもエラーがでました。これは様々な設定やパスが通っていない事が原因です。electron-rebuildのファイルがある場所を見つけて、環境変数に登録をまずはしましょう。
- C:\Users\ユーザ名\AppData\Roaming\npmの場所に通常はある
- タスクバーの検索窓より、「システムの詳細設定の表示」を検索して実行
- システムのプロパティが出てくるので、左サイドの「システムの詳細設定」をクリック
- 環境変数をクリックします。
- 上部のユーザ環境設定側にあるpathをクリックして、編集ボタンをクリック
- 一番上に1.のパスを追加する
図:electron-rebuildのパスを指定する
図:electron-rebuildのバージョン表示
node-gypの場所を調べる
これが今回の中でももっとも面倒。最新のNode.jsにははじめから含まれているにも関わらず、node-gypと打っても、単独で利用できない状態(つまりパスが通っていない)それが故にネイティブモジュールをリビルドする場合に困ることになる。
- C:\Users\ユーザ名\node_modules\.binに通常は存在する(C:\Users\ユーザ名\AppData\Roaming\npmの場合もある)
- この場所を前項のように環境変数に追加する。ただし位置は上から2番目の位置とした
- 見つからない場合は、npm install -g node-gypでインストールしてみると良いかも。node-gyp -vでv6.1.0が最新版で入ってると思います。
※v5.0.5以降はPython2だけでなくPython3もサポートしたようです。
図:node-gypもビルドに重要なツールです
図:node-gypと打って正常に表示された
Python.exeの場所を調べる
Windows Build Toolsをインストールしたことによって、Python2.7を使えるようになっています。これはコンパイルする場合に必要なので、パスをきちんと指定しておきます。ただし、現在はPython3も利用出来るので、別途インストールしてPython2.xは使わないほうが良いと思います。
- C:\Users\ユーザ名\.windows-build-tools\python27\の場所に通常はある。予め、Pythonを別でインストールしてると、C:\直下にあったりします。ただし、2.x系は今回使わないので、記述が残ってれば逆に削除しておく。
- Python3を使う場合には、C:\Users\ユーザ名\AppData\Local\Programs\Python\Python38にpython.exeがあります。
- この場所を前項のように環境変数に追加する。ただし位置は上から3番目の位置とした
- npm config set python python.exeのフルパス コマンドを実行する
図:環境設定の位置には意味がある
図:pythonのバージョン表記
msvsのバージョン指定
ビルドで使用できるmsvsのバージョンは現在、2015と2017の2つ。今回は2015を利用してみます。
- コマンドプロンプトを起動する
- npm config listで現在の設定を確認
- npm config set msvs_version 2017を打って今回はセットする
- ここまで完了したら再起動する
図:msvs_versionがセットされてるのを確認
プロキシーに阻まれて追加できない時
社内でnpmでモジュールを追加する時に、プロキシーに阻まれて(getaddrinfo ENOTFOUNDというエラーがでます)追加できない場合があります。その場合には以下の手順でnpmに対してProxyのセッティングを通しておくと追加が可能です。アドレスはお使いのプロキシーのURLを入力します。
- npm config set proxy http://proxy.example.com:8080 を実行する
- npm config set https-proxy http://proxy.example.com:8080 を実行する
- npm config set registry https://registry.npmjs.org/ を実行する
この設定ファイルは、c:\Users\ユーザ名\.npmrcに保存されています。
また、node-gypなどもProxyのセッティングが必要なのですが、これはコマンドプロンプトからプロキシー超え出来ないと駄目なので、以下のコマンドを入力すれば、一時的に使えます。いつでもプロキシにするには環境変数に登録が必要です。以下の例はhttpの無認証プロキシをhttpおよびhttpsで利用する場合のセットです。
1 2 |
set HTTP_PROXY=http://プロキシURL:ポート番号 set HTTPS_PROXY=http://プロキシURL:ポート番号 |
環境変数に登録する場合には、以下の手順で登録しておくといちいちコマンドを打つ必要がなくなります。
- コントロールパネルよりシステムの詳細設定を開く
- 環境変数を開く
- ユーザ環境変数に於いて、新規をクリック
- 変数名にhttp_proxyと入れる
- 変数値にhttp://を除いたプロキシのURL:ポート番号を入力し、OKをクリック
- 同じくhttps_proxyについても同じ様に登録する
再起動後、この設定は有効になり、node-gyp、electron-rebuildなどでプロキシ超えができるようになります。
ただ、electron7.0および一部のモジュール(electron-packager)などはプロキシ参照先変数が変更されており、以下の設定を同じく環境変数に追加しないと、ダウンロードやnpm installが出来ないです。以下の設定も追加しておきましょう。
- ELECTRON_GET_USE_PROXY:値はtrue
- GLOBAL_AGENT_HTTP_PROXY:値はhttpから始まるプロキシアドレス:プロキシポート
- GLOBAL_AGENT_HTTPS_PROXY:値はhttpから始まるプロキシアドレス:プロキシポート
セットしたら、さっそくelectron-packagerでパッケージングを実行してみたところ、エラーが解消し無事にパッケージの作成が成功しました。今後他のモジュールも移行していくのかもしれません。
図:プロキシ越えって本当に面倒
Keytarをネイティブビルドしてみる
さて、ここまででNode.jsのモジュールのネイティブビルド環境が整いました。しかし、これでモジュールをインストールすれば完了というわけにはいきません。ビルドに関しても手動で行う必要性があります。
keytarのインストール
今回は検証済みなのでelectron5.0.0を利用しましたが、keytarも必ずしも最新版が使えるとは限りません。すべてはNode.jsの仕組み上の弊害なのですが、Electronで使う為にはこれを乗り越えなくてはなりません。
- コマンドプロンプトを起動する
- 自分のプロジェクトフォルダ内まで移動する
- npm i keytar@4.6.0を実行する
- インストールがエラーなく終了したらOK
node-gypとelectron-rebuild
インストールが完了したらネイティブビルドをしてみる
- コマンドプロンプトを起動する
- 自分のプロジェクトフォルダ内まで移動する
- cd node_modulesで移動する
- cd keytarで移動する
- node-gyp configureを実行して、エラーなく完了すればOK.
- cd ..\..\にてプロジェクトフォルダ直下に戻る
- electron-rebuild -w keytar -p -fにてリビルドを実行する
- 問題なく完了したらOK
※最新版のelectron-rebuildとmsvs2015だとエラーが出た。npm i electron-rebuild@1.10.1で旧バージョンを入れ、msvs2017だとエラーでずにリビルドが出来た。相性があるのかもしれません。
図:リビルドが無事に完了した
検証用コード
さて、これでリビルドは完了しましたが、正しく動いてるかどうかはわかりません。実際に空のBrowserWindowを作って、資格情報マネージャにパスワードをセットし、同時にパスワードを取得して表示するコードを記述して、コマンドラインからelectronを起動してみれば、コマンドプロンプトに答えが表示されます。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 |
//モジュールの読み込み const electron = require('electron'); const { app, BrowserWindow } = require('electron'); const keytar = require('keytar'); //初期化 let setWindow = null; //サービス名を構築 var servicename = "zaseki_sakura"; app.on('ready', function() { //とりあえず、キャッシュをクリアしておく electron.session.defaultSession.clearCache(() => {}) //パスワードを取得してみる main() .then(function(){ //パスワードを保存する keytar.setPassword(servicename,"sakura","password"); console.log("OK") return "sakura"; }) .then(function(data){ const secret = keytar.getPassword(servicename,data); secret.then((result) => { console.log(result); return; }); }) }); // 全てのウィンドウが閉じたときの処理 app.on('window-all-closed', () => { // macOSの時以外はアプリケーションを終了させます(osxだとドックに残る) if (process.platform !== 'darwin') { app.quit(); } }); //puppeteerで操作するメインの処理 const main = async () => { //URLを指定してBrowserWindowに対してページの移動をさせる setWindow = new BrowserWindow({ 'width': 550, 'height': 380, 'autoHideMenuBar':true, //nodeIntegrationを有効にしないとrenderProcessでrequireを使えない。v5.0.0ではデフォルトで廃止 webPreferences: { nodeIntegration: true }, 'resizable':false, 'fullscreenable':false, 'fullscreen':false, 'modal':true, 'minimizable':false, 'maximizable':false, 'title':'テストウィンドウ' }); //URLを開く setWindow.loadURL('https://www.google.co.jp'); }; |
- プロジェクトフォルダ直下に上記のコードのindex.jsを作成する
- コマンドプロンプトでプロジェクト直下に移動して、electron .で実行するとテスト実行できます。
- zaseki_sakuraというサービス名で資格情報マネージャに作成がなされます。
- passwordは「password」、IDは「sakura」としました。
- タスクバーの検索窓から「資格情報マネージャ」で検索し、Windows資格情報を開くとそこに登録されています。
図:無事にID/PASSがservicenameと共に保存された