Просмотр исходного кода

Merge pull request #3451 from weseek/imprv/refactor-bolt-service

Imprv/refactor bolt service
Yuki Takei 5 лет назад
Родитель
Сommit
8d6f811cd4
2 измененных файлов с 59 добавлено и 44 удалено
  1. 11 1
      src/server/routes/apiv3/slack-bot.js
  2. 48 43
      src/server/service/bolt.js

+ 11 - 1
src/server/routes/apiv3/slack-bot.js

@@ -2,12 +2,22 @@
 const express = require('express');
 
 const router = express.Router();
+const ErrorV3 = require('../../models/vo/error-apiv3');
 
 module.exports = (crowi) => {
   this.app = crowi.express;
   const { boltService } = crowi;
+  const requestHandler = boltService.receiver.requestHandler.bind(boltService.receiver);
 
-  router.post('/', boltService.receiver.requestHandler.bind(boltService.receiver));
+  router.post('/', async(req, res) => {
+    try {
+      const response = await requestHandler(req.body) || null;
+      res.send(response);
+    }
+    catch (err) {
+      return res.apiv3Err(new ErrorV3(`Error:Slack-Bot:${err}`), 500);
+    }
+  });
 
   return router;
 };

+ 48 - 43
src/server/service/bolt.js

@@ -6,42 +6,48 @@ class BoltReciever {
     this.bolt = app;
   }
 
-  async requestHandler(req, res) {
+  async requestHandler(body) {
+    if (this.bolt === undefined) {
+      throw new Error('Slack Bot service is not setup');
+    }
+
     let ackCalled = false;
 
     // for verification request URL on Event Subscriptions
-    if (req.body.challenge && req.body.type) {
-      return res.send(req.body);
+    if (body.type === 'url_verification') {
+      return body;
     }
 
-    const payload = req.body.payload;
+    const payload = body.payload;
     let reqBody;
 
     if (payload != null) {
       reqBody = JSON.parse(payload);
     }
     else {
-      reqBody = req.body;
+      reqBody = body;
     }
 
     const event = {
       body: reqBody,
       ack: (response) => {
         if (ackCalled) {
-          return;
+          return null;
         }
 
+        ackCalled = true;
+
         if (response instanceof Error) {
-          res.status(500).send();
+          const message = response.message || 'Error occurred';
+          throw new Error(message);
         }
         else if (!response) {
-          res.send('');
+          return null;
         }
         else {
-          res.send(response);
+          return response;
         }
 
-        ackCalled = true;
       },
     };
 
@@ -66,7 +72,7 @@ class BoltService {
     this.client = client;
 
     if (token != null || signingSecret != null) {
-      logger.debug('TwitterStrategy: setup is done');
+      logger.debug('SlackBot: setup is done');
       this.bolt = new App({
         token,
         signingSecret,
@@ -101,11 +107,11 @@ class BoltService {
 
       switch (firstArg) {
         case 'search':
-          this.searchResults(command, args);
+          await this.searchResults(command, args);
           break;
 
         case 'create':
-          this.createModal(command, client, body);
+          await this.createModal(command, client, body);
           break;
 
         default:
@@ -116,7 +122,7 @@ class BoltService {
 
     this.bolt.view('createPage', async({ ack, view }) => {
       await ack();
-      return this.createPageInGrowi(view);
+      await this.createPageInGrowi(view);
     });
 
     this.bolt.action('button_click', async({ body, ack, say }) => {
@@ -127,27 +133,28 @@ class BoltService {
   }
 
   notCommand(command) {
-    logger.error('Input first arguments');
-    return this.client.chat.postEphemeral({
+    logger.error('Invalid first argument');
+    this.client.chat.postEphemeral({
       channel: command.channel_id,
       user: command.user_id,
       blocks: [
         this.generateMarkdownSectionBlock('*No command.*\n Hint\n `/growi [command] [keyword]`'),
       ],
     });
-
+    throw new Error('/growi command: Invalid first argument');
   }
 
   async searchResults(command, args) {
     const firstKeyword = args[1];
     if (firstKeyword == null) {
-      return this.client.chat.postEphemeral({
+      this.client.chat.postEphemeral({
         channel: command.channel_id,
         user: command.user_id,
         blocks: [
           this.generateMarkdownSectionBlock('*Input keywords.*\n Hint\n `/growi search [keyword]`'),
         ],
       });
+      throw new Error('/growi command:search: Invalid keyword');
     }
 
     // remove leading 'search'.
@@ -159,13 +166,13 @@ class BoltService {
 
     // no search results
     if (results.data.length === 0) {
-      return this.client.chat.postEphemeral({
+      logger.info(`No page found with "${keywords}"`);
+      this.client.chat.postEphemeral({
         channel: command.channel_id,
         user: command.user_id,
-        blocks: [
-          this.generateMarkdownSectionBlock('*No page that match your keywords.*'),
-        ],
+        blocks: [this.generateMarkdownSectionBlock('*No page that match your keywords.*')],
       });
+      return;
     }
 
     const resultPaths = results.data.map((data) => {
@@ -205,20 +212,26 @@ class BoltService {
           this.generateMarkdownSectionBlock('*Failed to search.*\n Hint\n `/growi search [keyword]`'),
         ],
       });
+      throw new Error('/growi command:search: Failed to search');
     }
   }
 
   async createModal(command, client, body) {
     const User = this.crowi.model('User');
+    const slackUser = await User.findUserByUsername('slackUser');
 
-    try {
-      const slackUser = await User.findUserByUsername('slackUser');
-
-      // if "slackUser" is null, don't show create Modal
-      if (slackUser == null) {
-        throw new Error('userNull');
-      }
+    // if "slackUser" is null, don't show create Modal
+    if (slackUser == null) {
+      logger.error('Failed to create a page because slackUser is not found.');
+      this.client.chat.postEphemeral({
+        channel: command.channel_id,
+        user: command.user_id,
+        blocks: [this.generateMarkdownSectionBlock('*slackUser does not exist.*')],
+      });
+      throw new Error('/growi command:create: slackUser is not found');
+    }
 
+    try {
       await client.views.open({
         trigger_id: body.trigger_id,
 
@@ -245,18 +258,8 @@ class BoltService {
         },
       });
     }
-    catch (e) {
-      if (e instanceof Error) {
-        return this.client.chat.postEphemeral({
-          channel: command.channel_id,
-          user: command.user_id,
-          blocks: [
-            this.generateMarkdownSectionBlock('*slackUser does not exist.*'),
-          ],
-        });
-      }
-
-      logger.error('Failed to create page.');
+    catch (err) {
+      logger.error('Failed to create a page.');
       await this.client.chat.postEphemeral({
         channel: command.channel_id,
         user: command.user_id,
@@ -264,6 +267,7 @@ class BoltService {
           this.generateMarkdownSectionBlock('*Failed to create new page.*\n Hint\n `/growi create`'),
         ],
       });
+      throw err;
     }
   }
 
@@ -285,10 +289,11 @@ class BoltService {
       path = pathUtils.normalizePath(path);
 
       const user = slackUser._id;
-      return Page.create(path, body, user, {});
+      await Page.create(path, body, user, {});
     }
-    catch {
+    catch (err) {
       logger.error('Failed to create page in GROWI.');
+      throw err;
     }
   }