@ubox-tools/deploy-xperience 1.0.0 → 1.1.1
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/README.md +6 -0
- package/deploy.js +39 -5
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -27,6 +27,8 @@ npx @ubox-tools/deploy-xperience [app1 app2 ...] [options]
|
|
|
27
27
|
| `--project-name <name>` | Override the project name (default: parent directory name) |
|
|
28
28
|
| `--noassets` | Skip uploading assets (images, fonts, files) |
|
|
29
29
|
| `--noplayer` | Skip Phase 3 — deploy apps only, do not create/update Uboxes |
|
|
30
|
+
| `--ubox-id <id>` | Use a pre-existing Ubox by ID — skips search/create (single-app deployments) |
|
|
31
|
+
| `--ubox-id <app>:<id>` | Scoped form for multi-app deployments (repeatable) |
|
|
30
32
|
| `--show` | Show the browser window (default: headless) |
|
|
31
33
|
| `--help` | Print usage and exit |
|
|
32
34
|
|
|
@@ -47,6 +49,8 @@ npx @ubox-tools/deploy-xperience mobile # Deploy only the mobile
|
|
|
47
49
|
npx @ubox-tools/deploy-xperience main --noassets # Deploy main app, skip asset uploads
|
|
48
50
|
npx @ubox-tools/deploy-xperience --noplayer # Deploy apps only, skip Uboxes
|
|
49
51
|
npx @ubox-tools/deploy-xperience --project-name "MyProject"
|
|
52
|
+
npx @ubox-tools/deploy-xperience mobile --ubox-id 42 # Use existing Ubox #42 for mobile
|
|
53
|
+
npx @ubox-tools/deploy-xperience --ubox-id mobile:42 --ubox-id main:99
|
|
50
54
|
```
|
|
51
55
|
|
|
52
56
|
## Deployment Phases
|
|
@@ -76,6 +80,8 @@ Runs once per app:
|
|
|
76
80
|
|
|
77
81
|
If the Ubox already exists, installation and parameter changes are skipped; the mobile virtual link is still retrieved so the main Ubox can use it.
|
|
78
82
|
|
|
83
|
+
When `--ubox-id` is provided, the search/create step is skipped entirely and the script navigates directly to `https://studio.ubox.world/#/ubox/<id>`. The same "already exists" logic then applies.
|
|
84
|
+
|
|
79
85
|
## Proxy / Source Transformation
|
|
80
86
|
|
|
81
87
|
Before injecting source files, `generateProxy()` applies three transforms to each file:
|
package/deploy.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
1
2
|
'use strict';
|
|
2
3
|
|
|
3
4
|
const puppeteer = require('puppeteer');
|
|
@@ -52,6 +53,8 @@ Options:
|
|
|
52
53
|
--project-name <name> Override project name (default: directory name)
|
|
53
54
|
--noassets Skip uploading assets (resources)
|
|
54
55
|
--noplayer Skip Ubox creation (Phase 3) — only deploy applications
|
|
56
|
+
--ubox-id <id> Use a pre-existing Ubox by ID (skips search/create)
|
|
57
|
+
--ubox-id <app>:<id> Scoped form when deploying multiple apps
|
|
55
58
|
--show Show the browser window (default: headless)
|
|
56
59
|
--help Show this help
|
|
57
60
|
|
|
@@ -61,6 +64,8 @@ Examples:
|
|
|
61
64
|
npx @ubox-tools/deploy-xperience main # Deploy only main
|
|
62
65
|
npx @ubox-tools/deploy-xperience --noassets # Deploy without re-uploading assets
|
|
63
66
|
npx @ubox-tools/deploy-xperience --noplayer # Deploy apps only, skip Uboxes
|
|
67
|
+
npx @ubox-tools/deploy-xperience --ubox-id 42 # Use existing Ubox #42 (single-app)
|
|
68
|
+
npx @ubox-tools/deploy-xperience --ubox-id mobile:42 --ubox-id main:99
|
|
64
69
|
UBOX_EMAIL=me@x.com npx @ubox-tools/deploy-xperience
|
|
65
70
|
`.trim());
|
|
66
71
|
process.exit(0);
|
|
@@ -73,6 +78,8 @@ Examples:
|
|
|
73
78
|
let noPlayer = false;
|
|
74
79
|
let show = false;
|
|
75
80
|
const appArgs = [];
|
|
81
|
+
const uboxIds = {};
|
|
82
|
+
let bareUboxId = null;
|
|
76
83
|
|
|
77
84
|
for (let i = 0; i < args.length; i++) {
|
|
78
85
|
if (args[i] === '--email') { email = args[++i]; }
|
|
@@ -81,6 +88,15 @@ Examples:
|
|
|
81
88
|
else if (args[i] === '--noassets') { noAssets = true; }
|
|
82
89
|
else if (args[i] === '--noplayer') { noPlayer = true; }
|
|
83
90
|
else if (args[i] === '--show') { show = true; }
|
|
91
|
+
else if (args[i] === '--ubox-id') {
|
|
92
|
+
const val = args[++i];
|
|
93
|
+
if (val.includes(':')) {
|
|
94
|
+
const colon = val.indexOf(':');
|
|
95
|
+
uboxIds[val.slice(0, colon)] = val.slice(colon + 1);
|
|
96
|
+
} else {
|
|
97
|
+
bareUboxId = val;
|
|
98
|
+
}
|
|
99
|
+
}
|
|
84
100
|
else if (!args[i].startsWith('--')) { appArgs.push(args[i]); }
|
|
85
101
|
}
|
|
86
102
|
|
|
@@ -101,7 +117,15 @@ Examples:
|
|
|
101
117
|
...selected.filter(a => !DEPLOY_ORDER.includes(a)),
|
|
102
118
|
];
|
|
103
119
|
|
|
104
|
-
|
|
120
|
+
if (bareUboxId !== null) {
|
|
121
|
+
if (ordered.length !== 1) {
|
|
122
|
+
console.error('Error: bare --ubox-id <id> requires exactly one app to be selected.\nUse --ubox-id <app>:<id> form when deploying multiple apps (e.g. --ubox-id mobile:42 --ubox-id main:99).');
|
|
123
|
+
process.exit(1);
|
|
124
|
+
}
|
|
125
|
+
uboxIds[ordered[0]] = bareUboxId;
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
return { apps: ordered, email, password, projectName, noAssets, noPlayer, show, uboxIds };
|
|
105
129
|
}
|
|
106
130
|
|
|
107
131
|
// ─── Credentials ──────────────────────────────────────────────────────────────
|
|
@@ -943,11 +967,20 @@ async function setMobileLink(page, appFullName, mobileVirtualLink) {
|
|
|
943
967
|
console.log(` [ubox] mobileLink = ${mobileVirtualLink}`);
|
|
944
968
|
}
|
|
945
969
|
|
|
946
|
-
async function deployUbox(page, appName, projectName, appParams, mobileVirtualLink) {
|
|
970
|
+
async function deployUbox(page, appName, projectName, appParams, mobileVirtualLink, targetUboxId = null) {
|
|
947
971
|
const fullName = `${projectName} ${appName}`;
|
|
948
972
|
console.log(`\n[Phase 3] Ubox: ${fullName}`);
|
|
949
973
|
|
|
950
|
-
|
|
974
|
+
let uboxUrl, created;
|
|
975
|
+
if (targetUboxId) {
|
|
976
|
+
uboxUrl = `${BASE_URL}/#/ubox/${targetUboxId}`;
|
|
977
|
+
console.log(` [ubox] Using pre-existing Ubox ID ${targetUboxId} — navigating directly...`);
|
|
978
|
+
await page.goto(uboxUrl, { waitUntil: 'networkidle2' });
|
|
979
|
+
await sleep(2000);
|
|
980
|
+
created = false;
|
|
981
|
+
} else {
|
|
982
|
+
({ url: uboxUrl, created } = await findOrCreateUbox(page, fullName));
|
|
983
|
+
}
|
|
951
984
|
|
|
952
985
|
let virtualLink = null;
|
|
953
986
|
|
|
@@ -990,7 +1023,7 @@ async function deployUbox(page, appName, projectName, appParams, mobileVirtualLi
|
|
|
990
1023
|
// ─── Main ─────────────────────────────────────────────────────────────────────
|
|
991
1024
|
|
|
992
1025
|
async function main() {
|
|
993
|
-
const { apps, email: emailArg, password: passwordArg, projectName: projectNameArg, noAssets, noPlayer, show } = parseArgs();
|
|
1026
|
+
const { apps, email: emailArg, password: passwordArg, projectName: projectNameArg, noAssets, noPlayer, show, uboxIds } = parseArgs();
|
|
994
1027
|
|
|
995
1028
|
if (apps.length === 0) {
|
|
996
1029
|
console.error('No apps found in apps/ directory. Nothing to deploy.');
|
|
@@ -1039,7 +1072,8 @@ async function main() {
|
|
|
1039
1072
|
let mobileVirtualLink = null;
|
|
1040
1073
|
for (const appName of apps) {
|
|
1041
1074
|
const { uboxId, virtualLink } = await deployUbox(
|
|
1042
|
-
page, appName, projectName, appParamsMap[appName], mobileVirtualLink
|
|
1075
|
+
page, appName, projectName, appParamsMap[appName], mobileVirtualLink,
|
|
1076
|
+
uboxIds[appName] ?? null
|
|
1043
1077
|
);
|
|
1044
1078
|
state[appName].uboxId = uboxId;
|
|
1045
1079
|
if (appName === 'mobile' && virtualLink) {
|
package/package.json
CHANGED