@adobe/aio-cli-plugin-app 14.5.1 → 14.5.2-pre.2026-03-10.sha-a80ded98

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/package.json CHANGED
@@ -1,15 +1,16 @@
1
1
  {
2
2
  "name": "@adobe/aio-cli-plugin-app",
3
3
  "description": "Create, Build and Deploy Adobe I/O Applications",
4
- "version": "14.5.1",
4
+ "version": "14.5.2-pre.2026-03-10.sha-a80ded98",
5
5
  "author": "Adobe Inc.",
6
6
  "bugs": "https://github.com/adobe/aio-cli-plugin-app/issues",
7
7
  "dependencies": {
8
- "@adobe/aio-cli-lib-app-config": "^4.0.3",
8
+ "@adobe/aio-cli-lib-app-config": "next",
9
9
  "@adobe/aio-cli-lib-console": "^5.0.3",
10
10
  "@adobe/aio-lib-core-config": "^5",
11
11
  "@adobe/aio-lib-core-logging": "^3",
12
12
  "@adobe/aio-lib-core-networking": "^5",
13
+ "@adobe/aio-lib-db": "^0.2.0-beta.1",
13
14
  "@adobe/aio-lib-env": "^3",
14
15
  "@adobe/aio-lib-ims": "^7",
15
16
  "@adobe/aio-lib-runtime": "^7.1.3",
@@ -103,5 +104,6 @@
103
104
  },
104
105
  "bin": {
105
106
  "aio-next": "./bin/run"
106
- }
107
- }
107
+ },
108
+ "prereleaseSha": "a80ded98da4306b7483cb65e2482a012851a65f0"
109
+ }
@@ -24,6 +24,8 @@ const {
24
24
  getFilesCountWithExtension
25
25
  } = require('../../lib/app-helper')
26
26
  const rtLib = require('@adobe/aio-lib-runtime')
27
+ const dbLib = require('@adobe/aio-lib-db')
28
+ const { DB_STATUS } = require('../../lib/defaults')
27
29
  const LogForwarding = require('../../lib/log-forwarding')
28
30
  const { sendAppAssetsDeployedAuditLog, sendAppDeployAuditLog } = require('../../lib/audit-logger')
29
31
  const { setRuntimeApiHostAndAuthHandler, getAccessToken } = require('../../lib/auth-helper')
@@ -204,6 +206,11 @@ class Deploy extends BuildCommand {
204
206
  this.error(err)
205
207
  }
206
208
 
209
+ // provision database if configured
210
+ if (config.manifest?.full?.database?.['auto-provision'] === true) {
211
+ await this.provisionDatabase(config, spinner, flags)
212
+ }
213
+
207
214
  if (flags.actions) {
208
215
  if (config.app.hasBackend) {
209
216
  let filterEntities
@@ -300,6 +307,74 @@ class Deploy extends BuildCommand {
300
307
  }
301
308
  }
302
309
 
310
+ async provisionDatabase (config, spinner, flags) {
311
+ const { namespace, auth } = config.ow || {}
312
+ if (!(namespace && auth)) {
313
+ throw new Error('Database deployment requires OW auth configuration.')
314
+ }
315
+ const region = config.manifest?.full?.database?.region
316
+ const regionMess = region ? `'${region}'` : 'default'
317
+
318
+ const progress = ({ next = undefined, status = undefined, verboseOnly = false }, statusMethod = spinner.info) => {
319
+ if (flags.verbose) {
320
+ const method = statusMethod.bind(spinner)
321
+ method(status)
322
+ spinner.start(next)
323
+ } else if (next && !verboseOnly) {
324
+ spinner.text = next
325
+ }
326
+ }
327
+
328
+ let provRes
329
+ try {
330
+ spinner.start(`Deploying database in the ${regionMess} region...`)
331
+
332
+ const db = await dbLib.init({ ow: { namespace, auth }, region })
333
+ progress({ next: 'Checking existing database deployment status...', verboseOnly: true })
334
+
335
+ let prevStatus
336
+ let statusRegion
337
+ const next = `Submitting database provisioning request in the ${regionMess} region...`
338
+ try {
339
+ const statusRes = await db.provisionStatus()
340
+ prevStatus = statusRes.status.toUpperCase()
341
+ statusRegion = statusRes.region
342
+ const regionMessage = statusRegion ? ` in region '${statusRegion}'` : ''
343
+ progress({ status: chalk.dim(`Existing database provisioning status: ${prevStatus}${regionMessage}`), next })
344
+ } catch (err) {
345
+ progress({ status: chalk.red(`Database status check failed: ${err.message}`), next }, spinner.warn)
346
+ prevStatus = null
347
+ }
348
+
349
+ if (prevStatus === DB_STATUS.PROVISIONED) {
350
+ spinner.succeed(chalk.green(`Database is deployed and ready for use in the '${statusRegion}' region`))
351
+ return
352
+ } else if (prevStatus === DB_STATUS.REQUESTED || prevStatus === DB_STATUS.PROCESSING) {
353
+ spinner.succeed(chalk.green(`Database provisioning request has already been submitted in the '${statusRegion}' region and is pending`))
354
+ return
355
+ }
356
+
357
+ provRes = await db.provisionRequest()
358
+ progress({ status: chalk.dim(`Database provisioning result:\n${JSON.stringify(provRes, null, 2)}`) })
359
+ } catch (error) {
360
+ spinner.fail(chalk.red('Database deployment failed'))
361
+ throw error
362
+ }
363
+
364
+ const resultStatus = provRes?.status?.toUpperCase() || DB_STATUS.UNKNOWN
365
+ if (resultStatus === DB_STATUS.PROVISIONED) {
366
+ spinner.succeed(chalk.green(`Database is deployed and ready for use in the '${provRes.region}' region`))
367
+ } else if (resultStatus === DB_STATUS.REQUESTED || resultStatus === DB_STATUS.PROCESSING) {
368
+ spinner.succeed(chalk.green(`Database provisioning request submitted in the '${provRes.region}' region, database deployment is now pending`))
369
+ } else if (resultStatus === DB_STATUS.FAILED || resultStatus === DB_STATUS.REJECTED) {
370
+ const message = `Database provisioning request failed with status '${resultStatus}'`
371
+ spinner.fail(chalk.red(message))
372
+ throw new Error(`${message}: ${provRes.message || 'Unknown error'}`)
373
+ } else {
374
+ spinner.warn(chalk.yellow(`Database provisioning request returned unexpected status '${resultStatus}', an update to the aio cli tool may be necessary.`))
375
+ }
376
+ }
377
+
303
378
  async publishExtensionPoints (deployConfigs, aioConfig, force) {
304
379
  const libConsoleCLI = await this.getLibConsoleCLI()
305
380
 
@@ -50,65 +50,60 @@ class Undeploy extends BaseCommand {
50
50
  }
51
51
 
52
52
  const spinner = ora()
53
- try {
54
- const { aio: aioConfig, packagejson: packageJson } = await this.getFullConfig({}, flags)
55
- const cliDetails = await getAccessToken({ useCachedToken: !flags.unpublish })
56
- const appInfo = {
57
- name: packageJson.name,
58
- version: packageJson.version,
59
- project: aioConfig?.project,
60
- runtimeNamespace: aioConfig?.runtime?.namespace
53
+
54
+ const { aio: aioConfig, packagejson: packageJson } = await this.getFullConfig({}, flags)
55
+ const cliDetails = await getAccessToken({ useCachedToken: !flags.unpublish })
56
+ const appInfo = {
57
+ name: packageJson.name,
58
+ version: packageJson.version,
59
+ project: aioConfig?.project,
60
+ runtimeNamespace: aioConfig?.runtime?.namespace
61
+ }
62
+
63
+ if (cliDetails?.accessToken) {
64
+ try {
65
+ // send audit log at start (don't wait for deployment to finish)
66
+ await sendAppUndeployAuditLog({
67
+ accessToken: cliDetails?.accessToken,
68
+ cliCommandFlags: flags,
69
+ appInfo,
70
+ env: cliDetails.env
71
+ })
72
+ } catch (error) {
73
+ if (flags.verbose) {
74
+ this.warn('Error: Audit Log Service Error: Failed to send audit log event for deployment.')
75
+ this.warn(error.message)
76
+ }
61
77
  }
78
+ }
62
79
 
80
+ for (let i = 0; i < keys.length; ++i) {
81
+ const k = keys[i]
82
+ // TODO: remove this check once the deploy service is enabled by default
83
+ const v = setRuntimeApiHostAndAuthHandler(values[i])
84
+
85
+ await this.undeployOneExt(k, v, flags, spinner)
63
86
  if (cliDetails?.accessToken) {
87
+ // send logs for case of web-assets undeployment
64
88
  try {
65
- // send audit log at start (don't wait for deployment to finish)
66
- await sendAppUndeployAuditLog({
89
+ await sendAppAssetsUndeployedAuditLog({
67
90
  accessToken: cliDetails?.accessToken,
68
91
  cliCommandFlags: flags,
69
92
  appInfo,
70
93
  env: cliDetails.env
71
94
  })
72
95
  } catch (error) {
73
- if (flags.verbose) {
74
- this.warn('Error: Audit Log Service Error: Failed to send audit log event for deployment.')
75
- this.warn(error.message)
76
- }
77
- }
78
- }
79
-
80
- for (let i = 0; i < keys.length; ++i) {
81
- const k = keys[i]
82
- // TODO: remove this check once the deploy service is enabled by default
83
- const v = setRuntimeApiHostAndAuthHandler(values[i])
84
-
85
- await this.undeployOneExt(k, v, flags, spinner)
86
- if (cliDetails?.accessToken) {
87
- // send logs for case of web-assets undeployment
88
- try {
89
- await sendAppAssetsUndeployedAuditLog({
90
- accessToken: cliDetails?.accessToken,
91
- cliCommandFlags: flags,
92
- appInfo,
93
- env: cliDetails.env
94
- })
95
- } catch (error) {
96
- this.warn('Warning: Audit Log Service Error: Failed to send audit log event for un-deployment.')
97
- }
96
+ this.warn('Warning: Audit Log Service Error: Failed to send audit log event for un-deployment.')
98
97
  }
99
98
  }
99
+ }
100
100
 
101
- // 1.2. unpublish extension manifest
102
- if (flags.unpublish) {
103
- const payload = await this.unpublishExtensionPoints(libConsoleCLI, undeployConfigs, aioConfig, flags['force-unpublish'])
104
- this.log(chalk.blue(chalk.bold(`New Extension Point(s) in Workspace '${aioConfig.project.workspace.name}': '${Object.keys(payload.endpoints)}'`)))
105
- } else {
106
- this.log('skipping unpublish phase...')
107
- }
108
- } catch (error) {
109
- spinner.stop()
110
- // delegate to top handler
111
- throw error
101
+ // 1.2. unpublish extension manifest
102
+ if (flags.unpublish) {
103
+ const payload = await this.unpublishExtensionPoints(libConsoleCLI, undeployConfigs, aioConfig, flags['force-unpublish'])
104
+ this.log(chalk.blue(chalk.bold(`New Extension Point(s) in Workspace '${aioConfig.project.workspace.name}': '${Object.keys(payload.endpoints)}'`)))
105
+ } else {
106
+ this.log('skipping unpublish phase...')
112
107
  }
113
108
 
114
109
  const command = await this.config.findCommand('app:clean')
@@ -151,8 +146,7 @@ class Undeploy extends BaseCommand {
151
146
  }
152
147
  spinner.succeed(chalk.green(`Un-deploying actions for ${extName}`))
153
148
  } catch (err) {
154
- spinner.fail(chalk.green(`Un-deploying actions for ${extName}`))
155
- throw err
149
+ spinner.warn(chalk.yellow(`Error when un-deploying actions for ${extName}: ${err.message}`))
156
150
  }
157
151
  } else {
158
152
  this.log('no manifest file, skipping action undeploy')
@@ -168,8 +162,7 @@ class Undeploy extends BaseCommand {
168
162
 
169
163
  spinner.succeed(chalk.green(`Un-Deploying web assets for ${extName}`))
170
164
  } catch (err) {
171
- spinner.fail(chalk.green(`Un-Deploying web assets for ${extName}`))
172
- throw err
165
+ spinner.warn(chalk.yellow(`Error when un-deploying web assets for ${extName}: ${err.message}`))
173
166
  }
174
167
  } else {
175
168
  this.log('no frontend, skipping frontend undeploy')
@@ -41,5 +41,16 @@ module.exports = {
41
41
  EXTENSIONS_CONFIG_KEY: 'extensions',
42
42
  // Adding tracking file constants
43
43
  LAST_BUILT_ACTIONS_FILENAME: 'last-built-actions.json',
44
- LAST_DEPLOYED_ACTIONS_FILENAME: 'last-deployed-actions.json'
44
+ LAST_DEPLOYED_ACTIONS_FILENAME: 'last-deployed-actions.json',
45
+ // Database constants
46
+ DB_STATUS: {
47
+ PROVISIONED: 'PROVISIONED',
48
+ REQUESTED: 'REQUESTED',
49
+ PROCESSING: 'PROCESSING',
50
+ FAILED: 'FAILED',
51
+ REJECTED: 'REJECTED',
52
+ NOT_PROVISIONED: 'NOT_PROVISIONED',
53
+ DELETED: 'DELETED',
54
+ UNKNOWN: 'UNKNOWN'
55
+ }
45
56
  }