2020-05-05

【Node.js】定期的にDiscordに連絡してくるNode.jsサーバー機能

サーバーのステータスを一定間隔で送りたいことはないだろうか?JavaScriptにてsetIntervalを利用して実現する。

Article Image

作るもの

サーバーを稼働しているときに一定間隔でDiscordにメッセージを送るシステム

だいたい1時間ぐらいでメッセージを送ってくる物を想定している。

なぜ作るのか

自宅サーバーでは突然のシャットダウン等あり得るためサーバーのステータス確認・データが正しく蓄積されているか・エラーはないか・HDD容量は足りているか・・・など定期的に確認したいケースが多々ある。

Discordであれば外出先からも確認ができる。

極めて簡単

極めて簡単に実装できるのがメリットだ。

DiscordのチャンネルとWebhookを作る

これに関しては私の記事の冒頭で画像付きで説明しているので参照していただきたい。

既に自分用のチャンネルが有る場合はチャンネル新規作成は飛ばしても良い。

【Discord Bot】Vue.jsでDiscordへメッセージを送る機能を実装する

使う関数

一定間隔でDiscordにメッセージを送ることを「繰り返す」必要があるためJavaScriptでよく使うsetTimeout関数ではダメだ。これは1回しか実行されない。

そこで使うのがsetInterval関数。こちらは設定した関数を指定間隔で無限に実行してくれる。

setIntervalの注意点

  1. 引数で指定した時間を「待ってから」関数が実行される

    たとえば1時間に設定した場合実行した直後は何も送信されない。最初の送信は実行後1時間後になる。

  2. 設定した時間は僅かに遅延がある。正確な計測用途では使えないので注意。

必要なライブラリ

  • axios

Discordのサーバーにデータをpostするために必要。httpアクセスを担当する。興味があれば調べてみてほしい。

インストール

npm i axios

今回のコード全部

import axios from 'axios'

const webhook_url = "https://discordapp.com/api/webhooks/ここにIDみたいなやつ"
const message = {
    content: "testです\r改行しました\r\\rで改行します"
}

console.log("Start")
setInterval(()=>{
    axios.post(webhook_url, message).then((msg) => {
        console.log("送信しました")
      }).catch((e)=>{
        console.log("送信失敗しました")
      })
},5000)
console.log("END")

サーバー側の実行結果

Start
END
送信しました
送信しました

覚えておくこと

axios.postの第一引数にurl、第2引数に送るメッセージを入れるがこれは連想配列型である必要がある。

そして、実際に送りたい内容は contentキーの値として入れてやる必要がある。

これはDiscord側のフォーマット指定によるもの。

オマケ:\rで改行できる。円マークを直接使いたい場合は\でエスケープする。

setIntervalのメリット

実行結果を見るとStartとEndが即座に表示されたあとにメッセージが送信されている。つまりsetIntervalは非同期ということだ。

例えばデータを蓄積し続けているサーバでは処理がブロックされると受信が間に合わずデータの欠落も考えられる。このsetIntervalは内部で非同期に実行されるため処理をブロックしないことはありがたい。

実行結果

2020 05 05 21h44 22

プログラムを止めるまで3秒毎に送られてくる。

送られてこないときは

送るメッセージが連想配列{}になっているかチェック。

さらに{ content: 送るメッセージ } になっているかチェック

これをどう活用するか

サーバー側にsetIntervalの間隔内で蓄積したエラーメッセージを添えて送ると良さげに思う。

データファイルに追記されたエラーメッセージを拾う方法等も次回共有できればやりたい。



この記事のタグ

この記事をシェア


謎の技術研究部 (謎技研)