2023-08-04 3 2 (C) Questetra, Inc. (MIT License) This item posts a message to Slack. Blocks are available. この工程は、Slack にメッセージを投稿します。Blocks に対応しています。 https://support.questetra.com/bpmn-icons/service-task-slack-message-post/ https://support.questetra.com/ja/bpmn-icons/service-task-slack-message-post/ iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAAAAXNSR0IArs4c6QAABFBJREFUWEfN l39ME2cYx79vofwSEljXirCwLWOSYJRotjgnJDPZWNKjg4BYpDgnCCuYKCxmxLUu7pcJZupitmqY XTfFLRnaqeXqYibbXExIdNQ/tj+WLMvCEjPoGGABxULf5b3Sy7W9a0+zhd0f/aP3Ps/zeZ/fR7DE D1Fr31RgygrNh2pBsYmCrAXoYwDyFuUnAPI7AfWB4FtNqsbtueWZVaM7KYBRb8wnIN0UsALIUKMU wF0CnKCgPV6/989EMgkBjIYqKyh9H8AylYZjj82AkL3esYETSvKKANzDnIMStD+g4SgxQnGc/4vv kNMlC2A0cJ+DYuu/YVzUQfCFd4xvjNUZB6Dm5kUlRRj5ZUTUlZOXA41Gg6nxqYTMcp6IAliM+XEl LcyQa9iFzGUZmJ6cxrbVL6PhNTO2dG4BIQS8i4ejW1E8rJaQdmlOiAAs2wHya6KEaznQjNqOWpHv 1MFTgvGMrHBxzAfnUV1YkyxyMwAtjlSHCMDpuaMU6EwkXVZRhoPn3hOPeD+7hBctlUhJTRH/4wxV yQBAgA94P98lOIT9sCazEAyNq6lzBtHR0460jDSc+9CNtndb7xuA9YkUrUbHmpUAwBm4JkpxOha9 4PEVaHmrBfmP5ke9unc3CM9JDwb7B3Hx1oU4gFXrS9HU3YShr4dwofeirEcIwTZ+jO8LA+g5JwWa Y0/2/XQaeYZIt43Xs+eFThy5dDgKwLyyAWd+7kOqNlUQ6GnrwdXzP8QJE+AT3s+3CABGfdUwQNfG nhoY9QjZrfSwJDR3mZGemS4cCd4Lwv2RW/gv8jAvHd51REYF8Xn9A+sWAbi/JYNFPGz71IZnjRtk 7c/dmYOl1ILttu0w7TQJZxyvO6B/RI/63fViVbRteBWjI6NyOia8fv6hCABVumVxWTHWbFyNhfkF TI3fDt90LohrA9dEEZYrLFSjf4xBl6/DqmdKMTt9B5fPXEZoIaToQa+fD/vXqOdkAXbsfwV1u+pA NERwr/nJBnw81AvdCp1wq53rW4XbN7+5Q4y51NqkfxLW8nYEJgKyEFIA2RBIM1wuvr32XjTubUR2 brbiLRN0R2kI5JPw7G/9yMzOFJT7vvdh5vYsyk0bRWOsEZWVr0HhE4WKAM4DTrgdXyVOQqUyfPr5 p9D6TisCkwHYN9vReawrDsD1tgs21xsoWVcSZYTlzPB3PhyyHgINxUc4qgyVGlEs9j7nvjiAXH0u snKy8OOVGwo3lXdOVCNS24rlAKSz4ObVm7BttiuGQ/IiuhWzF2qG0Z6ju1FpqRT19B/rR421Bto0 rfAfc/tLBdVJAeKGUbgUk4/j5UXL4bx+UuiOLK6NpRZhMFVUV4iJaq/fnwxAfhwLEOElNOFGwUpu U91zuPLlIGYD4c2bTci0dC2uf3MjmXHlhSQiqWYlS25FIfFkltP/31L6X3jivtfyCMSSfpiIEEv5 aSZNpSX7OH3QjFcr9w829dcwn81r2gAAAABJRU5ErkJggg== { const auth = httpClient.createAuthSettingToken('Slack', 'Slack'); configs.putObject('conf_Token', auth); const channelDef = engine.createDataDefinition('チャンネル', 1, 'q_channel', 'STRING_TEXTFIELD'); engine.setData(channelDef, channel); configs.putObject('conf_Channel', channelDef); const threadDef = engine.createDataDefinition('スレッド', 2, 'q_thread', 'STRING_TEXTFIELD'); engine.setData(threadDef, thread); configs.putObject('conf_Thread', threadDef); configs.putObject('conf_ReplyBroadcast', replyBroadcast); configs.put('conf_Blocks', blocks === null ? '' : JSON.stringify(blocks)); configs.put('conf_Text', text); }; /** * POSTリクエストのテスト(チャット投稿) * @param {Object} request * @param request.url * @param request.method * @param request.contentType * @param request.body * @param channel * @param thread * @param blocks * @param text */ const assertPostRequest = ({url, method, contentType, body}, channel, thread, replyBroadcast, blocks, text) => { expect(url).toEqual('https://slack.com/api/chat.postMessage'); expect(method).toEqual('POST'); expect(contentType).toEqual('application/json; charset=UTF-8'); const bodyObj = JSON.parse(body); expect(bodyObj.channel).toEqual(channel); if (thread === null) { expect(bodyObj['thread_ts']).toEqual(undefined); expect(bodyObj['reply_broadcast']).toEqual(undefined); } else { expect(bodyObj['thread_ts']).toEqual(thread); expect(bodyObj['reply_broadcast']).toEqual(replyBroadcast); } if (blocks === null) { expect(bodyObj.blocks).toEqual(undefined); } else { expect(bodyObj.blocks).toEqual(blocks.blocks); } expect(bodyObj.text).toEqual(text); }; /** * POST リクエストのレスポンスを準備(チャット投稿) * @param channel * @param text * @return responseObj */ const preparePostResponse = (channel, text) => { return { "ok": true, "channel": `${channel}`, "ts": "1650857142.223299", "message": { "type": "message", "subtype": "bot_message", "text": `${text}`, "ts": "1650857142.223299", "bot_id": "B01JPAT1P4J" } }; }; /** * POST API リクエストでエラーになる場合(チャット投稿) */ test('POST Failed', () => { prepareConfigs('channel1', null, false, null, 'text1'); httpClient.setRequestHandler((request) => { assertPostRequest(request, 'channel1', null, false, null, 'text1'); return httpClient.createHttpResponse(200, 'application/json', JSON.stringify({ "ok": false, "error": "channel_not_found" })); }); try { main(); } catch (e) { expect(e.message).toEqual('response is not ok. error: channel_not_found'); } }); /** * チャット投稿成功の場合 * スレッド指定なし * Blocks 指定なし */ test('Success - no thread, no blocks', () => { prepareConfigs('channel2', null, false, null, 'text2'); httpClient.setRequestHandler((request) => { assertPostRequest(request, 'channel2', null, false, null, 'text2'); return httpClient.createHttpResponse(200, 'application/json', JSON.stringify(preparePostResponse('channel2', 'text2'))); }); main(); }); /** * チャット投稿成功の場合 * スレッド指定あり * Blocks 指定あり */ test('Success - with thread, with blocks', () => { const blocks = { "blocks": [ { "type": "section", "text": { "type": "plain_text", "text": "This is a plain text section block.", "emoji": true } }, { "type": "section", "text": { "type": "plain_text", "text": "This is a plain text section block.", "emoji": true } } ] }; prepareConfigs('channel3', 'thread3', false, blocks, 'text3'); httpClient.setRequestHandler((request) => { assertPostRequest(request, 'channel3', 'thread3', false, blocks, 'text3'); return httpClient.createHttpResponse(200, 'application/json', JSON.stringify(preparePostResponse('channel3', 'text3'))); }); main(); }); /** * チャット投稿成功の場合 * スレッド指定あり * reply_broadcast * Blocks 指定なし */ test('Success - with thread, reply_broadcast, no blocks', () => { prepareConfigs('channel4', 'thread4', true, null, 'text4'); httpClient.setRequestHandler((request) => { assertPostRequest(request, 'channel4', 'thread4', true, null, 'text4'); return httpClient.createHttpResponse(200, 'application/json', JSON.stringify(preparePostResponse('channel3', 'text3'))); }); main(); }); /** * Block Kit が不正な場合 */ test('Invalid Blocks - not JSON', () => { prepareConfigs('channel4', null, false, 'text', 'text4'); try { main(); } catch (e) { const errorMsg = `Block Kit must be JSON like below.\n{ "blocks": [...] }`; expect(e.message).toEqual(errorMsg); } }); /** * Block Kit が不正な場合 */ test('Invalid Blocks - root it not blocks', () => { prepareConfigs('channel5', null, false, {type: 'text'}, 'text5'); try { main(); } catch (e) { const errorMsg = `Block Kit must be JSON like below.\n{ "blocks": [...] }`; expect(e.message).toEqual(errorMsg); } }); /** * Text が不正な場合 */ test('Invalid Text - empty', () => { prepareConfigs('channel6', null, false, { 'blocks': [] }, ''); try { main(); } catch (e) { const errorMsg = `Markdown must not be blank.`; expect(e.message).toEqual(errorMsg); } }); /** * Channel が不正な場合 */ test('Invalid Channel - empty', () => { prepareConfigs(null, null, false, null, 'text7'); try { main(); } catch (e) { const errorMsg = `Channel must not be blank.`; expect(e.message).toEqual(errorMsg); } }); ]]>