@capillarytech/creatives-library 8.0.236-alpha.4 → 8.0.236-beta.0
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.
- package/HOW_BEE_EDITOR_WORKS.md +375 -0
- package/assets/Android.png +0 -0
- package/assets/iOS.png +0 -0
- package/constants/unified.js +2 -1
- package/initialReducer.js +0 -2
- package/package.json +1 -1
- package/services/api.js +5 -5
- package/services/tests/api.test.js +0 -18
- package/utils/common.js +7 -1
- package/utils/commonUtils.js +1 -14
- package/utils/tests/commonUtil.test.js +0 -224
- package/utils/transformTemplateConfig.js +10 -0
- package/v2Components/CapDeviceContent/index.js +56 -61
- package/v2Components/CapTagList/index.js +2 -5
- package/v2Components/CapTagListWithInput/index.js +5 -1
- package/v2Components/CapTagListWithInput/messages.js +1 -1
- package/v2Components/CapWhatsappCTA/tests/index.test.js +0 -5
- package/v2Components/ErrorInfoNote/style.scss +1 -1
- package/v2Components/HtmlEditor/HTMLEditor.js +123 -136
- package/v2Components/HtmlEditor/__tests__/HTMLEditor.test.js +0 -532
- package/v2Components/HtmlEditor/__tests__/index.lazy.test.js +12 -17
- package/v2Components/HtmlEditor/_htmlEditor.scss +0 -2
- package/v2Components/HtmlEditor/_index.lazy.scss +1 -0
- package/v2Components/HtmlEditor/components/CodeEditorPane/_codeEditorPane.scss +12 -0
- package/v2Components/HtmlEditor/components/CodeEditorPane/index.js +109 -24
- package/v2Components/HtmlEditor/components/DeviceToggle/_deviceToggle.scss +1 -2
- package/v2Components/HtmlEditor/components/DeviceToggle/index.js +3 -3
- package/v2Components/HtmlEditor/components/FullscreenModal/_fullscreenModal.scss +0 -1
- package/v2Components/HtmlEditor/components/InAppPreviewPane/DeviceFrame.js +7 -4
- package/v2Components/HtmlEditor/components/InAppPreviewPane/__tests__/DeviceFrame.test.js +45 -35
- package/v2Components/HtmlEditor/components/InAppPreviewPane/_inAppPreviewPane.scss +3 -1
- package/v2Components/HtmlEditor/components/InAppPreviewPane/constants.js +33 -33
- package/v2Components/HtmlEditor/components/InAppPreviewPane/index.js +6 -7
- package/v2Components/HtmlEditor/components/SplitContainer/_splitContainer.scss +1 -1
- package/v2Components/HtmlEditor/constants.js +20 -29
- package/v2Components/HtmlEditor/hooks/__tests__/useInAppContent.test.js +16 -360
- package/v2Components/HtmlEditor/hooks/useEditorContent.js +5 -2
- package/v2Components/HtmlEditor/hooks/useInAppContent.js +146 -57
- package/v2Components/HtmlEditor/index.js +1 -1
- package/v2Components/HtmlEditor/messages.js +85 -85
- package/v2Components/MobilePushPreviewV2/index.js +7 -32
- package/v2Components/TemplatePreview/_templatePreview.scss +21 -41
- package/v2Components/TemplatePreview/index.js +32 -47
- package/v2Components/TemplatePreview/messages.js +0 -4
- package/v2Components/TestAndPreviewSlidebox/index.js +31 -25
- package/v2Containers/BeeEditor/index.js +80 -82
- package/v2Containers/CreativesContainer/SlideBoxContent.js +117 -104
- package/v2Containers/CreativesContainer/SlideBoxFooter.js +9 -3
- package/v2Containers/CreativesContainer/SlideBoxHeader.js +1 -2
- package/v2Containers/CreativesContainer/constants.js +0 -1
- package/v2Containers/CreativesContainer/index.js +96 -76
- package/v2Containers/CreativesContainer/messages.js +4 -0
- package/v2Containers/CreativesContainer/tests/__snapshots__/SlideBoxContent.test.js.snap +12 -4
- package/v2Containers/CreativesContainer/tests/__snapshots__/index.test.js.snap +0 -15
- package/v2Containers/Email/actions.js +7 -0
- package/v2Containers/Email/constants.js +5 -1
- package/v2Containers/Email/index.js +13 -0
- package/v2Containers/Email/messages.js +32 -0
- package/v2Containers/Email/reducer.js +12 -1
- package/v2Containers/Email/sagas.js +17 -0
- package/v2Containers/EmailWrapper/components/EmailHTMLEditor.js +1034 -0
- package/v2Containers/EmailWrapper/components/EmailWrapperView.js +193 -7
- package/v2Containers/EmailWrapper/components/HTMLEditorTesting.js +74 -40
- package/v2Containers/EmailWrapper/components/__tests__/HTMLEditorTesting.test.js +67 -2
- package/v2Containers/EmailWrapper/constants.js +2 -0
- package/v2Containers/EmailWrapper/hooks/useEmailWrapper.js +436 -67
- package/v2Containers/EmailWrapper/index.js +99 -23
- package/v2Containers/EmailWrapper/messages.js +61 -1
- package/v2Containers/EmailWrapper/tests/EmailHTMLEditor.test.js +177 -0
- package/v2Containers/EmailWrapper/tests/EmailHTMLEditorValidation.test.js +90 -0
- package/v2Containers/EmailWrapper/tests/useEmailWrapper.test.js +49 -49
- package/v2Containers/InApp/actions.js +0 -7
- package/v2Containers/InApp/constants.js +4 -19
- package/v2Containers/InApp/index.js +354 -751
- package/v2Containers/InApp/index.scss +3 -4
- package/v2Containers/InApp/messages.js +3 -7
- package/v2Containers/InApp/reducer.js +3 -21
- package/v2Containers/InApp/sagas.js +9 -29
- package/v2Containers/InApp/selectors.js +5 -25
- package/v2Containers/InApp/tests/index.test.js +50 -154
- package/v2Containers/InApp/tests/reducer.test.js +0 -34
- package/v2Containers/InApp/tests/sagas.test.js +9 -61
- package/v2Containers/Line/Container/ImageCarousel/tests/__snapshots__/content.test.js.snap +0 -3
- package/v2Containers/Line/Container/ImageCarousel/tests/__snapshots__/index.test.js.snap +0 -2
- package/v2Containers/Line/Container/Wrapper/tests/__snapshots__/index.test.js.snap +0 -2
- package/v2Containers/Line/Container/tests/__snapshots__/index.test.js.snap +0 -9
- package/v2Containers/Rcs/tests/__snapshots__/index.test.js.snap +0 -12
- package/v2Containers/SmsTrai/Edit/tests/__snapshots__/index.test.js.snap +0 -4
- package/v2Containers/TagList/index.js +3 -65
- package/v2Containers/Templates/_templates.scss +1 -60
- package/v2Containers/Templates/index.js +9 -89
- package/v2Containers/Templates/messages.js +0 -4
- package/v2Containers/Whatsapp/tests/__snapshots__/index.test.js.snap +0 -35
- package/v2Containers/BeePopupEditor/constants.js +0 -10
- package/v2Containers/BeePopupEditor/index.js +0 -181
- package/v2Containers/BeePopupEditor/tests/index.test.js +0 -627
- package/v2Containers/InApp/__tests__/InAppHTMLEditor.test.js +0 -376
- package/v2Containers/InApp/__tests__/sagas.test.js +0 -363
- package/v2Containers/InApp/tests/selectors.test.js +0 -612
- package/v2Containers/InAppWrapper/components/InAppWrapperView.js +0 -162
- package/v2Containers/InAppWrapper/components/__tests__/InAppWrapperView.test.js +0 -267
- package/v2Containers/InAppWrapper/components/inAppWrapperView.scss +0 -9
- package/v2Containers/InAppWrapper/constants.js +0 -16
- package/v2Containers/InAppWrapper/hooks/__tests__/useInAppWrapper.test.js +0 -473
- package/v2Containers/InAppWrapper/hooks/useInAppWrapper.js +0 -198
- package/v2Containers/InAppWrapper/index.js +0 -148
- package/v2Containers/InAppWrapper/messages.js +0 -49
- package/v2Containers/InappAdvance/index.js +0 -1032
- package/v2Containers/InappAdvance/index.scss +0 -10
- package/v2Containers/InappAdvance/tests/index.test.js +0 -448
|
@@ -0,0 +1,375 @@
|
|
|
1
|
+
Tracing how the BEE editor is loaded in the Email create and edit flows. Searching the codebase for relevant code.
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
[5 tools called]
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
Reviewing key files to understand the flow:
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
[4 tools called]
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
Reviewing how BEE editor gets initialized with token and JSON data:
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
[4 tools called]
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
Reviewing the edit flow initialization:
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
[1 tool called]
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
## How BEE Editor is Loaded in Email Create and Edit Flows
|
|
26
|
+
|
|
27
|
+
### Overview
|
|
28
|
+
The BEE editor loads via a multi-step process that fetches CMS settings (token and JSON) and renders the editor component when conditions are met.
|
|
29
|
+
|
|
30
|
+
---
|
|
31
|
+
|
|
32
|
+
## CREATE FLOW
|
|
33
|
+
|
|
34
|
+
### 1. Initial Setup (EmailWrapper)
|
|
35
|
+
Location: `app/v2Containers/EmailWrapper/hooks/useEmailWrapper.js`
|
|
36
|
+
|
|
37
|
+
- User selects "Use Editor" mode
|
|
38
|
+
- When step is `TEMPLATE_SELECTION` and templates are needed:
|
|
39
|
+
```223:230:app/v2Containers/EmailWrapper/hooks/useEmailWrapper.js
|
|
40
|
+
case STEPS.TEMPLATE_SELECTION:
|
|
41
|
+
const needsTemplates = emailCreateMode === EMAIL_CREATE_MODES.EDITOR
|
|
42
|
+
&& !CmsTemplates
|
|
43
|
+
&& !getCmsTemplatesInProgress;
|
|
44
|
+
|
|
45
|
+
if (needsTemplates) {
|
|
46
|
+
templatesActions.getDefaultBeeTemplates();
|
|
47
|
+
}
|
|
48
|
+
```
|
|
49
|
+
- User selects a template → `handleEdmDefaultTemplateSelection` is called
|
|
50
|
+
- Sets `selectedCreateMode` to `EDITOR` and stores the selected template
|
|
51
|
+
|
|
52
|
+
### 2. Email Component Initialization
|
|
53
|
+
Location: `app/v2Containers/Email/index.js`
|
|
54
|
+
|
|
55
|
+
In `componentWillMount`:
|
|
56
|
+
```208:219:app/v2Containers/Email/index.js
|
|
57
|
+
const isBEESupport = (this.props.location.query.isBEESupport !== "false") || false;
|
|
58
|
+
const isBEEAppEnable = this.checkBeeEditorAllowedForLibrary();
|
|
59
|
+
if (!_.isEmpty(this.props.Templates.BEETemplate)) {
|
|
60
|
+
if (this.props.Templates.BEETemplate.versions.base.is_drag_drop && isBEEAppEnable ) {
|
|
61
|
+
this.setState({isDragDrop: true});
|
|
62
|
+
}
|
|
63
|
+
if (this.props.params.id) {
|
|
64
|
+
this.props.actions.getCmsSetting(BEE_PLUGIN, _.get(this.props.Templates.BEETemplate, 'versions.base.drag_drop_id', this.props.Templates.BEETemplate?._id), 'open', undefined, isBEESupport, isBEEAppEnable);
|
|
65
|
+
} else if (this.props.location.query.module !== "library" || (this.props.location.query.module === "library" && !this.props.templateData)) {
|
|
66
|
+
this.props.actions.getCmsSetting(BEE_PLUGIN, _.get(this.props.Templates.BEETemplate, 'versions.base.drag_drop_id', this.props.Templates.BEETemplate?._id), 'create', undefined, isBEESupport, isBEEAppEnable);
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
- For create flow: calls `getCmsSetting` with `cmsMode: 'create'`
|
|
72
|
+
- This fetches the BEE token and settings from the API
|
|
73
|
+
|
|
74
|
+
### 3. Receiving CMS Settings
|
|
75
|
+
Location: `app/v2Containers/Email/index.js` - `componentWillReceiveProps`
|
|
76
|
+
|
|
77
|
+
When `CmsSettings` are received:
|
|
78
|
+
```379:419:app/v2Containers/Email/index.js
|
|
79
|
+
if (!_.isEmpty(nextProps.Email.CmsSettings) && !_.isEqual(this.props.Email.CmsSettings, nextProps.Email.CmsSettings) && !_.isEmpty(this.state.schema)) {
|
|
80
|
+
const apiLangId = nextProps.Email.CmsSettings.langId;
|
|
81
|
+
const langId = nextProps.Email.CmsSettings.langId !== "undefined" ? nextProps.Email.CmsSettings.langId : nextProps.currentOrgDetails.basic_details.base_language;
|
|
82
|
+
|
|
83
|
+
const formData = _.cloneDeep(this.state.formData);
|
|
84
|
+
|
|
85
|
+
const schema = _.cloneDeep(this.state.schema);
|
|
86
|
+
const langIndex = formData[this.state.currentTab - 1].selectedLanguages.indexOf(langId);
|
|
87
|
+
|
|
88
|
+
const temp = (schema.containers || {})[this.state.currentTab - 1];
|
|
89
|
+
|
|
90
|
+
const { currentTab } = this.state;
|
|
91
|
+
if (nextProps.Email.CmsSettings.isDragDrop && this.checkBeeEditorAllowedForLibrary()) {
|
|
92
|
+
const beeJson = `BEEeditor${currentTab > 1 ? currentTab : ''}json`;
|
|
93
|
+
const beeToken = `BEEeditor${currentTab > 1 ? currentTab : ''}token`;
|
|
94
|
+
let beeJsonValue = _.get(nextProps, 'Templates.BEETemplate.versions.base.json-content', '');
|
|
95
|
+
const selectedId = _.get(this.props, 'Email.templateDetails._id', '') || _.get(this.props, 'Templates.BEETemplate.versions.base.drag_drop_id', '');
|
|
96
|
+
if (this.state.isEdit) {
|
|
97
|
+
if (this.props.location.query.module === "library") {
|
|
98
|
+
beeJsonValue = _.get(this.state, `formData[${currentTab - 1}][${langId}].json-content`, '');
|
|
99
|
+
} else {
|
|
100
|
+
beeJsonValue = _.get(nextProps, `Email.templateDetails.versions.base[${langId}].json-content`, '');
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
formData[`${currentTab - 1}`][langId] = {
|
|
104
|
+
...formData[`${currentTab - 1}`][langId],
|
|
105
|
+
is_drag_drop: true,
|
|
106
|
+
[beeJson]: beeJsonValue,
|
|
107
|
+
[beeToken]: nextProps.Email.CmsSettings.tokenData,
|
|
108
|
+
id: selectedId,
|
|
109
|
+
};
|
|
110
|
+
_.forEach(temp.panes, (pane, index) => {
|
|
111
|
+
const tempPane = pane;
|
|
112
|
+
//
|
|
113
|
+
if (parseInt(index, 10) === parseInt(langIndex, 10)) {
|
|
114
|
+
//
|
|
115
|
+
tempPane.sections[0].inputFields[0].cols[1].colStyle = {display: ""};
|
|
116
|
+
tempPane.sections[0].inputFields[0].cols[0].colStyle = {display: "none"};
|
|
117
|
+
}
|
|
118
|
+
});
|
|
119
|
+
this.setState({schema, isSchemaChanged: true, loadingStatus: this.state.loadingStatus + 1});
|
|
120
|
+
```
|
|
121
|
+
|
|
122
|
+
- Stores `tokenData` and `json-content` in formData
|
|
123
|
+
- Updates schema to show BEE editor (hide CKEditor)
|
|
124
|
+
- Sets `is_drag_drop: true`
|
|
125
|
+
|
|
126
|
+
### 4. FormBuilder Renders BEE Editor
|
|
127
|
+
Location: `app/v2Components/FormBuilder/index.js`
|
|
128
|
+
|
|
129
|
+
When schema type is `"BEEeditor"`:
|
|
130
|
+
```3976:4027:app/v2Components/FormBuilder/index.js
|
|
131
|
+
case "BEEeditor": {
|
|
132
|
+
let langTab = 1;
|
|
133
|
+
if (val.id.match(/BEEeditor/g)) {
|
|
134
|
+
if (val.id.length > 9 && val.id.charAt(9)) {
|
|
135
|
+
langTab = val.id.charAt(9);
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
const { currentTab, formData } = this.state;
|
|
139
|
+
const supportedLanguages = (formData[currentTab - 1] || {}).selectedLanguages || {};
|
|
140
|
+
const currentLang = supportedLanguages[langTab - 1];
|
|
141
|
+
|
|
142
|
+
let beeJson = '',
|
|
143
|
+
beeToken = '',
|
|
144
|
+
uuid = '';
|
|
145
|
+
const data = formData[`${currentTab - 1}`][currentLang];
|
|
146
|
+
if (data) {
|
|
147
|
+
beeJson = data[`BEEeditor${currentTab > 1 ? currentTab : ''}json`];
|
|
148
|
+
beeToken = data[`BEEeditor${currentTab > 1 ? currentTab : ''}token`];
|
|
149
|
+
uuid = this.props.uuid;
|
|
150
|
+
}
|
|
151
|
+
if (!beeJson || !beeToken) {
|
|
152
|
+
return false;
|
|
153
|
+
}
|
|
154
|
+
let isModuleFilterEnabled = _.get(this.props.location, 'query.type', '') !== 'embedded';
|
|
155
|
+
const schemaChannel = _.get(this.props.schema, 'channel', "");
|
|
156
|
+
if (schemaChannel === 'EMAIL') {
|
|
157
|
+
isModuleFilterEnabled = this.props.isFullMode;
|
|
158
|
+
}
|
|
159
|
+
columns.push(
|
|
160
|
+
<CapColumn style={val.colStyle ? val.colStyle : {}} span={val.width} className={`${(this.state.liquidErrorMessage?.LIQUID_ERROR_MSG?.length || this.state.liquidErrorMessage?.STANDARD_ERROR_MSG?.length) && this.liquidFlow() && "error-boundary"}`}>
|
|
161
|
+
<BeeEditor
|
|
162
|
+
uid={uuid}
|
|
163
|
+
tokenData={beeToken}
|
|
164
|
+
id={val.id}
|
|
165
|
+
beeJson={beeJson}
|
|
166
|
+
showTagsPopover={this.showTagsPopover}
|
|
167
|
+
location={this.props.location}
|
|
168
|
+
label={val.label || ''}
|
|
169
|
+
className={val.className || ''}
|
|
170
|
+
userLocale={this.props.userLocale}
|
|
171
|
+
selectedOfferDetails={this.props.selectedOfferDetails}
|
|
172
|
+
tags={this.props.tags || []}
|
|
173
|
+
injectedTags={this.props.injectedTags ? this.props.injectedTags : {}}
|
|
174
|
+
saveBeeInstance={this.props.saveBeeInstance}
|
|
175
|
+
saveBeeData={this.props.saveBeeData}
|
|
176
|
+
onContextChange={this.props.onContextChange}
|
|
177
|
+
moduleFilterEnabled={isModuleFilterEnabled}
|
|
178
|
+
eventContextTags={this.props?.eventContextTags}
|
|
179
|
+
/>
|
|
180
|
+
</CapColumn>
|
|
181
|
+
);
|
|
182
|
+
}
|
|
183
|
+
```
|
|
184
|
+
|
|
185
|
+
- Extracts `beeJson` and `beeToken` from formData
|
|
186
|
+
- Renders `<BeeEditor>` with these props
|
|
187
|
+
|
|
188
|
+
### 5. BeeEditor Component Initialization
|
|
189
|
+
Location: `app/v2Containers/BeeEditor/index.js`
|
|
190
|
+
|
|
191
|
+
In `useEffect`:
|
|
192
|
+
```107:197:app/v2Containers/BeeEditor/index.js
|
|
193
|
+
useEffect(() => {
|
|
194
|
+
const beeConfig = {
|
|
195
|
+
uid,
|
|
196
|
+
container: 'bee-plugin-container',
|
|
197
|
+
translationsUrl: defaultFormattedUrl,
|
|
198
|
+
rowsConfiguration: {
|
|
199
|
+
emptyRows: true,
|
|
200
|
+
defaultRows: true,
|
|
201
|
+
externalContentURLs: getExternalContentURLs(),
|
|
202
|
+
},
|
|
203
|
+
contentDialog: {
|
|
204
|
+
specialLinks: {
|
|
205
|
+
label: UNSUBSCRIBE,
|
|
206
|
+
handler(resolve) {
|
|
207
|
+
resolve({
|
|
208
|
+
type: 'custom',
|
|
209
|
+
label: UNSUBSCRIBE,
|
|
210
|
+
link: `{{${UNSUBSCRIBE}}}`,
|
|
211
|
+
});
|
|
212
|
+
},
|
|
213
|
+
},
|
|
214
|
+
mergeTags: {
|
|
215
|
+
label: formatMessage(messages.addLabel),
|
|
216
|
+
handler: async (resolve, reject) => {
|
|
217
|
+
// this will open tag modal
|
|
218
|
+
await setVisibleTaglist(true);
|
|
219
|
+
// until tag modal will not open promise will not execute
|
|
220
|
+
// once tag modal is opened it will start 2 sec interval to wait use has selected any tag or cancel the tag selection
|
|
221
|
+
const promise = new Promise((resolveP) => {
|
|
222
|
+
intervalTimer = setInterval(() => {
|
|
223
|
+
// this will execute, if user cancel the tag selection
|
|
224
|
+
if ((savedCallback.current || {}).close === true) {
|
|
225
|
+
reject();
|
|
226
|
+
clearInterval(intervalTimer);
|
|
227
|
+
return;
|
|
228
|
+
}
|
|
229
|
+
// this block is checking use has selected any tag or not
|
|
230
|
+
if (Object.keys(savedCallback.current || {}).length > 0) {
|
|
231
|
+
resolveP(savedCallback.current);
|
|
232
|
+
setSelectedTag({});
|
|
233
|
+
clearInterval(intervalTimer);
|
|
234
|
+
}
|
|
235
|
+
}, 2000);
|
|
236
|
+
});
|
|
237
|
+
// once prmise will resolve , pass the resolve data to handler to show tags in bee edior
|
|
238
|
+
const result = await promise;
|
|
239
|
+
resolve(result);
|
|
240
|
+
},
|
|
241
|
+
},
|
|
242
|
+
saveRow: {
|
|
243
|
+
handler: async (resolve, reject) => {
|
|
244
|
+
await setRowMetaModal(true);
|
|
245
|
+
const promise = new Promise((resolveP) => {
|
|
246
|
+
intervalTimer = setInterval(() => {
|
|
247
|
+
if ((savedCallback.current || {}).close === true) {
|
|
248
|
+
reject();
|
|
249
|
+
clearInterval(intervalTimer);
|
|
250
|
+
setRowMetaInfo({});
|
|
251
|
+
setRowName('');
|
|
252
|
+
setRowCategory('');
|
|
253
|
+
return;
|
|
254
|
+
}
|
|
255
|
+
if (Object.keys(savedCallback.current || {}).length > 0) {
|
|
256
|
+
resolveP(savedCallback.current);
|
|
257
|
+
}
|
|
258
|
+
}, 2000);
|
|
259
|
+
});
|
|
260
|
+
const result = await promise;
|
|
261
|
+
resolve(result); // "done!"
|
|
262
|
+
setRowMetaInfo({});
|
|
263
|
+
setRowName('');
|
|
264
|
+
setRowCategory('');
|
|
265
|
+
clearInterval(intervalTimer);
|
|
266
|
+
},
|
|
267
|
+
},
|
|
268
|
+
},
|
|
269
|
+
onSave: (jsonFile, htmlFile) => {
|
|
270
|
+
saveBeeData(jsonFile, htmlFile);
|
|
271
|
+
},
|
|
272
|
+
onSaveRow: (rowJSON) => {
|
|
273
|
+
actions.createCustomRow(JSON.parse(rowJSON), callbackSaveRow);
|
|
274
|
+
},
|
|
275
|
+
};
|
|
276
|
+
window.BeePlugin.create(tokenData, beeConfig, (instance) => {
|
|
277
|
+
beePluginInstance = instance;
|
|
278
|
+
const parseJson = JSON.parse(beeJson);
|
|
279
|
+
beePluginInstance.start(parseJson);
|
|
280
|
+
saveBeeInstance(beePluginInstance);
|
|
281
|
+
});
|
|
282
|
+
return () => clearInterval(intervalTimer);
|
|
283
|
+
}, []);
|
|
284
|
+
```
|
|
285
|
+
|
|
286
|
+
- Creates BEE plugin instance with `tokenData`
|
|
287
|
+
- Starts editor with parsed `beeJson`
|
|
288
|
+
- Saves instance reference
|
|
289
|
+
|
|
290
|
+
---
|
|
291
|
+
|
|
292
|
+
## EDIT FLOW
|
|
293
|
+
|
|
294
|
+
### 1. Component Initialization
|
|
295
|
+
Location: `app/v2Containers/Email/index.js`
|
|
296
|
+
|
|
297
|
+
In `componentWillMount`:
|
|
298
|
+
```193:199:app/v2Containers/Email/index.js
|
|
299
|
+
if (this.props.params.id || (this.props.location.query.module === "library" && this.props.templateData && !_.isEmpty(this.props.templateData))) {
|
|
300
|
+
this.setState({isEdit: true}, () => {
|
|
301
|
+
if (this.props.params.id) {
|
|
302
|
+
this.props.actions.getTemplateDetails(this.props.params.id, 'email');
|
|
303
|
+
}
|
|
304
|
+
});
|
|
305
|
+
}
|
|
306
|
+
```
|
|
307
|
+
|
|
308
|
+
- Sets `isEdit: true`
|
|
309
|
+
- Fetches template details if `params.id` exists
|
|
310
|
+
|
|
311
|
+
### 2. Setting Edit Data
|
|
312
|
+
Location: `app/v2Containers/Email/index.js` - `setEditData`
|
|
313
|
+
|
|
314
|
+
After template details load:
|
|
315
|
+
```992:1003:app/v2Containers/Email/index.js
|
|
316
|
+
const isBEEAppEnable = this.checkBeeEditorAllowedForLibrary();
|
|
317
|
+
_.forEach((editData.versions.base.selectedLanguages), (language) => {
|
|
318
|
+
// if (formData[this.state.currentTab - 1].tabKey === formData[this.state.currentTab - 1][language].tabKey) {
|
|
319
|
+
// formData[this.state.currentTab - 1].activeTab = language;
|
|
320
|
+
// }
|
|
321
|
+
// if (formData.base.tabKey === formData.base[language].tabKey) {
|
|
322
|
+
// formData.base.activeTab = language;
|
|
323
|
+
// }
|
|
324
|
+
if (language && editData.versions.base[language].is_drag_drop && isBEEAppEnable) {
|
|
325
|
+
this.props.actions.getCmsSetting(BEE_PLUGIN, editData._id, 'open', language, isBEESupport, isBEEAppEnable);
|
|
326
|
+
}
|
|
327
|
+
});
|
|
328
|
+
```
|
|
329
|
+
|
|
330
|
+
- For each language with `is_drag_drop: true`, calls `getCmsSetting` with `cmsMode: 'open'` and the template `_id`
|
|
331
|
+
|
|
332
|
+
### 3. Receiving CMS Settings (Same as Create)
|
|
333
|
+
When `CmsSettings` are received, the same logic applies:
|
|
334
|
+
- Stores token and JSON in formData
|
|
335
|
+
- Updates schema to show BEE editor
|
|
336
|
+
- For edit, uses existing `json-content` from template data:
|
|
337
|
+
```396:401:app/v2Containers/Email/index.js
|
|
338
|
+
if (this.state.isEdit) {
|
|
339
|
+
if (this.props.location.query.module === "library") {
|
|
340
|
+
beeJsonValue = _.get(this.state, `formData[${currentTab - 1}][${langId}].json-content`, '');
|
|
341
|
+
} else {
|
|
342
|
+
beeJsonValue = _.get(nextProps, `Email.templateDetails.versions.base[${langId}].json-content`, '');
|
|
343
|
+
}
|
|
344
|
+
}
|
|
345
|
+
```
|
|
346
|
+
|
|
347
|
+
### 4. FormBuilder Renders BEE Editor (Same as Create)
|
|
348
|
+
Same rendering logic as create flow.
|
|
349
|
+
|
|
350
|
+
### 5. BeeEditor Component Initialization (Same as Create)
|
|
351
|
+
Same initialization logic as create flow.
|
|
352
|
+
|
|
353
|
+
---
|
|
354
|
+
|
|
355
|
+
## Key Differences: Create vs Edit
|
|
356
|
+
|
|
357
|
+
| Aspect | Create Flow | Edit Flow |
|
|
358
|
+
|--------|-------------|-----------|
|
|
359
|
+
| CMS Mode | `'create'` | `'open'` |
|
|
360
|
+
| Template ID | From `BEETemplate.versions.base.drag_drop_id` | From `editData._id` |
|
|
361
|
+
| JSON Content | From `BEETemplate.versions.base.json-content` (template default) | From `templateDetails.versions.base[langId].json-content` (saved template) |
|
|
362
|
+
| Trigger | User selects template in EmailWrapper | Template details loaded in `setEditData` |
|
|
363
|
+
|
|
364
|
+
---
|
|
365
|
+
|
|
366
|
+
## API Flow
|
|
367
|
+
|
|
368
|
+
1. `getCmsSetting` action → calls `getCmsTemplateSettingsV2` API
|
|
369
|
+
2. API returns: `tokenData`, `isDragDrop`, `uuid`, `langId`
|
|
370
|
+
3. Redux stores result in `Email.CmsSettings`
|
|
371
|
+
4. Component receives props → updates formData and schema
|
|
372
|
+
5. FormBuilder renders BeeEditor with token and JSON
|
|
373
|
+
6. BeeEditor initializes BEE plugin instance
|
|
374
|
+
|
|
375
|
+
This flow ensures the BEE editor loads with the correct authentication token and template content for both create and edit scenarios.
|
package/assets/Android.png
CHANGED
|
Binary file
|
package/assets/iOS.png
CHANGED
|
Binary file
|
package/constants/unified.js
CHANGED
|
@@ -45,6 +45,7 @@ export const GIFT_CARDS = 'GIFT_CARDS';
|
|
|
45
45
|
export const PROMO_ENGINE = 'PROMO_ENGINE';
|
|
46
46
|
export const LIQUID_SUPPORT = 'ENABLE_LIQUID_SUPPORT';
|
|
47
47
|
export const ENABLE_NEW_MPUSH = 'ENABLE_NEW_MPUSH';
|
|
48
|
+
export const SUPPORT_CK_EDITOR = 'SUPPORT_CK_EDITOR';
|
|
48
49
|
export const CUSTOM_TAG = 'CustomTagMessage';
|
|
49
50
|
export const CUSTOMER_EXTENDED_FIELD = 'Customer extended fields';
|
|
50
51
|
export const EXTENDED_TAG = 'ExtendedTagMessage';
|
|
@@ -168,7 +169,7 @@ export const JAPANESE_HIDE_DATE_TAGS = [
|
|
|
168
169
|
"dd.mm.yy",
|
|
169
170
|
"dd Mon",
|
|
170
171
|
"dd/m/yyyy",
|
|
171
|
-
];
|
|
172
|
+
];
|
|
172
173
|
|
|
173
174
|
export const LIQUID_SUPPORTED_CHANNELS = [EMAIL, SMS, MOBILE_PUSH, INAPP];
|
|
174
175
|
|
package/initialReducer.js
CHANGED
|
@@ -15,7 +15,6 @@ import galleryReducer from './v2Containers/Assets/Gallery/reducer';
|
|
|
15
15
|
import CapCollapsibleLeftNavigationReducer from '@capillarytech/cap-ui-library/CapCollapsibleLeftNavigation/reducer';
|
|
16
16
|
import { AIRA_REDUCER_DOMAIN, askAiraReducer } from '@capillarytech/cap-ui-library/CapAskAira';
|
|
17
17
|
import previewAndTestReducer from './v2Components/TestAndPreviewSlidebox/reducer';
|
|
18
|
-
import inAppReducer from './v2Containers/InApp/reducer';
|
|
19
18
|
|
|
20
19
|
export const initialReducer = {
|
|
21
20
|
language: languageProviderReducer,
|
|
@@ -34,5 +33,4 @@ export const initialReducer = {
|
|
|
34
33
|
gallery: galleryReducer,
|
|
35
34
|
navigationConfig: CapCollapsibleLeftNavigationReducer,
|
|
36
35
|
previewAndTest: previewAndTestReducer,
|
|
37
|
-
inApp: inAppReducer,
|
|
38
36
|
};
|
package/package.json
CHANGED
package/services/api.js
CHANGED
|
@@ -465,6 +465,11 @@ export const getCmsTemplateSettingsV2 = (cmsType, projectId, cmsMode, langId, is
|
|
|
465
465
|
return API.get(url);
|
|
466
466
|
};
|
|
467
467
|
|
|
468
|
+
export const getCmsAccounts = (cmsType) => {
|
|
469
|
+
const url = `${API_ENDPOINT}/cms/accounts?type=${cmsType}`;
|
|
470
|
+
return API.get(url);
|
|
471
|
+
};
|
|
472
|
+
|
|
468
473
|
export const getCmsTemplateData = (cmsType, projectId, langId) => {
|
|
469
474
|
const url = `${API_ENDPOINT}/cms/getContent?type=${cmsType}&projectId=${projectId}&langId=${langId}`;
|
|
470
475
|
return API.get(url);
|
|
@@ -709,9 +714,4 @@ export const updateTestMessageMeta = (payload) => {
|
|
|
709
714
|
return request(url, getAPICallObject('POST', payload?.data, false, true));
|
|
710
715
|
};
|
|
711
716
|
|
|
712
|
-
export const getBeePopupBuilderToken = () => {
|
|
713
|
-
const url = `${API_ENDPOINT}/common/getInappTokenData`;
|
|
714
|
-
return request(url, getAPICallObject('GET'));
|
|
715
|
-
};
|
|
716
|
-
|
|
717
717
|
export {request, getAPICallObject};
|
|
@@ -25,7 +25,6 @@ import {
|
|
|
25
25
|
updateTestMessageMeta,
|
|
26
26
|
updateMetaConfig,
|
|
27
27
|
getMediaDetails,
|
|
28
|
-
getBeePopupBuilderToken,
|
|
29
28
|
} from '../api';
|
|
30
29
|
import { mockData } from './mockData';
|
|
31
30
|
import getSchema from '../getSchema';
|
|
@@ -850,20 +849,3 @@ describe('getMediaDetails', () => {
|
|
|
850
849
|
});
|
|
851
850
|
});
|
|
852
851
|
});
|
|
853
|
-
|
|
854
|
-
describe('getBeePopupBuilderToken', () => {
|
|
855
|
-
it('should return correct response', async () => {
|
|
856
|
-
global.fetch.mockReturnValue(Promise.resolve({
|
|
857
|
-
status: 200,
|
|
858
|
-
json: () => Promise.resolve({
|
|
859
|
-
status: 200,
|
|
860
|
-
response: 'test',
|
|
861
|
-
}),
|
|
862
|
-
}));
|
|
863
|
-
const result = await getBeePopupBuilderToken();
|
|
864
|
-
expect(result).toEqual({
|
|
865
|
-
status: 200,
|
|
866
|
-
response: 'test',
|
|
867
|
-
});
|
|
868
|
-
});
|
|
869
|
-
});
|
package/utils/common.js
CHANGED
|
@@ -22,7 +22,9 @@ import {
|
|
|
22
22
|
BADGES_ISSUE,
|
|
23
23
|
ENABLE_WECHAT,
|
|
24
24
|
LIQUID_SUPPORT,
|
|
25
|
-
ENABLE_NEW_MPUSH
|
|
25
|
+
ENABLE_NEW_MPUSH,
|
|
26
|
+
SUPPORT_CK_EDITOR
|
|
27
|
+
} from '../constants/unified';
|
|
26
28
|
import { apiMessageFormatHandler } from './commonUtils';
|
|
27
29
|
|
|
28
30
|
export function getUserNameById(userId, allUserList) {
|
|
@@ -94,6 +96,10 @@ export const hasLiquidSupportFeature = Auth.hasFeatureAccess.bind(
|
|
|
94
96
|
LIQUID_SUPPORT,
|
|
95
97
|
);
|
|
96
98
|
|
|
99
|
+
export const hasSupportCKEditor = Auth.hasFeatureAccess.bind(
|
|
100
|
+
null,
|
|
101
|
+
SUPPORT_CK_EDITOR,
|
|
102
|
+
);
|
|
97
103
|
|
|
98
104
|
export const hasGiftVoucherFeature = Auth.hasFeatureAccess.bind(
|
|
99
105
|
null,
|
package/utils/commonUtils.js
CHANGED
|
@@ -398,20 +398,7 @@ export const validateMobilePushContent = async (formData, options) => {
|
|
|
398
398
|
// Helper function to extract content for a platform
|
|
399
399
|
export const extractContent = (platformData) => {
|
|
400
400
|
if (!platformData) return '';
|
|
401
|
-
const { title, message, ctas
|
|
402
|
-
|
|
403
|
-
// For BEE editor, extract content from beeHtml
|
|
404
|
-
if (isBEEeditor && beeHtml) {
|
|
405
|
-
// beeHtml can be an object with value property or a string
|
|
406
|
-
const beeHtmlContent = typeof beeHtml === 'string' ? beeHtml : (beeHtml?.value || '');
|
|
407
|
-
return [
|
|
408
|
-
title,
|
|
409
|
-
beeHtmlContent,
|
|
410
|
-
...((ctas?.map((cta) => cta?.text || cta?.actionLink)) || []),
|
|
411
|
-
].filter(Boolean).join(' ');
|
|
412
|
-
}
|
|
413
|
-
|
|
414
|
-
// For regular content
|
|
401
|
+
const { title, message, ctas } = platformData;
|
|
415
402
|
return [
|
|
416
403
|
title,
|
|
417
404
|
message,
|