今の組織で、フリーアドレスの推進のアシストアプリとして、かねてより作ってきた「座席表アプリ」について、新機能を都度都度追加しています。前回の「組織図」をElectronに移植し、今回は「顔写真を変更する」機能を搭載を考案。顔写真はサーバ側にあり、写真のファイル名は社員番号.jpgといった形で置いてある。

一般ユーザは自分のIDでログインし自分の写真のみ変更可とし、管理者は全員の写真に対して変更可にする必要性もある。ローカルの画像をElectronからサーバ側(Node.js)に送って、既存のファイルを置換しつつ、MySQLサーバのpictフラグを-1にするよう(写真未登録時のみ)にコードを追加する必要があるので、記録の為に下記に残します。

今回使用するファイルやライブラリ

ExpressでAPIを作って画像ファイルの受け口を作るのは、前回の記事でも実装しています。続編的にはこちらの記事の続編です。

事前準備

サーバー側の準備

サーバー側の準備は至ってシンプルです。

  • 画像保存用のフォルダを作成しておく(Node.jsから書き込めるパーミッションも設定しておく)
  • npm init -yでプロジェクトを作成しておく
  • 使用するモジュール(今回は、expressモジュールのみ)をインストールしておく
  • index.jsを作成しコードを記述する

モジュールをインストールするコマンドは以下の通りです。

クライアント側の準備

keytarモジュールのインストールは非常に大変なので、こちらを参照してインストールしてください。それ以外で「今回必要な分のモジュール」をインストールしておきましょう。

ソースコード

クライアント側

クライアントであるelectron側では、ファイルの選択やBase64エンコード、MySQLのデータの読み書きなど様々な処理を担当しています。今回のコードは必要な箇所だけに絞っていますので、注意してください。

レンダラープロセス側

  • メインプロセス側のファイル選択ダイアログの呼び出しと、アップロード結果を受け取るipcRendererだけが今回は行う仕事です。

メインプロセス側

  • picturl変数にはサーバー側のPOSTで用意しておいたAPIのURLを入れる(ポート番号も含めて)
  • showOpenDialogにて、画像のファイル形式のみを選択可能なようにfilter設定しています。
  • filetypeモジュールにて、ファイルの拡張子およびMIMETYPEを取得しています。
  • 変数base64manにbase64エンコードしたデータ含めて、変換と組み立てを行っています。
  • chkpictFlg関数にて一度MySQLへログインさせて、pictフラグの取得をさせることで認証としています。
  • requestモジュールでサーバー側のNode.jsで作成したAPIへPOST通信を送っています。この時、json:trueとしておくと、返り値をJSONパースした状態で取得可能です。
  • リクエストを送って、サーバステータスコードの200が返ってきたら無事にリクエストは成功
  • なおかつ、アップロード完了の返り値をサーバ側から受け取ったら、MySQLサーバの対象者のpictフラグを-1にしてあげるようにしています。
  • chkpictFlgからのcallbackを拾って、無事に完了すればevent.sender.sendにてレンダラプロセスのIPCである「uploaded」へ最終的に返しています(ここで処理が完了。場合によっては、ここから更にレンダラプロセス側で画像のリロードなどを入れておくと良い)

サーバー側

サーバー側の主な処理は、

  1. APIで受け取ったBase64データをデコード
  2. 指定のフォルダに社員番号と拡張子を持ってして、ファイルを上書き生成

のみです。非常にシンプルな作業だけを担当させています。

  • bodyParserのlimitを50MBに設定していますが、デフォルトは100KBです。画像ですので、適切なファイルサイズを指定しないと「request entity too large」のエラーが発生します。
  • 今回は3700番ポート/api/v1/pictchangeというURLにてPOST用のAPIを待機させてます。
  • POSTで受信するので、app.postで受信したデータを冒頭で分解しています。
  • savepathですが、このnode.jsのサーバがきちんと書き込めるパーミッションである必要があります。(今回は、このindex.jsがあるフォルダにimgフォルダを作っておきました)
  • デコードはBuffer.fromで行います。new Bufferは現在非推奨ですので注意してください。
  • fs.writeFileにてデコードしたデータをファイルに戻し、指定のフォルダに生成します。
  • res.jsonにてクライアント側にレスポンスを返しています。

関連リンク

共有してみる: