@remogram/cli 0.1.0-beta.2 → 0.1.0-beta.4
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/index.js +120 -3
- package/package.json +7 -7
package/index.js
CHANGED
|
@@ -19,6 +19,9 @@ import {
|
|
|
19
19
|
getEffectiveIngestMaxBytes,
|
|
20
20
|
FORGE_INGEST_MAX_BYTES_ENV,
|
|
21
21
|
throwIfStaleHeadByNumber,
|
|
22
|
+
FACT_INVENTORY_PACKET_TYPES,
|
|
23
|
+
forgeFactInventoryPacket,
|
|
24
|
+
assertWriteCommandConfigured,
|
|
22
25
|
} from '@remogram/core';
|
|
23
26
|
import { provider as giteaApi } from '@remogram/provider-gitea-api';
|
|
24
27
|
import { provider as githubApi } from '@remogram/provider-github-api';
|
|
@@ -34,6 +37,13 @@ const PROVIDERS = {
|
|
|
34
37
|
'github-gh': githubGh,
|
|
35
38
|
};
|
|
36
39
|
|
|
40
|
+
const REPEATABLE_FLAGS = new Set(['allowed_path']);
|
|
41
|
+
|
|
42
|
+
function parseAllowedPathFlags(flags) {
|
|
43
|
+
if (flags.allowed_path == null) return undefined;
|
|
44
|
+
return Array.isArray(flags.allowed_path) ? flags.allowed_path : [flags.allowed_path];
|
|
45
|
+
}
|
|
46
|
+
|
|
37
47
|
function parsePositiveInt(value, name) {
|
|
38
48
|
if (value == null) return undefined;
|
|
39
49
|
const n = Number(value);
|
|
@@ -210,6 +220,22 @@ async function buildDoctorPacket(cwd, providers) {
|
|
|
210
220
|
),
|
|
211
221
|
);
|
|
212
222
|
|
|
223
|
+
if (providerCapabilities.write_support) {
|
|
224
|
+
const providerWrites = (providerCapabilities.write_commands || []).filter(Boolean);
|
|
225
|
+
const configuredWrites = Array.isArray(config?.write_commands) ? config.write_commands : [];
|
|
226
|
+
const missing = providerWrites.filter((name) => !configuredWrites.includes(name));
|
|
227
|
+
checks.push(
|
|
228
|
+
doctorCheck(
|
|
229
|
+
'write_config',
|
|
230
|
+
missing.length ? 'warn' : 'pass',
|
|
231
|
+
missing.length
|
|
232
|
+
? `Provider supports write commands but .remogram.json write_commands omits: ${missing.join(', ')}`
|
|
233
|
+
: 'Consumer write_commands matches provider write surface',
|
|
234
|
+
{ provider_write_commands: providerWrites, configured_write_commands: configuredWrites },
|
|
235
|
+
),
|
|
236
|
+
);
|
|
237
|
+
}
|
|
238
|
+
|
|
213
239
|
if (!providerCapabilities.check_sources?.length) {
|
|
214
240
|
checks.push(doctorCheck('checks', 'warn', 'Provider does not report forge check sources'));
|
|
215
241
|
} else {
|
|
@@ -268,7 +294,13 @@ export async function runCli(argv, options = {}) {
|
|
|
268
294
|
else if (arg.startsWith('--')) {
|
|
269
295
|
const key = arg.slice(2).replace(/-/g, '_');
|
|
270
296
|
const next = argv[i + 1];
|
|
271
|
-
if (
|
|
297
|
+
if (REPEATABLE_FLAGS.has(key)) {
|
|
298
|
+
if (!flags[key]) flags[key] = [];
|
|
299
|
+
if (next != null && !next.startsWith('--')) {
|
|
300
|
+
flags[key].push(next);
|
|
301
|
+
i += 1;
|
|
302
|
+
}
|
|
303
|
+
} else if (next != null && !next.startsWith('--')) {
|
|
272
304
|
flags[key] = next;
|
|
273
305
|
i += 1;
|
|
274
306
|
} else {
|
|
@@ -336,6 +368,83 @@ export async function runCli(argv, options = {}) {
|
|
|
336
368
|
ctx,
|
|
337
369
|
await provider.refsCompare(ctx, flags.base, flags.head),
|
|
338
370
|
);
|
|
371
|
+
} else if (group === 'refs' && sub === 'inventory') {
|
|
372
|
+
if (typeof provider.refsInventory !== 'function') {
|
|
373
|
+
throw Object.assign(new Error('refs inventory not implemented for provider'), {
|
|
374
|
+
forgeError: forgeError(
|
|
375
|
+
ERROR_CODES.PROVIDER_UNSUPPORTED,
|
|
376
|
+
'refs inventory not implemented for provider',
|
|
377
|
+
),
|
|
378
|
+
});
|
|
379
|
+
}
|
|
380
|
+
packet = forgeFactInventoryPacket(
|
|
381
|
+
FACT_INVENTORY_PACKET_TYPES.REF_INVENTORY,
|
|
382
|
+
ctx,
|
|
383
|
+
await provider.refsInventory(ctx),
|
|
384
|
+
);
|
|
385
|
+
} else if (group === 'cr' && sub === 'inventory') {
|
|
386
|
+
if (typeof provider.crInventory !== 'function') {
|
|
387
|
+
throw Object.assign(new Error('cr inventory not implemented for provider'), {
|
|
388
|
+
forgeError: forgeError(
|
|
389
|
+
ERROR_CODES.PROVIDER_UNSUPPORTED,
|
|
390
|
+
'cr inventory not implemented for provider',
|
|
391
|
+
),
|
|
392
|
+
});
|
|
393
|
+
}
|
|
394
|
+
const inventoryBody = await provider.crInventory(ctx, {
|
|
395
|
+
slice_ref: flags.slice_ref,
|
|
396
|
+
limit: parsePositiveInt(flags.limit, '--limit'),
|
|
397
|
+
sort: flags.sort,
|
|
398
|
+
});
|
|
399
|
+
if (inventoryBody.list_truncated === true) {
|
|
400
|
+
throw Object.assign(new Error('Open CR list incomplete'), {
|
|
401
|
+
forgeError: forgeError(
|
|
402
|
+
ERROR_CODES.INVENTORY_LIST_INCOMPLETE,
|
|
403
|
+
'Open change request list could not be proved complete within pagination bounds',
|
|
404
|
+
null,
|
|
405
|
+
{
|
|
406
|
+
inventory_list: {
|
|
407
|
+
entry_count: inventoryBody.entry_count,
|
|
408
|
+
},
|
|
409
|
+
},
|
|
410
|
+
),
|
|
411
|
+
});
|
|
412
|
+
}
|
|
413
|
+
packet = forgeFactInventoryPacket(
|
|
414
|
+
FACT_INVENTORY_PACKET_TYPES.CR_INVENTORY_SLICE,
|
|
415
|
+
ctx,
|
|
416
|
+
inventoryBody,
|
|
417
|
+
);
|
|
418
|
+
} else if (group === 'cr' && sub === 'open') {
|
|
419
|
+
if (typeof provider.crOpen !== 'function') {
|
|
420
|
+
throw Object.assign(new Error('cr open not implemented for provider'), {
|
|
421
|
+
forgeError: forgeError(
|
|
422
|
+
ERROR_CODES.PROVIDER_UNSUPPORTED,
|
|
423
|
+
'cr open not implemented for provider',
|
|
424
|
+
),
|
|
425
|
+
});
|
|
426
|
+
}
|
|
427
|
+
if (!flags.head || !flags.base || !flags.title) {
|
|
428
|
+
throw Object.assign(new Error('--head, --base, and --title required'), {
|
|
429
|
+
forgeError: forgeError(
|
|
430
|
+
ERROR_CODES.INVALID_ARGS,
|
|
431
|
+
'--head, --base, and --title required for cr open',
|
|
432
|
+
),
|
|
433
|
+
});
|
|
434
|
+
}
|
|
435
|
+
assertGitRef(flags.head, '--head');
|
|
436
|
+
assertGitRef(flags.base, '--base');
|
|
437
|
+
assertWriteCommandConfigured(ctx.config, 'cr_open');
|
|
438
|
+
packet = forgePacket(
|
|
439
|
+
PACKET_TYPES.CHANGE_REQUEST_OPENED,
|
|
440
|
+
ctx,
|
|
441
|
+
await provider.crOpen(ctx, {
|
|
442
|
+
head: flags.head,
|
|
443
|
+
base: flags.base,
|
|
444
|
+
title: flags.title,
|
|
445
|
+
body: flags.body,
|
|
446
|
+
}),
|
|
447
|
+
);
|
|
339
448
|
} else if (group === 'pr' && sub === 'view') {
|
|
340
449
|
const number = parsePositiveInt(flags.number, '--number');
|
|
341
450
|
if (number == null) {
|
|
@@ -382,7 +491,15 @@ export async function runCli(argv, options = {}) {
|
|
|
382
491
|
forgeError: forgeError(ERROR_CODES.INVALID_ARGS, '--number required for merge plan'),
|
|
383
492
|
});
|
|
384
493
|
}
|
|
385
|
-
|
|
494
|
+
const allowedPaths = parseAllowedPathFlags(flags);
|
|
495
|
+
packet = forgePacket(
|
|
496
|
+
PACKET_TYPES.MERGE_PLAN,
|
|
497
|
+
ctx,
|
|
498
|
+
await provider.mergePlan(ctx, {
|
|
499
|
+
number,
|
|
500
|
+
...(allowedPaths ? { allowed_paths: allowedPaths } : {}),
|
|
501
|
+
}),
|
|
502
|
+
);
|
|
386
503
|
} else if (group === 'sync' && sub === 'plan') {
|
|
387
504
|
const remote = flags.remote || ctx.config.remote;
|
|
388
505
|
assertGitRemote(remote, '--remote');
|
|
@@ -395,7 +512,7 @@ export async function runCli(argv, options = {}) {
|
|
|
395
512
|
throw Object.assign(new Error(`Unknown command: ${positional.join(' ')}`), {
|
|
396
513
|
forgeError: forgeError(
|
|
397
514
|
ERROR_CODES.INVALID_ARGS,
|
|
398
|
-
'Unknown command. Try: provider capabilities, repo status, refs compare, pr view, pr checks, merge plan, sync plan',
|
|
515
|
+
'Unknown command. Try: provider capabilities, repo status, refs compare, refs inventory, cr inventory, cr open, pr view, pr checks, merge plan, sync plan',
|
|
399
516
|
),
|
|
400
517
|
});
|
|
401
518
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@remogram/cli",
|
|
3
|
-
"version": "0.1.0-beta.
|
|
3
|
+
"version": "0.1.0-beta.4",
|
|
4
4
|
"description": "Remogram forge boundary CLI",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
@@ -27,11 +27,11 @@
|
|
|
27
27
|
"node": ">=20"
|
|
28
28
|
},
|
|
29
29
|
"dependencies": {
|
|
30
|
-
"@remogram/core": "0.1.0-beta.
|
|
31
|
-
"@remogram/provider-gitea-api": "0.1.0-beta.
|
|
32
|
-
"@remogram/provider-github-api": "0.1.0-beta.
|
|
33
|
-
"@remogram/provider-gitlab-api": "0.1.0-beta.
|
|
34
|
-
"@remogram/provider-gitea-tea": "0.1.0-beta.
|
|
35
|
-
"@remogram/provider-github-gh": "0.1.0-beta.
|
|
30
|
+
"@remogram/core": "0.1.0-beta.4",
|
|
31
|
+
"@remogram/provider-gitea-api": "0.1.0-beta.4",
|
|
32
|
+
"@remogram/provider-github-api": "0.1.0-beta.4",
|
|
33
|
+
"@remogram/provider-gitlab-api": "0.1.0-beta.4",
|
|
34
|
+
"@remogram/provider-gitea-tea": "0.1.0-beta.4",
|
|
35
|
+
"@remogram/provider-github-gh": "0.1.0-beta.4"
|
|
36
36
|
}
|
|
37
37
|
}
|