botframework-webchat-core 4.14.0 → 4.15.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (67) hide show
  1. package/.eslintrc.yml +4 -198
  2. package/.prettierrc.yml +1 -1
  3. package/lib/actions/setNotification.js +1 -1
  4. package/lib/createPromiseQueue.js +1 -1
  5. package/lib/createStore.d.ts.map +1 -1
  6. package/lib/createStore.js +5 -5
  7. package/lib/index.d.ts +2 -1
  8. package/lib/index.d.ts.map +1 -1
  9. package/lib/index.js +15 -3
  10. package/lib/reducers/activities.js +1 -1
  11. package/lib/reducers/clockSkewAdjustment.js +1 -1
  12. package/lib/reducers/lastTypingAt.js +1 -1
  13. package/lib/reducers/notifications.js +21 -14
  14. package/lib/reducers/typing.js +1 -1
  15. package/lib/sagas/connectSaga.js +14 -8
  16. package/lib/sagas/connectionStatusToNotificationSaga.js +1 -1
  17. package/lib/sagas/effects/forkPut.js +1 -1
  18. package/lib/sagas/markAllAsSpokenOnStopSpeakActivitySaga.js +1 -1
  19. package/lib/sagas/observeActivitySaga.js +1 -1
  20. package/lib/sagas/postActivitySaga.js +1 -1
  21. package/lib/sagas/queueIncomingActivitySaga.js +7 -3
  22. package/lib/sagas/sendMessageBackToPostActivitySaga.js +1 -1
  23. package/lib/sagas/sendTypingIndicatorOnSetSendBoxSaga.js +1 -1
  24. package/lib/sagas/speakActivityAndStartDictateOnIncomingActivityFromOthersSaga.js +1 -1
  25. package/lib/sagas/startSpeakActivityOnPostActivitySaga.js +1 -1
  26. package/lib/sagas/stopSpeakingActivityOnInputSaga.js +1 -1
  27. package/lib/sagas/submitSendBoxSaga.js +1 -1
  28. package/lib/selectors/combineSelectors.js +8 -3
  29. package/lib/types/external/DirectLineActivity.d.ts +1 -1
  30. package/lib/types/external/DirectLineActivity.d.ts.map +1 -1
  31. package/lib/types/external/DirectLineCardAction.d.ts +108 -1
  32. package/lib/types/external/DirectLineCardAction.d.ts.map +1 -1
  33. package/lib/utils/deleteKey.js +2 -3
  34. package/lib/utils/isForbiddenPropertyName.d.ts +2 -0
  35. package/lib/utils/isForbiddenPropertyName.d.ts.map +1 -0
  36. package/lib/utils/isForbiddenPropertyName.js +21 -0
  37. package/lib/utils/mime-wrapper.js +2 -4
  38. package/lib/utils/uniqueID.js +1 -1
  39. package/package.json +15 -22
  40. package/src/__tests__/detectSlowConnectionSaga.spec.js +1 -1
  41. package/src/__tests__/observeOnce.spec.js +3 -3
  42. package/src/actions/setNotification.js +8 -2
  43. package/src/createStore.ts +4 -4
  44. package/src/index.ts +2 -0
  45. package/src/reducers/notifications.js +22 -16
  46. package/src/sagas/connectSaga.js +9 -2
  47. package/src/sagas/connectionStatusToNotificationSaga.js +1 -1
  48. package/src/sagas/queueIncomingActivitySaga.js +40 -39
  49. package/src/sagas/sendMessageBackToPostActivitySaga.js +0 -1
  50. package/src/sagas/sendTypingIndicatorOnSetSendBoxSaga.js +1 -1
  51. package/src/sagas/speakActivityAndStartDictateOnIncomingActivityFromOthersSaga.js +1 -1
  52. package/src/sagas/startSpeakActivityOnPostActivitySaga.js +1 -1
  53. package/src/sagas/stopSpeakingActivityOnInputSaga.js +1 -1
  54. package/src/sagas/submitSendBoxSaga.js +1 -1
  55. package/src/selectors/combineSelectors.js +9 -1
  56. package/src/types/external/DirectLineActivity.ts +3 -1
  57. package/src/types/external/DirectLineCardAction.ts +125 -2
  58. package/src/utils/dateToLocaleISOString.chatham.spec.js +1 -0
  59. package/src/utils/dateToLocaleISOString.japan.spec.js +1 -0
  60. package/src/utils/dateToLocaleISOString.pacific.spec.js +1 -0
  61. package/src/utils/dateToLocaleISOString.utc.spec.js +2 -0
  62. package/src/utils/deleteKey.js +1 -3
  63. package/src/utils/isForbiddenPropertyName.spec.js +6 -0
  64. package/src/utils/isForbiddenPropertyName.ts +33 -0
  65. package/src/utils/mime-wrapper.js +1 -2
  66. package/src/utils/uniqueID.js +1 -6
  67. package/.eslintignore +0 -9
@@ -1,8 +1,16 @@
1
+ import isForbiddenPropertyName from '../utils/isForbiddenPropertyName';
2
+
1
3
  export default function combineSelectors(selectors) {
2
4
  if (Array.isArray(selectors)) {
3
5
  return state => selectors.reduce((combinedState, selector) => [...combinedState, selector(state)], []);
4
6
  }
5
7
 
6
8
  return state =>
7
- Object.keys(selectors).reduce((combinedState, key) => ({ ...combinedState, [key]: selectors[key](state) }), {});
9
+ Object.keys(selectors).reduce(
10
+ (combinedState, key) =>
11
+ // Mitigated through denylisting.
12
+ // eslint-disable-next-line security/detect-object-injection
13
+ isForbiddenPropertyName(key) ? combinedState : { ...combinedState, [key]: selectors[key](state) },
14
+ {}
15
+ );
8
16
  }
@@ -1,5 +1,7 @@
1
1
  // TODO: [P1] #3953 We should fully type it out.
2
2
 
3
- type DirectLineActivity = any;
3
+ // Until we fully typed out DirectLineActivity, we need to use "any" here.
4
+ // We only know the DirectLineActivity must be a map, and not other primitive types.
5
+ type DirectLineActivity = Exclude<any, [] | boolean | Function | number | string>;
4
6
 
5
7
  export default DirectLineActivity;
@@ -1,5 +1,128 @@
1
- // TODO: [P1] #3953 We should fully type it out.
1
+ type CardActionWithImageAndTitle =
2
+ | { image: string }
3
+ | { title: string }
4
+ | {
5
+ image: string;
6
+ title: string;
7
+ };
2
8
 
3
- type DirectLineCardAction = any;
9
+ /**
10
+ * A `call` action represents a telephone number that may be called.
11
+ *
12
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#call
13
+ */
14
+ type CallCardAction = CardActionWithImageAndTitle & {
15
+ type: 'call';
16
+ value: string;
17
+ };
18
+
19
+ /**
20
+ * A `downloadFile` action represents a hyperlink to be downloaded.
21
+ *
22
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#download-file-actions
23
+ */
24
+ type DownloadFileCardAction = CardActionWithImageAndTitle & {
25
+ type: 'downloadFile';
26
+ value: string;
27
+ };
28
+
29
+ /**
30
+ * An `imBack` action represents a text response that is added to the chat feed.
31
+ *
32
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#im-back
33
+ */
34
+ type IMBackCardAction = CardActionWithImageAndTitle & {
35
+ type: 'imBack';
36
+ value: string;
37
+ };
38
+
39
+ /**
40
+ * A `messageBack` action represents a text response to be sent via the chat system.
41
+ *
42
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#message-back
43
+ */
44
+ type MessageBackCardAction = CardActionWithImageAndTitle & {
45
+ displayText?: string;
46
+ text?: string;
47
+ type: 'messageBack';
48
+ value?: { [key: string]: any };
49
+ };
50
+
51
+ /**
52
+ * An `openUrl` action represents a hyperlink to be handled by the client.
53
+ *
54
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#open-url-actions
55
+ */
56
+ type OpenURLCardAction = CardActionWithImageAndTitle & {
57
+ type: 'openUrl';
58
+ value: string;
59
+ };
60
+
61
+ /**
62
+ * A `playAudio` action represents audio media that may be played.
63
+ *
64
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#play-audio
65
+ */
66
+ type PlayAudioCardAction = CardActionWithImageAndTitle & {
67
+ type: 'playAudio';
68
+ value: string;
69
+ };
70
+
71
+ /**
72
+ * A `playVideo` action represents video media that may be played.
73
+ *
74
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#play-video
75
+ */
76
+ type PlayVideoCardAction = CardActionWithImageAndTitle & {
77
+ type: 'playVideo';
78
+ value: string;
79
+ };
80
+
81
+ /**
82
+ * A `postBack` action represents a text response that is not added to the chat feed.
83
+ *
84
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#post-back
85
+ */
86
+ type PostBackCardAction = CardActionWithImageAndTitle & {
87
+ type: 'postBack';
88
+ value: any; // For legacy reason, postBack support any.
89
+ };
90
+
91
+ /**
92
+ * A `showImage` action represents an image that may be displayed.
93
+ *
94
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#show-image-file-actions
95
+ */
96
+ type ShowImageCardAction = CardActionWithImageAndTitle & {
97
+ type: 'showImage';
98
+ value: string;
99
+ };
100
+
101
+ /**
102
+ * A `signin` action represents a hyperlink to be handled by the client's signin system.
103
+ *
104
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#signin
105
+ */
106
+ type SignInCardAction = CardActionWithImageAndTitle & {
107
+ type: 'signin';
108
+ value: string;
109
+ };
110
+
111
+ /**
112
+ * A card action represents a clickable or interactive button for use within cards or as suggested actions. They are used to solicit input from users. Despite their name, card actions are not limited to use solely on cards.
113
+ *
114
+ * https://github.com/Microsoft/botframework-sdk/blob/main/specs/botframework-activity/botframework-activity.md#card-action
115
+ */
116
+ type DirectLineCardAction =
117
+ | CallCardAction
118
+ | DownloadFileCardAction
119
+ | IMBackCardAction
120
+ | MessageBackCardAction
121
+ | OpenURLCardAction
122
+ | PlayAudioCardAction
123
+ | PlayVideoCardAction
124
+ | PostBackCardAction
125
+ | ShowImageCardAction
126
+ | SignInCardAction;
4
127
 
5
128
  export default DirectLineCardAction;
@@ -6,6 +6,7 @@
6
6
  import dateToLocaleISOString from './dateToLocaleISOString';
7
7
 
8
8
  test('formatting a time in Chatham Islands timezone', () => {
9
+ // eslint-disable-next-line no-magic-numbers
9
10
  const date = new Date(Date.UTC(2000, 0, 1, 0, 12, 34, 567));
10
11
  const actual = dateToLocaleISOString(date);
11
12
 
@@ -6,6 +6,7 @@
6
6
  import dateToLocaleISOString from './dateToLocaleISOString';
7
7
 
8
8
  test('formatting a time in Japan timezone', () => {
9
+ // eslint-disable-next-line no-magic-numbers
9
10
  const date = new Date(Date.UTC(2000, 0, 1, 0, 12, 34, 567));
10
11
  const actual = dateToLocaleISOString(date);
11
12
 
@@ -6,6 +6,7 @@
6
6
  import dateToLocaleISOString from './dateToLocaleISOString';
7
7
 
8
8
  test('formatting a time in Pacific Standard Time timezone', () => {
9
+ // eslint-disable-next-line no-magic-numbers
9
10
  const date = new Date(Date.UTC(2000, 0, 1, 0, 12, 34, 567));
10
11
  const actual = dateToLocaleISOString(date);
11
12
 
@@ -6,6 +6,7 @@
6
6
  import dateToLocaleISOString from './dateToLocaleISOString';
7
7
 
8
8
  test('formatting a time in UTC timezone', () => {
9
+ // eslint-disable-next-line no-magic-numbers
9
10
  const date = new Date(Date.UTC(2000, 0, 1, 0, 12, 34, 567));
10
11
  const actual = dateToLocaleISOString(date);
11
12
 
@@ -13,6 +14,7 @@ test('formatting a time in UTC timezone', () => {
13
14
  });
14
15
 
15
16
  test('formatting a time in UTC timezone with zero milliseconds', () => {
17
+ // eslint-disable-next-line no-magic-numbers
16
18
  const date = new Date(Date.UTC(2000, 0, 1, 0, 12, 34, 0));
17
19
  const actual = dateToLocaleISOString(date);
18
20
 
@@ -1,11 +1,9 @@
1
- /* eslint no-unused-vars: ["error", { "varsIgnorePattern": "^deleted$" }] */
2
-
3
1
  export default function deleteKey(map, key) {
4
2
  if (!map) {
5
3
  return map;
6
4
  }
7
5
 
8
- const { [key]: deleted, ...nextMap } = map;
6
+ const { [key]: _deleted, ...nextMap } = map;
9
7
 
10
8
  return nextMap;
11
9
  }
@@ -0,0 +1,6 @@
1
+ import isForbiddenPropertyName from './isForbiddenPropertyName';
2
+
3
+ test('should forbid "__proto__"', () => expect(isForbiddenPropertyName('__proto__')).toBeTruthy());
4
+ test('should forbid "constructor"', () => expect(isForbiddenPropertyName('constructor')).toBeTruthy());
5
+ test('should forbid "prototype"', () => expect(isForbiddenPropertyName('prototype')).toBeTruthy());
6
+ test('should not forbid "abc"', () => expect(isForbiddenPropertyName('abc')).toBeFalsy());
@@ -0,0 +1,33 @@
1
+ let FORBIDDEN_PROPERTY_NAMES;
2
+
3
+ function getForbiddenPropertyNames(): string[] {
4
+ return (
5
+ FORBIDDEN_PROPERTY_NAMES ||
6
+ (FORBIDDEN_PROPERTY_NAMES = Object.freeze(
7
+ Array.from(
8
+ new Set([
9
+ // As-of writing, `Object.prototype` includes:
10
+ // __defineGetter__
11
+ // __defineSetter__
12
+ // __lookupGetter__
13
+ // __lookupSetter
14
+ // __proto__
15
+ // constructor
16
+ // hasOwnProperty
17
+ // isPrototypeOf
18
+ // propertyIsEnumerable
19
+ // toLocaleString
20
+ // toString
21
+ // valueOf
22
+ ...Object.getOwnPropertyNames(Object.prototype),
23
+
24
+ 'prototype'
25
+ ])
26
+ )
27
+ ))
28
+ );
29
+ }
30
+
31
+ export default function isForbiddenPropertyName(propertyName: string): boolean {
32
+ return getForbiddenPropertyNames().includes(propertyName);
33
+ }
@@ -1,5 +1,4 @@
1
- /* eslint no-undef: "off"*/
2
- /* eslint node/global-require: "off"*/
1
+ /* eslint no-undef: "off" */
3
2
 
4
3
  // We adopted the work from mime-wrapper, at https://github.com/marlon360/mime-wrapper.
5
4
 
@@ -3,10 +3,5 @@
3
3
  import random from 'math-random';
4
4
 
5
5
  export default function uniqueID() {
6
- return (
7
- Date.now() +
8
- random()
9
- .toString(36)
10
- .substr(2)
11
- );
6
+ return Date.now() + random().toString(36).substr(2);
12
7
  }
package/.eslintignore DELETED
@@ -1,9 +0,0 @@
1
- /src/__tests__/**/*
2
- /src/**/*.spec.js
3
- /src/**/*.spec.jsx
4
- /src/**/*.spec.ts
5
- /src/**/*.spec.tsx
6
- /src/**/*.test.js
7
- /src/**/*.test.jsx
8
- /src/**/*.test.ts
9
- /src/**/*.test.tsx