From 9efbecbbc749cbcf4e13eda593ed20a5be65d55b Mon Sep 17 00:00:00 2001 From: Dmytro Rudzik Date: Tue, 20 Mar 2018 15:19:35 +0200 Subject: [PATCH 1/2] parse links into adf nodes --- __tests__/adapter/replyLink.js | 68 ++++++++++++++++++++++++++++++++++ __tests__/adapter/sendLink.js | 57 ++++++++++++++++++++++++++++ lib/StrideAdapter.js | 43 ++++++++++++++++++--- package.json | 5 ++- 4 files changed, 166 insertions(+), 7 deletions(-) create mode 100644 __tests__/adapter/replyLink.js create mode 100644 __tests__/adapter/sendLink.js diff --git a/__tests__/adapter/replyLink.js b/__tests__/adapter/replyLink.js new file mode 100644 index 0000000..f4655ae --- /dev/null +++ b/__tests__/adapter/replyLink.js @@ -0,0 +1,68 @@ +const {Context, mocks, utils} = require('../helpers') +const context = new Context() + +beforeAll(() => context.begin()) +afterAll(() => context.end()) + +test('Adapter.reply sends message with parsed links to Stride and with user mention prepended', async () => { + const getTokenRequest = utils.waitForRequest(mocks.stride.listeners.getToken) + const sendMessageRequest = utils.waitForRequest(mocks.stride.listeners.sendMessage) + + context.app.adapter.reply({ + room: { + cloudId: mocks.stride.listeners.defaultCloudId, + conversationId: mocks.stride.listeners.defaultConversationId + }, + user: { + id: 'dummy-user-id' + } + }, ' test message https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif test https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif test ') + + await getTokenRequest + const res = await sendMessageRequest + expect(res.body).toEqual({ + 'body': { + 'content': [{ + 'content': [{ + 'attrs': { + 'id': 'dummy-user-id' + }, + 'type': 'mention' + }, { + 'text': ': ', + 'type': 'text' + }, { + 'text': ' test message ', + 'type': 'text' + }, { + 'marks': [{ + 'attrs': { + 'href': 'https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif' + }, + 'type': 'link' + }], + 'text': 'https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif', + 'type': 'text' + }, { + 'text': ' test ', + 'type': 'text' + }, { + 'marks': [{ + 'attrs': { + 'href': 'https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif' + }, + 'type': 'link' + }], + 'text': 'https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif', + 'type': 'text' + }, { + 'text': ' test ', + 'type': 'text' + }], + 'type': 'paragraph' + }], + 'type': 'doc', + 'version': 1 + } + }) +}) diff --git a/__tests__/adapter/sendLink.js b/__tests__/adapter/sendLink.js new file mode 100644 index 0000000..c91a14f --- /dev/null +++ b/__tests__/adapter/sendLink.js @@ -0,0 +1,57 @@ +const {Context, mocks, utils} = require('../helpers') +const context = new Context() + +beforeAll(() => context.begin()) +afterAll(() => context.end()) + +test('Adapter.send sends message with parsed links to Stride', async () => { + const getTokenRequest = utils.waitForRequest(mocks.stride.listeners.getToken) + const sendMessageRequest = utils.waitForRequest(mocks.stride.listeners.sendMessage) + + context.app.adapter.send({ + room: { + cloudId: mocks.stride.listeners.defaultCloudId, + conversationId: mocks.stride.listeners.defaultConversationId + } + }, ' test message https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif test https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif test ') + + await getTokenRequest + const res = await sendMessageRequest + expect(res.body).toEqual({ + 'body': { + 'content': [{ + 'content': [{ + 'text': ' test message ', + 'type': 'text' + }, { + 'marks': [{ + 'attrs': { + 'href': 'https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif' + }, + 'type': 'link' + }], + 'text': 'https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif', + 'type': 'text' + }, { + 'text': ' test ', + 'type': 'text' + }, { + 'marks': [{ + 'attrs': { + 'href': 'https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif' + }, + 'type': 'link' + }], + 'text': 'https://media.giphy.com/media/dTJd5ygpxkzWo/giphy.gif', + 'type': 'text' + }, { + 'text': ' test ', + 'type': 'text' + }], + 'type': 'paragraph' + }], + 'type': 'doc', + 'version': 1 + } + }) +}) diff --git a/lib/StrideAdapter.js b/lib/StrideAdapter.js index 9652de2..cf78184 100644 --- a/lib/StrideAdapter.js +++ b/lib/StrideAdapter.js @@ -2,8 +2,10 @@ const {Adapter} = require('hubot') const Promise = require('bluebird') const config = require('./common/config') const components = require('./components') -const { Document } = require('adf-builder') +const { Document, Paragraph } = require('adf-builder') const sc = require('./common/net/Stride')() +const { extractUrlsWithIndices } = require('twitter-text') +const _ = require('lodash') class StrideAdapter extends Adapter { constructor (robot, options) { @@ -64,8 +66,8 @@ class StrideAdapter extends Adapter { const doc = new Document() messages.forEach(msg => { - doc.paragraph() - .text(msg) + const paragraph = doc.paragraph() + this._textToParsedParagraph(msg, paragraph) }) sc.sendMessage(envelope.room.cloudId, envelope.room.conversationId, doc) @@ -79,10 +81,11 @@ class StrideAdapter extends Adapter { const doc = new Document() messages.forEach(msg => { - doc.paragraph() + const paragraph = doc.paragraph() + paragraph .mention(userId) .text(': ') - .text(msg) + this._textToParsedParagraph(msg, paragraph) }) sc.sendMessage(envelope.room.cloudId, envelope.room.conversationId, doc) @@ -90,6 +93,36 @@ class StrideAdapter extends Adapter { this.robot.emit('error', error) }) } + + _textToParsedParagraph (text, paragraph) { + const urlsWithIndices = extractUrlsWithIndices(text) + + const plainIndices = urlsWithIndices.reduce((acc, urlIndex) => { + acc.push(urlIndex.indices[0]) + acc.push(urlIndex.indices[1]) + return acc + }, [0]) + plainIndices.push(text.length) + + plainIndices.forEach((item, currIndex) => { + const nextItem = plainIndices[currIndex + 1] + if (nextItem) { + if (currIndex % 2) { + const nodeText = text.slice(item, nextItem) + if (nodeText) { + paragraph.link(nodeText, nodeText) + } + } else { + const nodeText = text.slice(item, nextItem) + if (nodeText) { + paragraph.text(nodeText) + } + } + } + }) + + return paragraph + } } function invokeReduce (order, funcName, acc) { diff --git a/package.json b/package.json index 1537828..8b3997b 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "hubot-stride", - "version": "1.0.4", + "version": "1.0.5", "description": "Hubot adapter for Atlassian Stride", "main": "lib/web.js", "directories": { @@ -55,7 +55,8 @@ "jsonwebtoken": "^8.1.1", "lodash": "^4.17.5", "node-fetch": "^2.0.0", - "require-directory": "^2.1.1" + "require-directory": "^2.1.1", + "twitter-text": "^2.0.4" }, "jest": { "testPathIgnorePatterns": [ From 3a4ee8b5f31572ac681eab81d2b14d483a8ff909 Mon Sep 17 00:00:00 2001 From: Dmytro Rudzik Date: Tue, 20 Mar 2018 15:45:50 +0200 Subject: [PATCH 2/2] remove unused imports --- lib/StrideAdapter.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/lib/StrideAdapter.js b/lib/StrideAdapter.js index cf78184..1089ec4 100644 --- a/lib/StrideAdapter.js +++ b/lib/StrideAdapter.js @@ -2,10 +2,9 @@ const {Adapter} = require('hubot') const Promise = require('bluebird') const config = require('./common/config') const components = require('./components') -const { Document, Paragraph } = require('adf-builder') +const { Document } = require('adf-builder') const sc = require('./common/net/Stride')() const { extractUrlsWithIndices } = require('twitter-text') -const _ = require('lodash') class StrideAdapter extends Adapter { constructor (robot, options) {