@seamly/web-ui 20.7.0 → 20.8.0-beta.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 (226) hide show
  1. package/build/dist/lib/hooks.js +1 -1
  2. package/build/dist/lib/hooks.min.js +1 -1
  3. package/build/dist/lib/index.debug.js +945 -790
  4. package/build/dist/lib/index.debug.min.js +1 -1
  5. package/build/dist/lib/index.debug.min.js.LICENSE.txt +187 -131
  6. package/build/dist/lib/index.js +24800 -19606
  7. package/build/dist/lib/index.min.js +1 -1
  8. package/build/dist/lib/index.min.js.LICENSE.txt +38 -4
  9. package/build/dist/lib/standalone.js +32920 -26742
  10. package/build/dist/lib/standalone.min.js +1 -1
  11. package/build/dist/lib/standalone.min.js.LICENSE.txt +39 -0
  12. package/build/dist/lib/storage.js +2 -2
  13. package/build/dist/lib/storage.min.js +1 -1
  14. package/build/dist/lib/style-guide.js +8780 -7907
  15. package/build/dist/lib/style-guide.min.js +2 -1
  16. package/build/dist/lib/style-guide.min.js.LICENSE.txt +38 -0
  17. package/build/dist/lib/styles.css +1 -1
  18. package/build/dist/lib/utils.js +1 -2
  19. package/build/dist/lib/utils.min.js +1 -1
  20. package/package.json +19 -9
  21. package/src/icons/avatar_agent-32.svg +7 -0
  22. package/src/icons/avatar_bot-32.svg +6 -1
  23. package/src/javascripts/api/index.js +1 -1
  24. package/src/javascripts/{config.js → config.ts} +3 -1
  25. package/src/javascripts/config.types.ts +96 -0
  26. package/src/javascripts/domains/app/actions.ts +83 -0
  27. package/src/javascripts/domains/app/app.types.ts +3 -0
  28. package/src/javascripts/domains/app/hooks.js +3 -5
  29. package/src/javascripts/domains/app/selectors.ts +6 -0
  30. package/src/javascripts/domains/app/slice.ts +30 -0
  31. package/src/javascripts/domains/config/actions.ts +45 -0
  32. package/src/javascripts/domains/config/hooks.ts +19 -0
  33. package/src/javascripts/domains/config/selectors.ts +24 -0
  34. package/src/javascripts/domains/config/slice.ts +113 -0
  35. package/src/javascripts/domains/errors/index.js +13 -9
  36. package/src/javascripts/domains/forms/context.ts +14 -0
  37. package/src/javascripts/domains/forms/forms.types.ts +24 -0
  38. package/src/javascripts/domains/forms/{hooks.js → hooks.ts} +23 -26
  39. package/src/javascripts/domains/forms/{provider.js → provider.tsx} +20 -14
  40. package/src/javascripts/domains/forms/{selectors.js → selectors.ts} +7 -8
  41. package/src/javascripts/domains/forms/slice.ts +84 -0
  42. package/src/javascripts/domains/forms/utils.ts +15 -0
  43. package/src/javascripts/domains/i18n/actions.ts +24 -0
  44. package/src/javascripts/domains/i18n/{hooks.js → hooks.ts} +2 -2
  45. package/src/javascripts/domains/i18n/i18n.types.ts +6 -0
  46. package/src/javascripts/domains/i18n/selectors.ts +16 -0
  47. package/src/javascripts/domains/i18n/{reducer.js → slice.ts} +40 -37
  48. package/src/javascripts/domains/interrupt/{hooks.js → hooks.ts} +2 -2
  49. package/src/javascripts/domains/interrupt/{middleware.js → middleware.ts} +11 -8
  50. package/src/javascripts/domains/interrupt/selectors.ts +6 -0
  51. package/src/javascripts/domains/interrupt/slice.ts +40 -0
  52. package/src/javascripts/domains/options/middleware.js +9 -6
  53. package/src/javascripts/domains/redux/redux.types.ts +11 -0
  54. package/src/javascripts/domains/store/index.ts +53 -0
  55. package/src/javascripts/domains/store/slice.ts +642 -0
  56. package/src/javascripts/domains/store/store.types.ts +146 -0
  57. package/src/javascripts/domains/translations/components/chat-status.js +2 -2
  58. package/src/javascripts/domains/translations/components/options-button.js +1 -1
  59. package/src/javascripts/domains/translations/components/options-dialog/form.js +5 -5
  60. package/src/javascripts/domains/translations/components/options-dialog/index.js +2 -2
  61. package/src/javascripts/domains/translations/hooks.ts +114 -0
  62. package/src/javascripts/domains/translations/middleware.js +29 -27
  63. package/src/javascripts/domains/translations/selectors.ts +12 -0
  64. package/src/javascripts/domains/translations/slice.ts +120 -0
  65. package/src/javascripts/domains/translations/translations.types.ts +19 -0
  66. package/src/javascripts/domains/visibility/{actions.js → actions.ts} +25 -19
  67. package/src/javascripts/domains/visibility/{hooks.js → hooks.ts} +13 -10
  68. package/src/javascripts/domains/visibility/{selectors.js → selectors.ts} +3 -6
  69. package/src/javascripts/domains/visibility/slice.ts +38 -0
  70. package/src/javascripts/domains/visibility/utils.js +0 -9
  71. package/src/javascripts/domains/visibility/visibility.types.ts +6 -0
  72. package/src/javascripts/index.ts +92 -0
  73. package/src/javascripts/lib/engine/index.js +15 -11
  74. package/src/javascripts/lib/external-api/initialize-api.js +1 -1
  75. package/src/javascripts/lib/id.js +5 -8
  76. package/src/javascripts/lib/mutex.js +3 -1
  77. package/src/javascripts/lib/store/providers/cookie-storage.js +1 -1
  78. package/src/javascripts/lib/store/providers/session-storage.js +1 -1
  79. package/src/javascripts/package/hooks.js +2 -2
  80. package/src/javascripts/package/utils.js +0 -1
  81. package/src/javascripts/schema.ts +1448 -0
  82. package/src/javascripts/style-guide/components/app.js +6 -6
  83. package/src/javascripts/style-guide/components/static-core.js +87 -65
  84. package/src/javascripts/style-guide/components/view.js +4 -4
  85. package/src/javascripts/style-guide/state-helpers/index.js +5 -5
  86. package/src/javascripts/style-guide/states.js +67 -7
  87. package/src/javascripts/style-guide.ts +5 -0
  88. package/src/javascripts/ui/components/app-options/index.js +2 -4
  89. package/src/javascripts/ui/components/conversation/component-filter.js +1 -1
  90. package/src/javascripts/ui/components/conversation/conversation.js +11 -7
  91. package/src/javascripts/ui/components/conversation/event/card-message.js +2 -2
  92. package/src/javascripts/ui/components/conversation/event/carousel-component/components/controls.js +1 -1
  93. package/src/javascripts/ui/components/conversation/event/carousel-message/components/slide.js +1 -1
  94. package/src/javascripts/ui/components/conversation/event/carousel-message/index.js +2 -2
  95. package/src/javascripts/ui/components/conversation/event/choice-prompt.js +3 -3
  96. package/src/javascripts/ui/components/conversation/event/conversation-suggestions.js +19 -15
  97. package/src/javascripts/ui/components/conversation/event/cta.js +2 -2
  98. package/src/javascripts/ui/components/conversation/event/divider/variants/default.js +1 -1
  99. package/src/javascripts/ui/components/conversation/event/divider/variants/new-translation.js +44 -5
  100. package/src/javascripts/ui/components/conversation/event/event-participant.js +2 -2
  101. package/src/javascripts/ui/components/conversation/event/hooks/use-formatted-date.js +2 -2
  102. package/src/javascripts/ui/components/conversation/event/image-lightbox.js +1 -1
  103. package/src/javascripts/ui/components/conversation/event/image.js +6 -8
  104. package/src/javascripts/ui/components/conversation/event/participant.js +2 -2
  105. package/src/javascripts/ui/components/conversation/event/splash.js +4 -4
  106. package/src/javascripts/ui/components/conversation/event/text.js +2 -2
  107. package/src/javascripts/ui/components/conversation/event/translation.js +3 -3
  108. package/src/javascripts/ui/components/conversation/event/upload.js +3 -3
  109. package/src/javascripts/ui/components/conversation/event/video.js +2 -2
  110. package/src/javascripts/ui/components/conversation/message-container.js +4 -26
  111. package/src/javascripts/ui/components/core/seamly-api-context.js +1 -1
  112. package/src/javascripts/ui/components/core/seamly-core.js +15 -14
  113. package/src/javascripts/ui/components/core/seamly-event-subscriber.js +98 -92
  114. package/src/javascripts/ui/components/core/seamly-file-upload.js +20 -24
  115. package/src/javascripts/ui/components/core/seamly-initializer.js +1 -1
  116. package/src/javascripts/ui/components/core/seamly-instance-functions-loader.js +5 -4
  117. package/src/javascripts/ui/components/core/seamly-new-notifications.js +2 -2
  118. package/src/javascripts/ui/components/core/seamly-read-state.js +10 -17
  119. package/src/javascripts/ui/components/entry/deprecated-toggle-button.js +3 -3
  120. package/src/javascripts/ui/components/entry/entry-container.js +4 -6
  121. package/src/javascripts/ui/components/entry/text-entry/hooks.js +3 -3
  122. package/src/javascripts/ui/components/entry/text-entry/index.js +3 -2
  123. package/src/javascripts/ui/components/entry/text-entry/text-entry-form.js +6 -10
  124. package/src/javascripts/ui/components/entry/upload/file-upload-form.js +2 -2
  125. package/src/javascripts/ui/components/entry/upload/index.js +10 -9
  126. package/src/javascripts/ui/components/entry/upload-toggle.js +2 -2
  127. package/src/javascripts/ui/components/faq/faq.js +9 -7
  128. package/src/javascripts/ui/components/form-controls/file-input.js +1 -1
  129. package/src/javascripts/ui/components/form-controls/form.js +1 -1
  130. package/src/javascripts/ui/components/form-controls/input.js +1 -1
  131. package/src/javascripts/ui/components/form-controls/select.js +1 -1
  132. package/src/javascripts/ui/components/layout/agent-info.js +4 -4
  133. package/src/javascripts/ui/components/layout/chat-frame.js +3 -3
  134. package/src/javascripts/ui/components/layout/chat.js +11 -12
  135. package/src/javascripts/ui/components/layout/deprecated-app-frame.js +10 -9
  136. package/src/javascripts/ui/components/layout/header.js +1 -1
  137. package/src/javascripts/ui/components/layout/interrupt.js +23 -24
  138. package/src/javascripts/ui/components/layout/pre-chat-messages.js +11 -11
  139. package/src/javascripts/ui/components/layout/privacy-disclaimer.js +2 -2
  140. package/src/javascripts/ui/components/options/options-button.js +14 -10
  141. package/src/javascripts/ui/components/options/transcript/index.js +2 -2
  142. package/src/javascripts/ui/components/options/transcript/transcript-form.js +1 -1
  143. package/src/javascripts/ui/components/suggestions/index.js +14 -10
  144. package/src/javascripts/ui/components/view/deprecated-view.js +19 -16
  145. package/src/javascripts/ui/components/view/index.js +12 -12
  146. package/src/javascripts/ui/components/view/inline-view.js +2 -2
  147. package/src/javascripts/ui/components/view/window-view/collapse-button.js +3 -3
  148. package/src/javascripts/ui/components/view/window-view/index.js +13 -13
  149. package/src/javascripts/ui/components/view/window-view/window-open-button.js +13 -13
  150. package/src/javascripts/ui/components/warnings/idle-detach-warning.js +1 -1
  151. package/src/javascripts/ui/components/warnings/resume-conversation-prompt.js +1 -1
  152. package/src/javascripts/ui/components/widgets/lightbox.js +2 -2
  153. package/src/javascripts/ui/components/widgets/upload-progress.js +1 -1
  154. package/src/javascripts/ui/hooks/component-helper-hooks.js +1 -1
  155. package/src/javascripts/ui/hooks/file-upload-hooks.js +4 -6
  156. package/src/javascripts/ui/hooks/focus-helper-hooks.js +14 -12
  157. package/src/javascripts/ui/hooks/live-region-hooks.js +2 -0
  158. package/src/javascripts/ui/hooks/seamly-api-hooks.js +8 -3
  159. package/src/javascripts/ui/hooks/seamly-entry-hooks.js +28 -25
  160. package/src/javascripts/ui/hooks/seamly-hooks.js +25 -25
  161. package/src/javascripts/ui/hooks/seamly-option-hooks.js +17 -19
  162. package/src/javascripts/ui/hooks/seamly-state-hooks.js +20 -13
  163. package/src/javascripts/ui/hooks/use-seamly-chat.js +15 -25
  164. package/src/javascripts/ui/hooks/use-seamly-commands.js +46 -46
  165. package/src/javascripts/ui/hooks/use-seamly-idle-detach-countdown.js +22 -24
  166. package/src/javascripts/ui/hooks/use-seamly-resume-conversation-prompt.js +8 -9
  167. package/src/javascripts/ui/hooks/use-single-file-upload.js +4 -6
  168. package/src/javascripts/ui/hooks/utility-hooks.js +4 -4
  169. package/src/javascripts/ui/utils/form-utils.js +0 -145
  170. package/src/javascripts/ui/utils/general-utils.js +3 -4
  171. package/src/javascripts/ui/utils/seamly-utils.ts +73 -0
  172. package/src/stylesheets/5-components/_message-carousel.scss +10 -8
  173. package/webpack/config.common.js +16 -0
  174. package/webpack/config.dev.js +1 -0
  175. package/webpack/config.package.js +26 -5
  176. package/webpack/defaults.js +7 -2
  177. package/webpack/parts/babel-loader-browser-plugins.js +1 -0
  178. package/webpack/parts/dev-server.js +4 -3
  179. package/CHANGELOG.md +0 -791
  180. package/src/javascripts/domains/app/actions.js +0 -112
  181. package/src/javascripts/domains/app/index.js +0 -7
  182. package/src/javascripts/domains/app/reducer.js +0 -16
  183. package/src/javascripts/domains/app/selectors.js +0 -8
  184. package/src/javascripts/domains/app/utils.js +0 -4
  185. package/src/javascripts/domains/config/actions.js +0 -7
  186. package/src/javascripts/domains/config/hooks.js +0 -23
  187. package/src/javascripts/domains/config/index.js +0 -7
  188. package/src/javascripts/domains/config/reducer.js +0 -79
  189. package/src/javascripts/domains/config/selectors.js +0 -23
  190. package/src/javascripts/domains/config/utils.js +0 -4
  191. package/src/javascripts/domains/forms/actions.js +0 -21
  192. package/src/javascripts/domains/forms/context.js +0 -6
  193. package/src/javascripts/domains/forms/index.js +0 -8
  194. package/src/javascripts/domains/forms/reducer.js +0 -84
  195. package/src/javascripts/domains/forms/utils.js +0 -20
  196. package/src/javascripts/domains/i18n/actions.js +0 -20
  197. package/src/javascripts/domains/i18n/index.js +0 -7
  198. package/src/javascripts/domains/i18n/selectors.js +0 -15
  199. package/src/javascripts/domains/i18n/utils.js +0 -4
  200. package/src/javascripts/domains/interrupt/actions.js +0 -4
  201. package/src/javascripts/domains/interrupt/index.js +0 -9
  202. package/src/javascripts/domains/interrupt/reducer.js +0 -22
  203. package/src/javascripts/domains/interrupt/selectors.js +0 -6
  204. package/src/javascripts/domains/interrupt/utils.js +0 -4
  205. package/src/javascripts/domains/options/index.js +0 -1
  206. package/src/javascripts/domains/redux/context.js +0 -6
  207. package/src/javascripts/domains/redux/create-redux-store.js +0 -21
  208. package/src/javascripts/domains/redux/hooks.js +0 -80
  209. package/src/javascripts/domains/redux/index.js +0 -19
  210. package/src/javascripts/domains/redux/provider.js +0 -5
  211. package/src/javascripts/domains/redux/utils.js +0 -12
  212. package/src/javascripts/domains/store/index.js +0 -46
  213. package/src/javascripts/domains/store/state-reducer.js +0 -56
  214. package/src/javascripts/domains/translations/actions.js +0 -11
  215. package/src/javascripts/domains/translations/hooks.js +0 -103
  216. package/src/javascripts/domains/translations/index.js +0 -10
  217. package/src/javascripts/domains/translations/reducer.js +0 -69
  218. package/src/javascripts/domains/translations/selectors.js +0 -16
  219. package/src/javascripts/domains/translations/utils.js +0 -4
  220. package/src/javascripts/domains/visibility/index.js +0 -8
  221. package/src/javascripts/domains/visibility/reducer.js +0 -24
  222. package/src/javascripts/index.js +0 -153
  223. package/src/javascripts/lib/redux-helpers/index.js +0 -99
  224. package/src/javascripts/style-guide.js +0 -5
  225. package/src/javascripts/ui/hooks/use-seamly-dispatch.js +0 -3
  226. package/src/javascripts/ui/utils/seamly-utils.js +0 -832
@@ -1,112 +0,0 @@
1
- import { actionTypes, seamlyActions } from 'ui/utils/seamly-utils'
2
- import * as ConfigActions from 'domains/config/actions'
3
- import * as I18nActions from 'domains/i18n/actions'
4
- import * as TranslationActions from 'domains/translations/actions'
5
- import * as VisibilityActions from 'domains/visibility/actions'
6
- import SeamlyUnavailableError from 'api/errors/seamly-unavailable-error'
7
- import SeamlySessionExpiredError from 'api/errors/seamly-session-expired-error'
8
- import * as InterruptActions from 'domains/interrupt/actions'
9
- import { createAction, createThunk } from './utils'
10
-
11
- export const setHasResponded = createAction(
12
- 'setHasResponded',
13
- (hasResponded) => ({ hasResponded }),
14
- )
15
-
16
- export const initialize = createThunk(
17
- 'initialize',
18
- async (_, { dispatch, extra: { api, config } }) => {
19
- dispatch(ConfigActions.initialize(config))
20
- let locale = config?.context?.locale
21
-
22
- try {
23
- const {
24
- features,
25
- defaultLocale,
26
- preChat,
27
- agentParticipant,
28
- userParticipant,
29
- startChatIcon,
30
- } = await api.getConfig()
31
-
32
- dispatch({ type: seamlyActions.SET_FEATURES, features })
33
- locale = locale || defaultLocale
34
- dispatch(I18nActions.setInitialLocale(locale))
35
- dispatch(
36
- ConfigActions.setPreChatEvents(
37
- preChat.map((payload) => ({ type: 'message', payload })),
38
- ),
39
- )
40
- dispatch(
41
- ConfigActions.update({
42
- agentParticipant,
43
- userParticipant,
44
- startChatIcon,
45
- }),
46
- )
47
-
48
- if (agentParticipant?.name) {
49
- dispatch({
50
- type: seamlyActions.SET_HEADER_SUB_TITLE,
51
- title: agentParticipant.name,
52
- })
53
- }
54
- } catch (e) {
55
- throw new SeamlyUnavailableError()
56
- }
57
-
58
- try {
59
- if (api.hasConversation()) {
60
- const initialState = await api.getConversationIntitialState()
61
- dispatch({ type: seamlyActions.SET_INITIAL_STATE, initialState })
62
-
63
- locale = initialState.translation?.locale || locale
64
-
65
- if ('userResponded' in initialState) {
66
- dispatch(setHasResponded(initialState.userResponded))
67
- }
68
- } else {
69
- if (config?.context?.topic) {
70
- api.send('action', {
71
- type: actionTypes.setTopic,
72
- body: {
73
- name: config.context.topic,
74
- // Separate fallback message is not needed here. Only an attached service will use this, but none will
75
- // be attached before the conversation has started (meaning the fallback message will never be shown).
76
- fallbackMessage: config.context.topic,
77
- },
78
- })
79
- }
80
- if (config?.context?.translationLocale) {
81
- locale = config.context.translationLocale
82
- api.send('action', {
83
- type: actionTypes.setTranslation,
84
- body: { enabled: true, locale },
85
- })
86
- dispatch(TranslationActions.enable(locale))
87
- }
88
- }
89
- } catch (e) {
90
- if (e instanceof SeamlySessionExpiredError) {
91
- throw e
92
- }
93
- throw new SeamlyUnavailableError()
94
- } finally {
95
- await dispatch(I18nActions.setLocale(locale))
96
- dispatch(VisibilityActions.initialize())
97
- }
98
- },
99
- )
100
-
101
- export const reset = createThunk(
102
- 'reset',
103
- async (config, { dispatch, extra: { api } }) => {
104
- try {
105
- await api.disconnect()
106
- await api.clearStore()
107
- dispatch(initialize())
108
- } catch (error) {
109
- dispatch(InterruptActions.set(error))
110
- }
111
- },
112
- )
@@ -1,7 +0,0 @@
1
- import * as Actions from './actions'
2
- import * as Selectors from './selectors'
3
-
4
- export * from './hooks'
5
- export { default as Reducer } from './reducer'
6
-
7
- export { Actions, Selectors }
@@ -1,16 +0,0 @@
1
- import { createReducer } from './utils'
2
- import * as Actions from './actions'
3
-
4
- const initialState = {
5
- userHasResponded: false,
6
- }
7
-
8
- export default createReducer(
9
- {
10
- [Actions.setHasResponded]: (state, { hasResponded }) => ({
11
- ...state,
12
- userHasResponded: hasResponded,
13
- }),
14
- },
15
- initialState,
16
- )
@@ -1,8 +0,0 @@
1
- import { createSelector } from 'reselect'
2
- import { selectState } from './utils'
3
-
4
- export const selectUserHasResponded = createSelector(
5
- selectState,
6
- (state) => state.userHasResponded,
7
- )
8
- export { selectState }
@@ -1,4 +0,0 @@
1
- import { createDomain } from 'lib/redux-helpers'
2
-
3
- export const { createAction, createThunk, createReducer, selectState } =
4
- createDomain('app')
@@ -1,7 +0,0 @@
1
- import { createAction } from './utils'
2
-
3
- export const initialize = createAction('initialize', (config) => ({ config }))
4
- export const update = createAction('update', (config) => ({ config }))
5
- export const setPreChatEvents = createAction('setPreChatEvents', (events) => ({
6
- events,
7
- }))
@@ -1,23 +0,0 @@
1
- import { useSelector } from 'domains/redux'
2
- import * as Selectors from './selectors'
3
-
4
- export function useConfig() {
5
- return useSelector(Selectors.selectConfig)
6
- }
7
-
8
- export function useParticipants() {
9
- const { agentParticipant, userParticipant } = useSelector(
10
- Selectors.selectConfig,
11
- )
12
-
13
- return {
14
- agent: agentParticipant,
15
- user: userParticipant,
16
- }
17
- }
18
-
19
- export function useStartChatIcon() {
20
- const { startChatIcon } = useSelector(Selectors.selectConfig)
21
-
22
- return startChatIcon
23
- }
@@ -1,7 +0,0 @@
1
- import * as Actions from './actions'
2
- import * as Selectors from './selectors'
3
-
4
- export * from './hooks'
5
- export { default as Reducer } from './reducer'
6
-
7
- export { Actions, Selectors }
@@ -1,79 +0,0 @@
1
- import { defaultConfig } from 'config'
2
- import { pick } from 'ui/utils/general-utils'
3
- import * as AppActions from 'domains/app/actions'
4
- import { createReducer } from './utils'
5
- import * as Actions from './actions'
6
-
7
- const initialState = {
8
- ...defaultConfig,
9
- hideOnNoUserResponse: false,
10
- connectWhenInView: true,
11
- showDisclaimer: false,
12
- showFaq: false,
13
- customComponents: {},
14
- defaults: {},
15
- preChatEvents: [],
16
- }
17
-
18
- const configKeys = [
19
- 'hideOnNoUserResponse',
20
- 'connectWhenInView',
21
- 'showDisclaimer',
22
- 'showFaq',
23
- 'namespace',
24
- 'customComponents',
25
- 'defaults',
26
- 'layoutMode',
27
- 'api',
28
- 'zIndex',
29
- 'context',
30
- 'appContainerClassNames',
31
- 'messages',
32
- 'visible',
33
- 'visibilityCallback',
34
- 'errorCallback',
35
- 'agentParticipant',
36
- 'userParticipant',
37
- 'startChatIcon',
38
- ]
39
-
40
- const updateState = (state, { config }) => {
41
- const { messages, ...partialConfig } = pick(config, configKeys)
42
- let newState = state
43
- if (Object.keys(partialConfig).length > 0) {
44
- newState = {
45
- ...newState,
46
- ...partialConfig,
47
- }
48
- }
49
- if (messages) {
50
- newState = {
51
- ...newState,
52
- messages: {
53
- ...newState.messages,
54
- ...messages,
55
- },
56
- }
57
- }
58
-
59
- return newState
60
- }
61
-
62
- export default createReducer(
63
- {
64
- [Actions.initialize]: (state, action) => {
65
- return updateState(state, action)
66
- },
67
- [Actions.update]: (state, action) => {
68
- return updateState(state, action)
69
- },
70
- [AppActions.initialize.pending]: () => initialState,
71
- [Actions.setPreChatEvents]: (state, { events }) => {
72
- return {
73
- ...state,
74
- preChatEvents: events,
75
- }
76
- },
77
- },
78
- initialState,
79
- )
@@ -1,23 +0,0 @@
1
- import { createSelector } from 'reselect'
2
- import { visibilityStates } from 'domains/visibility/constants'
3
- import { selectState } from './utils'
4
-
5
- export const selectConfig = createSelector(selectState, (config) => {
6
- let newConfig = {
7
- visible:
8
- config?.layoutMode === 'inline'
9
- ? visibilityStates.open
10
- : visibilityStates.minimized,
11
- appContainerClassNames: config.appContainerClassNames || [],
12
- ...config,
13
- }
14
- if (typeof newConfig.appContainerClassNames === 'function') {
15
- newConfig = {
16
- ...newConfig,
17
- appContainerClassNames: newConfig.appContainerClassNames(newConfig),
18
- }
19
- }
20
- return newConfig
21
- })
22
-
23
- export { selectState }
@@ -1,4 +0,0 @@
1
- import { createDomain } from 'lib/redux-helpers'
2
-
3
- export const { createAction, createThunk, createReducer, selectState } =
4
- createDomain('config')
@@ -1,21 +0,0 @@
1
- import { createActions } from './utils'
2
-
3
- export const [registerForm, deregisterForm] = createActions('form', {
4
- register: (formId, persistData) => ({ formId, persistData }),
5
- deregister: (formId) => ({ formId }),
6
- })
7
-
8
- export const [
9
- registerControl,
10
- deregisterControl,
11
- updateControlValue,
12
- updateControlTouched,
13
- ] = createActions('control', {
14
- register: (formId, name) => ({
15
- formId,
16
- name,
17
- }),
18
- deregister: (formId, name) => ({ formId, name }),
19
- updateValue: (formId, name, value) => ({ formId, name, value }),
20
- updateTouched: (formId, name, touched) => ({ formId, name, touched }),
21
- })
@@ -1,6 +0,0 @@
1
- import { createContext } from 'preact'
2
-
3
- const FormContext = createContext({})
4
-
5
- export default FormContext
6
- export const { Provider, Consumer } = FormContext
@@ -1,8 +0,0 @@
1
- import * as Actions from './actions'
2
- import * as Selectors from './selectors'
3
-
4
- export * from './hooks'
5
- export { default as FormProvider } from './provider'
6
- export { default as Reducer } from './reducer'
7
-
8
- export { Actions, Selectors }
@@ -1,84 +0,0 @@
1
- import * as AppActions from 'domains/app/actions'
2
- import { createReducer } from './utils'
3
- import * as Actions from './actions'
4
-
5
- const initialState = {}
6
-
7
- const initialFormState = {
8
- controls: {},
9
- }
10
-
11
- const initialControlState = {
12
- value: '',
13
- touched: false,
14
- }
15
-
16
- function updateFormControl(state, formId, name, controlState) {
17
- const currentControlState =
18
- state[formId]?.controls[name] || initialControlState
19
- return {
20
- ...state,
21
- [formId]: {
22
- ...state[formId],
23
- controls: {
24
- ...state[formId].controls,
25
- [name]: {
26
- ...currentControlState,
27
- ...controlState,
28
- },
29
- },
30
- },
31
- }
32
- }
33
-
34
- export default createReducer(
35
- {
36
- // Form handlers
37
- [Actions.registerForm]: (state, { formId, persistData }) => {
38
- const formState = persistData
39
- ? state[formId] ?? { ...initialFormState, persistData }
40
- : { ...initialFormState, persistData }
41
- return {
42
- ...state,
43
- [formId]: formState,
44
- }
45
- },
46
- [Actions.deregisterForm]: (state, { formId }) => {
47
- const newState = { ...state }
48
- if (!newState[formId]?.persistData) {
49
- delete newState[formId]
50
- }
51
- return newState
52
- },
53
- // Form control handlers
54
- [Actions.registerControl]: (state, { name, formId }) => {
55
- return updateFormControl(state, formId, name)
56
- },
57
- [Actions.deregisterControl]: (state, { formId, name }) => {
58
- const form = state[formId]
59
- if (!form) {
60
- return state
61
- }
62
- if (form.persistData) {
63
- return state
64
- }
65
- const controls = { ...form.controls }
66
- delete controls[name]
67
- return {
68
- ...state,
69
- [formId]: {
70
- ...form,
71
- controls,
72
- },
73
- }
74
- },
75
- [Actions.updateControlValue]: (state, { formId, name, value }) => {
76
- return updateFormControl(state, formId, name, { value })
77
- },
78
- [Actions.updateControlTouched]: (state, { formId, name, touched }) => {
79
- return updateFormControl(state, formId, name, { touched })
80
- },
81
- [AppActions.initialize.pending]: () => initialState,
82
- },
83
- initialState,
84
- )
@@ -1,20 +0,0 @@
1
- import { createDomain } from 'lib/redux-helpers'
2
-
3
- export const { createActions, createReducer, selectState } =
4
- createDomain('forms')
5
-
6
- export function validate(values, schema = {}) {
7
- return Object.entries(schema).reduce((errors, [key, validations]) => {
8
- if (validations && !Array.isArray(validations)) {
9
- // eslint-disable-next-line no-param-reassign
10
- validations = [validations]
11
- }
12
- for (let i = 0; i < validations?.length ?? 0; i++) {
13
- if (!validations[i].fn(values[key], validations[i].compareValue)) {
14
- errors[key] = validations[i].errorText
15
- break
16
- }
17
- }
18
- return errors
19
- }, {})
20
- }
@@ -1,20 +0,0 @@
1
- import createMutex from 'lib/mutex'
2
- import { selectLocale } from './selectors'
3
- import { createAction, createThunk } from './utils'
4
-
5
- export const setInitialLocale = createAction('setInitialLocale', (locale) => ({
6
- locale,
7
- }))
8
-
9
- const mutex = createMutex()
10
- export const setLocale = createThunk(
11
- 'setLocale',
12
- async (locale, { getState, extra: { api } }) => {
13
- return mutex.runExclusively(() => {
14
- if (locale === selectLocale(getState())) {
15
- return undefined
16
- }
17
- return api.getTranslations(locale)
18
- })
19
- },
20
- )
@@ -1,7 +0,0 @@
1
- import * as Actions from './actions'
2
- import * as Selectors from './selectors'
3
-
4
- export * from './hooks'
5
- export { default as Reducer } from './reducer'
6
-
7
- export { Actions, Selectors }
@@ -1,15 +0,0 @@
1
- import { createSelector } from 'reselect'
2
- import { selectState } from './utils'
3
-
4
- export const selectTranslations = createSelector(
5
- selectState,
6
- (state) => state.translations,
7
- )
8
-
9
- export const selectInitialLocale = createSelector(
10
- selectState,
11
- (state) => state.initialLocale,
12
- )
13
- export const selectLocale = createSelector(selectState, (state) => state.locale)
14
-
15
- export { selectState }
@@ -1,4 +0,0 @@
1
- import { createDomain } from 'lib/redux-helpers'
2
-
3
- export const { createAction, createThunk, createReducer, selectState } =
4
- createDomain('i18n')
@@ -1,4 +0,0 @@
1
- import { createAction } from './utils'
2
-
3
- export const set = createAction('set', (error) => ({ error }))
4
- export const clear = createAction('clear')
@@ -1,9 +0,0 @@
1
- import * as Actions from './actions'
2
- import * as Selectors from './selectors'
3
-
4
- export * from './hooks'
5
-
6
- export { default as createMiddleware } from './middleware'
7
- export { default as Reducer } from './reducer'
8
-
9
- export { Actions, Selectors }
@@ -1,22 +0,0 @@
1
- import * as AppActions from 'domains/app/actions'
2
- import { createReducer } from './utils'
3
- import * as Actions from './actions'
4
-
5
- const initialState = {
6
- error: undefined,
7
- }
8
-
9
- const handleError = (state, { error }) => ({
10
- ...state,
11
- error,
12
- })
13
-
14
- export default createReducer(
15
- {
16
- [Actions.set]: handleError,
17
- [AppActions.initialize.rejected]: handleError,
18
- [Actions.clear]: () => initialState,
19
- [AppActions.initialize.pending]: () => initialState,
20
- },
21
- initialState,
22
- )
@@ -1,6 +0,0 @@
1
- import { createSelector } from 'reselect'
2
- import { selectState } from './utils'
3
-
4
- export const selectError = createSelector(selectState, ({ error }) => error)
5
-
6
- export { selectState }
@@ -1,4 +0,0 @@
1
- import { createDomain } from 'lib/redux-helpers'
2
-
3
- export const { createAction, createReducer, selectState } =
4
- createDomain('interrupt')
@@ -1 +0,0 @@
1
- export { default as createMiddleware } from './middleware'
@@ -1,6 +0,0 @@
1
- import { createContext } from 'preact'
2
-
3
- const StoreContext = createContext(undefined)
4
-
5
- export default StoreContext
6
- export const { Provider, Consumer } = StoreContext
@@ -1,21 +0,0 @@
1
- import { combineReducers, createStore, applyMiddleware, compose } from 'redux'
2
-
3
- let composeEnhancers = compose
4
- if (process.env.NODE_ENV === 'development') {
5
- /* eslint-disable no-underscore-dangle */
6
- composeEnhancers =
7
- window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || composeEnhancers
8
- /* eslint-enable no-underscore-dangle */
9
- }
10
-
11
- export default function createReduxStore({
12
- reducers = {},
13
- initialState = {},
14
- middlewares = [],
15
- } = {}) {
16
- return createStore(
17
- combineReducers(reducers),
18
- initialState,
19
- composeEnhancers(applyMiddleware(...middlewares)),
20
- )
21
- }
@@ -1,80 +0,0 @@
1
- import {
2
- useCallback,
3
- useContext,
4
- useLayoutEffect,
5
- useReducer,
6
- useRef,
7
- } from 'preact/hooks'
8
- import StoreContext from './context'
9
- // import { arrayContentEquals } from './utils'
10
-
11
- export function useStoreContext() {
12
- return useContext(StoreContext)
13
- }
14
-
15
- export function useStoreDispatch() {
16
- return useStoreContext().dispatch
17
- }
18
-
19
- export function useSelector(selector, deps = []) {
20
- const store = useStoreContext()
21
- // we need a force-update because we're manually updating a ref instead of a useState
22
- const [, forceUpdate] = useReducer((x) => x + 1, 0)
23
- // we're keeping the value to compare against
24
- const valueRef = useRef()
25
-
26
- // instead of accepting a stabilized selector, we stick to the signature
27
- // of useCallback, as that makes the exposed api much more dev-friendly
28
- // otherwise you'd have to stabilize selectors externally
29
- // eslint-disable-next-line react-hooks/exhaustive-deps
30
- const selectorCb = useCallback(selector, deps)
31
- // we're keeping the selector in a ref to compare against
32
- // we need this both in the store subscription and for
33
- // synchronous state updates if the selector changes, but the store didn't
34
- // if the selector changes, we want to synchronously select the new information
35
- // otherwise, the rendered component does not accurately and predictably reflect
36
- // the selector+state
37
- // in order to keep multiple selectors in sync, we also re-calculate when
38
- // the state has changed but the selector hasn't re-calculated async.
39
- // selectors *might* be heavy, which could kill FPS, but the alternative is
40
- // stale data
41
- const selectorRef = useRef()
42
- const stateRef = useRef()
43
- const state = store.getState()
44
- if (selectorRef.current !== selectorCb || stateRef.current !== state) {
45
- stateRef.current = state
46
- valueRef.current = selectorCb(stateRef.current)
47
- selectorRef.current = selectorCb
48
- }
49
-
50
- useLayoutEffect(() => {
51
- // we subscribe to the store changes
52
- return store.subscribe(() => {
53
- const newState = store.getState()
54
- // prevent recalculating if the state hasn't changed
55
- // if the selector changed, it was already handled synchronously
56
- if (newState === stateRef.current) {
57
- return
58
- }
59
- // calculate the new value based on selector+state
60
- const newValue = selectorRef.current?.(store.getState())
61
- // only if the value changed we update. this saves heaps of re-rendering
62
- if (newValue !== valueRef.current) {
63
- valueRef.current = newValue
64
- forceUpdate()
65
- }
66
- })
67
- }, [store])
68
- return valueRef.current
69
- }
70
-
71
- export const useSelectorWithProps = function useSelectorWithProps(
72
- selector,
73
- props,
74
- inputs = [],
75
- // equalityFn = arrayContentEquals,
76
- ) {
77
- // eslint-disable-next-line react-hooks/exhaustive-deps
78
- const wrappedMapper = useCallback((state) => selector(state, props), inputs)
79
- return useSelector(wrappedMapper, inputs)
80
- }