@sap/cds-dk 9.7.2 → 9.8.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/CHANGELOG.md +35 -2
- package/bin/bind.js +7 -2
- package/bin/build.js +14 -4
- package/bin/cds.js +2 -2
- package/bin/completion/completionFs.js +1 -1
- package/bin/completion/index.js +2 -2
- package/bin/data-products/get-csn-via-dp-cli.js +1 -1
- package/bin/debug.js +1 -1
- package/bin/deploy/index.js +3 -2
- package/bin/gen.js +1 -1
- package/bin/help.js +1 -1
- package/bin/import.js +3 -0
- package/bin/minify.js +1 -1
- package/bin/mock.js +1 -1
- package/bin/repl.js +212 -39
- package/bin/test.js +0 -2
- package/bin/up.js +27 -3
- package/bin/util/containerize.js +1 -3
- package/bin/version.js +27 -7
- package/bin/watch.js +20 -4
- package/lib/bind/cf.js +2 -2
- package/lib/bind/k8s.js +0 -1
- package/lib/bind/plugin.js +2 -0
- package/lib/bind/shared.js +6 -1
- package/lib/build/constants.js +0 -8
- package/lib/build/index.js +569 -25
- package/lib/build/{provider/edmxBuildPlugin.js → plugins/edmx.js} +6 -15
- package/lib/build/{provider/featureToggleBuildPlugin.js → plugins/featureToggles.js} +3 -23
- package/lib/build/{provider → plugins}/fiori/index.js +27 -38
- package/lib/build/{provider → plugins}/hana/index.js +61 -83
- package/lib/build/{provider → plugins}/hana/migrationtable.js +4 -3
- package/lib/build/plugins/helm/index.js +6 -6
- package/lib/build/{provider/internalBuildPlugin.js → plugins/internal.js} +7 -31
- package/lib/build/{provider → plugins}/java/index.js +18 -26
- package/lib/build/plugins/mtx/index.js +41 -0
- package/lib/build/plugins/mtx/resourcesTarBuilder.js +41 -0
- package/lib/build/{provider → plugins}/mtx-extension/extensionCompilation.js +1 -1
- package/lib/build/{provider → plugins}/mtx-extension/index.js +35 -44
- package/lib/build/{provider → plugins}/mtx-sidecar/index.js +17 -3
- package/lib/build/{provider → plugins}/nodejs/index.js +29 -28
- package/lib/build/{plugin.js → plugins/plugin.js} +45 -59
- package/lib/build/plugins.js +11 -8
- package/lib/build/util.js +0 -8
- package/lib/compile/to-xsuaa.js +2 -2
- package/lib/deploy/to-hana/hana.js +64 -56
- package/lib/import/common.js +1 -1
- package/lib/import/odata/metadataconverter/MetadataConverter.js +4 -3
- package/lib/import/odata/v2parser.js +28 -28
- package/lib/import/odata/v4parser.js +37 -2
- package/lib/import/openapi/index.js +1 -1
- package/lib/init/constants.js +0 -1
- package/lib/init/template/app-frontend/index.js +1 -1
- package/lib/init/template/approuter/files/package.json +1 -1
- package/lib/init/template/completion/completionSetup.js +1 -1
- package/lib/init/template/data/as-csv.js +1 -1
- package/lib/init/template/github-actions/index.js +1 -1
- package/lib/init/template/handler/index.js +1 -1
- package/lib/init/template/helm/index.js +3 -3
- package/lib/init/template/kyma/index.js +3 -3
- package/lib/init/template/lint/index.js +7 -21
- package/lib/init/template/multitenancy/files/package.json.hbs +0 -5
- package/lib/init/template/postgres/files/containerize.yaml.hbs +15 -0
- package/lib/init/template/postgres/files/package.json.hbs +35 -0
- package/lib/init/template/postgres/files/values.yaml.hbs +23 -0
- package/lib/init/template/postgres/index.js +34 -9
- package/lib/init/template/test/files/package.json +1 -1
- package/lib/init/template/typescript/files/package.json +1 -1
- package/lib/init/template/workzone-standard/files/mta.yaml.hbs +1 -0
- package/lib/lint/eslintHelp.json +1 -1
- package/lib/lint/io.js +9 -13
- package/lib/mtx/pull.js +1 -1
- package/lib/mtx/settings_manager.js +11 -5
- package/lib/mtx/tenant_action.js +1 -1
- package/lib/mtx/util/fs.js +2 -2
- package/lib/util/fs.js +3 -3
- package/lib/util/git.js +1 -1
- package/lib/util/glob.js +1 -1
- package/lib/watch/hot-reload.js +202 -0
- package/lib/watch/livereload-server.js +6 -4
- package/lib/watch/node-watch.js +5 -1
- package/lib/watch/watched.js +7 -3
- package/lib/watch/watcher.js +41 -3
- package/npm-shrinkwrap.json +31 -22
- package/package.json +1 -1
- package/lib/build/buildTaskEngine.js +0 -377
- package/lib/build/buildTaskFactory.js +0 -198
- package/lib/build/buildTaskProvider.js +0 -38
- package/lib/build/buildTaskProviderFactory.js +0 -233
- package/lib/build/provider/internalBuildTaskProvider.js +0 -227
- package/lib/build/provider/java-cf/index.js +0 -1
- package/lib/build/provider/mtx/index.js +0 -36
- package/lib/build/provider/mtx/resourcesTarBuilder.js +0 -102
- package/lib/build/provider/node-cf/index.js +0 -1
- package/lib/init/template/lint/files/.eslint/rules/no-entity-moo.js +0 -40
- package/lib/init/template/lint/files/.eslint/tests/no-entity-moo/fixed/schema.cds +0 -4
- package/lib/init/template/lint/files/.eslint/tests/no-entity-moo/invalid/schema.cds +0 -4
- package/lib/init/template/lint/files/.eslint/tests/no-entity-moo/rule.test.js +0 -15
- package/lib/init/template/lint/files/.eslint/tests/no-entity-moo/valid/schema.cds +0 -6
- package/lib/init/types.d.ts +0 -23
- /package/lib/build/{provider → plugins}/hana/2migration.js +0 -0
- /package/lib/build/{provider → plugins}/hana/template/.hdiconfig-all +0 -0
- /package/lib/build/{provider → plugins}/hana/template/.hdiconfig-cloud +0 -0
- /package/lib/build/{provider → plugins}/hana/template/.hdinamespace +0 -0
- /package/lib/build/{provider → plugins}/hana/template/package.json +0 -0
- /package/lib/build/{provider → plugins}/hana/template/undeploy.json +0 -0
|
@@ -1,15 +1,22 @@
|
|
|
1
1
|
const fs = require('fs')
|
|
2
|
-
const path = require('path')
|
|
3
2
|
const cds = require('../../../cds')
|
|
4
|
-
const
|
|
5
|
-
const {
|
|
6
|
-
|
|
7
|
-
const { getI18nDefaultFolder } = require('../../util')
|
|
3
|
+
const { exists, isdir, path } = cds.utils
|
|
4
|
+
const { FILE_EXT_CDS, CONTENT_LANGUAGE_BUNDLES, CONTENT_DEFAULT_CSN, DEFAULT_CSN_FILE_NAME, FLAVOR_LOCALIZED_EDMX, CONTENT_EDMX, CONTENT_LOCALIZED_EDMX } = require('../../constants')
|
|
5
|
+
const { getI18nDefaultFolder, normalizePath } = require('../../util')
|
|
8
6
|
const DEFAULT_COMPILE_DEST_FOLDER = path.normalize('src/main/resources/edmx')
|
|
9
7
|
const DEBUG = cds.debug('cli|build')
|
|
10
8
|
const LOG = cds.log('cli|build')
|
|
11
9
|
|
|
12
|
-
class JavaBuildPlugin extends
|
|
10
|
+
module.exports = class JavaBuildPlugin extends require('../edmx') {
|
|
11
|
+
|
|
12
|
+
static get taskDefaults() { return { src: normalizePath(cds.env.folders.srv) } }
|
|
13
|
+
|
|
14
|
+
static hasTask() {
|
|
15
|
+
const src = path.join(cds.root, this.taskDefaults?.src ?? 'srv')
|
|
16
|
+
const hasSrc = exists(src) || this.taskDefaults?.src === '.'
|
|
17
|
+
return cds.env['project-nature'] === 'java' && hasSrc && !cds.env.extends
|
|
18
|
+
}
|
|
19
|
+
|
|
13
20
|
init() {
|
|
14
21
|
super.init()
|
|
15
22
|
this.task.options.compileDest = path.resolve(this.task.dest, this.task.options.compileDest || DEFAULT_COMPILE_DEST_FOLDER)
|
|
@@ -45,15 +52,11 @@ class JavaBuildPlugin extends EdmxBuildPlugin {
|
|
|
45
52
|
|
|
46
53
|
if (!this.hasBuildOption(CONTENT_LANGUAGE_BUNDLES, false)) {
|
|
47
54
|
// collect and write language bundles containing all features
|
|
48
|
-
|
|
49
|
-
if (i18n && this.hasBuildOption(OUTPUT_MODE, OUTPUT_MODE_RESULT)) {
|
|
50
|
-
this._result.languageBundles = i18n.bundles
|
|
51
|
-
}
|
|
55
|
+
await this.collectLanguageBundles(model, path.join(compileDest, getI18nDefaultFolder()))
|
|
52
56
|
}
|
|
53
|
-
if (this.isStagingBuild()
|
|
57
|
+
if (this.isStagingBuild()) {
|
|
54
58
|
await this._copyNativeContent(src, dest)
|
|
55
59
|
}
|
|
56
|
-
return this._result
|
|
57
60
|
}
|
|
58
61
|
|
|
59
62
|
async clean() {
|
|
@@ -66,7 +69,7 @@ class JavaBuildPlugin extends EdmxBuildPlugin {
|
|
|
66
69
|
|
|
67
70
|
async _copyNativeContent(src, dest) {
|
|
68
71
|
return super.copyNativeContent(src, dest, (entry) => {
|
|
69
|
-
if (
|
|
72
|
+
if (isdir(entry)) {
|
|
70
73
|
return true // using common filter for folders
|
|
71
74
|
} else {
|
|
72
75
|
const extname = path.extname(entry)
|
|
@@ -84,21 +87,10 @@ class JavaBuildPlugin extends EdmxBuildPlugin {
|
|
|
84
87
|
const csnFile = path.join(csnDest, DEFAULT_CSN_FILE_NAME)
|
|
85
88
|
// adding csn to build result containing @source and _where persisted properties
|
|
86
89
|
if (this.hasBuildOption(CONTENT_DEFAULT_CSN, true)) { //default true or undefined
|
|
87
|
-
|
|
88
|
-
if (this.hasBuildOption(OUTPUT_MODE, OUTPUT_MODE_RESULT)) {
|
|
89
|
-
const csnModel = JSON.parse(csnStr)
|
|
90
|
-
csnModel.meta = model.meta
|
|
91
|
-
this._result.csn = csnModel
|
|
92
|
-
}
|
|
90
|
+
await this.compileToJson(model, csnFile)
|
|
93
91
|
} else {
|
|
94
|
-
|
|
95
|
-
if (this.hasBuildOption(OUTPUT_MODE, OUTPUT_MODE_RESULT)) {
|
|
96
|
-
const csnModel = JSON.parse(csnStr)
|
|
97
|
-
csnModel.meta = m.meta
|
|
98
|
-
this._result.csn = csnModel
|
|
99
|
-
}
|
|
92
|
+
await this.compileToJson(m, csnFile)
|
|
100
93
|
}
|
|
101
94
|
return m
|
|
102
95
|
}
|
|
103
96
|
}
|
|
104
|
-
module.exports = JavaBuildPlugin
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
const cds = require('../../../cds')
|
|
2
|
+
const { path, exists, rimraf } = cds.utils
|
|
3
|
+
const ResourcesTarBuilder = require('./resourcesTarBuilder')
|
|
4
|
+
const { FOLDER_GEN } = require('../../constants')
|
|
5
|
+
const { normalizePath } = require('../../util')
|
|
6
|
+
|
|
7
|
+
module.exports = class MtxBuildPlugin extends require('../edmx') {
|
|
8
|
+
|
|
9
|
+
static get taskDefaults() { return { src: normalizePath(cds.env.folders.srv) } }
|
|
10
|
+
|
|
11
|
+
static hasTask() {
|
|
12
|
+
const isMtxs = cds.env.requires.multitenancy || cds.env.requires.toggles || cds.env.requires['cds.xt.ModelProviderService']
|
|
13
|
+
const hasSidecar = exists(path.join(cds.root, 'mtx/sidecar'))
|
|
14
|
+
return isMtxs && !hasSidecar && cds.env['project-nature'] === 'nodejs' && !cds.env.extends
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
get requires() {
|
|
18
|
+
return ['hana']
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
init() {
|
|
22
|
+
super.init()
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
async build() {
|
|
26
|
+
// Only create resources TAR, compiled CSN(s) are created by the Nodejs app build task.
|
|
27
|
+
const dest = cds.env.build.target !== '.' ? this.task.dest : path.join(this.task.dest, FOLDER_GEN)
|
|
28
|
+
const model = await this.model()
|
|
29
|
+
if (!model) {
|
|
30
|
+
return
|
|
31
|
+
}
|
|
32
|
+
return new ResourcesTarBuilder(this).createTar(dest, model)
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
async clean() {
|
|
36
|
+
// staging build content is deleted by default
|
|
37
|
+
if (cds.env.build.target === '.') {
|
|
38
|
+
return rimraf(this.task.dest, FOLDER_GEN)
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
const cds = require('../../../cds')
|
|
2
|
+
const { path, exists, tar } = cds.utils
|
|
3
|
+
const { BUILD_TASK_HANA } = require('../../constants')
|
|
4
|
+
const { WARNING } = require('../internal')
|
|
5
|
+
|
|
6
|
+
module.exports = class ResourcesTarBuilder {
|
|
7
|
+
constructor(plugin) {
|
|
8
|
+
this._plugin = plugin
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
get plugin() { return this._plugin }
|
|
12
|
+
|
|
13
|
+
async createTar(dest, model) {
|
|
14
|
+
let root = getHanaTenantDbTask(this.plugin)?.dest
|
|
15
|
+
let resources
|
|
16
|
+
if (root) {
|
|
17
|
+
const items = ['src', 'cfg', 'undeploy.json', '.hdiignore']
|
|
18
|
+
resources = items.map(item => path.join(root, item)).filter(exists)
|
|
19
|
+
} else {
|
|
20
|
+
root = cds.root
|
|
21
|
+
resources = Object.keys(await cds.deploy.resources(model))
|
|
22
|
+
}
|
|
23
|
+
if (resources.length === 0) {
|
|
24
|
+
this.plugin.pushMessage("No deployment resources found - skip resources.tgz", WARNING)
|
|
25
|
+
return
|
|
26
|
+
}
|
|
27
|
+
const tarFile = path.join(dest, "resources.tgz")
|
|
28
|
+
await tar.czfd(tarFile, root, resources)
|
|
29
|
+
this.plugin.pushFile(tarFile)
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
function getHanaTenantDbTask({ task, context: { tasks } }) {
|
|
34
|
+
const hanaTasks = tasks.filter(task => task.for === BUILD_TASK_HANA)
|
|
35
|
+
if (hanaTasks.length === 1) return hanaTasks[0]
|
|
36
|
+
return hanaTasks.find(({ src }) => {
|
|
37
|
+
if (!src) return true // an existing second shared db always requires src to be set
|
|
38
|
+
const srcFolder = path.isAbsolute(src) ? path.relative(cds.root, src) : src
|
|
39
|
+
return task.options?.model?.includes(srcFolder) || srcFolder === cds.env.folders.db.replace('/', '')
|
|
40
|
+
})
|
|
41
|
+
}
|
|
@@ -1,8 +1,5 @@
|
|
|
1
|
-
const path = require('path')
|
|
2
|
-
const fs = require('fs')
|
|
3
1
|
const cds = require('../../../cds')
|
|
4
|
-
const
|
|
5
|
-
const ResourcesTarBuilder = require('../mtx/resourcesTarBuilder')
|
|
2
|
+
const { exists, path, isdir, rimraf, tar } = cds.utils
|
|
6
3
|
const ExtensionCompilation = require('./extensionCompilation')
|
|
7
4
|
const { FOLDER_GEN, EXTENSION_POINT_VALIDATION } = require('../../constants')
|
|
8
5
|
const { BuildError, BuildMessage } = require('../../util')
|
|
@@ -10,7 +7,12 @@ const DEBUG = cds.debug('cli|build')
|
|
|
10
7
|
|
|
11
8
|
const BUILT_IN_NAMESPACES = ['cds.core', 'cds.outbox', 'cds.xt']
|
|
12
9
|
|
|
13
|
-
class MtxExtensionBuildPlugin extends
|
|
10
|
+
module.exports = class MtxExtensionBuildPlugin extends require('../internal') {
|
|
11
|
+
|
|
12
|
+
static get taskDefaults() { return { src: '.' } }
|
|
13
|
+
|
|
14
|
+
static hasTask() { return cds.env.extends }
|
|
15
|
+
|
|
14
16
|
init() {
|
|
15
17
|
super.init()
|
|
16
18
|
if (cds.env.build.target === '.') {
|
|
@@ -27,7 +29,11 @@ class MtxExtensionBuildPlugin extends InternalBuildPlugin {
|
|
|
27
29
|
// REVISIT: check existence of SaaS app package folder only
|
|
28
30
|
// cds.resolve will fail as no index.csn file exists in this folder for the extension migration use case
|
|
29
31
|
// a compilation error is thrown anyhow if any base model refs cannot be resolved
|
|
30
|
-
|
|
32
|
+
|
|
33
|
+
if (!cds.env.extends) throw new BuildError(`Missing configuration 'cds.extends' in package.json`)
|
|
34
|
+
// cds.env.extends holds the SaaS app package name, also if the extends field is defined on root level
|
|
35
|
+
// older projects might not have a workspace definition
|
|
36
|
+
const saasPkgPath = _getWorkspacePath(cds.env.extends) ?? _getNodeModulesPath()
|
|
31
37
|
const extensionCompilation = new ExtensionCompilation(this)
|
|
32
38
|
|
|
33
39
|
// full model compilation including base model ensures consistency
|
|
@@ -92,8 +98,7 @@ class MtxExtensionBuildPlugin extends InternalBuildPlugin {
|
|
|
92
98
|
// throws error in case of linting errors
|
|
93
99
|
this._lintExtModel(extensionModel, model, saasPkgPath)
|
|
94
100
|
} catch (error) {
|
|
95
|
-
|
|
96
|
-
await fs.promises.rm(dest, { recursive: true })
|
|
101
|
+
await rimraf(dest)
|
|
97
102
|
throw error
|
|
98
103
|
}
|
|
99
104
|
}
|
|
@@ -105,7 +110,7 @@ class MtxExtensionBuildPlugin extends InternalBuildPlugin {
|
|
|
105
110
|
// copy handlers from srv folder
|
|
106
111
|
const folder = path.join(cds.root, cds.env.folders.srv).replace(/[/\\]$/, '')
|
|
107
112
|
await this.copyNativeContent(cds.root, destExt, res => {
|
|
108
|
-
if (
|
|
113
|
+
if (isdir(res)) {
|
|
109
114
|
return res.startsWith(folder)
|
|
110
115
|
}
|
|
111
116
|
if (path.dirname(res).startsWith(folder) && /\.js$/.test(res)) {
|
|
@@ -114,7 +119,9 @@ class MtxExtensionBuildPlugin extends InternalBuildPlugin {
|
|
|
114
119
|
})
|
|
115
120
|
|
|
116
121
|
// add all resources contained in 'gen/ext' folder
|
|
117
|
-
|
|
122
|
+
const tarFile = path.join(dest, 'extension.tgz')
|
|
123
|
+
await tar.czfd(tarFile, destExt)
|
|
124
|
+
this.pushFile(tarFile)
|
|
118
125
|
}
|
|
119
126
|
|
|
120
127
|
_lintExtModel(extModel, model, saasPkgPath) {
|
|
@@ -135,48 +142,32 @@ class MtxExtensionBuildPlugin extends InternalBuildPlugin {
|
|
|
135
142
|
|
|
136
143
|
_linter() {
|
|
137
144
|
try {
|
|
138
|
-
// Make sure cds-mtxs APIs are loaded, from local mtxs
|
|
139
|
-
|
|
140
|
-
return mtxs.xt.linter
|
|
145
|
+
// Make sure cds-mtxs APIs are loaded, from local mtxs preferably
|
|
146
|
+
return require(require.resolve('@sap/cds-mtxs', { paths: [cds.root, __dirname] })).xt.linter
|
|
141
147
|
} catch (e) {
|
|
142
148
|
if (e.code !== 'MODULE_NOT_FOUND') throw e
|
|
143
149
|
this.pushMessage('MTXS linter cannot be loaded, @sap/cds-mtxs not installed. Skipping extension model lint step.')
|
|
144
150
|
}
|
|
145
151
|
}
|
|
152
|
+
}
|
|
146
153
|
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
saasPkgPath = this._getNodeModulesPath(saasPkgPath)
|
|
156
|
-
}
|
|
157
|
-
return saasPkgPath
|
|
158
|
-
}
|
|
159
|
-
|
|
160
|
-
static _getWorkspacePath(pkg) {
|
|
161
|
-
const pkgJson = require(path.join(cds.root, 'package.json'))
|
|
162
|
-
if (pkgJson.workspaces) {
|
|
163
|
-
try {
|
|
164
|
-
// loading package.json of SaaS app - might not exist for older projects
|
|
165
|
-
return path.dirname(require.resolve(path.join(pkg, 'package.json'), { paths: [cds.root] }))
|
|
166
|
-
} catch (e) {
|
|
167
|
-
if (e.code !== 'MODULE_NOT_FOUND') throw e
|
|
168
|
-
throw new BuildError(`The SaaS application base model is missing. Did you execute 'cds pull' and 'npm install'?`)
|
|
169
|
-
}
|
|
170
|
-
}
|
|
171
|
-
}
|
|
172
|
-
|
|
173
|
-
static _getNodeModulesPath() {
|
|
174
|
-
const saasPkgPath = path.join(cds.root, 'node_modules', cds.env.extends)
|
|
175
|
-
if (!fs.existsSync(saasPkgPath)) {
|
|
154
|
+
function _getWorkspacePath(pkg) {
|
|
155
|
+
const pkgJson = require(path.join(cds.root, 'package.json'))
|
|
156
|
+
if (pkgJson.workspaces) {
|
|
157
|
+
try {
|
|
158
|
+
// loading package.json of SaaS app - might not exist for older projects
|
|
159
|
+
return path.dirname(require.resolve(path.join(pkg, 'package.json'), { paths: [cds.root] }))
|
|
160
|
+
} catch (e) {
|
|
161
|
+
if (e.code !== 'MODULE_NOT_FOUND') throw e
|
|
176
162
|
throw new BuildError(`The SaaS application base model is missing. Did you execute 'cds pull' and 'npm install'?`)
|
|
177
163
|
}
|
|
178
|
-
return saasPkgPath
|
|
179
164
|
}
|
|
180
165
|
}
|
|
181
166
|
|
|
182
|
-
|
|
167
|
+
function _getNodeModulesPath() {
|
|
168
|
+
const saasPkgPath = path.join(cds.root, 'node_modules', cds.env.extends)
|
|
169
|
+
if (!exists(saasPkgPath)) {
|
|
170
|
+
throw new BuildError(`The SaaS application base model is missing. Did you execute 'cds pull' and 'npm install'?`)
|
|
171
|
+
}
|
|
172
|
+
return saasPkgPath
|
|
173
|
+
}
|
|
@@ -10,11 +10,25 @@ const DEFAULT_MAIN_FOLDER = "_main"
|
|
|
10
10
|
const [major, minor] = cds.version.split('.').map(Number)
|
|
11
11
|
const COMPAT = major === 9 && minor < 7 // cds10: remove
|
|
12
12
|
|
|
13
|
-
module.exports = class extends require('../nodejs') {
|
|
13
|
+
module.exports = class MtxSidecarBuildPlugin extends require('../nodejs') {
|
|
14
14
|
|
|
15
|
-
get
|
|
16
|
-
|
|
15
|
+
static get taskDefaults() { return { src: 'mtx/sidecar' } }
|
|
16
|
+
|
|
17
|
+
static hasTask() {
|
|
18
|
+
if (cds.env.extends) return
|
|
19
|
+
const mps = cds.env.requires['cds.xt.ModelProviderService']
|
|
20
|
+
const isMtxs = cds.env.requires.multitenancy || cds.env.requires.toggles || cds.env.requires['cds.xt.ModelProviderService']
|
|
21
|
+
const src = path.join(cds.root, this.taskDefaults?.src ?? 'mtx/sidecar')
|
|
22
|
+
if (mps?._in_sidecar) {
|
|
23
|
+
throw new BuildError(`Seems that you are executing 'cds build' in the 'mtx/sidecar' folder. Execute 'cds build' in the project root folder instead.`)
|
|
24
|
+
}
|
|
25
|
+
return isMtxs && exists(src)
|
|
17
26
|
}
|
|
27
|
+
|
|
28
|
+
get requires() {
|
|
29
|
+
return ['hana']
|
|
30
|
+
}
|
|
31
|
+
|
|
18
32
|
init() {
|
|
19
33
|
super.init()
|
|
20
34
|
if (cds.env.build.target === '.') {
|
|
@@ -1,26 +1,26 @@
|
|
|
1
|
-
const fs = require('fs')
|
|
2
|
-
const path = require('path')
|
|
3
1
|
const cds = require('../../../cds')
|
|
4
|
-
const
|
|
5
|
-
const
|
|
6
|
-
const { BuildError, getWorkspaces, findWorkspaceRoot } = require('../../util')
|
|
7
|
-
const {
|
|
2
|
+
const { path, exists, rimraf, isdir, read, write } = cds.utils
|
|
3
|
+
const cmd = require('../../../util/command')
|
|
4
|
+
const { BuildError, getWorkspaces, findWorkspaceRoot, normalizePath } = require('../../util')
|
|
5
|
+
const { ODATA_VERSION_V2, FOLDER_GEN, CONTENT_EDMX, CONTENT_PACKAGELOCK_JSON,
|
|
8
6
|
CONTENT_NPMRC, CONTENT_CDSRC_JSON, CONTENT_ENV, CONTENT_DEFAULT_ENV_JSON, FLAVOR_LOCALIZED_EDMX,
|
|
9
|
-
OPTION_WS_PACK} = require('../../constants');
|
|
10
|
-
const { WARNING } = EdmxBuildPlugin
|
|
7
|
+
OPTION_WS_PACK, SEVERITY_WARNING } = require('../../constants');
|
|
11
8
|
const LOG = cds.log('cli|build')
|
|
12
9
|
const DEBUG = cds.debug('cli|build')
|
|
13
10
|
const NODE_ENGINE_VERSION = '>=20'
|
|
14
11
|
const { exec } = require('node:child_process')
|
|
15
|
-
const pexec = require('node:util').promisify(exec)
|
|
12
|
+
const pexec = require('node:util').promisify(exec)
|
|
16
13
|
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
14
|
+
module.exports = class NodejsBuildPlugin extends require('../edmx') {
|
|
15
|
+
|
|
16
|
+
static get taskDefaults() { return { src: normalizePath(cds.env.folders.srv) } }
|
|
17
|
+
|
|
18
|
+
static hasTask() {
|
|
19
|
+
const src = path.join(cds.root, this.taskDefaults?.src || 'srv')
|
|
20
|
+
const hasSrc = exists(src) || (this.taskDefaults?.src === '.')
|
|
21
|
+
return cds.env['project-nature'] === 'nodejs' && hasSrc && !cds.env.extends
|
|
22
|
+
}
|
|
22
23
|
|
|
23
|
-
class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
24
24
|
init() {
|
|
25
25
|
super.init()
|
|
26
26
|
// fallback if src has been defined as '.'
|
|
@@ -36,11 +36,15 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
36
36
|
}
|
|
37
37
|
|
|
38
38
|
async build() {
|
|
39
|
+
if (!exists('package.json')) {
|
|
40
|
+
throw new BuildError(`No 'package.json' found in project root folder '${cds.root}'`)
|
|
41
|
+
}
|
|
42
|
+
|
|
39
43
|
const destSrv = this.isStagingBuild() ? this.destSrv : path.resolve(this.destSrv, cds.env.folders.srv)
|
|
40
44
|
const destRoot = this.isStagingBuild() ? this.task.dest : this.destSrv
|
|
41
45
|
if (cds.env.odata.version === ODATA_VERSION_V2) {
|
|
42
46
|
// log warning as nodejs is only supporting odata version V4
|
|
43
|
-
this.pushMessage("OData v2 is not supported by node runtime. Make sure to define OData v2 in cds configuration.",
|
|
47
|
+
this.pushMessage("OData v2 is not supported by node runtime. Make sure to define OData v2 in cds configuration.", SEVERITY_WARNING)
|
|
44
48
|
}
|
|
45
49
|
// by default model contains all features
|
|
46
50
|
const model = await this.model()
|
|
@@ -61,7 +65,7 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
61
65
|
await this.compileToEdmx(baseModel, path.join(this.destSrv, 'odata', cds.env.odata.version), compileOptions)
|
|
62
66
|
}
|
|
63
67
|
}
|
|
64
|
-
if (this.isStagingBuild()
|
|
68
|
+
if (this.isStagingBuild()) {
|
|
65
69
|
const srcSrv = this.task.src === cds.root ? path.resolve(this.task.src, cds.env.folders.srv) : this.task.src
|
|
66
70
|
await this._copyNativeContent(cds.root, srcSrv, destRoot, destSrv)
|
|
67
71
|
try {
|
|
@@ -87,8 +91,6 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
87
91
|
}
|
|
88
92
|
|
|
89
93
|
await this.#cleanupPackageJson(destRoot)
|
|
90
|
-
|
|
91
|
-
return this._result
|
|
92
94
|
}
|
|
93
95
|
|
|
94
96
|
/**
|
|
@@ -101,7 +103,7 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
101
103
|
|
|
102
104
|
const packageJsonPath = path.join(this.task.dest, 'package.json')
|
|
103
105
|
try {
|
|
104
|
-
const packageJson = await
|
|
106
|
+
const packageJson = await read(packageJsonPath)
|
|
105
107
|
|
|
106
108
|
DEBUG?.(`Sanitizing the package.json for "${this.task.src}'...`)
|
|
107
109
|
|
|
@@ -124,9 +126,9 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
124
126
|
}
|
|
125
127
|
// overwrite the package.json if it was modified only
|
|
126
128
|
if (modified) {
|
|
127
|
-
await
|
|
129
|
+
await write(packageJsonPath, JSON.stringify(packageJson, null, 2), 'utf-8')
|
|
128
130
|
// update the package-lock.json if it exists
|
|
129
|
-
if (
|
|
131
|
+
if (exists(path.join(this.task.dest, 'package-lock.json'))) {
|
|
130
132
|
DEBUG?.(`Updating the package-lock.json for '${this.task.src}'...`)
|
|
131
133
|
// run the npm install --package-lock-only to only update the package-lock.json
|
|
132
134
|
// without installing the dependencies to node_modules
|
|
@@ -145,12 +147,12 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
145
147
|
}
|
|
146
148
|
|
|
147
149
|
async clean() {
|
|
148
|
-
// staging build content is deleted by
|
|
150
|
+
// staging build content is deleted by default
|
|
149
151
|
if (cds.env.build.target === '.') {
|
|
150
152
|
// delete the entire 'task.dest' folder otherwise, for details see #constructor
|
|
151
153
|
// - the value of the folder 'src' has been appended to the origin 'task.dest' dir
|
|
152
154
|
DEBUG?.(`Deleting build target folder ${this.destSrv}`)
|
|
153
|
-
await
|
|
155
|
+
await rimraf(this.isStagingBuild() ? this.task.dest : this.destSrv)
|
|
154
156
|
}
|
|
155
157
|
}
|
|
156
158
|
|
|
@@ -180,7 +182,7 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
180
182
|
// 1. copy all files to 'destSrv' except those contained in the blocklist (including node_modules)
|
|
181
183
|
// project/srv -> 'gen/srv/srv'
|
|
182
184
|
await super.copyNativeContent(src, destSrv, (entry) => {
|
|
183
|
-
if (
|
|
185
|
+
if (isdir(entry)) {
|
|
184
186
|
// TODO shall not copy language bundles - return !/(\/|\\)(node_modules|_i18n)(\/|\\)?$/.test(entry)
|
|
185
187
|
return !/(\/|\\)node_modules(\/|\\)?$/.test(entry)
|
|
186
188
|
}
|
|
@@ -230,7 +232,7 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
230
232
|
srvAllowList = new RegExp(srvAllowList)
|
|
231
233
|
|
|
232
234
|
await super.copyNativeContent(src, dest, (entry) => {
|
|
233
|
-
if (
|
|
235
|
+
if (isdir(entry)) {
|
|
234
236
|
return folders.some(folder => entry.startsWith(folder))
|
|
235
237
|
}
|
|
236
238
|
if (/\.js$|\.properties$/.test(entry)) {
|
|
@@ -246,6 +248,7 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
246
248
|
const allWorkspaces = await getWorkspaces(wsRoot, true, false)
|
|
247
249
|
let workspaces
|
|
248
250
|
if (this.task.options.workspaces) {
|
|
251
|
+
const arrayify = x => Array.isArray(x) ? x : [x]
|
|
249
252
|
const relevantWorkspaces = new Set(arrayify(this.task.options.workspaces))
|
|
250
253
|
workspaces = allWorkspaces
|
|
251
254
|
.filter(ws => relevantWorkspaces.has(ws.workspace))
|
|
@@ -302,5 +305,3 @@ class NodejsBuildPlugin extends EdmxBuildPlugin {
|
|
|
302
305
|
return JSON.parse(result)
|
|
303
306
|
}
|
|
304
307
|
}
|
|
305
|
-
|
|
306
|
-
module.exports = NodejsBuildPlugin
|