diff --git a/examples/src/customLayoutPluginWithInitialState.tsx b/examples/src/customLayoutPluginWithInitialState.tsx index a8e7f8b79..b1e3fafa1 100644 --- a/examples/src/customLayoutPluginWithInitialState.tsx +++ b/examples/src/customLayoutPluginWithInitialState.tsx @@ -27,7 +27,7 @@ export default () => state: reducedSlate.createInitialSlateState(({ plugins }) => ({ children: [ { - plugin: plugins.headings.h2, + plugin: plugins.headings.h3, children: ['Hello world'], }, { diff --git a/examples/src/slate.tsx b/examples/src/slate.tsx index 6051623f1..af25b6b65 100644 --- a/examples/src/slate.tsx +++ b/examples/src/slate.tsx @@ -1,11 +1,13 @@ import slate from '@react-page/plugins-slate'; import '@react-page/plugins-slate/lib/index.css'; +import React from 'react'; import customSlatePlugin from './customSlatePlugin'; export const defaultSlate = slate(def => ({ ...def, plugins: { ...def.plugins, + custom: { custom1: customSlatePlugin, }, @@ -20,9 +22,17 @@ export const reducedSlate = slate(def => ({ plugins: { headings: { h2: def.plugins.headings.h2, - h3: def.plugins.headings.h3, + // you can also customize default slate plugins easily + h3: def.plugins.headings.h3(dh3 => { + const OriginalH3 = dh3.Component; + return { + ...dh3, + Component: props => , + }; + }), }, paragraphs: def.plugins.paragraphs, emphasize: def.plugins.emphasize, + alignment: def.plugins.alignment, }, })); diff --git a/package.json b/package.json index acffac1c7..85f3ac48e 100644 --- a/package.json +++ b/package.json @@ -36,7 +36,7 @@ "postcss-nested": "^3.0.0", "postcss-preset-env": "^5.3.0", "prettier": "1.15.3", - "prettier-tslint": "0.4.1", + "prettier-tslint": "0.4.2", "pushstate-server": "^3.0.0", "q-deep": "1.0.3", "react": "~16.9.0", @@ -44,9 +44,9 @@ "redux": "^3.6.0", "rimraf": "2.6.2", "ts-jest": "^24.1.0", - "tslint": "^5.11.0", + "tslint": "^5.20.0", "tslint-react": "^3.6.0", - "typescript": "^3.6.4", + "typescript": "^3.7.3", "unexpected": "^10.38.0" }, "scripts": { diff --git a/packages/plugins/content/slate/src/index.tsx b/packages/plugins/content/slate/src/index.tsx index 0574d7373..ad09f6ac2 100644 --- a/packages/plugins/content/slate/src/index.tsx +++ b/packages/plugins/content/slate/src/index.tsx @@ -20,63 +20,53 @@ * */ +import { lazyLoad } from '@react-page/core'; +import { ContentPluginConfig } from '@react-page/core/lib/service/plugin/classes'; +import { pathOr } from 'ramda/src/pathOr'; import * as React from 'react'; - +import { AnyAction } from 'redux'; +import { ActionTypes } from 'redux-undo'; +import { Value } from 'slate'; import Component from './Component'; -import Renderer from './Renderer'; - -import { SlatePluginCollection } from './types/SlatePlugin'; +import { defaultTranslations } from './default/settings'; import * as hooks from './hooks'; - import v002 from './migrations/v002'; import v003 from './migrations/v003'; - -import { ContentPluginConfig } from '@react-page/core/lib/service/plugin/classes'; -import { SlateState } from './types/state'; - -import { pathOr } from 'ramda/src/pathOr'; -import { ActionTypes } from 'redux-undo'; -import { AnyAction } from 'redux'; -import { defaultTranslations } from './default/settings'; - -import * as defaultPlugins from './plugins/index'; import * as pluginFactories from './pluginFactories/index'; +import * as defaultPlugins from './plugins/index'; +import Renderer from './Renderer'; import serialization from './serialization'; import { SlateProps } from './types/component'; -import { lazyLoad } from '@react-page/core'; - -import { SlateRendererProps } from './types/renderer'; import { SlateControlsProps } from './types/controls'; -import makeSlatePluginsFromDef from './utils/makeSlatePluginsFromDef'; import { InitialSlateStateDef } from './types/initialSlateState'; +import { SlateRendererProps } from './types/renderer'; +import { SlatePluginCollection } from './types/SlatePlugin'; +import { SlateState } from './types/state'; +import makeSlatePluginsFromDef from './utils/makeSlatePluginsFromDef'; import transformInitialSlateState from './utils/transformInitialSlateState'; -import { Value } from 'slate'; const slatePlugins = defaultPlugins; export { defaultPlugins, slatePlugins, pluginFactories }; - const Subject = lazyLoad(() => import('@material-ui/icons/Subject')); const Controls = lazyLoad(() => import('./Controls/')); const migrations = [v002, v003]; -type SlateDefinition = { +type SlateDefinition = { icon: JSX.Element; - plugins: SlatePluginCollection; + plugins: TPlugins; Renderer: React.ComponentType; Controls: React.ComponentType; name: string; version: string; translations: typeof defaultTranslations; migrations: typeof migrations; - createInitialSlateState: CreateInitialStateCustomizer; allowInlineNeighbours: boolean; hideInMenu?: boolean; }; -type DefaultSlateDefinition = SlateDefinition & { - plugins: typeof defaultPlugins; -}; -export type CreateInitialStateCustomizer = ( - { plugins }: { plugins: SlatePluginCollection } +type DefaultPlugins = typeof defaultPlugins; +type DefaultSlateDefinition = SlateDefinition; +export type CreateInitialStateCustomizer = ( + { plugins }: { plugins: TPlugins } ) => InitialSlateStateDef; const defaultConfig: DefaultSlateDefinition = { @@ -89,32 +79,44 @@ const defaultConfig: DefaultSlateDefinition = { translations: defaultTranslations, migrations, - createInitialSlateState: ({ plugins }) => ({ - children: [ - { - plugin: plugins.paragraphs.paragraph, - children: [''], - }, - ], - }), allowInlineNeighbours: true, }; -type CreateInitialSlateState = ( - custom?: CreateInitialStateCustomizer +type CreateInitialSlateState = ( + custom?: CreateInitialStateCustomizer ) => { editorState: Value }; -export type SlatePlugin = ContentPluginConfig & { - createInitialSlateState: CreateInitialSlateState; +export type SlatePlugin = ContentPluginConfig & { + createInitialSlateState: CreateInitialSlateState; }; -export type SlateCustomizeFunction = ( +export type SlateCustomizeFunction = ( def: DefaultSlateDefinition -) => SlateDefinition; -export default (customize?: SlateCustomizeFunction): SlatePlugin => { - const settings = customize ? customize(defaultConfig) : defaultConfig; +) => SlateDefinition; + +function plugin( + customize?: SlateCustomizeFunction +): SlatePlugin { + const settings = (customize + ? customize(defaultConfig) + : defaultConfig) as SlateDefinition; + const createInitialState = ( - customizeInitialSlateState?: CreateInitialStateCustomizer + customizeInitialSlateState?: CreateInitialStateCustomizer ) => { - const func = customizeInitialSlateState || settings.createInitialSlateState; + const defaultInitialState = ({ + plugins: cplugins, + }: { + plugins: TPlugins; + }) => ({ + children: [ + { + plugin: cplugins.paragraphs.paragraph, + children: [''], + }, + ], + }); + const func = customizeInitialSlateState + ? customizeInitialSlateState + : defaultInitialState; return transformInitialSlateState(func({ plugins: settings.plugins })); }; @@ -185,4 +187,6 @@ export default (customize?: SlateCustomizeFunction): SlatePlugin => { migrations: settings.migrations, }; -}; +} + +export default plugin; diff --git a/packages/plugins/content/slate/src/pluginFactories/createComponentPlugin.tsx b/packages/plugins/content/slate/src/pluginFactories/createComponentPlugin.tsx index c074a1c29..4fb1a00e5 100644 --- a/packages/plugins/content/slate/src/pluginFactories/createComponentPlugin.tsx +++ b/packages/plugins/content/slate/src/pluginFactories/createComponentPlugin.tsx @@ -104,19 +104,17 @@ function createComponentPluginWithDefinition( }; } -export type CustomizeFunction = ( - def: SlateComponentPluginDefinition -) => SlateComponentPluginDefinition; - -function createComponentPlugin( - definition: SlateComponentPluginDefinition -) { - return function(customize?: CustomizeFunction) { - if (customize) { - return createComponentPluginWithDefinition(customize(definition)); - } - return createComponentPluginWithDefinition(definition); +function createComponentPlugin(def: SlateComponentPluginDefinition) { + const customizablePlugin = function( + customize: ( + t: SlateComponentPluginDefinition + ) => SlateComponentPluginDefinition = d => + (d as unknown) as SlateComponentPluginDefinition + ) { + return createComponentPlugin(customize(def)); }; + customizablePlugin.toPlugin = () => createComponentPluginWithDefinition(def); + return customizablePlugin; } export default createComponentPlugin; diff --git a/packages/plugins/content/slate/src/pluginFactories/createDataPlugin.tsx b/packages/plugins/content/slate/src/pluginFactories/createDataPlugin.tsx index b0dfb9f04..632255b06 100644 --- a/packages/plugins/content/slate/src/pluginFactories/createDataPlugin.tsx +++ b/packages/plugins/content/slate/src/pluginFactories/createDataPlugin.tsx @@ -10,18 +10,17 @@ function createDataPluginWithDefinition( }; } -type CustomizeFunction = ( - def: SlateDataPluginDefinition -) => SlateDataPluginDefinition; - -function createDataPlugin( - definition: SlateDataPluginDefinition -) { - return (customize?: CustomizeFunction): SlatePlugin => { - return createDataPluginWithDefinition( - customize ? customize(definition) : definition - ); +function createDataPlugin(def: SlateDataPluginDefinition) { + const customizablePlugin = function( + customize: ( + t: SlateDataPluginDefinition + ) => SlateDataPluginDefinition = d => + (d as unknown) as SlateDataPluginDefinition + ) { + return createDataPlugin(customize(def)); }; + customizablePlugin.toPlugin = () => createDataPluginWithDefinition(def); + return customizablePlugin; } export default createDataPlugin; diff --git a/packages/plugins/content/slate/src/pluginFactories/createListIndentionPlugin.tsx b/packages/plugins/content/slate/src/pluginFactories/createListIndentionPlugin.tsx index 7e265add0..cb086568e 100644 --- a/packages/plugins/content/slate/src/pluginFactories/createListIndentionPlugin.tsx +++ b/packages/plugins/content/slate/src/pluginFactories/createListIndentionPlugin.tsx @@ -8,11 +8,7 @@ type Definition = { listTypes: string[]; }; -type Customize = (d: Definition) => Definition; - -export default (defaultDefinition: Definition) => (customize?: Customize) => { - const def = customize ? customize(defaultDefinition) : defaultDefinition; - +const ceateSlatePlugin = (def: Definition) => { const slateEditList = createSlateEditList({ typeItem: def.listItemType, types: def.listTypes, @@ -62,3 +58,15 @@ export default (defaultDefinition: Definition) => (customize?: Customize) => { }), ]; }; + +function createListIndentionPlugin(def: Definition) { + const customizablePlugin = function( + customize: (def2: Definition) => Definition + ) { + return createListIndentionPlugin(customize(def)); + }; + customizablePlugin.toPlugin = () => ceateSlatePlugin(def); + return customizablePlugin; +} + +export default createListIndentionPlugin; diff --git a/packages/plugins/content/slate/src/pluginFactories/createListPlugin.tsx b/packages/plugins/content/slate/src/pluginFactories/createListPlugin.tsx index 2e97bac87..15435f1cb 100644 --- a/packages/plugins/content/slate/src/pluginFactories/createListPlugin.tsx +++ b/packages/plugins/content/slate/src/pluginFactories/createListPlugin.tsx @@ -1,6 +1,5 @@ -import { CustomizeFunction } from './createComponentPlugin'; import createSlateEditList from '@guestbell/slate-edit-list'; - +import { SlateComponentPluginDefinition } from '../types/slatePluginDefinitions'; import createListItemPlugin from './createListItemPlugin'; import createSimpleHtmlBlockPlugin, { HtmlBlockData @@ -19,38 +18,83 @@ type ListDef = { }; }; -function createListPlugin(def: ListDef) { +type ListItemDef = SlateComponentPluginDefinition>; + +type CustomizeFunction = (def: ListItemDef) => ListItemDef; + +type ListCustomizers = { + customizeList?: CustomizeFunction; + customizeListItem?: CustomizeFunction; +}; + +function createSlatePlugins( + def: ListDef, + customizers: ListCustomizers = {} +) { const slateEditList = createSlateEditList({ typeItem: def.listItem.type, types: [def.type], }); + return [ + createSimpleHtmlBlockPlugin({ + type: def.type, + icon: def.icon, + noButton: def.noButton, + tagName: def.tagName, - return function(customizers?: { - customizeList?: CustomizeFunction, HtmlBlockData>; - customizeListItem?: CustomizeFunction< - HtmlBlockData, - HtmlBlockData - >; - }) { - return [ - createSimpleHtmlBlockPlugin({ - type: def.type, - icon: def.icon, - noButton: def.noButton, - tagName: def.tagName, - - customAdd: editor => slateEditList.changes.wrapInList(editor, def.type), - customRemove: editor => slateEditList.changes.unwrapList(editor), - })(customizers && customizers.customizeList), - createListItemPlugin(def.listItem)( - customizers && customizers.customizeListItem - ), - { + customAdd: editor => slateEditList.changes.wrapInList(editor, def.type), + customRemove: editor => slateEditList.changes.unwrapList(editor), + })(customizers.customizeList), + createListItemPlugin(def.listItem)(customizers.customizeListItem), + { + toPlugin: () => ({ onKeyDown: (e: React.KeyboardEvent, editor, next) => slateEditList.onKeyDown((e as unknown) as Event, editor, next), - }, - ]; + }), + }, + ]; +} + +function mergeCustomizer( + c1: ListCustomizers, + c2: ListCustomizers +): ListCustomizers { + return { + customizeList(def: ListItemDef) { + const def2 = c1.customizeList + ? c1.customizeList(def) + : ((def as unknown) as ListItemDef); + return c2.customizeList + ? c2.customizeList(def2) + : ((def2 as unknown) as ListItemDef); + }, + customizeListItem(def: ListItemDef) { + const def2 = c1.customizeList + ? c1.customizeListItem(def) + : ((def as unknown) as ListItemDef); + return c2.customizeList + ? c2.customizeListItem(def2) + : ((def2 as unknown) as ListItemDef); + }, + }; +} + +function createListPlugin(def: ListDef) { + const inner = function( + innerdef: ListDef, + customizersIn?: ListCustomizers + ) { + const customizablePlugin = function(customizers: ListCustomizers) { + return inner(innerdef, mergeCustomizer(customizersIn, customizers)); + }; + customizablePlugin.toPlugin = () => + createSlatePlugins(innerdef, customizersIn).map(plugin => + plugin.toPlugin() + ); + return customizablePlugin; }; + + return inner(def); } export default createListPlugin; diff --git a/packages/plugins/content/slate/src/pluginFactories/createSimpleHtmlBlockPlugin.tsx b/packages/plugins/content/slate/src/pluginFactories/createSimpleHtmlBlockPlugin.tsx index ce2294850..adb917373 100644 --- a/packages/plugins/content/slate/src/pluginFactories/createSimpleHtmlBlockPlugin.tsx +++ b/packages/plugins/content/slate/src/pluginFactories/createSimpleHtmlBlockPlugin.tsx @@ -1,7 +1,6 @@ -import createComponentPlugin from './createComponentPlugin'; - import React from 'react'; import { SlateComponentPluginDefinition } from '../types/slatePluginDefinitions'; +import createComponentPlugin from './createComponentPlugin'; type Def = Pick< SlateComponentPluginDefinition>, @@ -42,12 +41,17 @@ function createSimpleHtmlBlockPlugin(def: Def>) { deserialize: { tagName: def.tagName, }, - Component: ({ data, children, attributes }) => { + Component: ({ data, children, attributes, style, className }) => { const Tag = (def.tagName as unknown) as React.ComponentType<{ style: object; + className?: string; }>; return ( - + {children} ); diff --git a/packages/plugins/content/slate/src/plugins/code/index.tsx b/packages/plugins/content/slate/src/plugins/code/index.tsx index 4fae64d2f..f2d870d81 100644 --- a/packages/plugins/content/slate/src/plugins/code/index.tsx +++ b/packages/plugins/content/slate/src/plugins/code/index.tsx @@ -1,5 +1,5 @@ -import React from 'react'; import { lazyLoad } from '@react-page/core'; +import React from 'react'; import createComponentPlugin from '../../pluginFactories/createComponentPlugin'; const Icon = lazyLoad(() => import('@material-ui/icons/Code')); diff --git a/packages/plugins/content/slate/src/types/SlatePlugin.ts b/packages/plugins/content/slate/src/types/SlatePlugin.ts index 76de6cc11..443e0e432 100644 --- a/packages/plugins/content/slate/src/types/SlatePlugin.ts +++ b/packages/plugins/content/slate/src/types/SlatePlugin.ts @@ -87,7 +87,10 @@ export type SlatePluginOrListOfPlugins = SlatePlugin | SlatePlugin[]; export type SlatePluginOrFactory = // tslint:disable-next-line:no-any - ((...args: any) => SlatePluginOrListOfPlugins) | SlatePluginOrListOfPlugins; + | { + toPlugin: () => SlatePluginOrListOfPlugins; + } + | SlatePluginOrListOfPlugins; export type SlatePluginCollection = { [group: string]: { [key: string]: SlatePluginOrFactory; diff --git a/packages/plugins/content/slate/src/types/slatePluginDefinitions.ts b/packages/plugins/content/slate/src/types/slatePluginDefinitions.ts index 0bba80332..4feec6067 100644 --- a/packages/plugins/content/slate/src/types/slatePluginDefinitions.ts +++ b/packages/plugins/content/slate/src/types/slatePluginDefinitions.ts @@ -1,6 +1,6 @@ +import { JsonSchema } from '@react-page/create-plugin-materialui'; import { Editor, Value } from 'slate'; import { NextType } from '../types/next'; -import { JsonSchema } from '@react-page/create-plugin-materialui'; import { Translations } from './translations'; export interface PluginButtonProps { @@ -83,6 +83,8 @@ export type SlateComponentPluginDefinition< }; Component: React.ComponentType<{ attributes?: object; + style?: object; + className?: string; data: MapLike; }>; } & (ObjectProps | InlineProps | MarkProps); diff --git a/packages/plugins/content/slate/src/utils/makeSlatePluginsFromDef.ts b/packages/plugins/content/slate/src/utils/makeSlatePluginsFromDef.ts index 47c2db4e7..9a5fc9d3c 100644 --- a/packages/plugins/content/slate/src/utils/makeSlatePluginsFromDef.ts +++ b/packages/plugins/content/slate/src/utils/makeSlatePluginsFromDef.ts @@ -6,10 +6,11 @@ export default (plugins: SlatePluginCollection) => { const group = plugins[groupKey]; const groupPlugins = Object.keys(group).reduce((innerAcc, key) => { const pluginOrFactory = plugins[groupKey][key]; - const result = - typeof pluginOrFactory === 'function' - ? pluginOrFactory() - : pluginOrFactory; + // tslint:disable-next-line:no-any + const result = (pluginOrFactory as any).toPlugin + ? // tslint:disable-next-line:no-any + (pluginOrFactory as any).toPlugin() + : pluginOrFactory; return [...innerAcc, ...flattenDeep(result)]; }, []); diff --git a/packages/plugins/content/slate/src/utils/transformInitialSlateState.ts b/packages/plugins/content/slate/src/utils/transformInitialSlateState.ts index 203612397..13e6e9697 100644 --- a/packages/plugins/content/slate/src/utils/transformInitialSlateState.ts +++ b/packages/plugins/content/slate/src/utils/transformInitialSlateState.ts @@ -26,12 +26,13 @@ const transformChildren = (defNodes: SlateDefNode[]) => defNodes.map(defNode => { if ((defNode as SlatePluginNode).plugin) { const defPluginNode: SlatePluginNode = defNode as SlatePluginNode; - const slatePluginOrList = - typeof defPluginNode.plugin === 'function' - ? defPluginNode.plugin() - : defPluginNode.plugin; + // tslint:disable-next-line:no-any + const slatePluginOrList = (defPluginNode.plugin as any).toPlugin + ? // tslint:disable-next-line:no-any + (defPluginNode.plugin as any).toPlugin() + : defPluginNode.plugin; - // the result of plugin() might be an array, e.g. the list plugin is an array, because it defines ul, li AND indention-options on the same plugin + // the result of plugin.toPlugin might be an array, e.g. the list plugin is an array, because it defines ul, li AND indention-options on the same plugin const firstComponentPlugin = flattenDeep( slatePluginOrList ).find( diff --git a/yarn.lock b/yarn.lock index 3b2faa364..56b65de79 100644 --- a/yarn.lock +++ b/yarn.lock @@ -9759,10 +9759,10 @@ prepend-http@^1.0.0, prepend-http@^1.0.1: resolved "https://registry.yarnpkg.com/prepend-http/-/prepend-http-1.0.4.tgz#d4f4562b0ce3696e41ac52d0e002e57a635dc6dc" integrity sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw= -prettier-tslint@0.4.1: - version "0.4.1" - resolved "https://registry.yarnpkg.com/prettier-tslint/-/prettier-tslint-0.4.1.tgz#75011da65b555cda9909e7285a63b2b4f96772e6" - integrity sha512-bd95F9mvhlG8G0VMZF1OYkektsO7AcNGz33ndiHaKpfeuNvaaGTppr34ANfO5jduRQPKC27L4OAr7ljAYopZJw== +prettier-tslint@0.4.2: + version "0.4.2" + resolved "https://registry.yarnpkg.com/prettier-tslint/-/prettier-tslint-0.4.2.tgz#37dd009ad6a482ea8101f40cf70b777bc86f3438" + integrity sha512-urhX7U/F+fu8sztEs/Z7CxNS8PdEytEwGKhQaH5fxxCdRmHGT45FoClyDlcZrMk9cK/8JpX/asFmTOHtSGJfLg== dependencies: chalk "^2.4.0" globby "^8.0.1" @@ -11866,7 +11866,26 @@ tslint-react@^3.6.0: dependencies: tsutils "^2.13.1" -tslint@^5.11.0, tslint@^5.9.1: +tslint@^5.20.0: + version "5.20.1" + resolved "https://registry.yarnpkg.com/tslint/-/tslint-5.20.1.tgz#e401e8aeda0152bc44dd07e614034f3f80c67b7d" + integrity sha512-EcMxhzCFt8k+/UP5r8waCf/lzmeSyVlqxqMEDQE7rWYiQky8KpIBz1JAoYXfROHrPZ1XXd43q8yQnULOLiBRQg== + dependencies: + "@babel/code-frame" "^7.0.0" + builtin-modules "^1.1.1" + chalk "^2.3.0" + commander "^2.12.1" + diff "^4.0.1" + glob "^7.1.1" + js-yaml "^3.13.1" + minimatch "^3.0.4" + mkdirp "^0.5.1" + resolve "^1.3.2" + semver "^5.3.0" + tslib "^1.8.0" + tsutils "^2.29.0" + +tslint@^5.9.1: version "5.20.0" resolved "https://registry.yarnpkg.com/tslint/-/tslint-5.20.0.tgz#fac93bfa79568a5a24e7be9cdde5e02b02d00ec1" integrity sha512-2vqIvkMHbnx8acMogAERQ/IuINOq6DFqgF8/VDvhEkBqQh/x6SP0Y+OHnKth9/ZcHQSroOZwUQSN18v8KKF0/g== @@ -11926,10 +11945,10 @@ typedarray@^0.0.6, typedarray@~0.0.5: resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777" integrity sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c= -typescript@^3.6.4: - version "3.6.4" - resolved "https://registry.yarnpkg.com/typescript/-/typescript-3.6.4.tgz#b18752bb3792bc1a0281335f7f6ebf1bbfc5b91d" - integrity sha512-unoCll1+l+YK4i4F8f22TaNVPRHcD9PA3yCuZ8g5e0qGqlVlJ/8FSateOLLSagn+Yg5+ZwuPkL8LFUc0Jcvksg== +typescript@^3.7.3: + version "3.7.4" + resolved "https://registry.yarnpkg.com/typescript/-/typescript-3.7.4.tgz#1743a5ec5fef6a1fa9f3e4708e33c81c73876c19" + integrity sha512-A25xv5XCtarLwXpcDNZzCGvW2D1S3/bACratYBx2sax8PefsFhlYmkQicKHvpYflFS8if4zne5zT5kpJ7pzuvw== uglify-js@^3.1.4: version "3.6.4"