@servicenow/sdk-build-core 3.0.2 → 4.0.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/app.d.ts +25 -0
- package/dist/app.js +8 -0
- package/dist/app.js.map +1 -0
- package/dist/compiler.d.ts +60 -0
- package/dist/compiler.js +320 -0
- package/dist/compiler.js.map +1 -0
- package/dist/compression.d.ts +7 -0
- package/dist/compression.js +79 -0
- package/dist/compression.js.map +1 -0
- package/dist/crypto.d.ts +1 -0
- package/dist/crypto.js +9 -0
- package/dist/crypto.js.map +1 -0
- package/dist/diagnostic.d.ts +41 -0
- package/dist/diagnostic.js +130 -0
- package/dist/diagnostic.js.map +1 -0
- package/dist/{plugins/Diagnostic.d.ts → fluent-diagnostic.d.ts} +3 -2
- package/dist/fluent-diagnostic.js +23 -0
- package/dist/fluent-diagnostic.js.map +1 -0
- package/dist/fluent-directive.d.ts +8 -0
- package/dist/fluent-directive.js +54 -0
- package/dist/fluent-directive.js.map +1 -0
- package/dist/fluent-file.d.ts +5 -0
- package/dist/fluent-file.js +15 -0
- package/dist/fluent-file.js.map +1 -0
- package/dist/formatter.d.ts +11 -0
- package/dist/formatter.js +77 -0
- package/dist/formatter.js.map +1 -0
- package/dist/fs.d.ts +174 -0
- package/dist/fs.js +313 -0
- package/dist/fs.js.map +1 -0
- package/dist/guid.d.ts +2 -0
- package/dist/{GUID.js → guid.js} +3 -6
- package/dist/guid.js.map +1 -0
- package/dist/index.d.ts +19 -5
- package/dist/index.js +19 -5
- package/dist/index.js.map +1 -1
- package/dist/json.d.ts +5 -0
- package/dist/json.js +43 -0
- package/dist/json.js.map +1 -0
- package/dist/keys-registry.d.ts +64 -0
- package/dist/keys-registry.js +339 -0
- package/dist/keys-registry.js.map +1 -0
- package/dist/logger.d.ts +8 -0
- package/dist/logger.js +17 -0
- package/dist/logger.js.map +1 -0
- package/dist/now-config.d.ts +348 -0
- package/dist/now-config.js +283 -0
- package/dist/now-config.js.map +1 -0
- package/dist/path.d.ts +3 -0
- package/dist/path.js +12 -0
- package/dist/path.js.map +1 -0
- package/dist/plugins/cache.d.ts +20 -0
- package/dist/plugins/cache.js +46 -0
- package/dist/plugins/cache.js.map +1 -0
- package/dist/plugins/context.d.ts +85 -0
- package/dist/plugins/{Context.js → context.js} +1 -1
- package/dist/plugins/context.js.map +1 -0
- package/dist/plugins/database.d.ts +27 -0
- package/dist/plugins/database.js +102 -0
- package/dist/plugins/database.js.map +1 -0
- package/dist/plugins/file.d.ts +10 -0
- package/dist/plugins/{behaviors/Arranger.js → file.js} +1 -1
- package/dist/plugins/file.js.map +1 -0
- package/dist/plugins/index.d.ts +9 -5
- package/dist/plugins/index.js +9 -6
- package/dist/plugins/index.js.map +1 -1
- package/dist/plugins/plugin.d.ts +478 -0
- package/dist/plugins/plugin.js +533 -0
- package/dist/plugins/plugin.js.map +1 -0
- package/dist/plugins/product.d.ts +15 -0
- package/dist/plugins/product.js +38 -0
- package/dist/plugins/product.js.map +1 -0
- package/dist/plugins/project.d.ts +25 -0
- package/dist/plugins/{behaviors/Generator.js → project.js} +1 -1
- package/dist/plugins/project.js.map +1 -0
- package/dist/plugins/shape.d.ts +424 -0
- package/dist/plugins/shape.js +1181 -0
- package/dist/plugins/shape.js.map +1 -0
- package/dist/plugins/time.d.ts +12 -0
- package/dist/plugins/time.js +84 -0
- package/dist/plugins/time.js.map +1 -0
- package/dist/plugins/usage.d.ts +11 -0
- package/dist/plugins/usage.js +26 -0
- package/dist/plugins/usage.js.map +1 -0
- package/dist/prettier/config-loader.d.ts +13 -0
- package/dist/prettier/config-loader.js +105 -0
- package/dist/prettier/config-loader.js.map +1 -0
- package/dist/telemetry/index.d.ts +25 -0
- package/dist/telemetry/index.js +18 -0
- package/dist/telemetry/index.js.map +1 -0
- package/dist/typescript.d.ts +293 -0
- package/dist/typescript.js +454 -0
- package/dist/typescript.js.map +1 -0
- package/dist/util/get-file-type.d.ts +2 -0
- package/dist/util/get-file-type.js +13 -0
- package/dist/util/get-file-type.js.map +1 -0
- package/dist/util/index.d.ts +2 -6
- package/dist/util/index.js +2 -6
- package/dist/util/index.js.map +1 -1
- package/dist/util/{Scope.js → is-sn-scope.js} +1 -1
- package/dist/util/is-sn-scope.js.map +1 -0
- package/dist/xml.d.ts +24 -0
- package/dist/xml.js +71 -0
- package/dist/xml.js.map +1 -0
- package/now.config.schema.json +336 -0
- package/package.json +22 -12
- package/src/app.ts +33 -0
- package/src/compiler.ts +384 -0
- package/src/compression.ts +93 -0
- package/src/crypto.ts +5 -0
- package/src/diagnostic.ts +108 -0
- package/src/{plugins/Diagnostic.ts → fluent-diagnostic.ts} +3 -10
- package/src/fluent-directive.ts +63 -0
- package/src/fluent-file.ts +13 -0
- package/src/formatter.ts +58 -0
- package/src/fs.ts +438 -0
- package/src/{GUID.ts → guid.ts} +2 -6
- package/src/index.ts +19 -5
- package/src/json.ts +20 -0
- package/src/keys-registry.ts +384 -0
- package/src/logger.ts +20 -0
- package/src/now-config.ts +337 -0
- package/src/path.ts +9 -0
- package/src/plugins/cache.ts +45 -0
- package/src/plugins/context.ts +93 -0
- package/src/plugins/database.ts +121 -0
- package/src/plugins/file.ts +19 -0
- package/src/plugins/index.ts +9 -5
- package/src/plugins/plugin.ts +995 -0
- package/src/plugins/product.ts +44 -0
- package/src/plugins/project.ts +39 -0
- package/src/plugins/shape.ts +1532 -0
- package/src/plugins/time.ts +108 -0
- package/src/plugins/usage.ts +26 -0
- package/src/prettier/config-loader.ts +130 -0
- package/src/telemetry/index.ts +27 -0
- package/src/typescript.ts +502 -0
- package/src/util/get-file-type.ts +11 -0
- package/src/util/index.ts +2 -6
- package/src/xml.ts +86 -0
- package/dist/GUID.d.ts +0 -2
- package/dist/GUID.js.map +0 -1
- package/dist/IncludePaths.d.ts +0 -25
- package/dist/IncludePaths.js +0 -97
- package/dist/IncludePaths.js.map +0 -1
- package/dist/Keys.d.ts +0 -32
- package/dist/Keys.js +0 -245
- package/dist/Keys.js.map +0 -1
- package/dist/TypeScript.d.ts +0 -5
- package/dist/TypeScript.js +0 -58
- package/dist/TypeScript.js.map +0 -1
- package/dist/XML.d.ts +0 -32
- package/dist/XML.js +0 -77
- package/dist/XML.js.map +0 -1
- package/dist/plugins/Context.d.ts +0 -190
- package/dist/plugins/Context.js.map +0 -1
- package/dist/plugins/Diagnostic.js +0 -28
- package/dist/plugins/Diagnostic.js.map +0 -1
- package/dist/plugins/Plugin.d.ts +0 -175
- package/dist/plugins/Plugin.js +0 -15
- package/dist/plugins/Plugin.js.map +0 -1
- package/dist/plugins/behaviors/Arranger.d.ts +0 -26
- package/dist/plugins/behaviors/Arranger.js.map +0 -1
- package/dist/plugins/behaviors/Composer.d.ts +0 -102
- package/dist/plugins/behaviors/Composer.js +0 -15
- package/dist/plugins/behaviors/Composer.js.map +0 -1
- package/dist/plugins/behaviors/Diagnostics.d.ts +0 -7
- package/dist/plugins/behaviors/Diagnostics.js +0 -3
- package/dist/plugins/behaviors/Diagnostics.js.map +0 -1
- package/dist/plugins/behaviors/Generator.d.ts +0 -21
- package/dist/plugins/behaviors/Generator.js.map +0 -1
- package/dist/plugins/behaviors/OwnedTables.d.ts +0 -6
- package/dist/plugins/behaviors/OwnedTables.js +0 -3
- package/dist/plugins/behaviors/OwnedTables.js.map +0 -1
- package/dist/plugins/behaviors/PostProcessor.d.ts +0 -5
- package/dist/plugins/behaviors/PostProcessor.js +0 -3
- package/dist/plugins/behaviors/PostProcessor.js.map +0 -1
- package/dist/plugins/behaviors/Serializer.d.ts +0 -30
- package/dist/plugins/behaviors/Serializer.js +0 -3
- package/dist/plugins/behaviors/Serializer.js.map +0 -1
- package/dist/plugins/behaviors/Transformer.d.ts +0 -23
- package/dist/plugins/behaviors/Transformer.js +0 -3
- package/dist/plugins/behaviors/Transformer.js.map +0 -1
- package/dist/plugins/behaviors/extractors/Data.d.ts +0 -119
- package/dist/plugins/behaviors/extractors/Data.js +0 -244
- package/dist/plugins/behaviors/extractors/Data.js.map +0 -1
- package/dist/plugins/behaviors/extractors/Extractors.d.ts +0 -63
- package/dist/plugins/behaviors/extractors/Extractors.js +0 -3
- package/dist/plugins/behaviors/extractors/Extractors.js.map +0 -1
- package/dist/plugins/behaviors/extractors/index.d.ts +0 -2
- package/dist/plugins/behaviors/extractors/index.js +0 -19
- package/dist/plugins/behaviors/extractors/index.js.map +0 -1
- package/dist/plugins/behaviors/index.d.ts +0 -9
- package/dist/plugins/behaviors/index.js +0 -26
- package/dist/plugins/behaviors/index.js.map +0 -1
- package/dist/plugins/util/CallExpression.d.ts +0 -5
- package/dist/plugins/util/CallExpression.js +0 -88
- package/dist/plugins/util/CallExpression.js.map +0 -1
- package/dist/plugins/util/CodeTransformation.d.ts +0 -95
- package/dist/plugins/util/CodeTransformation.js +0 -624
- package/dist/plugins/util/CodeTransformation.js.map +0 -1
- package/dist/plugins/util/ObjectLiteral.d.ts +0 -9
- package/dist/plugins/util/ObjectLiteral.js +0 -37
- package/dist/plugins/util/ObjectLiteral.js.map +0 -1
- package/dist/plugins/util/index.d.ts +0 -3
- package/dist/plugins/util/index.js +0 -20
- package/dist/plugins/util/index.js.map +0 -1
- package/dist/util/Debug.d.ts +0 -4
- package/dist/util/Debug.js +0 -20
- package/dist/util/Debug.js.map +0 -1
- package/dist/util/Directive.d.ts +0 -16
- package/dist/util/Directive.js +0 -107
- package/dist/util/Directive.js.map +0 -1
- package/dist/util/RuntimeTableSchema.d.ts +0 -5
- package/dist/util/RuntimeTableSchema.js +0 -58
- package/dist/util/RuntimeTableSchema.js.map +0 -1
- package/dist/util/Scope.js.map +0 -1
- package/dist/util/Util.d.ts +0 -1
- package/dist/util/Util.js +0 -12
- package/dist/util/Util.js.map +0 -1
- package/dist/util/XMLUploadParser.d.ts +0 -22
- package/dist/util/XMLUploadParser.js +0 -67
- package/dist/util/XMLUploadParser.js.map +0 -1
- package/src/IncludePaths.ts +0 -122
- package/src/Keys.ts +0 -274
- package/src/TypeScript.ts +0 -65
- package/src/XML.ts +0 -92
- package/src/plugins/Context.ts +0 -239
- package/src/plugins/Plugin.ts +0 -278
- package/src/plugins/behaviors/Arranger.ts +0 -42
- package/src/plugins/behaviors/Composer.ts +0 -125
- package/src/plugins/behaviors/Diagnostics.ts +0 -12
- package/src/plugins/behaviors/Generator.ts +0 -31
- package/src/plugins/behaviors/OwnedTables.ts +0 -5
- package/src/plugins/behaviors/PostProcessor.ts +0 -6
- package/src/plugins/behaviors/Serializer.ts +0 -40
- package/src/plugins/behaviors/Transformer.ts +0 -32
- package/src/plugins/behaviors/extractors/Data.ts +0 -332
- package/src/plugins/behaviors/extractors/Extractors.ts +0 -73
- package/src/plugins/behaviors/extractors/index.ts +0 -2
- package/src/plugins/behaviors/index.ts +0 -9
- package/src/plugins/util/CallExpression.ts +0 -110
- package/src/plugins/util/CodeTransformation.ts +0 -731
- package/src/plugins/util/ObjectLiteral.ts +0 -37
- package/src/plugins/util/index.ts +0 -3
- package/src/util/Debug.ts +0 -24
- package/src/util/Directive.ts +0 -123
- package/src/util/RuntimeTableSchema.ts +0 -44
- package/src/util/Util.ts +0 -7
- package/src/util/XMLUploadParser.ts +0 -90
- /package/dist/util/{Scope.d.ts → is-sn-scope.d.ts} +0 -0
- /package/src/util/{Scope.ts → is-sn-scope.ts} +0 -0
|
@@ -1,731 +0,0 @@
|
|
|
1
|
-
import { Logger, NOW_FILE_EXTENSION, SupportedNode, path, ts, tsc } from '@servicenow/sdk-project'
|
|
2
|
-
const { format, resolve } = path
|
|
3
|
-
import { Context } from '../Context'
|
|
4
|
-
import { getCallExpressionName } from './CallExpression'
|
|
5
|
-
import { isArray, isEmpty, isObject, isPlainObject } from 'lodash'
|
|
6
|
-
import * as z from 'zod'
|
|
7
|
-
import { Action, Document } from '../behaviors'
|
|
8
|
-
import { isGUID } from '../../GUID'
|
|
9
|
-
import { noThrow } from '../../util'
|
|
10
|
-
import { getPropertyAssignment } from './ObjectLiteral'
|
|
11
|
-
|
|
12
|
-
export function stringify(val: unknown) {
|
|
13
|
-
if (typeof val === 'function') {
|
|
14
|
-
return val.toString()
|
|
15
|
-
}
|
|
16
|
-
return JSON.stringify(val)
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
export type PartialElements<A extends unknown[]> = {
|
|
20
|
-
[I in keyof A]: Partial<A[I]>
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
/**
|
|
24
|
-
* Formats a source file name with the .now.ts extension.
|
|
25
|
-
*/
|
|
26
|
-
export function formatSourceFileName(name: string) {
|
|
27
|
-
return format({
|
|
28
|
-
name,
|
|
29
|
-
ext: NOW_FILE_EXTENSION,
|
|
30
|
-
})
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
export function getSysUpdateName(document: Document & { xml?: string }, table: string) {
|
|
34
|
-
if (document.xmlFilePath) {
|
|
35
|
-
return path.basename(document.xmlFilePath, path.extname(document.xmlFilePath))
|
|
36
|
-
}
|
|
37
|
-
return `${table}_${document.guid}`
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
export function getOrCreateEntitySourceFile(context: Context, sysUpdateName: string) {
|
|
41
|
-
const fullPath = resolve(context.app.rootDir, context.app.config.generatedDir, formatSourceFileName(sysUpdateName))
|
|
42
|
-
const sourceFile = context.compiler.getSourceFile(fullPath)
|
|
43
|
-
if (sourceFile) {
|
|
44
|
-
return sourceFile
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
context.logger.info(`Generating new source file: ${fullPath}`)
|
|
48
|
-
return context.compiler.createSourceFile(fullPath)
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
export function addDefaultImportIfAbsent(sourceFile: ts.SourceFile, moduleSpecifier: string, module: string) {
|
|
52
|
-
const importDeclaration = sourceFile.getImportDeclaration((d) => d.getModuleSpecifierValue() === moduleSpecifier)
|
|
53
|
-
if (!importDeclaration) {
|
|
54
|
-
sourceFile.addImportDeclaration({
|
|
55
|
-
moduleSpecifier,
|
|
56
|
-
defaultImport: module,
|
|
57
|
-
})
|
|
58
|
-
return
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
const defaultImport = importDeclaration.getDefaultImport()?.getText()
|
|
62
|
-
if (defaultImport && defaultImport === module) {
|
|
63
|
-
return
|
|
64
|
-
}
|
|
65
|
-
importDeclaration.setDefaultImport(module)
|
|
66
|
-
}
|
|
67
|
-
|
|
68
|
-
export function addNamedImportIfAbsent(
|
|
69
|
-
context: Context,
|
|
70
|
-
sourceFile: ts.SourceFile,
|
|
71
|
-
moduleSpecifier: string,
|
|
72
|
-
module: { name: string } | string
|
|
73
|
-
): ts.ImportSpecifier {
|
|
74
|
-
let importDeclaration = sourceFile.getImportDeclaration(
|
|
75
|
-
(d) => d.getModuleSpecifierValue() === moduleSpecifier && !d.getNamespaceImport() // If it's a namespace import we cannot add named imports, so we have to create a new one
|
|
76
|
-
)
|
|
77
|
-
|
|
78
|
-
const importName = typeof module === 'string' ? module : module.name
|
|
79
|
-
if (!importDeclaration) {
|
|
80
|
-
importDeclaration = sourceFile.addImportDeclaration({
|
|
81
|
-
moduleSpecifier,
|
|
82
|
-
namedImports: [importName],
|
|
83
|
-
})
|
|
84
|
-
}
|
|
85
|
-
|
|
86
|
-
const namedImports = importDeclaration.getNamedImports().find((n) => n.getName() === importName)
|
|
87
|
-
if (namedImports) {
|
|
88
|
-
return namedImports
|
|
89
|
-
}
|
|
90
|
-
|
|
91
|
-
context.logger.debug(
|
|
92
|
-
`Adding named import '${importName}' from module '${moduleSpecifier}' to source file: ${sourceFile.getFilePath()}`
|
|
93
|
-
)
|
|
94
|
-
|
|
95
|
-
return importDeclaration.addNamedImport(importName)
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
/**
|
|
99
|
-
* Generate an exported variable assignment initialized by a function call with
|
|
100
|
-
* the provided arguments.
|
|
101
|
-
*/
|
|
102
|
-
export function generateCallExpressionDefaultExport<const A extends unknown[]>(
|
|
103
|
-
context: Context,
|
|
104
|
-
sourceFile: ts.SourceFile,
|
|
105
|
-
moduleSpecifier: string,
|
|
106
|
-
fn: (...args: A) => unknown,
|
|
107
|
-
...args: PartialElements<A>
|
|
108
|
-
) {
|
|
109
|
-
addNamedImportIfAbsent(context, sourceFile, moduleSpecifier, fn)
|
|
110
|
-
const exportAssignment = sourceFile.addExportAssignment({
|
|
111
|
-
isExportEquals: false,
|
|
112
|
-
expression: `${fn.name}()`,
|
|
113
|
-
})
|
|
114
|
-
|
|
115
|
-
const callExpression = exportAssignment.getExpressionIfKindOrThrow(ts.SyntaxKind.CallExpression)
|
|
116
|
-
transformFunctionArguments(callExpression, fn, ...args)
|
|
117
|
-
|
|
118
|
-
return exportAssignment
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
export function generateCallExpressionExport<const A extends unknown[]>(
|
|
122
|
-
context: Context,
|
|
123
|
-
sourceFile: ts.SourceFile,
|
|
124
|
-
moduleSpecifier: string,
|
|
125
|
-
exportName: string,
|
|
126
|
-
fn: (...args: A) => unknown,
|
|
127
|
-
...args: PartialElements<A>
|
|
128
|
-
) {
|
|
129
|
-
addNamedImportIfAbsent(context, sourceFile, moduleSpecifier, fn)
|
|
130
|
-
const variableDeclaration = sourceFile
|
|
131
|
-
.addVariableStatement({
|
|
132
|
-
isExported: true,
|
|
133
|
-
declarationKind: ts.VariableDeclarationKind.Const,
|
|
134
|
-
declarations: [
|
|
135
|
-
{
|
|
136
|
-
name: exportName,
|
|
137
|
-
initializer: `${fn.name}()`, // Generate empty function call since we will add arguments later
|
|
138
|
-
},
|
|
139
|
-
],
|
|
140
|
-
})
|
|
141
|
-
.getDeclarations()[0]!
|
|
142
|
-
|
|
143
|
-
// Transform function call to add arguments
|
|
144
|
-
const callExpression = variableDeclaration.getInitializerIfKindOrThrow(ts.SyntaxKind.CallExpression)
|
|
145
|
-
transformFunctionArguments(callExpression, fn, ...args)
|
|
146
|
-
|
|
147
|
-
return variableDeclaration
|
|
148
|
-
}
|
|
149
|
-
|
|
150
|
-
export function generateCallExpression<const A extends unknown[]>(
|
|
151
|
-
context: Context,
|
|
152
|
-
sourceFile: ts.SourceFile,
|
|
153
|
-
moduleSpecifier: string,
|
|
154
|
-
fn: (...args: A) => unknown,
|
|
155
|
-
...args: PartialElements<A>
|
|
156
|
-
) {
|
|
157
|
-
addNamedImportIfAbsent(context, sourceFile, moduleSpecifier, fn)
|
|
158
|
-
sourceFile.addStatements((writer) => writer.newLine())
|
|
159
|
-
const [statement] = sourceFile.addStatements(`${fn.name}()`)
|
|
160
|
-
|
|
161
|
-
const expression = statement!.getChildAtIndexIfKindOrThrow(0, ts.SyntaxKind.CallExpression)
|
|
162
|
-
|
|
163
|
-
transformFunctionArguments(expression, fn, ...args)
|
|
164
|
-
|
|
165
|
-
return expression
|
|
166
|
-
}
|
|
167
|
-
|
|
168
|
-
/**
|
|
169
|
-
* Generate an exported variable assignment initialized by a function call with the
|
|
170
|
-
* provided arguments. The exported variable name will be automatically determined
|
|
171
|
-
* based on the function's name and the document's ID.
|
|
172
|
-
*/
|
|
173
|
-
export function generateCallExpressionExportForDocument<const A extends unknown[]>(
|
|
174
|
-
context: Context,
|
|
175
|
-
info: {
|
|
176
|
-
sourceFile: ts.SourceFile
|
|
177
|
-
moduleSpecifier: string
|
|
178
|
-
},
|
|
179
|
-
fn: (...args: A) => unknown,
|
|
180
|
-
...args: PartialElements<A>
|
|
181
|
-
) {
|
|
182
|
-
const { sourceFile, moduleSpecifier } = info
|
|
183
|
-
return generateCallExpressionDefaultExport(context, sourceFile, moduleSpecifier, fn, ...args)
|
|
184
|
-
}
|
|
185
|
-
|
|
186
|
-
export function getOrCreatePropertyAssignment(
|
|
187
|
-
obj: ts.ObjectLiteralExpression,
|
|
188
|
-
name: string,
|
|
189
|
-
initializer: string = 'undefined'
|
|
190
|
-
): ts.PropertyAssignment {
|
|
191
|
-
const stringifiedName = stringify(name)
|
|
192
|
-
const prop =
|
|
193
|
-
obj.getProperty(name)?.asKind(ts.SyntaxKind.PropertyAssignment) ??
|
|
194
|
-
obj.getProperty(stringifiedName)?.asKind(ts.SyntaxKind.PropertyAssignment)
|
|
195
|
-
|
|
196
|
-
if (prop) {
|
|
197
|
-
return prop
|
|
198
|
-
}
|
|
199
|
-
|
|
200
|
-
let propOrErr
|
|
201
|
-
/**
|
|
202
|
-
* Adding back the previous stringify regex check because property name with space when set without stringified works but later on throws error
|
|
203
|
-
*/
|
|
204
|
-
if (/^[a-zA-Z0-9_$]*$/.test(name)) {
|
|
205
|
-
propOrErr = noThrow(() => obj.addPropertyAssignment({ name, initializer }))
|
|
206
|
-
}
|
|
207
|
-
|
|
208
|
-
if (!propOrErr || propOrErr instanceof Error) {
|
|
209
|
-
return obj.addPropertyAssignment({ name: stringifiedName, initializer })
|
|
210
|
-
}
|
|
211
|
-
return propOrErr
|
|
212
|
-
}
|
|
213
|
-
|
|
214
|
-
export function isEscapedPropertyAssignment(args: ts.ObjectLiteralExpression, name: string) {
|
|
215
|
-
const prop = args.getProperty(name)
|
|
216
|
-
if (!prop) {
|
|
217
|
-
return false
|
|
218
|
-
}
|
|
219
|
-
|
|
220
|
-
const asExpression = prop.getChildAtIndexIfKind(2, ts.SyntaxKind.AsExpression)
|
|
221
|
-
if (asExpression && asExpression.getFullText().indexOf('any') !== -1) {
|
|
222
|
-
return true
|
|
223
|
-
}
|
|
224
|
-
|
|
225
|
-
return false
|
|
226
|
-
}
|
|
227
|
-
|
|
228
|
-
function isResolvablePropertyAssignment(args: ts.ObjectLiteralExpression, propertyName: string) {
|
|
229
|
-
const prop = args.getProperty(propertyName)
|
|
230
|
-
if (!prop) {
|
|
231
|
-
return false
|
|
232
|
-
}
|
|
233
|
-
|
|
234
|
-
const identifierExp = prop.getChildAtIndexIfKind(2, ts.SyntaxKind.Identifier)
|
|
235
|
-
if (!identifierExp) {
|
|
236
|
-
return false
|
|
237
|
-
}
|
|
238
|
-
|
|
239
|
-
// Variable definition may be from other file
|
|
240
|
-
identifierExp.getSourceFile().fixMissingImports()
|
|
241
|
-
|
|
242
|
-
const definitions = identifierExp.getDefinitionNodes()
|
|
243
|
-
if (definitions && definitions.length > 0) {
|
|
244
|
-
return true
|
|
245
|
-
}
|
|
246
|
-
return false
|
|
247
|
-
}
|
|
248
|
-
|
|
249
|
-
/** utility function to get the $id value in a object literal node */
|
|
250
|
-
export const getNodeId = (node: ts.ObjectLiteralExpression) => {
|
|
251
|
-
const prop = node.getPropertyOrThrow('$id').asKindOrThrow(ts.SyntaxKind.PropertyAssignment)
|
|
252
|
-
|
|
253
|
-
if (prop.getInitializerIfKind(ts.SyntaxKind.ElementAccessExpression)) {
|
|
254
|
-
const expression = prop.getInitializerIfKind(ts.SyntaxKind.ElementAccessExpression)?.getArgumentExpression()
|
|
255
|
-
return (
|
|
256
|
-
expression?.asKind(ts.SyntaxKind.StringLiteral)?.getLiteralValue() ??
|
|
257
|
-
expression?.asKind(ts.SyntaxKind.NumericLiteral)?.getLiteralValue().toString()
|
|
258
|
-
)
|
|
259
|
-
} else if (prop.getInitializerIfKind(ts.SyntaxKind.StringLiteral)) {
|
|
260
|
-
return prop.getInitializerIfKind(ts.SyntaxKind.StringLiteral)?.getLiteralValue()
|
|
261
|
-
}
|
|
262
|
-
return `${prop.getInitializerIfKind(ts.SyntaxKind.NumericLiteral)?.getLiteralValue()}`
|
|
263
|
-
}
|
|
264
|
-
|
|
265
|
-
/** utility iterator for iterating array structures in rest api*/
|
|
266
|
-
export class ArrayIterator {
|
|
267
|
-
arrayExpression: ts.ArrayLiteralExpression
|
|
268
|
-
elements: ts.Expression<tsc.Expression>[]
|
|
269
|
-
idx: number
|
|
270
|
-
|
|
271
|
-
constructor(private prop: ts.PropertyAssignment) {
|
|
272
|
-
this.arrayExpression = this.prop.getInitializerIfKindOrThrow(ts.SyntaxKind.ArrayLiteralExpression)!
|
|
273
|
-
this.elements = this.arrayExpression.getElements()
|
|
274
|
-
this.idx = 0
|
|
275
|
-
}
|
|
276
|
-
|
|
277
|
-
hasNext() {
|
|
278
|
-
return this.idx < this.elements.length
|
|
279
|
-
}
|
|
280
|
-
|
|
281
|
-
next() {
|
|
282
|
-
return this.elements[this.idx++]!
|
|
283
|
-
}
|
|
284
|
-
|
|
285
|
-
getExpression() {
|
|
286
|
-
return this.arrayExpression
|
|
287
|
-
}
|
|
288
|
-
}
|
|
289
|
-
|
|
290
|
-
export function writeArrayPropertyAsReference(
|
|
291
|
-
arg: ts.ObjectLiteralExpression,
|
|
292
|
-
name: string,
|
|
293
|
-
def: string,
|
|
294
|
-
value: string[]
|
|
295
|
-
) {
|
|
296
|
-
if (!value || !isArray(value)) {
|
|
297
|
-
return
|
|
298
|
-
}
|
|
299
|
-
|
|
300
|
-
const propertyAssignment = getOrCreatePropertyAssignment(arg, name, def)
|
|
301
|
-
|
|
302
|
-
const newValues = value.map((val) => {
|
|
303
|
-
propertyAssignment.setInitializer((writer) => {
|
|
304
|
-
writer.write(val)
|
|
305
|
-
})
|
|
306
|
-
|
|
307
|
-
return isResolvablePropertyAssignment(arg, name) ? val : `'${val}' as any`
|
|
308
|
-
})
|
|
309
|
-
|
|
310
|
-
propertyAssignment.setInitializer((writer) => {
|
|
311
|
-
writer.write(`[${newValues}]`)
|
|
312
|
-
})
|
|
313
|
-
}
|
|
314
|
-
|
|
315
|
-
export const recordSchema = z.object({
|
|
316
|
-
$id: z.union([z.string(), z.number()]),
|
|
317
|
-
data: z.record(z.any()),
|
|
318
|
-
table: z.string(),
|
|
319
|
-
})
|
|
320
|
-
|
|
321
|
-
export function addCallExpressionToProperty(obj: ts.ObjectLiteralExpression, field: string, functionCall) {
|
|
322
|
-
const property = getOrCreatePropertyAssignment(obj, field, functionCall)
|
|
323
|
-
property.setInitializer((writer) => {
|
|
324
|
-
writer.write(functionCall)
|
|
325
|
-
})
|
|
326
|
-
}
|
|
327
|
-
|
|
328
|
-
export function writePropertyAsReference(
|
|
329
|
-
logger: Logger,
|
|
330
|
-
arg: ts.ObjectLiteralExpression,
|
|
331
|
-
name: string,
|
|
332
|
-
def: string,
|
|
333
|
-
value: unknown
|
|
334
|
-
) {
|
|
335
|
-
if (!value || isArray(value)) {
|
|
336
|
-
return
|
|
337
|
-
}
|
|
338
|
-
|
|
339
|
-
// This value is already a reference that we shouldn't attempt to resolve
|
|
340
|
-
if (recordSchema.safeParse(value).success) {
|
|
341
|
-
return
|
|
342
|
-
}
|
|
343
|
-
|
|
344
|
-
const propertyAssignment = getOrCreatePropertyAssignment(arg, name, def)
|
|
345
|
-
|
|
346
|
-
if (isEmpty(value)) {
|
|
347
|
-
propertyAssignment.setInitializer((writer) => {
|
|
348
|
-
writer.write(stringify(value))
|
|
349
|
-
})
|
|
350
|
-
}
|
|
351
|
-
|
|
352
|
-
if (isPlainObject(value)) {
|
|
353
|
-
const nestedArgs = propertyAssignment.getInitializerIfKindOrThrow(ts.SyntaxKind.ObjectLiteralExpression)
|
|
354
|
-
for (const property in value) {
|
|
355
|
-
if (isArray(value[property])) {
|
|
356
|
-
writeArrayPropertyAsReference(nestedArgs, property, '[]', value[property])
|
|
357
|
-
} else {
|
|
358
|
-
writePropertyAsReference(logger, nestedArgs, property, '{}', value[property])
|
|
359
|
-
}
|
|
360
|
-
}
|
|
361
|
-
|
|
362
|
-
return
|
|
363
|
-
}
|
|
364
|
-
|
|
365
|
-
const escapedPreTransform = isEscapedPropertyAssignment(arg, name)
|
|
366
|
-
|
|
367
|
-
if (isGUID(value as string)) {
|
|
368
|
-
propertyAssignment.setInitializer((writer) => {
|
|
369
|
-
writer.write(stringify(value))
|
|
370
|
-
})
|
|
371
|
-
return
|
|
372
|
-
}
|
|
373
|
-
|
|
374
|
-
// This first write is to check whether the value is a resolvable idenfifier
|
|
375
|
-
// We don't want to throw here if the property assignment would be malformed
|
|
376
|
-
const maybeError = noThrow(() => {
|
|
377
|
-
propertyAssignment.setInitializer((writer) => {
|
|
378
|
-
if (value === 'default') {
|
|
379
|
-
writer.write(stringify(value))
|
|
380
|
-
} else {
|
|
381
|
-
writer.write(value as string)
|
|
382
|
-
}
|
|
383
|
-
})
|
|
384
|
-
})
|
|
385
|
-
if (maybeError instanceof Error) {
|
|
386
|
-
logger.warn(
|
|
387
|
-
`Invalid reference value '${value}' for property '${name}' in file ${arg.getSourceFile().getFilePath()}`
|
|
388
|
-
)
|
|
389
|
-
}
|
|
390
|
-
if (isResolvablePropertyAssignment(arg, name)) {
|
|
391
|
-
return
|
|
392
|
-
}
|
|
393
|
-
|
|
394
|
-
value = `${stringify(value)} as any`
|
|
395
|
-
if (!escapedPreTransform) {
|
|
396
|
-
// Generate comment
|
|
397
|
-
value = `${value} /*Generated*/` // comment like this '//comment' breaks the code in some occasion
|
|
398
|
-
}
|
|
399
|
-
|
|
400
|
-
propertyAssignment.setInitializer((writer) => {
|
|
401
|
-
writer.write(value as string)
|
|
402
|
-
})
|
|
403
|
-
}
|
|
404
|
-
|
|
405
|
-
export function writeCustomProperty(arg: ts.ObjectLiteralExpression, name: string, def: string, value: string) {
|
|
406
|
-
if (!value) {
|
|
407
|
-
return
|
|
408
|
-
}
|
|
409
|
-
|
|
410
|
-
const propertyAssignment = getOrCreatePropertyAssignment(arg, name, def)
|
|
411
|
-
propertyAssignment.setInitializer((writer) => {
|
|
412
|
-
writer.write(value)
|
|
413
|
-
})
|
|
414
|
-
}
|
|
415
|
-
|
|
416
|
-
export function mergeDataIntoObjectLiteral(node: ts.ObjectLiteralExpression, data: object) {
|
|
417
|
-
const properties = node
|
|
418
|
-
.getProperties()
|
|
419
|
-
.reduce((a, v) => ({ ...a, [getObjectPropertyAssignmentName(v as ts.PropertyAssignment)]: v }), {})
|
|
420
|
-
for (const [key, value] of Object.entries(data)) {
|
|
421
|
-
const array = isArray(value)
|
|
422
|
-
if (!isEmpty(properties) && (value === '' || (array && value.length === 0))) {
|
|
423
|
-
const existingAssignment = properties[key]
|
|
424
|
-
if (existingAssignment) {
|
|
425
|
-
removeNode(existingAssignment)
|
|
426
|
-
}
|
|
427
|
-
}
|
|
428
|
-
|
|
429
|
-
if (isObject(value) && !Object.values(value).some((value) => value !== undefined)) {
|
|
430
|
-
// Don't write an empty object literal
|
|
431
|
-
continue
|
|
432
|
-
}
|
|
433
|
-
|
|
434
|
-
if (value !== '' && value !== undefined && !(array && value.length === 0)) {
|
|
435
|
-
const propertyAssignment = properties[key]
|
|
436
|
-
if (propertyAssignment) {
|
|
437
|
-
if (isNowIncludeCall(propertyAssignment.getInitializerIfKind(ts.SyntaxKind.CallExpression))) {
|
|
438
|
-
// Don't transform any updates to Now.includes calls
|
|
439
|
-
continue
|
|
440
|
-
}
|
|
441
|
-
setPropertyAssignmentValue(propertyAssignment, value)
|
|
442
|
-
} else {
|
|
443
|
-
const newPropertyAssignment = getOrCreatePropertyAssignment(node, key, array ? '[]' : '{}')
|
|
444
|
-
setPropertyAssignmentValue(newPropertyAssignment, value)
|
|
445
|
-
}
|
|
446
|
-
}
|
|
447
|
-
}
|
|
448
|
-
}
|
|
449
|
-
|
|
450
|
-
/**
|
|
451
|
-
* Merges an array of object literal data in to an existing array of object literal values
|
|
452
|
-
* @param arrayNode Node with array to transform
|
|
453
|
-
* @param data Array of object literals
|
|
454
|
-
* @param comparisonProperty a property to be treated as the primary key of each object literal for comparison
|
|
455
|
-
* @param action Should this item be deleted if found?
|
|
456
|
-
*/
|
|
457
|
-
export function mergeDataIntoObjectLiteralArray(
|
|
458
|
-
arrayNode: ts.ArrayLiteralExpression,
|
|
459
|
-
data: any[],
|
|
460
|
-
comparisonProperty: string,
|
|
461
|
-
action?: Action
|
|
462
|
-
) {
|
|
463
|
-
if (!data || data.length < 1) {
|
|
464
|
-
return
|
|
465
|
-
}
|
|
466
|
-
|
|
467
|
-
const mappedData = data.reduce((map, obj) => ((map[obj[`${comparisonProperty}`]] = obj), map), {})
|
|
468
|
-
arrayNode.getElements().forEach((element) => {
|
|
469
|
-
const existingProperty =
|
|
470
|
-
element
|
|
471
|
-
.asKindOrThrow(ts.SyntaxKind.ObjectLiteralExpression)
|
|
472
|
-
.getProperty(`${comparisonProperty}`)
|
|
473
|
-
?.getFirstChildByKind(ts.SyntaxKind.StringLiteral)
|
|
474
|
-
?.getLiteralValue() ?? undefined
|
|
475
|
-
if (existingProperty && !mappedData[existingProperty]) {
|
|
476
|
-
arrayNode.removeElement(element)
|
|
477
|
-
}
|
|
478
|
-
})
|
|
479
|
-
const existingElements = arrayNode.getElements()
|
|
480
|
-
data.forEach((obj) => {
|
|
481
|
-
const transformElement = existingElements.find((element) => {
|
|
482
|
-
const prop = element.asKindOrThrow(ts.SyntaxKind.ObjectLiteralExpression)
|
|
483
|
-
const existingProperty = getPropertyAssignment(prop, `${comparisonProperty}`)?.getInitializerIfKind(
|
|
484
|
-
ts.SyntaxKind.StringLiteral
|
|
485
|
-
)
|
|
486
|
-
return obj[`${comparisonProperty}`] === existingProperty?.getLiteralValue()
|
|
487
|
-
})
|
|
488
|
-
|
|
489
|
-
// Found existing element in arrays
|
|
490
|
-
if (transformElement) {
|
|
491
|
-
if (action && action === 'DELETE') {
|
|
492
|
-
arrayNode.removeElement(transformElement)
|
|
493
|
-
} else {
|
|
494
|
-
mergeDataIntoObjectLiteral(transformElement.asKindOrThrow(ts.SyntaxKind.ObjectLiteralExpression), obj)
|
|
495
|
-
}
|
|
496
|
-
} else {
|
|
497
|
-
arrayNode.addElement(stringify(filterEmpty(obj)))
|
|
498
|
-
}
|
|
499
|
-
})
|
|
500
|
-
}
|
|
501
|
-
|
|
502
|
-
// Remove default empty values
|
|
503
|
-
export function filterEmpty(data: any) {
|
|
504
|
-
return Object.entries(data).reduce((acc, [key, value]) => {
|
|
505
|
-
if (value !== '') {
|
|
506
|
-
acc[key] = value
|
|
507
|
-
}
|
|
508
|
-
return acc
|
|
509
|
-
}, {})
|
|
510
|
-
}
|
|
511
|
-
|
|
512
|
-
export function escapeStringLiteralValues(str: string) {
|
|
513
|
-
return str.replace(/[`\\]|\${/g, (char) => {
|
|
514
|
-
switch (char) {
|
|
515
|
-
case '`':
|
|
516
|
-
return '\\`'
|
|
517
|
-
case '\\':
|
|
518
|
-
return '\\' + char
|
|
519
|
-
case '${':
|
|
520
|
-
return '\\${'
|
|
521
|
-
default:
|
|
522
|
-
return char
|
|
523
|
-
}
|
|
524
|
-
})
|
|
525
|
-
}
|
|
526
|
-
|
|
527
|
-
export function setPropertyAssignmentValue(
|
|
528
|
-
property: ts.PropertyAssignment,
|
|
529
|
-
value: string | ts.PropertyAssignmentStructure | ts.ImportSpecifierStructure | object
|
|
530
|
-
) {
|
|
531
|
-
if (typeof value === 'object') {
|
|
532
|
-
if (ts.Structure.isPropertyAssignment(value)) {
|
|
533
|
-
property.setInitializer(value.initializer)
|
|
534
|
-
} else if (ts.Structure.isImportSpecifier(value)) {
|
|
535
|
-
property.setInitializer(value.name)
|
|
536
|
-
} else if (isArray(value)) {
|
|
537
|
-
property.setInitializer(stringify(value))
|
|
538
|
-
} else {
|
|
539
|
-
mergeDataIntoObjectLiteral(
|
|
540
|
-
property.getInitializerIfKindOrThrow(ts.SyntaxKind.ObjectLiteralExpression),
|
|
541
|
-
value
|
|
542
|
-
)
|
|
543
|
-
}
|
|
544
|
-
return
|
|
545
|
-
}
|
|
546
|
-
|
|
547
|
-
//preserve any tagged template literals
|
|
548
|
-
const taggedInitializer = property.getInitializerIfKind(ts.SyntaxKind.TaggedTemplateExpression)
|
|
549
|
-
if (taggedInitializer) {
|
|
550
|
-
const template = taggedInitializer.getTemplate()
|
|
551
|
-
|
|
552
|
-
template.setLiteralValue(escapeStringLiteralValues(value))
|
|
553
|
-
} else {
|
|
554
|
-
const stringified =
|
|
555
|
-
typeof value !== 'string' || value.indexOf('\n') < 0
|
|
556
|
-
? stringify(value)
|
|
557
|
-
: `\`${escapeStringLiteralValues(value)}\``
|
|
558
|
-
property.setInitializer(stringified)
|
|
559
|
-
}
|
|
560
|
-
}
|
|
561
|
-
|
|
562
|
-
export function fixFunctionArgumentTypes(context: Context, node: ts.CallExpression) {
|
|
563
|
-
if (node.wasForgotten()) {
|
|
564
|
-
return
|
|
565
|
-
}
|
|
566
|
-
const typeChecker = context.compiler.getTypeChecker()
|
|
567
|
-
const signature = typeChecker.getResolvedSignature(node)
|
|
568
|
-
if (signature) {
|
|
569
|
-
const callParams = signature.getParameters()
|
|
570
|
-
for (let i = 0; i < callParams.length; i++) {
|
|
571
|
-
const argType = callParams[i]?.getTypeAtLocation(node)
|
|
572
|
-
const argNode = node.getArguments()[i]?.asKind(ts.SyntaxKind.ObjectLiteralExpression)
|
|
573
|
-
if (!argType || !argNode) {
|
|
574
|
-
break
|
|
575
|
-
}
|
|
576
|
-
fixNodeArgumentType(node, argNode, argType)
|
|
577
|
-
}
|
|
578
|
-
}
|
|
579
|
-
}
|
|
580
|
-
|
|
581
|
-
function fixNodeArgumentType(
|
|
582
|
-
node: ts.CallExpression,
|
|
583
|
-
argNode: ts.ObjectLiteralExpression | ts.PropertyAssignment,
|
|
584
|
-
argType: ts.Type
|
|
585
|
-
) {
|
|
586
|
-
if (argNode.getType().isObject()) {
|
|
587
|
-
argType.getApparentProperties().forEach((prop) => {
|
|
588
|
-
const propName = prop.getName()
|
|
589
|
-
const propType = prop.getTypeAtLocation(node)
|
|
590
|
-
let propNode: ts.PropertyAssignment | undefined
|
|
591
|
-
if (argNode.isKind(ts.SyntaxKind.ObjectLiteralExpression)) {
|
|
592
|
-
propNode = argNode.getProperty(propName)?.asKind(ts.SyntaxKind.PropertyAssignment)
|
|
593
|
-
} else {
|
|
594
|
-
propNode = argNode
|
|
595
|
-
.getInitializerIfKind(ts.SyntaxKind.ObjectLiteralExpression)
|
|
596
|
-
?.getProperty(propName)
|
|
597
|
-
?.asKind(ts.SyntaxKind.PropertyAssignment)
|
|
598
|
-
}
|
|
599
|
-
|
|
600
|
-
if (!propNode) {
|
|
601
|
-
return
|
|
602
|
-
}
|
|
603
|
-
fixNodeArgumentType(node, propNode, propType)
|
|
604
|
-
})
|
|
605
|
-
} else if (argNode.isKind(ts.SyntaxKind.PropertyAssignment)) {
|
|
606
|
-
const nodeType = argNode.getType()
|
|
607
|
-
if (nodeType.isAssignableTo(argType)) {
|
|
608
|
-
return
|
|
609
|
-
}
|
|
610
|
-
// isAssignableTo doesnot play well with string literals in union types
|
|
611
|
-
if (
|
|
612
|
-
nodeType.isStringLiteral() &&
|
|
613
|
-
argType.isUnion() &&
|
|
614
|
-
argType.getUnionTypes().some((type) => type.getText() === nodeType.getText())
|
|
615
|
-
) {
|
|
616
|
-
return
|
|
617
|
-
}
|
|
618
|
-
|
|
619
|
-
// fix types for string
|
|
620
|
-
if (isStringType(argType)) {
|
|
621
|
-
const argValue = argNode.getInitializer()?.getText()
|
|
622
|
-
argNode.setInitializer(`'${argValue}'`)
|
|
623
|
-
return
|
|
624
|
-
}
|
|
625
|
-
|
|
626
|
-
// cast 'as any' for other types
|
|
627
|
-
const argValue = argNode.getInitializer()?.getText()
|
|
628
|
-
argNode.setInitializer(`${argValue} as any`)
|
|
629
|
-
}
|
|
630
|
-
}
|
|
631
|
-
|
|
632
|
-
function isStringType(argType: ts.Type) {
|
|
633
|
-
if (argType.isUnion()) {
|
|
634
|
-
return argType.getUnionTypes().some((type) => type.isString())
|
|
635
|
-
}
|
|
636
|
-
return argType.isString()
|
|
637
|
-
}
|
|
638
|
-
|
|
639
|
-
export function transformFunctionArguments<const A extends unknown[]>(
|
|
640
|
-
node: ts.CallExpression,
|
|
641
|
-
fn: (...args: A) => unknown,
|
|
642
|
-
...args: PartialElements<A>
|
|
643
|
-
) {
|
|
644
|
-
if (getCallExpressionName(node) !== fn.name) {
|
|
645
|
-
return false
|
|
646
|
-
}
|
|
647
|
-
|
|
648
|
-
for (let i = 0; i < args.length; i++) {
|
|
649
|
-
const argValue = args[i]
|
|
650
|
-
const argNode = node.getArguments()[i] ?? node.insertArgument(i, '{}')
|
|
651
|
-
|
|
652
|
-
if (argValue && typeof argValue === 'object') {
|
|
653
|
-
mergeDataIntoObjectLiteral(argNode.asKindOrThrow(ts.SyntaxKind.ObjectLiteralExpression), argValue)
|
|
654
|
-
} else {
|
|
655
|
-
argNode.replaceWithText(stringify(argValue))
|
|
656
|
-
}
|
|
657
|
-
}
|
|
658
|
-
|
|
659
|
-
return true
|
|
660
|
-
}
|
|
661
|
-
|
|
662
|
-
export function removeNode(node: SupportedNode) {
|
|
663
|
-
if ('remove' in node) {
|
|
664
|
-
return node.remove()
|
|
665
|
-
} else if (ts.Node.isCallExpression(node)) {
|
|
666
|
-
const parent = node.getParent()
|
|
667
|
-
if (ts.Node.isExpressionStatement(parent) || ts.Node.isVariableDeclaration(parent)) {
|
|
668
|
-
return removeNode(parent)
|
|
669
|
-
}
|
|
670
|
-
} else if (ts.Node.isStatement(node)) {
|
|
671
|
-
removeNode(node)
|
|
672
|
-
}
|
|
673
|
-
|
|
674
|
-
// TODO: Nodes that aren't complete statements can't be arbitrarily removed because it
|
|
675
|
-
// will almost always result in broken code. Replacing with 'undefined' works pretty
|
|
676
|
-
// much anywhere, but isn't very elegant. We should revisit this and perhaps make the
|
|
677
|
-
// behavior configurable.
|
|
678
|
-
node.replaceWithText('undefined')
|
|
679
|
-
}
|
|
680
|
-
|
|
681
|
-
/**
|
|
682
|
-
* Re-extracts CallExpression property names for transform to check for customized properties on Plugin APIs.
|
|
683
|
-
* If CallExpression properties don't match don't match schema expected by fluent this function will tranform updates
|
|
684
|
-
* only to those properties (not new properties)
|
|
685
|
-
* @param fn type of CallExpression to extract
|
|
686
|
-
* @param node Node
|
|
687
|
-
* @param dataForTransform Document Data passed to a transformer function
|
|
688
|
-
* @param cleanedData Document data cleaned/parsed by a Zod step that has filtered out properties not handled by fluent
|
|
689
|
-
*/
|
|
690
|
-
export function transformCustomizedProperties<
|
|
691
|
-
const A extends unknown[],
|
|
692
|
-
const E extends A extends [infer T extends Record<string, unknown>] ? T : never,
|
|
693
|
-
>(fn: (...args: A) => E, node, dataForTransform, cleanedData) {
|
|
694
|
-
if (!dataForTransform || !cleanedData) {
|
|
695
|
-
return
|
|
696
|
-
}
|
|
697
|
-
|
|
698
|
-
const [arg] = node.getArguments()
|
|
699
|
-
const properties = arg?.asKind(ts.SyntaxKind.ObjectLiteralExpression)?.getProperties()
|
|
700
|
-
|
|
701
|
-
if (!properties) {
|
|
702
|
-
return
|
|
703
|
-
}
|
|
704
|
-
|
|
705
|
-
const customizedProperties = {}
|
|
706
|
-
Object.values(properties).forEach((prop) => {
|
|
707
|
-
const propName = getObjectPropertyAssignmentName(prop as ts.PropertyAssignment)
|
|
708
|
-
if (dataForTransform[propName] !== undefined && cleanedData[propName] === undefined) {
|
|
709
|
-
customizedProperties[propName] = dataForTransform[propName]
|
|
710
|
-
}
|
|
711
|
-
})
|
|
712
|
-
|
|
713
|
-
if (!isEmpty(customizedProperties)) {
|
|
714
|
-
transformFunctionArguments(node, fn, ...([customizedProperties] as PartialElements<A>))
|
|
715
|
-
}
|
|
716
|
-
}
|
|
717
|
-
|
|
718
|
-
export function isNowIncludeCall(callExpression?: ts.CallExpression) {
|
|
719
|
-
if (!callExpression) {
|
|
720
|
-
return false
|
|
721
|
-
}
|
|
722
|
-
const propertyAccessExp = callExpression.getExpressionIfKind(ts.SyntaxKind.PropertyAccessExpression)
|
|
723
|
-
const nowNamespace = propertyAccessExp?.getExpressionIfKind(ts.SyntaxKind.Identifier)?.getText()
|
|
724
|
-
const functionName = propertyAccessExp?.getName()
|
|
725
|
-
return nowNamespace === 'Now' && functionName === 'include'
|
|
726
|
-
}
|
|
727
|
-
|
|
728
|
-
export function getObjectPropertyAssignmentName(objectProperty: ts.PropertyAssignment) {
|
|
729
|
-
const nameNode = objectProperty.getNameNode()
|
|
730
|
-
return nameNode.isKind(ts.SyntaxKind.StringLiteral) ? nameNode.getLiteralValue() : objectProperty.getName()
|
|
731
|
-
}
|