From 55985951928e5ff433268e8cbcc6772d51dc6e80 Mon Sep 17 00:00:00 2001 From: Zhipeng Wang Date: Fri, 10 Jul 2020 17:12:27 +0800 Subject: [PATCH 1/7] add locale userid and username support --- src/directLine.ts | 32 +++++++++++++++++++++++++++++++- 1 file changed, 31 insertions(+), 1 deletion(-) diff --git a/src/directLine.ts b/src/directLine.ts index 3f6ca9744..f43628f8f 100644 --- a/src/directLine.ts +++ b/src/directLine.ts @@ -370,7 +370,10 @@ export interface DirectLineOptions { streamUrl?: string, timeout?: number, // Attached to all requests to identify requesting agent. - botAgent?: string + botAgent?: string, + locale?: string, + userid?: string, + username?: string } export interface Services { @@ -470,6 +473,10 @@ export class DirectLine implements IBotConnection { private timeout = 20 * 1000; private retries: number; + private locale: string; + private userid: string; + private username:string; + private pollingInterval: number = 1000; //ms private tokenRefreshSubscription: Subscription; @@ -479,6 +486,18 @@ export class DirectLine implements IBotConnection { this.token = options.secret || options.token; this.webSocket = (options.webSocket === undefined ? true : options.webSocket) && typeof WebSocket !== 'undefined' && WebSocket !== undefined; + if (options.locale) { + this.locale = options.locale; + } + + if (options.userid) { + this.userid = options.userid; + } + + if (options.username) { + this.username = options.username; + } + if (options.domain) { this.domain = options.domain; } @@ -617,12 +636,23 @@ export class DirectLine implements IBotConnection { ? `${this.domain}/conversations/${this.conversationId}?watermark=${this.watermark}` : `${this.domain}/conversations`; const method = this.conversationId ? "GET" : "POST"; + const body = this.conversationId + ? null + : { + user: { + id: this.userid, + name: this.username + }, + locale: this.locale + }; return this.services.ajax({ method, url, + body, timeout: this.timeout, headers: { "Accept": "application/json", + "Content-Type": "application/json", ...this.commonHeaders() } }) From cb44dca77aaa6f30b20f3ef78e85fbc241b9a171 Mon Sep 17 00:00:00 2001 From: Zhipeng Wang Date: Mon, 13 Jul 2020 17:01:35 +0800 Subject: [PATCH 2/7] change to locale support only --- src/directLine.ts | 16 +--------------- 1 file changed, 1 insertion(+), 15 deletions(-) diff --git a/src/directLine.ts b/src/directLine.ts index f43628f8f..1a970b993 100644 --- a/src/directLine.ts +++ b/src/directLine.ts @@ -474,8 +474,6 @@ export class DirectLine implements IBotConnection { private retries: number; private locale: string; - private userid: string; - private username:string; private pollingInterval: number = 1000; //ms @@ -490,14 +488,6 @@ export class DirectLine implements IBotConnection { this.locale = options.locale; } - if (options.userid) { - this.userid = options.userid; - } - - if (options.username) { - this.username = options.username; - } - if (options.domain) { this.domain = options.domain; } @@ -637,12 +627,8 @@ export class DirectLine implements IBotConnection { : `${this.domain}/conversations`; const method = this.conversationId ? "GET" : "POST"; const body = this.conversationId - ? null + ? undefined : { - user: { - id: this.userid, - name: this.username - }, locale: this.locale }; return this.services.ajax({ From bcc90741efee08c2200c3abab93940a254388a76 Mon Sep 17 00:00:00 2001 From: Zhipeng Wang Date: Mon, 13 Jul 2020 17:03:53 +0800 Subject: [PATCH 3/7] remove unused parameters --- src/directLine.ts | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/directLine.ts b/src/directLine.ts index 1a970b993..bc2ce8f2f 100644 --- a/src/directLine.ts +++ b/src/directLine.ts @@ -371,9 +371,7 @@ export interface DirectLineOptions { timeout?: number, // Attached to all requests to identify requesting agent. botAgent?: string, - locale?: string, - userid?: string, - username?: string + locale?: string } export interface Services { From 1c78ba887ac3056b2bf43b1f0cce33ba9ace2eb0 Mon Sep 17 00:00:00 2001 From: Zhipeng Wang Date: Mon, 20 Jul 2020 12:42:51 +0800 Subject: [PATCH 4/7] change locale to conversationStartLocale --- src/directLine.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/directLine.ts b/src/directLine.ts index bc2ce8f2f..c09c32e3b 100644 --- a/src/directLine.ts +++ b/src/directLine.ts @@ -371,7 +371,7 @@ export interface DirectLineOptions { timeout?: number, // Attached to all requests to identify requesting agent. botAgent?: string, - locale?: string + conversationStartLocale?: string } export interface Services { @@ -482,8 +482,8 @@ export class DirectLine implements IBotConnection { this.token = options.secret || options.token; this.webSocket = (options.webSocket === undefined ? true : options.webSocket) && typeof WebSocket !== 'undefined' && WebSocket !== undefined; - if (options.locale) { - this.locale = options.locale; + if (options.conversationStartLocale) { + this.locale = options.conversationStartLocale; } if (options.domain) { From 341206286a5e51c65b7592d85593c0458093494e Mon Sep 17 00:00:00 2001 From: Zhipeng Wang Date: Wed, 22 Jul 2020 14:59:54 +0800 Subject: [PATCH 5/7] change to conversation start properties JSON --- src/directLine.ts | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/src/directLine.ts b/src/directLine.ts index c09c32e3b..b991c2849 100644 --- a/src/directLine.ts +++ b/src/directLine.ts @@ -371,7 +371,7 @@ export interface DirectLineOptions { timeout?: number, // Attached to all requests to identify requesting agent. botAgent?: string, - conversationStartLocale?: string + conversationStartProperties?: any } export interface Services { @@ -471,7 +471,7 @@ export class DirectLine implements IBotConnection { private timeout = 20 * 1000; private retries: number; - private locale: string; + private localeOnStartConversation: string; private pollingInterval: number = 1000; //ms @@ -482,8 +482,10 @@ export class DirectLine implements IBotConnection { this.token = options.secret || options.token; this.webSocket = (options.webSocket === undefined ? true : options.webSocket) && typeof WebSocket !== 'undefined' && WebSocket !== undefined; - if (options.conversationStartLocale) { - this.locale = options.conversationStartLocale; + if (options.conversationStartProperties) { + if (options.conversationStartProperties.locale) { + this.localeOnStartConversation = options.conversationStartProperties.locale; + } } if (options.domain) { @@ -627,8 +629,8 @@ export class DirectLine implements IBotConnection { const body = this.conversationId ? undefined : { - locale: this.locale - }; + locale: this.localeOnStartConversation + }; return this.services.ajax({ method, url, From 2168453e8e947bf4261924ce6ab0fcf73a6a036f Mon Sep 17 00:00:00 2001 From: Zhipeng Wang Date: Wed, 29 Jul 2020 17:54:21 +0800 Subject: [PATCH 6/7] change the test bot endpoint and add locale tests --- __tests__/happy.localeOnStartConversation.js | 88 +++++++++++++++++++ __tests__/happy.receiveAttachmentStreams.js | 4 +- __tests__/happy.uploadAttachmentStreams.js | 4 +- __tests__/happy.uploadAttachments.js | 4 +- __tests__/setup/createDirectLine.js | 6 +- ...nhappy.invalidLocaleOnStartConversation.js | 43 +++++++++ src/directLine.ts | 6 +- 7 files changed, 145 insertions(+), 10 deletions(-) create mode 100644 __tests__/happy.localeOnStartConversation.js create mode 100644 __tests__/unhappy.invalidLocaleOnStartConversation.js diff --git a/__tests__/happy.localeOnStartConversation.js b/__tests__/happy.localeOnStartConversation.js new file mode 100644 index 000000000..5f5e9d398 --- /dev/null +++ b/__tests__/happy.localeOnStartConversation.js @@ -0,0 +1,88 @@ +import 'dotenv/config'; + +import onErrorResumeNext from 'on-error-resume-next'; + +import { timeouts } from './constants.json'; +import * as createDirectLine from './setup/createDirectLine'; +import waitForBotToRespond from './setup/waitForBotToRespond'; + +describe('Happy path', () => { + let unsubscribes; + + beforeEach(() => unsubscribes = []); + afterEach(() => unsubscribes.forEach(fn => onErrorResumeNext(fn))); + + describe('should receive the welcome message from bot in English', () => { + let directLine; + + describe('using REST', () => { + beforeEach(() => jest.setTimeout(timeouts.rest)); + + test('without conversation start properties', async () => { + directLine = await createDirectLine.forREST({ token: true }); + }); + + test('without locale in conversation start properties', async () => { + directLine = await createDirectLine.forREST({ token: true }, { conversationStartProperties: {} }); + }); + + test('with locale "en-US" in conversation start properties', async () => { + directLine = await createDirectLine.forREST({ token: true }, { conversationStartProperties: { locale: 'en-US' } }); + }); + }); + + describe('using Web Socket', () => { + beforeEach(() => jest.setTimeout(timeouts.webSocket)); + + test('without conversation start properties', async () => { + directLine = await createDirectLine.forWebSocket({ token: true }); + }); + + test('without locale in conversation start properties', async () => { + directLine = await createDirectLine.forWebSocket({ token: true }, { conversationStartProperties: {} }); + }); + + test('with locale "en-US" in conversation start properties', async () => { + directLine = await createDirectLine.forWebSocket({ token: true }, { conversationStartProperties: { locale: 'en-US' } }); + }); + }); + + afterEach(async () => { + // If directLine object is undefined, that means the test is failing. + if (!directLine) { return; } + + unsubscribes.push(directLine.end.bind(directLine)); + + await waitForBotToRespond(directLine, ({ text }) => text === 'Welcome'); + }); + }); + + describe('should receive the welcome message from bot in Chinese', () => { + let directLine; + + describe('using REST', () => { + beforeEach(() => jest.setTimeout(timeouts.rest)); + + test('with locale "zh-CN" in conversation start properties', async () => { + directLine = await createDirectLine.forREST({ token: true }, { conversationStartProperties: { locale: 'zh-CN' } }); + }); + }); + + describe('using Web Socket', () => { + beforeEach(() => jest.setTimeout(timeouts.webSocket)); + + test('with locale "zh-CN" in conversation start properties', async () => { + directLine = await createDirectLine.forWebSocket({ token: true }, { conversationStartProperties: { locale: 'zh-CN' } }); + }); + }); + + afterEach(async () => { + // If directLine object is undefined, that means the test is failing. + if (!directLine) { return; } + + unsubscribes.push(directLine.end.bind(directLine)); + + await waitForBotToRespond(directLine, ({ text }) => text === '欢迎'); + }); + }); +}); diff --git a/__tests__/happy.receiveAttachmentStreams.js b/__tests__/happy.receiveAttachmentStreams.js index 0cde94354..ce29337b7 100644 --- a/__tests__/happy.receiveAttachmentStreams.js +++ b/__tests__/happy.receiveAttachmentStreams.js @@ -31,8 +31,8 @@ describe('Happy path', () => { unsubscribes.push(directLine.end.bind(directLine)); unsubscribes.push(await waitForConnected(directLine)); - let url1 = 'http://myasebot.azurewebsites.net/177KB.jpg'; - let url2 = 'http://myasebot.azurewebsites.net/100KB.jpg'; + let url1 = 'http://dljstestbot.azurewebsites.net/177KB.jpg'; + let url2 = 'http://dljstestbot.azurewebsites.net/100KB.jpg'; const activityFromUser = { text: 'attach ' + url1 + ' ' + url2, diff --git a/__tests__/happy.uploadAttachmentStreams.js b/__tests__/happy.uploadAttachmentStreams.js index a8240d885..386452d6f 100644 --- a/__tests__/happy.uploadAttachmentStreams.js +++ b/__tests__/happy.uploadAttachmentStreams.js @@ -34,10 +34,10 @@ describe('Happy path', () => { // DirectLine.postActivityWithAttachments support "contentUrl" only but not "content" attachments: [{ contentType: 'image/jpg', - contentUrl: 'http://myasebot.azurewebsites.net/177KB.jpg' + contentUrl: 'http://dljstestbot.azurewebsites.net/177KB.jpg' }, { contentType: 'image/jpg', - contentUrl: 'http://myasebot.azurewebsites.net/100KB.jpg' + contentUrl: 'http://dljstestbot.azurewebsites.net/100KB.jpg' }], text: 'Hello, World!', type: 'message', diff --git a/__tests__/happy.uploadAttachments.js b/__tests__/happy.uploadAttachments.js index f61d44193..9e9ff6c7d 100644 --- a/__tests__/happy.uploadAttachments.js +++ b/__tests__/happy.uploadAttachments.js @@ -53,11 +53,11 @@ describe('Happy path', () => { // DirectLine.postActivityWithAttachments support "contentUrl" only but not "content" attachments: [{ contentType: 'image/jpg', - contentUrl: 'http://myasebot.azurewebsites.net/177KB.jpg', + contentUrl: 'http://dljstestbot.azurewebsites.net/177KB.jpg', thumbnailUrl: 'data:image/png;base64,===177KB.jpg' }, { contentType: 'image/png', - contentUrl: 'http://myasebot.azurewebsites.net/100KB.jpg', + contentUrl: 'http://dljstestbot.azurewebsites.net/100KB.jpg', thumbnailUrl: 'data:image/png;base64,===100KB.jpb' }], text: 'Hello, World!', diff --git a/__tests__/setup/createDirectLine.js b/__tests__/setup/createDirectLine.js index 5812a5f8b..e99bc77a9 100644 --- a/__tests__/setup/createDirectLine.js +++ b/__tests__/setup/createDirectLine.js @@ -6,13 +6,13 @@ import { DirectLineStreaming } from '../../src/directLineStreaming'; const { DIRECT_LINE_SECRET, - STREAMING_EXTENSIONS_DOMAIN = 'https://myasebot.azurewebsites.net/.bot/v3/directline' + STREAMING_EXTENSIONS_DOMAIN = 'https://dljstestbot.azurewebsites.net/.bot/v3/directline' } = process.env; const DEFAULT_DOMAIN = 'https://directline.botframework.com/v3/directline'; async function fetchDirectLineToken() { - const res = await fetch('https://myasebot.azurewebsites.net/token/directline'); + const res = await fetch('https://dljstestbot.azurewebsites.net/token/directline'); if (res.ok) { return await res.json(); @@ -22,7 +22,7 @@ async function fetchDirectLineToken() { } async function fetchDirectLineStreamingExtensionsToken() { - const res = await fetch(`https://myasebot.azurewebsites.net/token/directlinease`); + const res = await fetch(`https://dljstestbot.azurewebsites.net/token/directlinease`); if (res.ok) { return await res.json(); diff --git a/__tests__/unhappy.invalidLocaleOnStartConversation.js b/__tests__/unhappy.invalidLocaleOnStartConversation.js new file mode 100644 index 000000000..d251078c2 --- /dev/null +++ b/__tests__/unhappy.invalidLocaleOnStartConversation.js @@ -0,0 +1,43 @@ +import 'dotenv/config'; + +import onErrorResumeNext from 'on-error-resume-next'; + +import { timeouts } from './constants.json'; +import * as createDirectLine from './setup/createDirectLine'; +import waitForBotToRespond from './setup/waitForBotToRespond'; + +describe('Unhappy path', () => { + let unsubscribes; + + beforeEach(() => unsubscribes = []); + afterEach(() => unsubscribes.forEach(fn => onErrorResumeNext(fn))); + + describe('should receive the welcome message from bot in English', () => { + let directLine; + + describe('using REST', () => { + beforeEach(() => jest.setTimeout(timeouts.rest)); + + test('with invalid locale in conversation start properties', async () => { + directLine = await createDirectLine.forREST({ token: true }, { conversationStartProperties: { locale: { x: 'test' } } }); + }); + }); + + describe('using Web Socket', () => { + beforeEach(() => jest.setTimeout(timeouts.webSocket)); + + test('with invalid locale in conversation start properties', async () => { + directLine = await createDirectLine.forWebSocket({ token: true }, { conversationStartProperties: { locale: { x: 'test' } } }); + }); + }); + + afterEach(async () => { + // If directLine object is undefined, that means the test is failing. + if (!directLine) { return; } + + unsubscribes.push(directLine.end.bind(directLine)); + + await waitForBotToRespond(directLine, ({ text }) => text === 'Welcome'); + }); + }); +}); diff --git a/src/directLine.ts b/src/directLine.ts index 769979b0e..111d230cb 100644 --- a/src/directLine.ts +++ b/src/directLine.ts @@ -483,7 +483,11 @@ export class DirectLine implements IBotConnection { if (options.conversationStartProperties) { if (options.conversationStartProperties.locale) { - this.localeOnStartConversation = options.conversationStartProperties.locale; + if (Object.prototype.toString.call(options.conversationStartProperties.locale) === "[object String]") { + this.localeOnStartConversation = options.conversationStartProperties.locale; + } else { + console.warn('DirectLineJS: conversationStartProperties.locale was ignored: the locale name may be a BCP 47 language tag'); + } } } From 8fd7dc9ca9cc7fb77247d833a0e72bd54080640d Mon Sep 17 00:00:00 2001 From: Zhipeng Wang Date: Wed, 5 Aug 2020 09:24:07 +0800 Subject: [PATCH 7/7] fixed comments --- src/directLine.ts | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/src/directLine.ts b/src/directLine.ts index 111d230cb..5545ab1c1 100644 --- a/src/directLine.ts +++ b/src/directLine.ts @@ -481,13 +481,11 @@ export class DirectLine implements IBotConnection { this.token = options.secret || options.token; this.webSocket = (options.webSocket === undefined ? true : options.webSocket) && typeof WebSocket !== 'undefined' && WebSocket !== undefined; - if (options.conversationStartProperties) { - if (options.conversationStartProperties.locale) { - if (Object.prototype.toString.call(options.conversationStartProperties.locale) === "[object String]") { - this.localeOnStartConversation = options.conversationStartProperties.locale; - } else { - console.warn('DirectLineJS: conversationStartProperties.locale was ignored: the locale name may be a BCP 47 language tag'); - } + if (options.conversationStartProperties && options.conversationStartProperties.locale) { + if (Object.prototype.toString.call(options.conversationStartProperties.locale) === '[object String]') { + this.localeOnStartConversation = options.conversationStartProperties.locale; + } else { + console.warn('DirectLineJS: conversationStartProperties.locale was ignored: the locale name may be a BCP 47 language tag'); } }