構築したものハマったポイント実際につかってみたおわりにはじめにFundastaの片田です!今回はNFCシールを使用して会社の自動打刻システムを、完全に自分用で作ります!要件定義なぜつくるか?現在、弊社の勤怠は、エクセルで管理されています。毎日エクセルポチポチするの面倒すぎる!!!!!!!!!作業自体も面倒なのに、何日か打刻を忘れるとまあ面倒臭いことになります。いうことで、今回の自動打刻システムの開発を決意しました。作るか?今回開発する自動打刻システムでは、NFCシールを活用していきます。処理の流れとしては、NFCシールにスマホをかざして専用のWEBサイトを表示するWEBサイトから自動打刻システムにリクエストを投げる打刻するといった感じにしようかと思います。意図しない打刻を防ぐためです。手順は増えますが確実かなあということでワンクッションはさみました。現状では個人用なのでユーザーの識別は行いません。使うか?想定される使用フローは下記のとおりです。出社したらデスクのどこかしらに貼ったNFCシールにスマホをかざす表示されるWEBサイトで打刻時間を確認、出社ボタンを押す(退社時も同じ)かなりスマート...!(な気がする)使用技術インフラはAWSの各サービスを利用します。メイン処理の部分にはLambda、エクセルファイル(勤怠管理)はS3に保存します。サーバーサイドにnode.js、WEBフロントエンドにはVue.jsを使用しつつ、HTTP通信はaxiosを使用します。NFCシールを使うか?ただ使ってみたかった。実は今回の開発、個人的にNFCシールを使ったアプリを作ってみたかったので、NFCシールありきで考えていました。pythonなどなど、いろんな言語で書くことができます。サーバーサイドもJavaScriptで書こう!ということでnode.jsを選びました。Lambdaか?Lambdaとは、AWSが提供するサーバレスアーキテクチャを構築するためのサービスです。通常は、EC2インスタンスは常時存在し、アプリケーションも常時起動されているのですが、Lambdaはリクエストが送られてきたときのみインスタンスを生成→アプリケーションを実行→インスタンスを破棄という挙動をします。今回作成するアプリは常時起動している必要もないので、コストを抑える意味でもLambdaが適しているのではないかと考えました。Vue.jsか?個人的に使い慣れているのでフロントはVue.jsで書きます。言えば、ローディングのアニメーションを作り込むくらいでしょうか...。HTTP通信はaxiosを使用します。設計アーキテクチャ図アーキテクチャの全体像としては、下記の通りです。Gatewayで受け付け、Lambdaに投げます。勤怠を管理しているエクセルはS3においておき、Lambdaからそのエクセルファイルに書き込みをしていく感じです。処理が完了すると、処理結果をSuccessかFailでクライアントに通知します。自動打刻システム(node.js)実装コードの全貌は下記のGitHubリポジトリを御覧ください。リポジトリ​エクセルファイルの操作には、「xlsx-populate」というライブラリを使用しました。最初は「xlsx」というライブラリを使って実装していましたが、このライブラリだと処理をして、保存するとマクロや書式が無効化された状態になってしまうのでつかえず...。個人的にはドキュメントも「xlsx-populate」のほうが読みやすかったです!​処理としてはファイルを読み込んで、シートを指定して、セルを指定して値を書き込み、保存しているだけです。弊社の勤怠表は月ごとにシートが分かれているので、処理の頭でDateオブジェクトを生成して、得られた各値でシートや記入するセルを判定しています。弊社は30分ごとに勤務時間として打刻できるので、打刻する時刻を30分単位に変換する関数を用意しています。今後もっと本格的に運用していくことになったら、このあたりで拡張の余地がありますね。S3からファイルを取得して、書き込んだものをアップロードし直す処理のところ。{}上記のように記述すれば、指定されたバケットのオブジェクト(ファイル)を取得できて、data変数に格納されます。{})でアップロードできます!ここがnode.jsの情報がなかなか転がってなくて苦労しました。取得も書き込みも注意点としては、取ってきたり送信するためには、データ形式に気をつけなければなりません。今回僕は、これらの処理の前後にエクセルファイルをバッファーに変換する処理をはさみ、変換したものをparams変数のBodyとしています。​クライアントサイド(vue.js)実装クライアントサイド(WEB)はVue.jsで作りました。最終的には静的サイトとしてビルドして、Netlifyでホスティングします。こちらは特に難しいことはしていません。UIはVuetifyを使ったので適当に作った割には整っています。スクショですが、下記のようになりました。打刻すると、vue-loading-templateを使用したアニメーションが流れて、レスポンスが帰ってくるとアラートが表示されます。構築したもの​いよいよインフラの構築に入ります。今回は、メインのAPIをLambdaで動かします。勤怠表(エクセルファイル)はS3にアップロードしておき、Lambdaから読み取り、書き込みを行います。HTTPリクエストの受け口として、APIGatewayを配置します。ここに想定されるリクエストがとんできたら、それをトリガーにLambda関数が動く仕組みにしていきます。クライアントサイド(WEBアプリ)はNetlifyという静的サイトのホスティングサービスを利用します。Netlifyに関しては後日別記事で言及します。​ハマったポイント​私はインフラ超初心者なので、インフラ構築でかなりつまづきました...。何の状態が1時間くらい続きました...。今回使用した「xlsx-populate」は非同期処理をすることが前提のライブラリです。恥ずかしながら、node.jsだけでなく非同期処理の知識も乏しく、Lambdaはエラーなく終了するのに肝心の処理が実行できてない...。いう状態で約5日間潰しました。エラー箇所の切り出しが下手だったなあと反省しています。awaitを駆使してなんとか解決しました。実際にクライアントサイドからリクエストを投げる時にはまりました。今までなーんとなくしか理解してなかったですが、これを機にしっかり学べました。CROSに関しては別記事でまとめます。実際につかってみた​実際の動画がこちら明日から出社と退社が楽しみになりそう。(ちょっと処理は遅いですが)個人的にほぼノンストレスに打刻できるようになったので満足です。本当にきちんと勤怠をつけるためには小難しい会社のルールがあるみたいなので、そのうちきちんとしたものも作りたいです。コメントをキャンセルメールアドレスが公開されることはありません。※サイト次回のコメントで使用するためブラウザーに自分の名前、メールアドレス、サイトを保存する。上に表示された文字を入力してください。