@atlaskit/editor-plugin-paste 2.0.7 → 2.0.9
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/CHANGELOG.md +18 -0
- package/dist/cjs/handlers.js +49 -2
- package/dist/cjs/pm-plugins/analytics.js +9 -1
- package/dist/cjs/pm-plugins/main.js +10 -1
- package/dist/es2019/handlers.js +53 -0
- package/dist/es2019/index.js +3 -0
- package/dist/es2019/pm-plugins/analytics.js +5 -1
- package/dist/es2019/pm-plugins/main.js +11 -2
- package/dist/esm/handlers.js +48 -2
- package/dist/esm/index.js +3 -0
- package/dist/esm/pm-plugins/analytics.js +9 -1
- package/dist/esm/pm-plugins/main.js +11 -2
- package/dist/types/handlers.d.ts +1 -0
- package/dist/types/pm-plugins/analytics.d.ts +1 -0
- package/dist/types-ts4.5/handlers.d.ts +1 -0
- package/dist/types-ts4.5/pm-plugins/analytics.d.ts +1 -0
- package/package.json +8 -5
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,23 @@
|
|
|
1
1
|
# @atlaskit/editor-plugin-paste
|
|
2
2
|
|
|
3
|
+
## 2.0.9
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- [#179922](https://stash.atlassian.com/projects/CONFCLOUD/repos/confluence-frontend/pull-requests/179922)
|
|
8
|
+
[`3fac1d870e06c`](https://stash.atlassian.com/projects/CONFCLOUD/repos/confluence-frontend/commits/3fac1d870e06c) -
|
|
9
|
+
[ux] ED-25985 Table pasting logic for nested tables - prevents pasted tables from exceeding
|
|
10
|
+
nesting depth of 1 by either flattening deeply nested tables or moving the paste location to under
|
|
11
|
+
the destination table
|
|
12
|
+
|
|
13
|
+
## 2.0.8
|
|
14
|
+
|
|
15
|
+
### Patch Changes
|
|
16
|
+
|
|
17
|
+
- [#164986](https://stash.atlassian.com/projects/CONFCLOUD/repos/confluence-frontend/pull-requests/164986)
|
|
18
|
+
[`a85153a79b5e2`](https://stash.atlassian.com/projects/CONFCLOUD/repos/confluence-frontend/commits/a85153a79b5e2) -
|
|
19
|
+
Added the uiEvent paste meta back into the paste transaction
|
|
20
|
+
|
|
3
21
|
## 2.0.7
|
|
4
22
|
|
|
5
23
|
### Patch Changes
|
package/dist/cjs/handlers.js
CHANGED
|
@@ -13,6 +13,7 @@ exports.handleMacroAutoConvert = handleMacroAutoConvert;
|
|
|
13
13
|
exports.handleMarkdown = handleMarkdown;
|
|
14
14
|
exports.handleMediaSingle = handleMediaSingle;
|
|
15
15
|
exports.handleMention = handleMention;
|
|
16
|
+
exports.handleNestedTablePaste = handleNestedTablePaste;
|
|
16
17
|
exports.handleParagraphBlockMarks = handleParagraphBlockMarks;
|
|
17
18
|
exports.handlePasteAsPlainText = handlePasteAsPlainText;
|
|
18
19
|
exports.handlePasteIntoCaption = handlePasteIntoCaption;
|
|
@@ -31,6 +32,7 @@ var _v = _interopRequireDefault(require("uuid/v4"));
|
|
|
31
32
|
var _analytics = require("@atlaskit/editor-common/analytics");
|
|
32
33
|
var _coreUtils = require("@atlaskit/editor-common/core-utils");
|
|
33
34
|
var _mark = require("@atlaskit/editor-common/mark");
|
|
35
|
+
var _nesting = require("@atlaskit/editor-common/nesting");
|
|
34
36
|
var _selection = require("@atlaskit/editor-common/selection");
|
|
35
37
|
var _utils = require("@atlaskit/editor-common/utils");
|
|
36
38
|
var _history = require("@atlaskit/editor-prosemirror/history");
|
|
@@ -38,6 +40,7 @@ var _model = require("@atlaskit/editor-prosemirror/model");
|
|
|
38
40
|
var _state = require("@atlaskit/editor-prosemirror/state");
|
|
39
41
|
var _utils2 = require("@atlaskit/editor-prosemirror/utils");
|
|
40
42
|
var _utils3 = require("@atlaskit/editor-tables/utils");
|
|
43
|
+
var _experiments = require("@atlaskit/tmp-editor-statsig/experiments");
|
|
41
44
|
var _commands = require("./commands");
|
|
42
45
|
var _edgeCases = require("./edge-cases");
|
|
43
46
|
var _lists = require("./edge-cases/lists");
|
|
@@ -592,7 +595,6 @@ function handleMacroAutoConvert(text, slice, queueCardsFromChangedTr, runMacroAu
|
|
|
592
595
|
* if FF enabled, run through smart links and check for result
|
|
593
596
|
*/
|
|
594
597
|
if (cardsOptions && cardsOptions.resolveBeforeMacros && cardsOptions.resolveBeforeMacros.length) {
|
|
595
|
-
var _startTrackingPastedM;
|
|
596
598
|
if (cardsOptions.resolveBeforeMacros.indexOf(macro.attrs.extensionKey) < 0) {
|
|
597
599
|
return insertAutoMacro(slice, macro, view);
|
|
598
600
|
}
|
|
@@ -602,7 +604,7 @@ function handleMacroAutoConvert(text, slice, queueCardsFromChangedTr, runMacroAu
|
|
|
602
604
|
var trackingId = (0, _v.default)();
|
|
603
605
|
var trackingFrom = "handleMacroAutoConvert-from-".concat(trackingId);
|
|
604
606
|
var trackingTo = "handleMacroAutoConvert-to-".concat(trackingId);
|
|
605
|
-
(0, _commands.startTrackingPastedMacroPositions)((
|
|
607
|
+
(0, _commands.startTrackingPastedMacroPositions)((0, _defineProperty2.default)((0, _defineProperty2.default)({}, trackingFrom, state.selection.from), trackingTo, state.selection.to))(state, dispatch);
|
|
606
608
|
getSmartLinkAdf(text, 'inline', cardsOptions).then(function () {
|
|
607
609
|
// we use view.state rather than state because state becomes a stale
|
|
608
610
|
// state reference after getSmartLinkAdf's async work
|
|
@@ -697,6 +699,51 @@ function handleTableContentPasteInBodiedExtension(slice) {
|
|
|
697
699
|
return false;
|
|
698
700
|
};
|
|
699
701
|
}
|
|
702
|
+
function handleNestedTablePaste(slice, isNestingTablesSupported) {
|
|
703
|
+
return function (state, dispatch) {
|
|
704
|
+
if (!isNestingTablesSupported || !(0, _coreUtils.insideTable)(state)) {
|
|
705
|
+
return false;
|
|
706
|
+
}
|
|
707
|
+
var schema = state.schema,
|
|
708
|
+
selection = state.selection;
|
|
709
|
+
var sliceHasTable = false;
|
|
710
|
+
slice.content.forEach(function (node) {
|
|
711
|
+
if (node.type === state.schema.nodes.table) {
|
|
712
|
+
sliceHasTable = true;
|
|
713
|
+
}
|
|
714
|
+
});
|
|
715
|
+
if (sliceHasTable) {
|
|
716
|
+
if ((0, _experiments.editorExperiment)('nested-tables-in-tables', true, {
|
|
717
|
+
exposure: true
|
|
718
|
+
})) {
|
|
719
|
+
/* TEST COHORT */
|
|
720
|
+
// if slice has table - if pasting to deeply nested location place paste after top table
|
|
721
|
+
if ((0, _nesting.getParentOfTypeCount)(schema.nodes.table)(selection.$from) > 1) {
|
|
722
|
+
var positionAfterTopTable = (0, _nesting.getPositionAfterTopParentNodeOfType)(schema.nodes.table)(selection.$from);
|
|
723
|
+
var tr = state.tr;
|
|
724
|
+
tr = (0, _utils2.safeInsert)(slice.content, positionAfterTopTable)(tr);
|
|
725
|
+
tr.scrollIntoView();
|
|
726
|
+
if (dispatch) {
|
|
727
|
+
dispatch(tr);
|
|
728
|
+
return true;
|
|
729
|
+
}
|
|
730
|
+
}
|
|
731
|
+
} else {
|
|
732
|
+
/* CONTROL COHORT */
|
|
733
|
+
// if slice has table - place paste after top table
|
|
734
|
+
var _positionAfterTopTable = (0, _nesting.getPositionAfterTopParentNodeOfType)(schema.nodes.table)(selection.$from);
|
|
735
|
+
var _tr2 = state.tr;
|
|
736
|
+
_tr2 = (0, _utils2.safeInsert)(slice.content, _positionAfterTopTable)(_tr2);
|
|
737
|
+
_tr2.scrollIntoView();
|
|
738
|
+
if (dispatch) {
|
|
739
|
+
dispatch(_tr2);
|
|
740
|
+
return true;
|
|
741
|
+
}
|
|
742
|
+
}
|
|
743
|
+
}
|
|
744
|
+
return false;
|
|
745
|
+
};
|
|
746
|
+
}
|
|
700
747
|
function handleExpandPaste(slice, isNestingExpandsSupported) {
|
|
701
748
|
return function (state, dispatch) {
|
|
702
749
|
var isInsideNestableExpand = isNestingExpandsSupported && !!insideExpand(state);
|
|
@@ -9,7 +9,7 @@ exports.createPasteMeasurePayload = void 0;
|
|
|
9
9
|
exports.getContent = getContent;
|
|
10
10
|
exports.getContentNodeTypes = void 0;
|
|
11
11
|
exports.getMediaTraceId = getMediaTraceId;
|
|
12
|
-
exports.sendPasteAnalyticsEvent = exports.handleSelectedTableWithAnalytics = exports.handleRichTextWithAnalytics = exports.handlePastePreservingMarksWithAnalytics = exports.handlePastePanelOrDecisionIntoListWithAnalytics = exports.handlePasteNonNestableBlockNodesIntoListWithAnalytics = exports.handlePasteLinkOnSelectedTextWithAnalytics = exports.handlePasteIntoTaskAndDecisionWithAnalytics = exports.handlePasteIntoCaptionWithAnalytics = exports.handlePasteAsPlainTextWithAnalytics = exports.handleMediaSingleWithAnalytics = exports.handleMarkdownWithAnalytics = exports.handleExpandWithAnalytics = exports.handleCodeBlockWithAnalytics = void 0;
|
|
12
|
+
exports.sendPasteAnalyticsEvent = exports.handleSelectedTableWithAnalytics = exports.handleRichTextWithAnalytics = exports.handlePastePreservingMarksWithAnalytics = exports.handlePastePanelOrDecisionIntoListWithAnalytics = exports.handlePasteNonNestableBlockNodesIntoListWithAnalytics = exports.handlePasteLinkOnSelectedTextWithAnalytics = exports.handlePasteIntoTaskAndDecisionWithAnalytics = exports.handlePasteIntoCaptionWithAnalytics = exports.handlePasteAsPlainTextWithAnalytics = exports.handleNestedTablePasteWithAnalytics = exports.handleMediaSingleWithAnalytics = exports.handleMarkdownWithAnalytics = exports.handleExpandWithAnalytics = exports.handleCodeBlockWithAnalytics = void 0;
|
|
13
13
|
var _toConsumableArray2 = _interopRequireDefault(require("@babel/runtime/helpers/toConsumableArray"));
|
|
14
14
|
var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
|
|
15
15
|
var _analytics = require("@atlaskit/editor-common/analytics");
|
|
@@ -366,6 +366,14 @@ var handleExpandWithAnalytics = exports.handleExpandWithAnalytics = function han
|
|
|
366
366
|
}))((0, _handlers.handleExpandPaste)(slice, isNestingExpandsSupported));
|
|
367
367
|
};
|
|
368
368
|
};
|
|
369
|
+
var handleNestedTablePasteWithAnalytics = exports.handleNestedTablePasteWithAnalytics = function handleNestedTablePasteWithAnalytics(editorAnalyticsAPI, isNestingTablesSupported) {
|
|
370
|
+
return function (view, event, slice) {
|
|
371
|
+
return injectAnalyticsPayloadBeforeCommand(editorAnalyticsAPI)(createPasteAnalyticsPayloadBySelection(event, slice, {
|
|
372
|
+
type: _analytics.PasteTypes.richText,
|
|
373
|
+
pasteSplitList: true
|
|
374
|
+
}))((0, _handlers.handleNestedTablePaste)(slice, isNestingTablesSupported));
|
|
375
|
+
};
|
|
376
|
+
};
|
|
369
377
|
var handleSelectedTableWithAnalytics = exports.handleSelectedTableWithAnalytics = function handleSelectedTableWithAnalytics(editorAnalyticsAPI) {
|
|
370
378
|
return function (view, event, slice) {
|
|
371
379
|
return injectAnalyticsPayloadBeforeCommand(editorAnalyticsAPI)(createPasteAnalyticsPayloadBySelection(event, slice, {
|
|
@@ -268,7 +268,11 @@ function createPlugin(schema, dispatchAnalyticsEvent, dispatch, featureFlags, pl
|
|
|
268
268
|
contentPasted: contentPasted
|
|
269
269
|
});
|
|
270
270
|
}
|
|
271
|
-
|
|
271
|
+
|
|
272
|
+
// the handlePaste definition overrides the generic prosemirror behaviour which would previously
|
|
273
|
+
// include a uiEvent meta of paste. To align with the docs (https://prosemirror.net/docs/ref/#state.Transaction)
|
|
274
|
+
// This will re-add the uiEvent meta.
|
|
275
|
+
view.dispatch(tr.setMeta('uiEvent', 'paste'));
|
|
272
276
|
};
|
|
273
277
|
slice = (0, _handlers.handleParagraphBlockMarks)(state, slice);
|
|
274
278
|
var plainTextPasteSlice = (0, _utils.linkifyContent)(state.schema)(slice);
|
|
@@ -394,6 +398,11 @@ function createPlugin(schema, dispatchAnalyticsEvent, dispatch, featureFlags, pl
|
|
|
394
398
|
return true;
|
|
395
399
|
}
|
|
396
400
|
|
|
401
|
+
// handle paste of nested tables to ensure nesting limits are respected
|
|
402
|
+
if ((0, _analytics2.handleNestedTablePasteWithAnalytics)(editorAnalyticsAPI, (0, _platformFeatureFlags.fg)('platform_editor_use_nested_table_pm_nodes'))(view, event, slice)(state, dispatch)) {
|
|
403
|
+
return true;
|
|
404
|
+
}
|
|
405
|
+
|
|
397
406
|
// handle the case when copy content from a table cell inside bodied extension
|
|
398
407
|
if ((0, _handlers.handleTableContentPasteInBodiedExtension)(slice)(state, dispatch)) {
|
|
399
408
|
return true;
|
package/dist/es2019/handlers.js
CHANGED
|
@@ -2,6 +2,7 @@ import uuid from 'uuid/v4';
|
|
|
2
2
|
import { INPUT_METHOD } from '@atlaskit/editor-common/analytics';
|
|
3
3
|
import { insideTable } from '@atlaskit/editor-common/core-utils';
|
|
4
4
|
import { anyMarkActive } from '@atlaskit/editor-common/mark';
|
|
5
|
+
import { getParentOfTypeCount, getPositionAfterTopParentNodeOfType } from '@atlaskit/editor-common/nesting';
|
|
5
6
|
import { GapCursorSelection, Side } from '@atlaskit/editor-common/selection';
|
|
6
7
|
import { canLinkBeCreatedInRange, insideTableCell, isInListItem, isLinkMark, isListItemNode, isListNode, isNodeEmpty, isParagraph, isText, linkifyContent, mapSlice } from '@atlaskit/editor-common/utils';
|
|
7
8
|
import { closeHistory } from '@atlaskit/editor-prosemirror/history';
|
|
@@ -9,6 +10,7 @@ import { Fragment, Node as PMNode, Slice } from '@atlaskit/editor-prosemirror/mo
|
|
|
9
10
|
import { NodeSelection, TextSelection } from '@atlaskit/editor-prosemirror/state';
|
|
10
11
|
import { canInsert, contains, findParentNodeOfType, findParentNodeOfTypeClosestToPos, hasParentNode, hasParentNodeOfType, safeInsert } from '@atlaskit/editor-prosemirror/utils';
|
|
11
12
|
import { replaceSelectedTable } from '@atlaskit/editor-tables/utils';
|
|
13
|
+
import { editorExperiment } from '@atlaskit/tmp-editor-statsig/experiments';
|
|
12
14
|
// TODO: ED-20519 Needs Macro extraction
|
|
13
15
|
|
|
14
16
|
import { startTrackingPastedMacroPositions, stopTrackingPastedMacroPositions } from './commands';
|
|
@@ -681,6 +683,57 @@ export function handleTableContentPasteInBodiedExtension(slice) {
|
|
|
681
683
|
return false;
|
|
682
684
|
};
|
|
683
685
|
}
|
|
686
|
+
export function handleNestedTablePaste(slice, isNestingTablesSupported) {
|
|
687
|
+
return (state, dispatch) => {
|
|
688
|
+
if (!isNestingTablesSupported || !insideTable(state)) {
|
|
689
|
+
return false;
|
|
690
|
+
}
|
|
691
|
+
const {
|
|
692
|
+
schema,
|
|
693
|
+
selection
|
|
694
|
+
} = state;
|
|
695
|
+
let sliceHasTable = false;
|
|
696
|
+
slice.content.forEach(node => {
|
|
697
|
+
if (node.type === state.schema.nodes.table) {
|
|
698
|
+
sliceHasTable = true;
|
|
699
|
+
}
|
|
700
|
+
});
|
|
701
|
+
if (sliceHasTable) {
|
|
702
|
+
if (editorExperiment('nested-tables-in-tables', true, {
|
|
703
|
+
exposure: true
|
|
704
|
+
})) {
|
|
705
|
+
/* TEST COHORT */
|
|
706
|
+
// if slice has table - if pasting to deeply nested location place paste after top table
|
|
707
|
+
if (getParentOfTypeCount(schema.nodes.table)(selection.$from) > 1) {
|
|
708
|
+
const positionAfterTopTable = getPositionAfterTopParentNodeOfType(schema.nodes.table)(selection.$from);
|
|
709
|
+
let {
|
|
710
|
+
tr
|
|
711
|
+
} = state;
|
|
712
|
+
tr = safeInsert(slice.content, positionAfterTopTable)(tr);
|
|
713
|
+
tr.scrollIntoView();
|
|
714
|
+
if (dispatch) {
|
|
715
|
+
dispatch(tr);
|
|
716
|
+
return true;
|
|
717
|
+
}
|
|
718
|
+
}
|
|
719
|
+
} else {
|
|
720
|
+
/* CONTROL COHORT */
|
|
721
|
+
// if slice has table - place paste after top table
|
|
722
|
+
const positionAfterTopTable = getPositionAfterTopParentNodeOfType(schema.nodes.table)(selection.$from);
|
|
723
|
+
let {
|
|
724
|
+
tr
|
|
725
|
+
} = state;
|
|
726
|
+
tr = safeInsert(slice.content, positionAfterTopTable)(tr);
|
|
727
|
+
tr.scrollIntoView();
|
|
728
|
+
if (dispatch) {
|
|
729
|
+
dispatch(tr);
|
|
730
|
+
return true;
|
|
731
|
+
}
|
|
732
|
+
}
|
|
733
|
+
}
|
|
734
|
+
return false;
|
|
735
|
+
};
|
|
736
|
+
}
|
|
684
737
|
export function handleExpandPaste(slice, isNestingExpandsSupported) {
|
|
685
738
|
return (state, dispatch) => {
|
|
686
739
|
const isInsideNestableExpand = isNestingExpandsSupported && !!insideExpand(state);
|
package/dist/es2019/index.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { ACTION, ACTION_SUBJECT, ACTION_SUBJECT_ID, EVENT_TYPE, INPUT_METHOD, PasteContents, PasteTypes } from '@atlaskit/editor-common/analytics';
|
|
2
2
|
import { getLinkDomain, mapSlice } from '@atlaskit/editor-common/utils';
|
|
3
3
|
import { findParentNode } from '@atlaskit/editor-prosemirror/utils';
|
|
4
|
-
import { handleCodeBlock, handleExpandPaste, handleMarkdown, handleMediaSingle, handlePasteAsPlainText, handlePasteIntoCaption, handlePasteIntoTaskOrDecisionOrPanel, handlePasteLinkOnSelectedText, handlePasteNonNestableBlockNodesIntoList, handlePastePanelOrDecisionContentIntoList, handlePastePreservingMarks, handleRichText, handleSelectedTable } from '../handlers';
|
|
4
|
+
import { handleCodeBlock, handleExpandPaste, handleMarkdown, handleMediaSingle, handlePasteAsPlainText, handlePasteIntoCaption, handlePasteIntoTaskOrDecisionOrPanel, handlePasteLinkOnSelectedText, handlePasteNonNestableBlockNodesIntoList, handlePastePanelOrDecisionContentIntoList, handlePastePreservingMarks, handleRichText, handleSelectedTable, handleNestedTablePaste } from '../handlers';
|
|
5
5
|
import { getPasteSource } from '../util';
|
|
6
6
|
const contentToPasteContent = {
|
|
7
7
|
url: PasteContents.url,
|
|
@@ -329,6 +329,10 @@ export const handleExpandWithAnalytics = (editorAnalyticsAPI, isNestingExpandsSu
|
|
|
329
329
|
type: PasteTypes.richText,
|
|
330
330
|
pasteSplitList: true
|
|
331
331
|
}))(handleExpandPaste(slice, isNestingExpandsSupported));
|
|
332
|
+
export const handleNestedTablePasteWithAnalytics = (editorAnalyticsAPI, isNestingTablesSupported) => (view, event, slice) => injectAnalyticsPayloadBeforeCommand(editorAnalyticsAPI)(createPasteAnalyticsPayloadBySelection(event, slice, {
|
|
333
|
+
type: PasteTypes.richText,
|
|
334
|
+
pasteSplitList: true
|
|
335
|
+
}))(handleNestedTablePaste(slice, isNestingTablesSupported));
|
|
332
336
|
export const handleSelectedTableWithAnalytics = editorAnalyticsAPI => (view, event, slice) => injectAnalyticsPayloadBeforeCommand(editorAnalyticsAPI)(createPasteAnalyticsPayloadBySelection(event, slice, {
|
|
333
337
|
type: PasteTypes.richText
|
|
334
338
|
}))(handleSelectedTable(editorAnalyticsAPI)(slice));
|
|
@@ -19,7 +19,7 @@ import { handleMacroAutoConvert, handleMention, handleParagraphBlockMarks, handl
|
|
|
19
19
|
import { transformSliceForMedia, transformSliceToCorrectMediaWrapper, transformSliceToMediaSingleWithNewExperience, unwrapNestedMediaElements } from '../plugins/media';
|
|
20
20
|
import { escapeLinks, getPasteSource, htmlContainsSingleFile, htmlHasInvalidLinkTags, isPastedFromExcel, isPastedFromWord, removeDuplicateInvalidLinks, transformUnsupportedBlockCardToInline } from '../util';
|
|
21
21
|
import { htmlHasIncompleteTable, isPastedFromTinyMCEConfluence, tryRebuildCompleteTableHtml } from '../util/tinyMCE';
|
|
22
|
-
import { createPasteMeasurePayload, getContentNodeTypes, handleCodeBlockWithAnalytics, handleExpandWithAnalytics, handleMarkdownWithAnalytics, handleMediaSingleWithAnalytics, handlePasteAsPlainTextWithAnalytics, handlePasteIntoCaptionWithAnalytics, handlePasteIntoTaskAndDecisionWithAnalytics, handlePasteLinkOnSelectedTextWithAnalytics, handlePasteNonNestableBlockNodesIntoListWithAnalytics, handlePastePanelOrDecisionIntoListWithAnalytics, handlePastePreservingMarksWithAnalytics, handleRichTextWithAnalytics, handleSelectedTableWithAnalytics, sendPasteAnalyticsEvent } from './analytics';
|
|
22
|
+
import { createPasteMeasurePayload, getContentNodeTypes, handleCodeBlockWithAnalytics, handleExpandWithAnalytics, handleMarkdownWithAnalytics, handleMediaSingleWithAnalytics, handlePasteAsPlainTextWithAnalytics, handlePasteIntoCaptionWithAnalytics, handlePasteIntoTaskAndDecisionWithAnalytics, handlePasteLinkOnSelectedTextWithAnalytics, handlePasteNonNestableBlockNodesIntoListWithAnalytics, handlePastePanelOrDecisionIntoListWithAnalytics, handlePastePreservingMarksWithAnalytics, handleRichTextWithAnalytics, handleSelectedTableWithAnalytics, sendPasteAnalyticsEvent, handleNestedTablePasteWithAnalytics } from './analytics';
|
|
23
23
|
import { clipboardTextSerializer } from './clipboard-text-serializer';
|
|
24
24
|
import { createPluginState, pluginKey as stateKey } from './plugin-factory';
|
|
25
25
|
export { pluginKey as stateKey } from './plugin-factory';
|
|
@@ -237,7 +237,11 @@ export function createPlugin(schema, dispatchAnalyticsEvent, dispatch, featureFl
|
|
|
237
237
|
contentPasted
|
|
238
238
|
});
|
|
239
239
|
}
|
|
240
|
-
|
|
240
|
+
|
|
241
|
+
// the handlePaste definition overrides the generic prosemirror behaviour which would previously
|
|
242
|
+
// include a uiEvent meta of paste. To align with the docs (https://prosemirror.net/docs/ref/#state.Transaction)
|
|
243
|
+
// This will re-add the uiEvent meta.
|
|
244
|
+
view.dispatch(tr.setMeta('uiEvent', 'paste'));
|
|
241
245
|
};
|
|
242
246
|
slice = handleParagraphBlockMarks(state, slice);
|
|
243
247
|
const plainTextPasteSlice = linkifyContent(state.schema)(slice);
|
|
@@ -365,6 +369,11 @@ export function createPlugin(schema, dispatchAnalyticsEvent, dispatch, featureFl
|
|
|
365
369
|
return true;
|
|
366
370
|
}
|
|
367
371
|
|
|
372
|
+
// handle paste of nested tables to ensure nesting limits are respected
|
|
373
|
+
if (handleNestedTablePasteWithAnalytics(editorAnalyticsAPI, fg('platform_editor_use_nested_table_pm_nodes'))(view, event, slice)(state, dispatch)) {
|
|
374
|
+
return true;
|
|
375
|
+
}
|
|
376
|
+
|
|
368
377
|
// handle the case when copy content from a table cell inside bodied extension
|
|
369
378
|
if (handleTableContentPasteInBodiedExtension(slice)(state, dispatch)) {
|
|
370
379
|
return true;
|
package/dist/esm/handlers.js
CHANGED
|
@@ -10,6 +10,7 @@ import uuid from 'uuid/v4';
|
|
|
10
10
|
import { INPUT_METHOD } from '@atlaskit/editor-common/analytics';
|
|
11
11
|
import { insideTable } from '@atlaskit/editor-common/core-utils';
|
|
12
12
|
import { anyMarkActive } from '@atlaskit/editor-common/mark';
|
|
13
|
+
import { getParentOfTypeCount, getPositionAfterTopParentNodeOfType } from '@atlaskit/editor-common/nesting';
|
|
13
14
|
import { GapCursorSelection, Side } from '@atlaskit/editor-common/selection';
|
|
14
15
|
import { canLinkBeCreatedInRange, insideTableCell, isInListItem, isLinkMark, isListItemNode, isListNode, isNodeEmpty, isParagraph, isText, linkifyContent, mapSlice } from '@atlaskit/editor-common/utils';
|
|
15
16
|
import { closeHistory } from '@atlaskit/editor-prosemirror/history';
|
|
@@ -17,6 +18,7 @@ import { Fragment, Node as PMNode, Slice } from '@atlaskit/editor-prosemirror/mo
|
|
|
17
18
|
import { NodeSelection, TextSelection } from '@atlaskit/editor-prosemirror/state';
|
|
18
19
|
import { canInsert, contains, findParentNodeOfType, findParentNodeOfTypeClosestToPos, hasParentNode, hasParentNodeOfType, safeInsert } from '@atlaskit/editor-prosemirror/utils';
|
|
19
20
|
import { replaceSelectedTable } from '@atlaskit/editor-tables/utils';
|
|
21
|
+
import { editorExperiment } from '@atlaskit/tmp-editor-statsig/experiments';
|
|
20
22
|
// TODO: ED-20519 Needs Macro extraction
|
|
21
23
|
|
|
22
24
|
import { startTrackingPastedMacroPositions, stopTrackingPastedMacroPositions } from './commands';
|
|
@@ -568,7 +570,6 @@ export function handleMacroAutoConvert(text, slice, queueCardsFromChangedTr, run
|
|
|
568
570
|
* if FF enabled, run through smart links and check for result
|
|
569
571
|
*/
|
|
570
572
|
if (cardsOptions && cardsOptions.resolveBeforeMacros && cardsOptions.resolveBeforeMacros.length) {
|
|
571
|
-
var _startTrackingPastedM;
|
|
572
573
|
if (cardsOptions.resolveBeforeMacros.indexOf(macro.attrs.extensionKey) < 0) {
|
|
573
574
|
return insertAutoMacro(slice, macro, view);
|
|
574
575
|
}
|
|
@@ -578,7 +579,7 @@ export function handleMacroAutoConvert(text, slice, queueCardsFromChangedTr, run
|
|
|
578
579
|
var trackingId = uuid();
|
|
579
580
|
var trackingFrom = "handleMacroAutoConvert-from-".concat(trackingId);
|
|
580
581
|
var trackingTo = "handleMacroAutoConvert-to-".concat(trackingId);
|
|
581
|
-
startTrackingPastedMacroPositions((
|
|
582
|
+
startTrackingPastedMacroPositions(_defineProperty(_defineProperty({}, trackingFrom, state.selection.from), trackingTo, state.selection.to))(state, dispatch);
|
|
582
583
|
getSmartLinkAdf(text, 'inline', cardsOptions).then(function () {
|
|
583
584
|
// we use view.state rather than state because state becomes a stale
|
|
584
585
|
// state reference after getSmartLinkAdf's async work
|
|
@@ -673,6 +674,51 @@ export function handleTableContentPasteInBodiedExtension(slice) {
|
|
|
673
674
|
return false;
|
|
674
675
|
};
|
|
675
676
|
}
|
|
677
|
+
export function handleNestedTablePaste(slice, isNestingTablesSupported) {
|
|
678
|
+
return function (state, dispatch) {
|
|
679
|
+
if (!isNestingTablesSupported || !insideTable(state)) {
|
|
680
|
+
return false;
|
|
681
|
+
}
|
|
682
|
+
var schema = state.schema,
|
|
683
|
+
selection = state.selection;
|
|
684
|
+
var sliceHasTable = false;
|
|
685
|
+
slice.content.forEach(function (node) {
|
|
686
|
+
if (node.type === state.schema.nodes.table) {
|
|
687
|
+
sliceHasTable = true;
|
|
688
|
+
}
|
|
689
|
+
});
|
|
690
|
+
if (sliceHasTable) {
|
|
691
|
+
if (editorExperiment('nested-tables-in-tables', true, {
|
|
692
|
+
exposure: true
|
|
693
|
+
})) {
|
|
694
|
+
/* TEST COHORT */
|
|
695
|
+
// if slice has table - if pasting to deeply nested location place paste after top table
|
|
696
|
+
if (getParentOfTypeCount(schema.nodes.table)(selection.$from) > 1) {
|
|
697
|
+
var positionAfterTopTable = getPositionAfterTopParentNodeOfType(schema.nodes.table)(selection.$from);
|
|
698
|
+
var tr = state.tr;
|
|
699
|
+
tr = safeInsert(slice.content, positionAfterTopTable)(tr);
|
|
700
|
+
tr.scrollIntoView();
|
|
701
|
+
if (dispatch) {
|
|
702
|
+
dispatch(tr);
|
|
703
|
+
return true;
|
|
704
|
+
}
|
|
705
|
+
}
|
|
706
|
+
} else {
|
|
707
|
+
/* CONTROL COHORT */
|
|
708
|
+
// if slice has table - place paste after top table
|
|
709
|
+
var _positionAfterTopTable = getPositionAfterTopParentNodeOfType(schema.nodes.table)(selection.$from);
|
|
710
|
+
var _tr2 = state.tr;
|
|
711
|
+
_tr2 = safeInsert(slice.content, _positionAfterTopTable)(_tr2);
|
|
712
|
+
_tr2.scrollIntoView();
|
|
713
|
+
if (dispatch) {
|
|
714
|
+
dispatch(_tr2);
|
|
715
|
+
return true;
|
|
716
|
+
}
|
|
717
|
+
}
|
|
718
|
+
}
|
|
719
|
+
return false;
|
|
720
|
+
};
|
|
721
|
+
}
|
|
676
722
|
export function handleExpandPaste(slice, isNestingExpandsSupported) {
|
|
677
723
|
return function (state, dispatch) {
|
|
678
724
|
var isInsideNestableExpand = isNestingExpandsSupported && !!insideExpand(state);
|
package/dist/esm/index.js
CHANGED
|
@@ -5,7 +5,7 @@ function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t =
|
|
|
5
5
|
import { ACTION, ACTION_SUBJECT, ACTION_SUBJECT_ID, EVENT_TYPE, INPUT_METHOD, PasteContents, PasteTypes } from '@atlaskit/editor-common/analytics';
|
|
6
6
|
import { getLinkDomain, mapSlice } from '@atlaskit/editor-common/utils';
|
|
7
7
|
import { findParentNode } from '@atlaskit/editor-prosemirror/utils';
|
|
8
|
-
import { handleCodeBlock, handleExpandPaste, handleMarkdown, handleMediaSingle, handlePasteAsPlainText, handlePasteIntoCaption, handlePasteIntoTaskOrDecisionOrPanel, handlePasteLinkOnSelectedText, handlePasteNonNestableBlockNodesIntoList, handlePastePanelOrDecisionContentIntoList, handlePastePreservingMarks, handleRichText, handleSelectedTable } from '../handlers';
|
|
8
|
+
import { handleCodeBlock, handleExpandPaste, handleMarkdown, handleMediaSingle, handlePasteAsPlainText, handlePasteIntoCaption, handlePasteIntoTaskOrDecisionOrPanel, handlePasteLinkOnSelectedText, handlePasteNonNestableBlockNodesIntoList, handlePastePanelOrDecisionContentIntoList, handlePastePreservingMarks, handleRichText, handleSelectedTable, handleNestedTablePaste } from '../handlers';
|
|
9
9
|
import { getPasteSource } from '../util';
|
|
10
10
|
var contentToPasteContent = {
|
|
11
11
|
url: PasteContents.url,
|
|
@@ -354,6 +354,14 @@ export var handleExpandWithAnalytics = function handleExpandWithAnalytics(editor
|
|
|
354
354
|
}))(handleExpandPaste(slice, isNestingExpandsSupported));
|
|
355
355
|
};
|
|
356
356
|
};
|
|
357
|
+
export var handleNestedTablePasteWithAnalytics = function handleNestedTablePasteWithAnalytics(editorAnalyticsAPI, isNestingTablesSupported) {
|
|
358
|
+
return function (view, event, slice) {
|
|
359
|
+
return injectAnalyticsPayloadBeforeCommand(editorAnalyticsAPI)(createPasteAnalyticsPayloadBySelection(event, slice, {
|
|
360
|
+
type: PasteTypes.richText,
|
|
361
|
+
pasteSplitList: true
|
|
362
|
+
}))(handleNestedTablePaste(slice, isNestingTablesSupported));
|
|
363
|
+
};
|
|
364
|
+
};
|
|
357
365
|
export var handleSelectedTableWithAnalytics = function handleSelectedTableWithAnalytics(editorAnalyticsAPI) {
|
|
358
366
|
return function (view, event, slice) {
|
|
359
367
|
return injectAnalyticsPayloadBeforeCommand(editorAnalyticsAPI)(createPasteAnalyticsPayloadBySelection(event, slice, {
|
|
@@ -21,7 +21,7 @@ import { handleMacroAutoConvert, handleMention, handleParagraphBlockMarks, handl
|
|
|
21
21
|
import { transformSliceForMedia, transformSliceToCorrectMediaWrapper, transformSliceToMediaSingleWithNewExperience, unwrapNestedMediaElements } from '../plugins/media';
|
|
22
22
|
import { escapeLinks, getPasteSource, htmlContainsSingleFile, htmlHasInvalidLinkTags, isPastedFromExcel, isPastedFromWord, removeDuplicateInvalidLinks, transformUnsupportedBlockCardToInline } from '../util';
|
|
23
23
|
import { htmlHasIncompleteTable, isPastedFromTinyMCEConfluence, tryRebuildCompleteTableHtml } from '../util/tinyMCE';
|
|
24
|
-
import { createPasteMeasurePayload, getContentNodeTypes, handleCodeBlockWithAnalytics, handleExpandWithAnalytics, handleMarkdownWithAnalytics, handleMediaSingleWithAnalytics, handlePasteAsPlainTextWithAnalytics, handlePasteIntoCaptionWithAnalytics, handlePasteIntoTaskAndDecisionWithAnalytics, handlePasteLinkOnSelectedTextWithAnalytics, handlePasteNonNestableBlockNodesIntoListWithAnalytics, handlePastePanelOrDecisionIntoListWithAnalytics, handlePastePreservingMarksWithAnalytics, handleRichTextWithAnalytics, handleSelectedTableWithAnalytics, sendPasteAnalyticsEvent } from './analytics';
|
|
24
|
+
import { createPasteMeasurePayload, getContentNodeTypes, handleCodeBlockWithAnalytics, handleExpandWithAnalytics, handleMarkdownWithAnalytics, handleMediaSingleWithAnalytics, handlePasteAsPlainTextWithAnalytics, handlePasteIntoCaptionWithAnalytics, handlePasteIntoTaskAndDecisionWithAnalytics, handlePasteLinkOnSelectedTextWithAnalytics, handlePasteNonNestableBlockNodesIntoListWithAnalytics, handlePastePanelOrDecisionIntoListWithAnalytics, handlePastePreservingMarksWithAnalytics, handleRichTextWithAnalytics, handleSelectedTableWithAnalytics, sendPasteAnalyticsEvent, handleNestedTablePasteWithAnalytics } from './analytics';
|
|
25
25
|
import { clipboardTextSerializer } from './clipboard-text-serializer';
|
|
26
26
|
import { createPluginState, pluginKey as stateKey } from './plugin-factory';
|
|
27
27
|
export { pluginKey as stateKey } from './plugin-factory';
|
|
@@ -255,7 +255,11 @@ export function createPlugin(schema, dispatchAnalyticsEvent, dispatch, featureFl
|
|
|
255
255
|
contentPasted: contentPasted
|
|
256
256
|
});
|
|
257
257
|
}
|
|
258
|
-
|
|
258
|
+
|
|
259
|
+
// the handlePaste definition overrides the generic prosemirror behaviour which would previously
|
|
260
|
+
// include a uiEvent meta of paste. To align with the docs (https://prosemirror.net/docs/ref/#state.Transaction)
|
|
261
|
+
// This will re-add the uiEvent meta.
|
|
262
|
+
view.dispatch(tr.setMeta('uiEvent', 'paste'));
|
|
259
263
|
};
|
|
260
264
|
slice = handleParagraphBlockMarks(state, slice);
|
|
261
265
|
var plainTextPasteSlice = linkifyContent(state.schema)(slice);
|
|
@@ -381,6 +385,11 @@ export function createPlugin(schema, dispatchAnalyticsEvent, dispatch, featureFl
|
|
|
381
385
|
return true;
|
|
382
386
|
}
|
|
383
387
|
|
|
388
|
+
// handle paste of nested tables to ensure nesting limits are respected
|
|
389
|
+
if (handleNestedTablePasteWithAnalytics(editorAnalyticsAPI, fg('platform_editor_use_nested_table_pm_nodes'))(view, event, slice)(state, dispatch)) {
|
|
390
|
+
return true;
|
|
391
|
+
}
|
|
392
|
+
|
|
384
393
|
// handle the case when copy content from a table cell inside bodied extension
|
|
385
394
|
if (handleTableContentPasteInBodiedExtension(slice)(state, dispatch)) {
|
|
386
395
|
return true;
|
package/dist/types/handlers.d.ts
CHANGED
|
@@ -20,6 +20,7 @@ export declare function handleMacroAutoConvert(text: string, slice: Slice, queue
|
|
|
20
20
|
export declare function handleCodeBlock(text: string): Command;
|
|
21
21
|
export declare function handleMediaSingle(inputMethod: InputMethodInsertMedia, insertMediaAsMediaSingle: InsertMediaAsMediaSingle | undefined): (slice: Slice) => Command;
|
|
22
22
|
export declare function handleTableContentPasteInBodiedExtension(slice: Slice): Command;
|
|
23
|
+
export declare function handleNestedTablePaste(slice: Slice, isNestingTablesSupported?: boolean): Command;
|
|
23
24
|
export declare function handleExpandPaste(slice: Slice, isNestingExpandsSupported?: boolean): Command;
|
|
24
25
|
export declare function handleMarkdown(markdownSlice: Slice, queueCardsFromChangedTr: QueueCardsFromTransactionAction | undefined, from?: number, to?: number): Command;
|
|
25
26
|
export declare function handleParagraphBlockMarks(state: EditorState, slice: Slice): Slice;
|
|
@@ -32,6 +32,7 @@ export declare const handleRichTextWithAnalytics: (view: EditorView, event: Clip
|
|
|
32
32
|
export declare const handlePastePanelOrDecisionIntoListWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined) => (view: EditorView, event: ClipboardEvent, slice: Slice, findRootParentListNode: FindRootParentListNode | undefined) => Command;
|
|
33
33
|
export declare const handlePasteNonNestableBlockNodesIntoListWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined) => (view: EditorView, event: ClipboardEvent, slice: Slice) => Command;
|
|
34
34
|
export declare const handleExpandWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined, isNestingExpandsSupported: boolean) => (view: EditorView, event: ClipboardEvent, slice: Slice) => Command;
|
|
35
|
+
export declare const handleNestedTablePasteWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined, isNestingTablesSupported: boolean) => (view: EditorView, event: ClipboardEvent, slice: Slice) => Command;
|
|
35
36
|
export declare const handleSelectedTableWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined) => (view: EditorView, event: ClipboardEvent, slice: Slice) => Command;
|
|
36
37
|
export declare const handlePasteLinkOnSelectedTextWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined) => (view: EditorView, event: ClipboardEvent, slice: Slice, type: PasteType) => Command;
|
|
37
38
|
export declare const createPasteMeasurePayload: ({ view, duration, content, distortedDuration, }: {
|
|
@@ -20,6 +20,7 @@ export declare function handleMacroAutoConvert(text: string, slice: Slice, queue
|
|
|
20
20
|
export declare function handleCodeBlock(text: string): Command;
|
|
21
21
|
export declare function handleMediaSingle(inputMethod: InputMethodInsertMedia, insertMediaAsMediaSingle: InsertMediaAsMediaSingle | undefined): (slice: Slice) => Command;
|
|
22
22
|
export declare function handleTableContentPasteInBodiedExtension(slice: Slice): Command;
|
|
23
|
+
export declare function handleNestedTablePaste(slice: Slice, isNestingTablesSupported?: boolean): Command;
|
|
23
24
|
export declare function handleExpandPaste(slice: Slice, isNestingExpandsSupported?: boolean): Command;
|
|
24
25
|
export declare function handleMarkdown(markdownSlice: Slice, queueCardsFromChangedTr: QueueCardsFromTransactionAction | undefined, from?: number, to?: number): Command;
|
|
25
26
|
export declare function handleParagraphBlockMarks(state: EditorState, slice: Slice): Slice;
|
|
@@ -32,6 +32,7 @@ export declare const handleRichTextWithAnalytics: (view: EditorView, event: Clip
|
|
|
32
32
|
export declare const handlePastePanelOrDecisionIntoListWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined) => (view: EditorView, event: ClipboardEvent, slice: Slice, findRootParentListNode: FindRootParentListNode | undefined) => Command;
|
|
33
33
|
export declare const handlePasteNonNestableBlockNodesIntoListWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined) => (view: EditorView, event: ClipboardEvent, slice: Slice) => Command;
|
|
34
34
|
export declare const handleExpandWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined, isNestingExpandsSupported: boolean) => (view: EditorView, event: ClipboardEvent, slice: Slice) => Command;
|
|
35
|
+
export declare const handleNestedTablePasteWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined, isNestingTablesSupported: boolean) => (view: EditorView, event: ClipboardEvent, slice: Slice) => Command;
|
|
35
36
|
export declare const handleSelectedTableWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined) => (view: EditorView, event: ClipboardEvent, slice: Slice) => Command;
|
|
36
37
|
export declare const handlePasteLinkOnSelectedTextWithAnalytics: (editorAnalyticsAPI: EditorAnalyticsAPI | undefined) => (view: EditorView, event: ClipboardEvent, slice: Slice, type: PasteType) => Command;
|
|
37
38
|
export declare const createPasteMeasurePayload: ({ view, duration, content, distortedDuration, }: {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@atlaskit/editor-plugin-paste",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.9",
|
|
4
4
|
"description": "Paste plugin for @atlaskit/editor-core",
|
|
5
5
|
"author": "Atlassian Pty Ltd",
|
|
6
6
|
"license": "Apache-2.0",
|
|
@@ -31,7 +31,7 @@
|
|
|
31
31
|
".": "./src/index.ts"
|
|
32
32
|
},
|
|
33
33
|
"dependencies": {
|
|
34
|
-
"@atlaskit/editor-common": "^96.
|
|
34
|
+
"@atlaskit/editor-common": "^96.5.0",
|
|
35
35
|
"@atlaskit/editor-markdown-transformer": "^5.13.0",
|
|
36
36
|
"@atlaskit/editor-plugin-analytics": "^1.10.0",
|
|
37
37
|
"@atlaskit/editor-plugin-annotation": "^1.26.0",
|
|
@@ -39,14 +39,14 @@
|
|
|
39
39
|
"@atlaskit/editor-plugin-card": "^4.5.0",
|
|
40
40
|
"@atlaskit/editor-plugin-feature-flags": "^1.2.0",
|
|
41
41
|
"@atlaskit/editor-plugin-list": "^3.9.0",
|
|
42
|
-
"@atlaskit/editor-plugin-media": "^1.
|
|
42
|
+
"@atlaskit/editor-plugin-media": "^1.43.0",
|
|
43
43
|
"@atlaskit/editor-plugin-mentions": "^2.10.0",
|
|
44
44
|
"@atlaskit/editor-prosemirror": "6.2.1",
|
|
45
45
|
"@atlaskit/editor-tables": "^2.8.0",
|
|
46
|
-
"@atlaskit/media-client": "^28.
|
|
46
|
+
"@atlaskit/media-client": "^28.6.0",
|
|
47
47
|
"@atlaskit/media-common": "^11.7.0",
|
|
48
48
|
"@atlaskit/platform-feature-flags": "^0.3.0",
|
|
49
|
-
"@atlaskit/tmp-editor-statsig": "^2.
|
|
49
|
+
"@atlaskit/tmp-editor-statsig": "^2.27.0",
|
|
50
50
|
"@babel/runtime": "^7.0.0",
|
|
51
51
|
"lodash": "^4.17.21",
|
|
52
52
|
"uuid": "^3.1.0"
|
|
@@ -120,6 +120,9 @@
|
|
|
120
120
|
},
|
|
121
121
|
"editor_nest_media_and_codeblock_in_quotes_jira": {
|
|
122
122
|
"type": "boolean"
|
|
123
|
+
},
|
|
124
|
+
"platform_editor_use_nested_table_pm_nodes": {
|
|
125
|
+
"type": "boolean"
|
|
123
126
|
}
|
|
124
127
|
}
|
|
125
128
|
}
|