@teleporthq/teleport-project-plugin-parse-embed 0.27.9 → 0.29.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/dist/cjs/component-plugin.d.ts +8 -0
- package/dist/cjs/component-plugin.d.ts.map +1 -0
- package/dist/cjs/component-plugin.js +124 -0
- package/dist/cjs/component-plugin.js.map +1 -0
- package/dist/cjs/index.d.ts +4 -17
- package/dist/cjs/index.d.ts.map +1 -1
- package/dist/cjs/index.js +19 -123
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/tsconfig.tsbuildinfo +1 -1
- package/dist/cjs/utils.d.ts +1 -1
- package/dist/cjs/utils.d.ts.map +1 -1
- package/dist/cjs/utils.js.map +1 -1
- package/dist/esm/component-plugin.d.ts +8 -0
- package/dist/esm/component-plugin.d.ts.map +1 -0
- package/dist/esm/component-plugin.js +120 -0
- package/dist/esm/component-plugin.js.map +1 -0
- package/dist/esm/index.d.ts +4 -17
- package/dist/esm/index.d.ts.map +1 -1
- package/dist/esm/index.js +18 -123
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/tsconfig.tsbuildinfo +1 -1
- package/dist/esm/utils.d.ts +1 -1
- package/dist/esm/utils.d.ts.map +1 -1
- package/dist/esm/utils.js.map +1 -1
- package/package.json +4 -4
- package/src/component-plugin.ts +96 -0
- package/src/index.ts +17 -92
- package/src/utils.ts +2 -0
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
import { ComponentPlugin, ComponentPluginFactory, HastNode } from '@teleporthq/teleport-types'
|
|
2
|
+
import { UIDLUtils } from '@teleporthq/teleport-shared'
|
|
3
|
+
import { SUPPORTED_PROJECT_TYPES } from './utils'
|
|
4
|
+
import type { JSXElement, JSXIdentifier, JSXText } from '@babel/types'
|
|
5
|
+
|
|
6
|
+
interface ParseEmbedPluginConfig {
|
|
7
|
+
projectType: SUPPORTED_PROJECT_TYPES
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
const NODE_MAPPER: Record<
|
|
11
|
+
SUPPORTED_PROJECT_TYPES,
|
|
12
|
+
Promise<(content: unknown, options: unknown) => string>
|
|
13
|
+
> = {
|
|
14
|
+
html: import('hast-util-to-html').then((mod) => mod.toHtml),
|
|
15
|
+
jsx: import('hast-util-to-jsx-inline-script').then((mod) => mod.default),
|
|
16
|
+
'teleport-project-html': import('hast-util-to-html').then((mod) => mod.toHtml),
|
|
17
|
+
'teleport-project-react': import('hast-util-to-jsx-inline-script').then((mod) => mod.default),
|
|
18
|
+
'teleport-project-next': import('hast-util-to-jsx-inline-script').then((mod) => mod.default),
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
const COMPONENT_CHUNK_NAMES: Record<SUPPORTED_PROJECT_TYPES, string> = {
|
|
22
|
+
html: 'html-chunk',
|
|
23
|
+
jsx: 'jsx-component',
|
|
24
|
+
'teleport-project-html': 'html-chunk',
|
|
25
|
+
'teleport-project-next': 'jsx-component',
|
|
26
|
+
'teleport-project-react': 'jsx-component',
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
export const createParseEmbedPlugin: ComponentPluginFactory<ParseEmbedPluginConfig> = (config) => {
|
|
30
|
+
const { projectType } = config
|
|
31
|
+
|
|
32
|
+
if (!NODE_MAPPER[projectType]) {
|
|
33
|
+
throw new Error(`Received a invalid ${projectType}`)
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
const componentPlugin: ComponentPlugin = async (structure) => {
|
|
37
|
+
const { uidl, chunks, dependencies } = structure
|
|
38
|
+
const compontnChunk = chunks.find((chunk) => chunk?.name === COMPONENT_CHUNK_NAMES[projectType])
|
|
39
|
+
|
|
40
|
+
if (!compontnChunk) {
|
|
41
|
+
throw new Error(`MIssing component chunk to parse for embeds`)
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
const fromHtml = (await import('hast-util-from-html')).fromHtml
|
|
45
|
+
const hastToJsxOrHtml = await NODE_MAPPER[projectType]
|
|
46
|
+
|
|
47
|
+
UIDLUtils.traverseElements(uidl.node, (element) => {
|
|
48
|
+
const { key, elementType, attrs } = element
|
|
49
|
+
|
|
50
|
+
if (
|
|
51
|
+
(elementType === 'dangerous-html' || element.dependency?.path === 'dangerous-html') &&
|
|
52
|
+
attrs?.html
|
|
53
|
+
) {
|
|
54
|
+
const hastNodes = fromHtml(element.attrs.html.content as string, {
|
|
55
|
+
fragment: true,
|
|
56
|
+
})
|
|
57
|
+
const content = hastToJsxOrHtml(hastNodes, { wrapper: 'fragment' })
|
|
58
|
+
|
|
59
|
+
if (projectType === 'teleport-project-html' || projectType === 'html') {
|
|
60
|
+
const node = compontnChunk.meta.nodesLookup[key] as HastNode
|
|
61
|
+
if (!node) {
|
|
62
|
+
return
|
|
63
|
+
}
|
|
64
|
+
/*
|
|
65
|
+
Convert the HastNode to HastText
|
|
66
|
+
*/
|
|
67
|
+
|
|
68
|
+
Object.assign(node, {
|
|
69
|
+
type: 'text',
|
|
70
|
+
value: content,
|
|
71
|
+
})
|
|
72
|
+
|
|
73
|
+
delete node.children
|
|
74
|
+
delete node.properties
|
|
75
|
+
delete dependencies['dangerous-html']
|
|
76
|
+
} else {
|
|
77
|
+
const node = compontnChunk.meta.nodesLookup[key] as JSXElement
|
|
78
|
+
if (!node) {
|
|
79
|
+
return
|
|
80
|
+
}
|
|
81
|
+
;(node.openingElement.name as JSXIdentifier).name = 'React.Fragment'
|
|
82
|
+
;(node.closingElement.name as JSXIdentifier).name = 'React.Fragment'
|
|
83
|
+
node.openingElement.attributes = []
|
|
84
|
+
node.children.push({
|
|
85
|
+
type: 'JSXText' as const,
|
|
86
|
+
value: content,
|
|
87
|
+
} as JSXText)
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
})
|
|
91
|
+
|
|
92
|
+
return structure
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
return componentPlugin
|
|
96
|
+
}
|
package/src/index.ts
CHANGED
|
@@ -1,106 +1,31 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
|
|
4
|
-
ProjectPlugin,
|
|
5
|
-
UIDLElementNode,
|
|
6
|
-
UIDLRootComponent,
|
|
7
|
-
ComponentUIDL,
|
|
8
|
-
} from '@teleporthq/teleport-types'
|
|
9
|
-
import { JS_EXECUTION_DEPENDENCIES, SUPPORTED_PROJECT_TYPES } from './utils'
|
|
10
|
-
|
|
11
|
-
const NODE_MAPPER: Record<SUPPORTED_PROJECT_TYPES, Promise<(content: unknown) => string>> = {
|
|
12
|
-
'teleport-project-html': import('hast-util-to-html').then((mod) => mod.toHtml),
|
|
13
|
-
'teleport-project-react': import('hast-util-to-jsx-inline-script').then((mod) => mod.default),
|
|
14
|
-
'teleport-project-next': import('hast-util-to-jsx-inline-script').then((mod) => mod.default),
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
export class ProjectPluginParseEmbed implements ProjectPlugin {
|
|
18
|
-
fromHtml: (value: string, opts: { fragment: boolean }) => unknown
|
|
19
|
-
hastToJsxOrHtml: (content: unknown, opts: { wrapper: string }) => string
|
|
20
|
-
|
|
21
|
-
async loadFromHTML(): Promise<(value: string, opts: { fragment: boolean }) => unknown> {
|
|
22
|
-
if (!this.fromHtml) {
|
|
23
|
-
this.fromHtml = (await import('hast-util-from-html')).fromHtml
|
|
24
|
-
}
|
|
25
|
-
return this.fromHtml
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
async loadNodeMapper(
|
|
29
|
-
id: SUPPORTED_PROJECT_TYPES
|
|
30
|
-
): Promise<(content: unknown, opts: { wrapper: string }) => string> {
|
|
31
|
-
if (!this.hastToJsxOrHtml) {
|
|
32
|
-
this.hastToJsxOrHtml = await NODE_MAPPER[id]
|
|
33
|
-
}
|
|
34
|
-
return this.hastToJsxOrHtml
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
async traverseComponentUIDL(node: UIDLElementNode, id: SUPPORTED_PROJECT_TYPES): Promise<void> {
|
|
38
|
-
return new Promise((resolve, reject) => {
|
|
39
|
-
try {
|
|
40
|
-
UIDLUtils.traverseElements(node, (element) => {
|
|
41
|
-
if (element.elementType === 'html-node' && element.attrs?.html && NODE_MAPPER[id]) {
|
|
42
|
-
const hastNodes = this.fromHtml(element.attrs.html.content as string, {
|
|
43
|
-
fragment: true,
|
|
44
|
-
})
|
|
45
|
-
const content = this.hastToJsxOrHtml(hastNodes, { wrapper: 'fragment' })
|
|
46
|
-
element.elementType = 'container'
|
|
47
|
-
element.attrs = {}
|
|
48
|
-
element.style = { display: { type: 'static', content: 'contents' } }
|
|
49
|
-
element.children = [
|
|
50
|
-
{
|
|
51
|
-
type: 'inject',
|
|
52
|
-
content,
|
|
53
|
-
...(content.includes('<Script') && { dependency: JS_EXECUTION_DEPENDENCIES[id] }),
|
|
54
|
-
},
|
|
55
|
-
]
|
|
56
|
-
}
|
|
57
|
-
})
|
|
58
|
-
resolve()
|
|
59
|
-
} catch (error) {
|
|
60
|
-
reject(error)
|
|
61
|
-
}
|
|
62
|
-
})
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
async traverseNodeAndAddImport(
|
|
66
|
-
componentUIDL: UIDLRootComponent | ComponentUIDL,
|
|
67
|
-
projectType: SUPPORTED_PROJECT_TYPES
|
|
68
|
-
) {
|
|
69
|
-
await this.traverseComponentUIDL(componentUIDL.node, projectType)
|
|
70
|
-
}
|
|
1
|
+
import { ProjectPluginStructure, ProjectPlugin } from '@teleporthq/teleport-types'
|
|
2
|
+
import { createParseEmbedPlugin } from './component-plugin'
|
|
3
|
+
import { SUPPORTED_PROJECT_TYPES } from './utils'
|
|
71
4
|
|
|
5
|
+
class ProjectPluginParseEmbed implements ProjectPlugin {
|
|
72
6
|
async runBefore(structure: ProjectPluginStructure) {
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
7
|
+
const parseEmbedPlugin = createParseEmbedPlugin({
|
|
8
|
+
projectType: structure.strategy.id as SUPPORTED_PROJECT_TYPES,
|
|
9
|
+
})
|
|
76
10
|
|
|
77
|
-
if (
|
|
78
|
-
|
|
11
|
+
if (structure.strategy.pages?.plugins?.length > 0) {
|
|
12
|
+
structure.strategy.pages.plugins.push(parseEmbedPlugin)
|
|
13
|
+
} else {
|
|
14
|
+
structure.strategy.pages.plugins = [parseEmbedPlugin]
|
|
79
15
|
}
|
|
80
16
|
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
for (let i = 0; i < components.length; i++) {
|
|
86
|
-
promises.push(
|
|
87
|
-
this.traverseNodeAndAddImport(structure.uidl.components[components[i]], projectType)
|
|
88
|
-
)
|
|
17
|
+
if (structure.strategy.components?.plugins?.length > 0) {
|
|
18
|
+
structure.strategy.components.plugins.push(parseEmbedPlugin)
|
|
19
|
+
} else {
|
|
20
|
+
structure.strategy.components.plugins = [parseEmbedPlugin]
|
|
89
21
|
}
|
|
90
22
|
|
|
91
|
-
await Promise.all(promises)
|
|
92
23
|
return structure
|
|
93
24
|
}
|
|
94
25
|
|
|
95
26
|
async runAfter(structure: ProjectPluginStructure) {
|
|
96
|
-
if (!NODE_MAPPER[structure.strategy.id as SUPPORTED_PROJECT_TYPES]) {
|
|
97
|
-
return structure
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
if (structure.strategy.id === 'teleport-project-react') {
|
|
101
|
-
structure.dependencies['dangerous-html'] = '^0.1.13'
|
|
102
|
-
}
|
|
103
|
-
|
|
104
27
|
return structure
|
|
105
28
|
}
|
|
106
29
|
}
|
|
30
|
+
|
|
31
|
+
export { createParseEmbedPlugin, ProjectPluginParseEmbed }
|
package/src/utils.ts
CHANGED