ttmttko
    ttmttko

    Copyright ©︎ Takao Tatematsu. All Rights Reserved.

    X

    Zendeskの障害通知をDeepL APIを用いて日本語訳化しSlackに通知する

    🗓 作成日
    2022/12/19
    更新日
    2022/12/19
    🔖 タグ
    Zendesk

    この記事は、Pepabo CS Advent Calendar 2022 の19日目記事として書きました。PepaboのCSについて興味ある方は他の投稿も是非読んでみてください!

    Zendeskの障害通知って英語なのしんどくないですか!?

    Zendeskは日本でも事業展開を行っているとはいえ、Zendeskで何かしらの障害が発生した場合、確認する画面は全て英語です。そのため、障害が発生しているけど重大な障害なのか、関係のない障害なのかを判断するには少しエネルギーを必要とします。

    この記事では、Zendesk側で何かしらの障害が発生した際、その通知内容を日本語訳化して、だれでもカンタンにslack経由で障害の程度について把握できる方法について解説します。

    想定読者

    • Zendeskユーザー
    • Zendeskの障害が発生したときに右往左往した経験のある方
    • GASやSlack Workflow Builderを用いた開発経験をお持ちの方・開発してみたいという気持ちをお持ちの方

    Zendeskで発生する障害について

    現在Zendeskでは、 https://status.zendesk.com/ にて、発生している障害の状況を(ほぼ)リアルタイムで公開しています。

    Zendeskを利用されている場合は、お使いのサブドメインを入力して「Check status」をクリックすると90日間のサーバーのステータスが表示されます。

    障害自体は定期的に起きてますが、内容によっては自社に関係のないものも結構あります。
    障害自体は定期的に起きてますが、内容によっては自社に関係のないものも結構あります。

    何かが起きたとき、ここのページにやってきて状況を確認することが可能ですが、今回はそのお知らせをslackで受け取り、いち早く障害の発生を把握できる方法を解説します。

    完成型

    今回は次のような通知をslackに投げ込む所までを解説します。

    image

    実装のレシピ

    • Zendesk障害通知のSubscription登録する
    • 日本語化する製品を選ぶ
    • SlackワークフロービルダーにてWebhookを発行する
    • 通知する条件のGASを設計する

    処理の完成図

    image

    1. Zendesk障害通知のSubscription登録する

    Zendeskで障害が発生した時のお知らせを受け取るためには、Zendeskからのpush型で障害情報の取得が必要です。

    現在のところ、Zendeskから提供されている方法はメールでの購読しか提供されていません。

    購読するには、 https://status.zendesk.com/ に進み、利用するZendeskサブドメインを入力後「Subscribe」から購読するメールアドレスを設定します。

    image

    この後の流れで、Google Apps Scriptを用いた実装を解説する都合上、お使いのGoogle Workspaceのドメインを用いた購読を行ってください。

    実際に障害が起きたときに受け取るメールはこのような内容です。

    image
    💡
    受け取った英語のメールをそのままSlackに連携して通知する方法もあるけど、、、 Slackには、Email連携というものもあり、特定のメールアドレス宛に来た内容をSlackにそのまま飛ばすこともできます。 最初にこの方法を用いて運用していましたが、以下ご覧の通り、連携されたメールはクリックしないと本文が読めないため、クリックして開く作業すら煩わしく感じ、泣く泣く今回の設計を行っています。
    image

    2. 日本語化する製品を選ぶ

    メールで受け取った内容について日本語化する方法を紹介します。

    比較したのは以下の2つのサービスです

    • Google Translation
    • DeepL

    実際の翻訳された日本がより自然に読めるもので検証した結果、今回はDeepLを採用いたしました。

    これは、以下の実例を見ていただくのが一番早いと思います。

    実例

    原文
    We are investigating reports of Chat triggers intermittently firing when they should not. More information to follow shortly.
    Google Translation
    発生してはならないチャット トリガーが断続的に発生するというレポートを調査しています。詳細については、後ほど説明します。
    DeepL
    チャットトリガーが断続的に発射されないという報告を調査しています。詳細については、近日中にお知らせします。

    DeepLでは、DeepL APIが提供されておりますので、APIの利用規約を理解した上で、APIの利用申請を行います。

    DeepLのAPI翻訳 | 機械翻訳のテクノロジー

    翻訳に必要なものすべてを集約しています。ご自身のプロダクトやプラットフォームに簡単に統合できます。

    www.deepl.com

    DeepLのAPI翻訳 | 機械翻訳のテクノロジー

    DeepL APIの利用申請後、認証キーが発行されるので、こちらをクリップボードコピーしておきます。

    image

    DeepL APIには無料版と有料版があります。無料版翻訳できる文字数に制限があります(1ヶ月500,000文字)が、今のところzendeskから毎月届くincidentメールの翻訳のみを行う場合は無料の範囲内で利用することが出来ています。

    3. SlackワークフロービルダーにてWebhookを発行する

    最終的にSlackにて障害の通知を閲覧できることを目標に設計を行います。

    ここでは、SlackのWorkflow Builderを用いてこの後利用するWebhookURLの発行までを行います。

    Slackを立ち上げ、Tools > Workflow Builderに進みます

    image

    「Create」> 「Webhook」を選択

    image
    image

    「Add Variable」を押下し、データ型(Data type)がテキスト型のKeyを一つ作成します

    image

    「Add Step」>「Send a message」>「Add」に進みます

    image
    image

    通知を投下するSlackのチャンネルを指定し、Message textに必要な内容を書き込み、「Insert a variable」から先ほど作成した「text」フィールドも差し込みます。

    もののけ姫推し
    もののけ姫推し

    Workflowの完成型はこのようになります

    内容に間違いがなければ「Publish」しましょう

    image

    Publishすると、 https://hooks.slack.com/workflows/**** というURLが生成されます。これをクリップボードにコピーしておいてください。

    image

    4. 通知する条件のGASを設計する

    最後のステップは、GASを用いた実装です。

    まずは、DeepL APIの認証キーをプロパティに格納します。

    function setVal(){
    // スクリプトプロパティで各種キーに値を格納する
    PropertiesService.getScriptProperties().setProperty("key", "*ここに発行したAPIキーを入れる*");
    //スクリプトプロパティを取得する
    Logger.log(PropertiesService.getScriptProperties().getProperty("key"));
    }

    記述した後、「setVal」を一度実行します。すると実行ログにセットした認証キーが帰ってくればOKです

    image

    続いて、以下GASのファイルを作成します。GASの内容についての細かい説明はスクリプト内の説明にて記載しているので、詳細は割愛いたしますが、概要は以下の通りです。

    スクリプトの概要

    • status@support.zendesk.com から届くIncidentメールの未読メールの有無を定期的にチェックする
    • 未読メールがあった場合、次の処理を開始する。
      • 未読メールを既読に変える
      • 未読メールの件名と本文を抜き出す
      • 本文の中に含まれる改行要素等を全てなくす
        • DeepLに情報を渡す際に改行要素などが含まれることでエラーが発生するのを回避する目的です
      • 取り出した件名と本文の情報をDeepLに渡して日本語化
      • 日本語化した結果を受けとり、Slack webhookの「text」領域に代入する
      • 代入された情報を含めて、Slack Workflow Builder経由で設定したチャンネルに投下する
    image

    上記のスクリプトの記載完了後、トリガの設定で、main関数を1分おきに実行する設定で保存します。

    image

    以上の設定で、slackに日本語化されたIncidentメールが届くようになることをお確かめください。

    お疲れ様でした!

    icon
    share this page

    Copyright ©︎ Takao Tatematsu. All Rights Reserved. This website is made with 🄽 Notion and ⚡️ Super

    // slackワークフローのwebhookを設定
    var slack = 'https://hooks.slack.com/workflows/****';
    // DeepLで利用するAPIキーを呼び出す
    var properties = PropertiesService.getScriptProperties(),
      apiKey = properties.getProperty("key")
    
    // 通知対象とするメールを設定する
    function main() {
      var after = parseInt(((new Date()).getTime() - 1000 * 60 * 10000) / 1000);  // 24h前の時刻をUNIX時間で取得 10分前までのメールを検知範囲に指定
      var searchTarget = 'is:unread from:status@support.zendesk.com after:' + after;
      Logger.log(searchTarget)
    
      GmailApp
        .search(searchTarget)
        .forEach(thread => {
          thread.getMessages().forEach(message => {
            if (message.isUnread()) {
              send(message);
              message.markRead();  // 通知後はメールを既読化
            }
          });
        });
    }
    
    // メールの件名と本文を取得しslackに投下する
    function send(message) {
      var message = '[subject] ' + message.getSubject() + '[mail body] ' + message.getPlainBody().replace(/<("[^"]*"|'[^']*'|[^'">])*>|[\r\n]/g, "").slice(0, 1100);;
      var message = transDeepL(message)
    
      var jsonData = {
        "text": message
      };
    
      var options = {
        "method": "post",
        "contentType": "application/json",
        "payload": JSON.stringify(jsonData)
      };
    
      UrlFetchApp.fetch(slack, options);
    }
    
    // slackに投下する内容をDeepLに渡して日本語化する
    function transDeepL(text) {
      //DeepLのAPIにリクエストするURLを設定
      var apiUrl = 'https://api-free.deepl.com/v2/translate?auth_key=';
      //何の言語に翻訳するかで、日本語(ja)を設定
      var lang = 'JA';
      //APIリクエストのPOST時に必要なパラメータを設定
      apiUrl = apiUrl + apiKey + '&text=' + text + '&target_lang=' + lang;
      //DeepLのAPIに翻訳をリクエスト
      var response = UrlFetchApp.fetch(apiUrl).getContentText();
      var json = JSON.parse(response);
      //ログ出力にDeepLから返却された情報を出力
      console.log(json['translations'][0]['text']);
      return json.translations[0].text;
    }