2
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

QiitaのOrganization内のユーザーが記事を投稿したらGASでTeamsに通知するBOTを作ってみた

Posted at

はじめに

弊社(株式会社コードユニット)は、技術記事投稿の文化を根付けるためにQiita Organizationを始めました。
そこで、Organization内のユーザーが投稿したら弊社Teamsに通知をすることにより、社員同士の投稿を確認しやすくなるのでは・・・?
と思い、BOTを作ってみました。

内々で使用するBOTなので、仕組みはちょっと甘めですが、参考になれば幸いです!

使用技術

  • Teams Incomming Webhook
  • GAS
  • Qiita API

作り方

TeamsのIncomming Webhookを設定する

Teamsで任意のチャンネルを右クリック
image.png
こちらの チャネルの管理を押下し、コネクタの編集を押下します。
image.png
Incomming Webhook の構成を押下し、各情報を入力します。
払い出されたWebhook URLをメモしておきましょう。

GASで定期実行の処理を書く

処理内容としては以下のようになります。
今回はGASで10分毎の定期実行としました。

Qiita APIをコール

https://qiita.com/api/v2/items
でQiitaの全ての投稿が取得できます。

https://qiita.com/api/v2/docs
こちらによると、クエリパラメータで query=${}で、
https://help.qiita.com/ja/articles/qiita-search-options
の検索オプションが使えそうということがわかりましたので、試してみました。

結果、 https://qiita.com/api/v2/items?query=org:codeunit のようにOrganization名でも検索ができましたので、こちらを採用します。

https://qiita.com/fkooo/items/9f8e566c027bb833c29e
こちらを参考に、失敗回避のため、以下のオプションを追記しました。

headers: {
  'Accept-Encoding': 'identity',
},

キャッシュに保存する

今回は、処理を定期実行するにあたって、APIから取得した前回の値と、今回取得した値に変更があった場合に処理をしたいと考えました。
https://qiita.com/golyat/items/ba5d9ce38ec3308d3757
上記を参考に、100分間キャッシュすることにしました。

比較

キャッシュデータと今回取得したデータを比較して、
追加のあった記事のみを取得します。

Teamsに通知

追加のあった記事の内容を
先ほど取得したWebhook URLに対してPOSTでメッセージを送信します。

ソースコード全文

function makeCache() {
  const cache = CacheService.getScriptCache();
  return {
    get: function (key) {
      const value = cache.get(key);
      return value ? JSON.parse(value) : null;
    },
    put: function (key, value, sec) {
      cache.put(key, JSON.stringify(value), sec || 6000);
      return value;
    }
  };
}

// Qiita APIのエンドポイント
const qiitaApiUrl = 'https://qiita.com/api/v2/items?query=org:codeunit';

// Teams WebhookのURL
const teamsWebhookUrl = 'ここに先ほどコピーしたWebhook URLを書きます';
// キャッシュを作成
const cache = makeCache();

// Qiita APIを呼び出してデータを取得
function fetchData() {
  const options = {
    headers: {
      'Accept-Encoding': 'identity',
    },
  };
  const response = UrlFetchApp.fetch(qiitaApiUrl, options);
  const data = JSON.parse(response.getContentText());
  return data.map(item => ({
    title: item.title,
    url: item.url,
    user: {
      id: item.user.id,
    },
  }));
}

// 前回のデータと比較して新しい記事を通知する
function notifyNewArticles() {
  const currentData = fetchData();
  const previousData = cache.get('qiitaData') || [];

  // 前回のデータと比較して新しい記事を取得
  const newArticles = currentData.filter(item => !previousData.some(prevItem => prevItem.url === item.url));

  // 新しい記事がある場合、Teamsに通知する
  if (newArticles.length > 0) {
    newArticles.forEach(article => {
      const message = `${article.user.id} さんが新しい記事を投稿したよ <br> タイトル: ${article.title} <br> URL: ${article.url}`;
      postToTeams(message);
    });

    // 新しいデータをキャッシュとして保存
    cache.put('qiitaData', currentData);
  }
}

// Teamsにメッセージを投稿する
function postToTeams(message) {
  const payload = {
    text: message,
  };

  const options = {
    method: 'post',
    contentType: 'application/json',
    payload: JSON.stringify(payload),
  };

  UrlFetchApp.fetch(teamsWebhookUrl, options);
}

結果

image.png
こんな感じで通知するBOTが出来ました!

追伸

株式会社コードユニットでは北海道札幌市で一緒に働けるメンバーを絶賛募集中です!
起業したばかりのベンチャーですが、和気あいあいと楽しく仕事をしています!
ご興味のある方は一度ご連絡ください!

2
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?