@gjsify/cli 0.3.13 → 0.3.15
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/lib/actions/build.d.ts +14 -93
- package/lib/actions/build.js +182 -154
- package/lib/commands/flatpak/build.d.ts +16 -0
- package/lib/commands/flatpak/build.js +187 -0
- package/lib/commands/flatpak/ci.d.ts +13 -0
- package/lib/commands/flatpak/ci.js +133 -0
- package/lib/commands/flatpak/deps.d.ts +12 -0
- package/lib/commands/flatpak/deps.js +96 -0
- package/lib/commands/flatpak/index.d.ts +7 -0
- package/lib/commands/flatpak/index.js +23 -0
- package/lib/commands/flatpak/init.d.ts +15 -0
- package/lib/commands/flatpak/init.js +154 -0
- package/lib/commands/flatpak/utils.d.ts +32 -0
- package/lib/commands/flatpak/utils.js +63 -0
- package/lib/commands/gsettings.d.ts +9 -0
- package/lib/commands/gsettings.js +72 -0
- package/lib/commands/index.d.ts +2 -0
- package/lib/commands/index.js +2 -0
- package/lib/commands/install.d.ts +1 -0
- package/lib/commands/install.js +66 -11
- package/lib/config.js +103 -11
- package/lib/index.js +3 -1
- package/lib/types/cli-build-options.d.ts +1 -1
- package/lib/types/config-data.d.ts +194 -4
- package/lib/utils/install-global.d.ts +54 -0
- package/lib/utils/install-global.js +153 -0
- package/lib/utils/normalize-bundler-options.d.ts +17 -0
- package/lib/utils/normalize-bundler-options.js +123 -0
- package/lib/utils/resolve-plugin-by-name.d.ts +21 -0
- package/lib/utils/resolve-plugin-by-name.js +75 -0
- package/package.json +11 -11
- package/src/actions/build.ts +406 -352
- package/src/commands/flatpak/build.ts +225 -0
- package/src/commands/flatpak/ci.ts +173 -0
- package/src/commands/flatpak/deps.ts +120 -0
- package/src/commands/flatpak/index.ts +53 -0
- package/src/commands/flatpak/init.ts +191 -0
- package/src/commands/flatpak/utils.ts +76 -0
- package/src/commands/gsettings.ts +87 -0
- package/src/commands/index.ts +2 -0
- package/src/commands/install.ts +90 -11
- package/src/config.ts +103 -11
- package/src/index.ts +4 -0
- package/src/types/cli-build-options.ts +1 -1
- package/src/types/config-data.ts +191 -4
- package/src/utils/install-global.ts +182 -0
- package/src/utils/normalize-bundler-options.ts +129 -0
- package/src/utils/resolve-plugin-by-name.ts +106 -0
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import type { ConfigDataFlatpak } from '../../types/config-data.js';
|
|
2
|
+
/**
|
|
3
|
+
* Default GNOME-Platform runtime version. Bumped per release window.
|
|
4
|
+
* GNOME 50 = April 2026 stable; tracked in
|
|
5
|
+
* https://docs.flathub.org/docs/for-app-authors/requirements.
|
|
6
|
+
*/
|
|
7
|
+
export declare const DEFAULT_GNOME_RUNTIME_VERSION = "50";
|
|
8
|
+
/** Default Freedesktop-Platform runtime version (LTS-ish). */
|
|
9
|
+
export declare const DEFAULT_FREEDESKTOP_RUNTIME_VERSION = "24.08";
|
|
10
|
+
/** Permissive GUI defaults for GTK4 + Adwaita apps. */
|
|
11
|
+
export declare const DEFAULT_GUI_FINISH_ARGS: string[];
|
|
12
|
+
/** Lean defaults for headless CLI tools — no display, no GPU. */
|
|
13
|
+
export declare const DEFAULT_CLI_FINISH_ARGS: string[];
|
|
14
|
+
/** Read package.json from a directory. Throws a helpful error if missing/invalid. */
|
|
15
|
+
export declare function readPackageJson(dir: string): Record<string, unknown>;
|
|
16
|
+
/** True if a name string looks like a reverse-DNS Flatpak app id. */
|
|
17
|
+
export declare function looksLikeAppId(value: unknown): value is string;
|
|
18
|
+
/**
|
|
19
|
+
* Pick the runtime + sdk + version triple from config + CLI overrides.
|
|
20
|
+
* `--runtime` and `--runtime-version` flags win over config values.
|
|
21
|
+
*/
|
|
22
|
+
export declare function resolveRuntime(flatpak: ConfigDataFlatpak | undefined, overrides: {
|
|
23
|
+
runtime?: string;
|
|
24
|
+
runtimeVersion?: string;
|
|
25
|
+
}): {
|
|
26
|
+
runtime: 'gnome' | 'freedesktop';
|
|
27
|
+
runtimeId: string;
|
|
28
|
+
sdk: string;
|
|
29
|
+
runtimeVersion: string;
|
|
30
|
+
};
|
|
31
|
+
/** Default container image for the GitHub Actions workflow. */
|
|
32
|
+
export declare function defaultCiContainer(runtime: 'gnome' | 'freedesktop', runtimeVersion: string): string;
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
// Shared helpers for the `gjsify flatpak <sub>` subcommand group.
|
|
2
|
+
import { readFileSync } from 'node:fs';
|
|
3
|
+
import { resolve } from 'node:path';
|
|
4
|
+
/**
|
|
5
|
+
* Default GNOME-Platform runtime version. Bumped per release window.
|
|
6
|
+
* GNOME 50 = April 2026 stable; tracked in
|
|
7
|
+
* https://docs.flathub.org/docs/for-app-authors/requirements.
|
|
8
|
+
*/
|
|
9
|
+
export const DEFAULT_GNOME_RUNTIME_VERSION = '50';
|
|
10
|
+
/** Default Freedesktop-Platform runtime version (LTS-ish). */
|
|
11
|
+
export const DEFAULT_FREEDESKTOP_RUNTIME_VERSION = '24.08';
|
|
12
|
+
/** Permissive GUI defaults for GTK4 + Adwaita apps. */
|
|
13
|
+
export const DEFAULT_GUI_FINISH_ARGS = [
|
|
14
|
+
'--device=dri',
|
|
15
|
+
'--share=ipc',
|
|
16
|
+
'--socket=fallback-x11',
|
|
17
|
+
'--socket=wayland',
|
|
18
|
+
];
|
|
19
|
+
/** Lean defaults for headless CLI tools — no display, no GPU. */
|
|
20
|
+
export const DEFAULT_CLI_FINISH_ARGS = [];
|
|
21
|
+
/** Read package.json from a directory. Throws a helpful error if missing/invalid. */
|
|
22
|
+
export function readPackageJson(dir) {
|
|
23
|
+
const path = resolve(dir, 'package.json');
|
|
24
|
+
let raw;
|
|
25
|
+
try {
|
|
26
|
+
raw = readFileSync(path, 'utf-8');
|
|
27
|
+
}
|
|
28
|
+
catch {
|
|
29
|
+
throw new Error(`gjsify flatpak: no package.json found at ${path}`);
|
|
30
|
+
}
|
|
31
|
+
try {
|
|
32
|
+
return JSON.parse(raw);
|
|
33
|
+
}
|
|
34
|
+
catch (err) {
|
|
35
|
+
throw new Error(`gjsify flatpak: package.json at ${path} is not valid JSON: ${err.message}`);
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
/** True if a name string looks like a reverse-DNS Flatpak app id. */
|
|
39
|
+
export function looksLikeAppId(value) {
|
|
40
|
+
return typeof value === 'string' && /^[A-Za-z][A-Za-z0-9_-]*(\.[A-Za-z][A-Za-z0-9_-]*){2,}$/.test(value);
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Pick the runtime + sdk + version triple from config + CLI overrides.
|
|
44
|
+
* `--runtime` and `--runtime-version` flags win over config values.
|
|
45
|
+
*/
|
|
46
|
+
export function resolveRuntime(flatpak, overrides) {
|
|
47
|
+
const runtime = (overrides.runtime ?? flatpak?.runtime ?? 'gnome');
|
|
48
|
+
if (runtime !== 'gnome' && runtime !== 'freedesktop') {
|
|
49
|
+
throw new Error(`gjsify flatpak: unknown runtime "${runtime}" (expected "gnome" or "freedesktop")`);
|
|
50
|
+
}
|
|
51
|
+
const runtimeVersion = overrides.runtimeVersion ??
|
|
52
|
+
flatpak?.runtimeVersion ??
|
|
53
|
+
(runtime === 'gnome' ? DEFAULT_GNOME_RUNTIME_VERSION : DEFAULT_FREEDESKTOP_RUNTIME_VERSION);
|
|
54
|
+
if (runtime === 'gnome') {
|
|
55
|
+
return { runtime, runtimeId: 'org.gnome.Platform', sdk: 'org.gnome.Sdk', runtimeVersion };
|
|
56
|
+
}
|
|
57
|
+
return { runtime, runtimeId: 'org.freedesktop.Platform', sdk: 'org.freedesktop.Sdk', runtimeVersion };
|
|
58
|
+
}
|
|
59
|
+
/** Default container image for the GitHub Actions workflow. */
|
|
60
|
+
export function defaultCiContainer(runtime, runtimeVersion) {
|
|
61
|
+
const tag = `${runtime}-${runtimeVersion}`;
|
|
62
|
+
return `ghcr.io/flathub-infra/flatpak-github-actions:${tag}`;
|
|
63
|
+
}
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import { execFile } from 'node:child_process';
|
|
2
|
+
import { mkdir } from 'node:fs/promises';
|
|
3
|
+
import { resolve } from 'node:path';
|
|
4
|
+
import { promisify } from 'node:util';
|
|
5
|
+
const execFileAsync = promisify(execFile);
|
|
6
|
+
export const gsettingsCommand = {
|
|
7
|
+
command: 'gsettings <schemadir>',
|
|
8
|
+
description: 'Compile GSettings schema XML files into a binary gschemas.compiled (wraps `glib-compile-schemas`).',
|
|
9
|
+
builder: (yargs) => {
|
|
10
|
+
return yargs
|
|
11
|
+
.positional('schemadir', {
|
|
12
|
+
description: 'Directory containing *.gschema.xml descriptors',
|
|
13
|
+
type: 'string',
|
|
14
|
+
normalize: true,
|
|
15
|
+
demandOption: true,
|
|
16
|
+
})
|
|
17
|
+
.option('targetdir', {
|
|
18
|
+
alias: 't',
|
|
19
|
+
description: 'Directory to write gschemas.compiled (default: <schemadir>)',
|
|
20
|
+
type: 'string',
|
|
21
|
+
normalize: true,
|
|
22
|
+
})
|
|
23
|
+
.option('strict', {
|
|
24
|
+
description: 'Abort on any schema warning (passes --strict to glib-compile-schemas)',
|
|
25
|
+
type: 'boolean',
|
|
26
|
+
default: true,
|
|
27
|
+
})
|
|
28
|
+
.option('verbose', {
|
|
29
|
+
description: 'Print the underlying glib-compile-schemas invocation',
|
|
30
|
+
type: 'boolean',
|
|
31
|
+
default: false,
|
|
32
|
+
});
|
|
33
|
+
},
|
|
34
|
+
handler: async (args) => {
|
|
35
|
+
const schemadir = resolve(args.schemadir);
|
|
36
|
+
const targetdir = args.targetdir
|
|
37
|
+
? resolve(args.targetdir)
|
|
38
|
+
: schemadir;
|
|
39
|
+
const cmdArgs = [];
|
|
40
|
+
if (args.strict)
|
|
41
|
+
cmdArgs.push('--strict');
|
|
42
|
+
cmdArgs.push(`--targetdir=${targetdir}`);
|
|
43
|
+
cmdArgs.push(schemadir);
|
|
44
|
+
if (args.verbose) {
|
|
45
|
+
console.log(`[gjsify gsettings] glib-compile-schemas ${cmdArgs.join(' ')}`);
|
|
46
|
+
}
|
|
47
|
+
// glib-compile-schemas writes a temporary file in `targetdir` before
|
|
48
|
+
// renaming to gschemas.compiled — fails with ENOENT if missing.
|
|
49
|
+
await mkdir(targetdir, { recursive: true });
|
|
50
|
+
try {
|
|
51
|
+
const { stdout, stderr } = await execFileAsync('glib-compile-schemas', cmdArgs);
|
|
52
|
+
if (stdout)
|
|
53
|
+
process.stdout.write(stdout);
|
|
54
|
+
if (stderr)
|
|
55
|
+
process.stderr.write(stderr);
|
|
56
|
+
if (args.verbose) {
|
|
57
|
+
console.log(`[gjsify gsettings] wrote ${targetdir}/gschemas.compiled`);
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
catch (err) {
|
|
61
|
+
if (err?.code === 'ENOENT') {
|
|
62
|
+
console.error('[gjsify gsettings] glib-compile-schemas not found. Install it via your distro (package: glib2-devel / libglib2.0-dev).');
|
|
63
|
+
}
|
|
64
|
+
else {
|
|
65
|
+
if (err?.stderr)
|
|
66
|
+
process.stderr.write(err.stderr);
|
|
67
|
+
console.error(`[gjsify gsettings] glib-compile-schemas failed${err?.code !== undefined ? ` (exit ${err.code})` : ''}`);
|
|
68
|
+
}
|
|
69
|
+
process.exitCode = typeof err?.code === 'number' ? err.code : 1;
|
|
70
|
+
}
|
|
71
|
+
},
|
|
72
|
+
};
|
package/lib/commands/index.d.ts
CHANGED
|
@@ -6,5 +6,7 @@ export * from './showcase.js';
|
|
|
6
6
|
export * from './create.js';
|
|
7
7
|
export * from './gresource.js';
|
|
8
8
|
export * from './gettext.js';
|
|
9
|
+
export * from './gsettings.js';
|
|
10
|
+
export { flatpakCommand } from './flatpak/index.js';
|
|
9
11
|
export * from './dlx.js';
|
|
10
12
|
export * from './install.js';
|
package/lib/commands/index.js
CHANGED
|
@@ -6,5 +6,7 @@ export * from './showcase.js';
|
|
|
6
6
|
export * from './create.js';
|
|
7
7
|
export * from './gresource.js';
|
|
8
8
|
export * from './gettext.js';
|
|
9
|
+
export * from './gsettings.js';
|
|
10
|
+
export { flatpakCommand } from './flatpak/index.js';
|
|
9
11
|
export * from './dlx.js';
|
|
10
12
|
export * from './install.js';
|
package/lib/commands/install.js
CHANGED
|
@@ -1,36 +1,65 @@
|
|
|
1
|
-
// `gjsify install [pkg...]` —
|
|
2
|
-
//
|
|
3
|
-
// The actual install is delegated to `npm install` in the user's project root
|
|
4
|
-
// (no `--prefix` rewrite, unlike `gjsify dlx`). After install completes we run
|
|
5
|
-
// `runMinimalChecks()` so missing system deps (gjs, gtk4, libsoup, ...) surface
|
|
6
|
-
// immediately, and report any installed `@gjsify/*` packages that ship native
|
|
7
|
-
// prebuilds so users know they can use `gjsify run` to wire `LD_LIBRARY_PATH` /
|
|
8
|
-
// `GI_TYPELIB_PATH` automatically.
|
|
1
|
+
// `gjsify install [pkg...]` — install packages with gjsify-aware post-checks.
|
|
9
2
|
//
|
|
10
3
|
// Modes:
|
|
11
4
|
// gjsify install → project install (npm install)
|
|
12
|
-
// gjsify install <pkg> [<pkg>...] → add package(s) (npm install <pkg>...)
|
|
5
|
+
// gjsify install <pkg> [<pkg>...] → add package(s) to project (npm install <pkg>...)
|
|
6
|
+
// gjsify install -g <pkg> [...] → user-global install (XDG, GJS-runnable bin)
|
|
7
|
+
//
|
|
8
|
+
// Project mode delegates to `npm install` in cwd and runs `runMinimalChecks()`
|
|
9
|
+
// + `detectNativePackages()` to surface missing system deps and `@gjsify/*`
|
|
10
|
+
// packages with native prebuilds.
|
|
11
|
+
//
|
|
12
|
+
// Global mode is the GJS equivalent of `npm i -g`: extracts the package tree
|
|
13
|
+
// into `${XDG_DATA_HOME}/gjsify/global/node_modules/<pkg>/` via the native
|
|
14
|
+
// install backend (no Node/npm required at runtime), then symlinks the bins
|
|
15
|
+
// declared by `gjsify.bin` (preferred) or `bin` (fallback) into
|
|
16
|
+
// `~/.local/bin/`. Subsequent commands invoked by name resolve to the
|
|
17
|
+
// extracted package, so package-relative assets like `@ts-for-gir/cli`'s
|
|
18
|
+
// `dist-templates/` are found by ordinary `__dirname/..` resolution — no
|
|
19
|
+
// embedded asset stores, no separate release tarballs.
|
|
13
20
|
import { spawn } from 'node:child_process';
|
|
21
|
+
import { mkdirSync } from 'node:fs';
|
|
14
22
|
import { buildInstallCommand, detectPackageManager, runMinimalChecks, } from '../utils/check-system-deps.js';
|
|
15
23
|
import { detectNativePackages } from '../utils/detect-native-packages.js';
|
|
24
|
+
import { installPackages } from '../utils/install-backend.js';
|
|
25
|
+
import { binDirOnPath, defaultGlobalLayout, linkGlobalBins, specToPackageName, } from '../utils/install-global.js';
|
|
16
26
|
export const installCommand = {
|
|
17
27
|
command: 'install [packages..]',
|
|
18
|
-
description: 'Install npm dependencies in the current project, then run gjsify-aware post-checks.',
|
|
28
|
+
description: 'Install npm dependencies in the current project (or globally with -g), then run gjsify-aware post-checks.',
|
|
19
29
|
builder: (yargs) => yargs
|
|
20
30
|
.positional('packages', {
|
|
21
31
|
description: 'Optional package specs. With none, runs a full project install.',
|
|
22
32
|
type: 'string',
|
|
23
33
|
array: true,
|
|
34
|
+
})
|
|
35
|
+
.option('global', {
|
|
36
|
+
description: 'Install into the user-global XDG location and symlink bins into ~/.local/bin.',
|
|
37
|
+
type: 'boolean',
|
|
38
|
+
alias: 'g',
|
|
39
|
+
default: false,
|
|
24
40
|
})
|
|
25
41
|
.option('save-dev', { type: 'boolean', alias: 'D' })
|
|
26
42
|
.option('save-peer', { type: 'boolean' })
|
|
27
43
|
.option('save-optional', { type: 'boolean', alias: 'O' })
|
|
28
44
|
.option('verbose', {
|
|
29
|
-
description: 'Verbose
|
|
45
|
+
description: 'Verbose install logging.',
|
|
30
46
|
type: 'boolean',
|
|
31
47
|
default: false,
|
|
32
48
|
}),
|
|
33
49
|
handler: async (args) => {
|
|
50
|
+
if (args.global) {
|
|
51
|
+
if (!args.packages || args.packages.length === 0) {
|
|
52
|
+
console.error('gjsify install --global requires at least one <pkg> argument.');
|
|
53
|
+
process.exit(1);
|
|
54
|
+
}
|
|
55
|
+
for (const flag of ['save-dev', 'save-peer', 'save-optional']) {
|
|
56
|
+
if (args[flag]) {
|
|
57
|
+
console.warn(`gjsify install --global ignores --${flag}: global installs do not modify a project package.json.`);
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
await installGlobalAndLink(args.packages, { verbose: args.verbose });
|
|
61
|
+
return;
|
|
62
|
+
}
|
|
34
63
|
const npmArgs = ['install'];
|
|
35
64
|
if (args['save-dev'])
|
|
36
65
|
npmArgs.push('--save-dev');
|
|
@@ -68,6 +97,32 @@ async function spawnNpm(npmArgs) {
|
|
|
68
97
|
process.exit(1);
|
|
69
98
|
});
|
|
70
99
|
}
|
|
100
|
+
async function installGlobalAndLink(specs, opts) {
|
|
101
|
+
const layout = defaultGlobalLayout();
|
|
102
|
+
mkdirSync(layout.prefix, { recursive: true });
|
|
103
|
+
console.log(`gjsify install --global → ${layout.prefix}`);
|
|
104
|
+
console.log(` bins → ${layout.binDir}`);
|
|
105
|
+
await installPackages({
|
|
106
|
+
prefix: layout.prefix,
|
|
107
|
+
specs,
|
|
108
|
+
verbose: opts.verbose,
|
|
109
|
+
});
|
|
110
|
+
const packageNames = specs.map(specToPackageName);
|
|
111
|
+
const created = linkGlobalBins(packageNames, layout);
|
|
112
|
+
if (created.length === 0) {
|
|
113
|
+
console.warn('\nNo bins declared (neither `gjsify.bin` nor `bin` in package.json) — nothing was symlinked.');
|
|
114
|
+
}
|
|
115
|
+
else {
|
|
116
|
+
console.log(`\nLinked ${created.length} bin(s):`);
|
|
117
|
+
for (const e of created) {
|
|
118
|
+
console.log(` • ${e.link} → ${e.target}`);
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
if (created.length > 0 && !binDirOnPath(layout.binDir)) {
|
|
122
|
+
console.warn(`\nNote: ${layout.binDir} is not on your PATH.\n` +
|
|
123
|
+
`Add it to your shell rc file:\n export PATH="${layout.binDir}:$PATH"`);
|
|
124
|
+
}
|
|
125
|
+
}
|
|
71
126
|
async function runPostInstallChecks() {
|
|
72
127
|
console.log('\n--- gjsify post-install checks ---');
|
|
73
128
|
// 1. System deps that GJS apps typically need.
|
package/lib/config.js
CHANGED
|
@@ -43,6 +43,23 @@ function merge(target, ...sources) {
|
|
|
43
43
|
function isPlainObject(val) {
|
|
44
44
|
return typeof val === 'object' && val !== null && !Array.isArray(val) && Object.getPrototypeOf(val) === Object.prototype;
|
|
45
45
|
}
|
|
46
|
+
/**
|
|
47
|
+
* Read a dotted path (`a.b.c`) from a plain object. Returns `undefined` for
|
|
48
|
+
* any missing segment. Intentionally narrow — only used for surfacing
|
|
49
|
+
* `package.json` fields into compile-time defines, not for arbitrary deep
|
|
50
|
+
* traversal.
|
|
51
|
+
*/
|
|
52
|
+
function readDottedPath(obj, path) {
|
|
53
|
+
if (!path.includes('.'))
|
|
54
|
+
return obj[path];
|
|
55
|
+
let cursor = obj;
|
|
56
|
+
for (const segment of path.split('.')) {
|
|
57
|
+
if (cursor === null || cursor === undefined || typeof cursor !== 'object')
|
|
58
|
+
return undefined;
|
|
59
|
+
cursor = cursor[segment];
|
|
60
|
+
}
|
|
61
|
+
return cursor;
|
|
62
|
+
}
|
|
46
63
|
export class Config {
|
|
47
64
|
loadOptions = {};
|
|
48
65
|
constructor(loadOptions = {}) {
|
|
@@ -84,7 +101,7 @@ export class Config {
|
|
|
84
101
|
if (fileResult?.config && isPlainObject(fileResult.config)) {
|
|
85
102
|
merge(merged, fileResult.config);
|
|
86
103
|
}
|
|
87
|
-
merged.
|
|
104
|
+
merged.bundler ||= {};
|
|
88
105
|
merged.library ||= {};
|
|
89
106
|
merged.typescript ||= {};
|
|
90
107
|
return {
|
|
@@ -155,16 +172,91 @@ export class Config {
|
|
|
155
172
|
if (Object.keys(aliasMap).length) {
|
|
156
173
|
configData.aliases = { ...(configData.aliases ?? {}), ...aliasMap };
|
|
157
174
|
}
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
175
|
+
// Resolve `defineFromPackageJson` / `defineFromEnv` into raw
|
|
176
|
+
// KEY=<JSON-stringified value> entries that get merged into the
|
|
177
|
+
// bundler's `transform.define` map below. Both produce JS expressions
|
|
178
|
+
// (the value side of a Rolldown define is substituted at the call
|
|
179
|
+
// site, not stringified again) — so a missing env variable resolves
|
|
180
|
+
// to the literal `undefined`, letting consumer code use
|
|
181
|
+
// `typeof X === 'undefined'` or `X ?? fallback` guards.
|
|
182
|
+
const fromPkgDefines = {};
|
|
183
|
+
if (configData.defineFromPackageJson) {
|
|
184
|
+
for (const [name, spec] of Object.entries(configData.defineFromPackageJson)) {
|
|
185
|
+
if (!spec || typeof spec.field !== 'string' || !spec.field) {
|
|
186
|
+
throw new Error(`gjsify config: defineFromPackageJson["${name}"] is missing a "field" string`);
|
|
187
|
+
}
|
|
188
|
+
const value = readDottedPath(pkg, spec.field);
|
|
189
|
+
fromPkgDefines[name] = value === undefined ? 'undefined' : JSON.stringify(value);
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
const fromEnvDefines = {};
|
|
193
|
+
if (configData.defineFromEnv) {
|
|
194
|
+
for (const [name, spec] of Object.entries(configData.defineFromEnv)) {
|
|
195
|
+
if (!spec || typeof spec.env !== 'string' || !spec.env) {
|
|
196
|
+
throw new Error(`gjsify config: defineFromEnv["${name}"] is missing an "env" string`);
|
|
197
|
+
}
|
|
198
|
+
const raw = process.env[spec.env];
|
|
199
|
+
const value = raw !== undefined ? raw : spec.default;
|
|
200
|
+
fromEnvDefines[name] = value === undefined ? 'undefined' : JSON.stringify(value);
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
// Merge CLI flags into the Rolldown-shape `bundler` field. Mappings:
|
|
204
|
+
// --entry-points → bundler.input
|
|
205
|
+
// --outfile → bundler.output.file
|
|
206
|
+
// --outdir → bundler.output.dir
|
|
207
|
+
// --format → bundler.output.format
|
|
208
|
+
// --minify → bundler.output.minify
|
|
209
|
+
// --log-level → bundler.logLevel
|
|
210
|
+
// --external → bundler.external
|
|
211
|
+
// --define → bundler.transform.define
|
|
212
|
+
const bundler = (configData.bundler ??= {});
|
|
213
|
+
const output = (bundler.output ??= {});
|
|
214
|
+
const transform = (bundler.transform ??= {});
|
|
215
|
+
if (cliArgs.entryPoints?.length)
|
|
216
|
+
bundler.input = cliArgs.entryPoints;
|
|
217
|
+
if (cliArgs.outfile !== undefined)
|
|
218
|
+
output.file = cliArgs.outfile;
|
|
219
|
+
if (cliArgs.outdir !== undefined)
|
|
220
|
+
output.dir = cliArgs.outdir;
|
|
221
|
+
if (cliArgs.format !== undefined)
|
|
222
|
+
output.format = cliArgs.format;
|
|
223
|
+
if (cliArgs.minify !== undefined)
|
|
224
|
+
output.minify = cliArgs.minify;
|
|
225
|
+
if (cliArgs.logLevel) {
|
|
226
|
+
// Map esbuild log levels to Rolldown's narrower set:
|
|
227
|
+
// esbuild → rolldown
|
|
228
|
+
// silent → silent
|
|
229
|
+
// error → warn (rolldown has no error-only)
|
|
230
|
+
// warning → warn
|
|
231
|
+
// info → info
|
|
232
|
+
// debug → debug
|
|
233
|
+
// verbose → debug (rolldown has no verbose)
|
|
234
|
+
const map = {
|
|
235
|
+
silent: 'silent',
|
|
236
|
+
error: 'warn',
|
|
237
|
+
warning: 'warn',
|
|
238
|
+
warn: 'warn',
|
|
239
|
+
info: 'info',
|
|
240
|
+
debug: 'debug',
|
|
241
|
+
verbose: 'debug',
|
|
242
|
+
};
|
|
243
|
+
const level = map[cliArgs.logLevel] ?? 'warn';
|
|
244
|
+
bundler.logLevel = level;
|
|
245
|
+
}
|
|
246
|
+
if (cliArgs.external?.length) {
|
|
247
|
+
const userExternal = Array.isArray(bundler.external) ? bundler.external : [];
|
|
248
|
+
bundler.external = [...userExternal, ...cliArgs.external];
|
|
249
|
+
}
|
|
250
|
+
if (Object.keys(defineMap).length || Object.keys(fromPkgDefines).length || Object.keys(fromEnvDefines).length) {
|
|
251
|
+
// CLI --define wins over package.json/env (manual overrides during
|
|
252
|
+
// debugging beat declarative config).
|
|
253
|
+
transform.define = {
|
|
254
|
+
...(transform.define ?? {}),
|
|
255
|
+
...fromPkgDefines,
|
|
256
|
+
...fromEnvDefines,
|
|
257
|
+
...defineMap,
|
|
258
|
+
};
|
|
259
|
+
}
|
|
168
260
|
if (configData.verbose)
|
|
169
261
|
console.debug("configData", configData);
|
|
170
262
|
return configData;
|
package/lib/index.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import yargs from 'yargs';
|
|
3
3
|
import { hideBin } from 'yargs/helpers';
|
|
4
|
-
import { buildCommand as build, runCommand as run, infoCommand as info, checkCommand as check, showcaseCommand as showcase, createCommand as create, gresourceCommand as gresource, gettextCommand as gettext, dlxCommand as dlx, installCommand as install, } from './commands/index.js';
|
|
4
|
+
import { buildCommand as build, runCommand as run, infoCommand as info, checkCommand as check, showcaseCommand as showcase, createCommand as create, gresourceCommand as gresource, gettextCommand as gettext, gsettingsCommand as gsettings, flatpakCommand as flatpak, dlxCommand as dlx, installCommand as install, } from './commands/index.js';
|
|
5
5
|
import { APP_NAME } from './constants.js';
|
|
6
6
|
void yargs(hideBin(process.argv))
|
|
7
7
|
.scriptName(APP_NAME)
|
|
@@ -16,5 +16,7 @@ void yargs(hideBin(process.argv))
|
|
|
16
16
|
.command(showcase.command, showcase.description, showcase.builder, showcase.handler)
|
|
17
17
|
.command(gresource.command, gresource.description, gresource.builder, gresource.handler)
|
|
18
18
|
.command(gettext.command, gettext.description, gettext.builder, gettext.handler)
|
|
19
|
+
.command(gsettings.command, gsettings.description, gsettings.builder, gsettings.handler)
|
|
20
|
+
.command(flatpak.command, flatpak.description, flatpak.builder, flatpak.handler)
|
|
19
21
|
.demandCommand(1)
|
|
20
22
|
.help().argv;
|