@packmind/cli 0.25.0 → 0.26.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/main.cjs +1796 -1627
- package/package.json +3 -2
package/main.cjs
CHANGED
|
@@ -1582,6 +1582,9 @@ function stripAnsi(string21) {
|
|
|
1582
1582
|
if (typeof string21 !== "string") {
|
|
1583
1583
|
throw new TypeError(`Expected a \`string\`, got \`${typeof string21}\``);
|
|
1584
1584
|
}
|
|
1585
|
+
if (!string21.includes("\x1B") && !string21.includes("\x9B")) {
|
|
1586
|
+
return string21;
|
|
1587
|
+
}
|
|
1585
1588
|
return string21.replace(regex, "");
|
|
1586
1589
|
}
|
|
1587
1590
|
var regex;
|
|
@@ -3852,7 +3855,7 @@ var require_package = __commonJS({
|
|
|
3852
3855
|
"apps/cli/package.json"(exports2, module2) {
|
|
3853
3856
|
module2.exports = {
|
|
3854
3857
|
name: "@packmind/cli",
|
|
3855
|
-
version: "0.
|
|
3858
|
+
version: "0.26.1",
|
|
3856
3859
|
description: "A command-line interface for Packmind linting and code quality checks",
|
|
3857
3860
|
private: false,
|
|
3858
3861
|
bin: {
|
|
@@ -4427,6 +4430,48 @@ var SpaceCreatedEvent = class extends UserEvent {
|
|
|
4427
4430
|
}
|
|
4428
4431
|
};
|
|
4429
4432
|
|
|
4433
|
+
// packages/types/src/spaces/events/SpaceMembersAddedEvent.ts
|
|
4434
|
+
var SpaceMembersAddedEvent = class extends UserEvent {
|
|
4435
|
+
static {
|
|
4436
|
+
this.eventName = "spaces.space.members-added";
|
|
4437
|
+
}
|
|
4438
|
+
};
|
|
4439
|
+
|
|
4440
|
+
// packages/types/src/spaces/events/SpaceMembersRemovedEvent.ts
|
|
4441
|
+
var SpaceMembersRemovedEvent = class extends UserEvent {
|
|
4442
|
+
static {
|
|
4443
|
+
this.eventName = "spaces.space.members-removed";
|
|
4444
|
+
}
|
|
4445
|
+
};
|
|
4446
|
+
|
|
4447
|
+
// packages/types/src/spaces/events/SpaceMembersRoleUpdatedEvent.ts
|
|
4448
|
+
var SpaceMembersRoleUpdatedEvent = class extends UserEvent {
|
|
4449
|
+
static {
|
|
4450
|
+
this.eventName = "spaces.space.members-role-updated";
|
|
4451
|
+
}
|
|
4452
|
+
};
|
|
4453
|
+
|
|
4454
|
+
// packages/types/src/spaces/events/SpacePinnedEvent.ts
|
|
4455
|
+
var SpacePinnedEvent = class extends UserEvent {
|
|
4456
|
+
static {
|
|
4457
|
+
this.eventName = "spaces.space.pinned";
|
|
4458
|
+
}
|
|
4459
|
+
};
|
|
4460
|
+
|
|
4461
|
+
// packages/types/src/spaces/events/SpaceUnpinnedEvent.ts
|
|
4462
|
+
var SpaceUnpinnedEvent = class extends UserEvent {
|
|
4463
|
+
static {
|
|
4464
|
+
this.eventName = "spaces.space.unpinned";
|
|
4465
|
+
}
|
|
4466
|
+
};
|
|
4467
|
+
|
|
4468
|
+
// packages/types/src/spaces/events/SpaceVisibilityUpdatedEvent.ts
|
|
4469
|
+
var SpaceVisibilityUpdatedEvent = class extends UserEvent {
|
|
4470
|
+
static {
|
|
4471
|
+
this.eventName = "spaces.space.visibility-updated";
|
|
4472
|
+
}
|
|
4473
|
+
};
|
|
4474
|
+
|
|
4430
4475
|
// packages/types/src/spaces-management/events/PlaybookArtefactMovedEvent.ts
|
|
4431
4476
|
var PlaybookArtefactMovedEvent = class extends UserEvent {
|
|
4432
4477
|
static {
|
|
@@ -5335,30 +5380,30 @@ var GitService = class {
|
|
|
5335
5380
|
this.gitRunner = gitRunner;
|
|
5336
5381
|
this.logger = logger2;
|
|
5337
5382
|
}
|
|
5338
|
-
getGitRepositoryRoot(
|
|
5383
|
+
getGitRepositoryRoot(path37) {
|
|
5339
5384
|
try {
|
|
5340
5385
|
const { stdout } = this.gitRunner("rev-parse --show-toplevel", {
|
|
5341
|
-
cwd:
|
|
5386
|
+
cwd: path37
|
|
5342
5387
|
});
|
|
5343
5388
|
const gitRoot = stdout.trim();
|
|
5344
5389
|
this.logger.debug("Resolved git repository root", {
|
|
5345
|
-
inputPath:
|
|
5390
|
+
inputPath: path37,
|
|
5346
5391
|
gitRoot
|
|
5347
5392
|
});
|
|
5348
5393
|
return gitRoot;
|
|
5349
5394
|
} catch (error) {
|
|
5350
5395
|
if (error instanceof Error) {
|
|
5351
5396
|
throw new Error(
|
|
5352
|
-
`Failed to get Git repository root. The path '${
|
|
5397
|
+
`Failed to get Git repository root. The path '${path37}' does not appear to be inside a Git repository.
|
|
5353
5398
|
${error.message}`
|
|
5354
5399
|
);
|
|
5355
5400
|
}
|
|
5356
5401
|
throw new Error("Failed to get Git repository root: Unknown error");
|
|
5357
5402
|
}
|
|
5358
5403
|
}
|
|
5359
|
-
tryGetGitRepositoryRoot(
|
|
5404
|
+
tryGetGitRepositoryRoot(path37) {
|
|
5360
5405
|
try {
|
|
5361
|
-
return this.getGitRepositoryRoot(
|
|
5406
|
+
return this.getGitRepositoryRoot(path37);
|
|
5362
5407
|
} catch {
|
|
5363
5408
|
return null;
|
|
5364
5409
|
}
|
|
@@ -6623,10 +6668,10 @@ var PackmindHttpClient = class {
|
|
|
6623
6668
|
return null;
|
|
6624
6669
|
}
|
|
6625
6670
|
}
|
|
6626
|
-
async request(
|
|
6671
|
+
async request(path37, options = {}) {
|
|
6627
6672
|
const { host } = this.getAuthContext();
|
|
6628
6673
|
const { method = "GET", body } = options;
|
|
6629
|
-
const url = `${host}${
|
|
6674
|
+
const url = `${host}${path37}`;
|
|
6630
6675
|
try {
|
|
6631
6676
|
const response = await fetch(url, {
|
|
6632
6677
|
method,
|
|
@@ -6838,6 +6883,21 @@ var SpacesGateway = class {
|
|
|
6838
6883
|
);
|
|
6839
6884
|
};
|
|
6840
6885
|
}
|
|
6886
|
+
async getSpaceBySlug(slug3) {
|
|
6887
|
+
const { organizationId } = this.httpClient.getAuthContext();
|
|
6888
|
+
try {
|
|
6889
|
+
return await this.httpClient.request(
|
|
6890
|
+
`/api/v0/organizations/${organizationId}/spaces/${slug3}`
|
|
6891
|
+
);
|
|
6892
|
+
} catch (error) {
|
|
6893
|
+
if (error.statusCode === 404) return null;
|
|
6894
|
+
throw error;
|
|
6895
|
+
}
|
|
6896
|
+
}
|
|
6897
|
+
getApiContext() {
|
|
6898
|
+
const { host, organizationId } = this.httpClient.getAuthContext();
|
|
6899
|
+
return { host, organizationId };
|
|
6900
|
+
}
|
|
6841
6901
|
};
|
|
6842
6902
|
|
|
6843
6903
|
// apps/cli/src/infra/repositories/SkillsGateway.ts
|
|
@@ -7026,6 +7086,21 @@ var DeploymentGateway = class {
|
|
|
7026
7086
|
`/api/v0/organizations/${organizationId}/pull?${queryParams.toString()}`
|
|
7027
7087
|
);
|
|
7028
7088
|
};
|
|
7089
|
+
this.install = async (command33) => {
|
|
7090
|
+
const { organizationId } = this.httpClient.getAuthContext();
|
|
7091
|
+
return this.httpClient.request(
|
|
7092
|
+
`/api/v0/organizations/${organizationId}/install`,
|
|
7093
|
+
{
|
|
7094
|
+
method: "POST",
|
|
7095
|
+
body: {
|
|
7096
|
+
packagesSlugs: command33.packagesSlugs,
|
|
7097
|
+
packmindLockFile: command33.packmindLockFile,
|
|
7098
|
+
...command33.relativePath && { relativePath: command33.relativePath },
|
|
7099
|
+
...command33.agents !== void 0 && { agents: command33.agents }
|
|
7100
|
+
}
|
|
7101
|
+
}
|
|
7102
|
+
);
|
|
7103
|
+
};
|
|
7029
7104
|
this.getDeployed = async (command33) => {
|
|
7030
7105
|
const { organizationId } = this.httpClient.getAuthContext();
|
|
7031
7106
|
return this.httpClient.request(
|
|
@@ -7065,6 +7140,21 @@ var DeploymentGateway = class {
|
|
|
7065
7140
|
}
|
|
7066
7141
|
);
|
|
7067
7142
|
};
|
|
7143
|
+
this.notifyArtefactsDistribution = async (command33) => {
|
|
7144
|
+
const { organizationId } = this.httpClient.getAuthContext();
|
|
7145
|
+
return this.httpClient.request(
|
|
7146
|
+
`/api/v0/organizations/${organizationId}/deployments/notify-artifacts-distribution`,
|
|
7147
|
+
{
|
|
7148
|
+
method: "POST",
|
|
7149
|
+
body: {
|
|
7150
|
+
gitRemoteUrl: command33.gitRemoteUrl,
|
|
7151
|
+
gitBranch: command33.gitBranch,
|
|
7152
|
+
relativePath: command33.relativePath,
|
|
7153
|
+
packmindLockFile: command33.packmindLockFile
|
|
7154
|
+
}
|
|
7155
|
+
}
|
|
7156
|
+
);
|
|
7157
|
+
};
|
|
7068
7158
|
this.getRenderModeConfiguration = async () => {
|
|
7069
7159
|
const { organizationId } = this.httpClient.getAuthContext();
|
|
7070
7160
|
return this.httpClient.request(
|
|
@@ -7086,6 +7176,24 @@ var DeploymentGateway = class {
|
|
|
7086
7176
|
}
|
|
7087
7177
|
};
|
|
7088
7178
|
|
|
7179
|
+
// apps/cli/src/infra/repositories/OrganizationGateway.ts
|
|
7180
|
+
var OrganizationGateway = class {
|
|
7181
|
+
constructor(httpClient) {
|
|
7182
|
+
this.httpClient = httpClient;
|
|
7183
|
+
}
|
|
7184
|
+
async getOrganization() {
|
|
7185
|
+
const { organizationId } = this.httpClient.getAuthContext();
|
|
7186
|
+
const organizations = await this.httpClient.request(
|
|
7187
|
+
"/api/v0/organizations"
|
|
7188
|
+
);
|
|
7189
|
+
const org = organizations.find((o) => o.id === organizationId);
|
|
7190
|
+
if (!org) {
|
|
7191
|
+
throw new Error(`Organization ${organizationId} not found`);
|
|
7192
|
+
}
|
|
7193
|
+
return org;
|
|
7194
|
+
}
|
|
7195
|
+
};
|
|
7196
|
+
|
|
7089
7197
|
// apps/cli/src/infra/repositories/PackmindGateway.ts
|
|
7090
7198
|
var PackmindGateway = class {
|
|
7091
7199
|
constructor(apiKey) {
|
|
@@ -7100,6 +7208,7 @@ var PackmindGateway = class {
|
|
|
7100
7208
|
this.standards = new StandardsGateway(this.httpClient);
|
|
7101
7209
|
this.packages = new PackagesGateway(apiKey, this.httpClient);
|
|
7102
7210
|
this.deployment = new DeploymentGateway(this.httpClient);
|
|
7211
|
+
this.organization = new OrganizationGateway(this.httpClient);
|
|
7103
7212
|
}
|
|
7104
7213
|
};
|
|
7105
7214
|
|
|
@@ -9927,69 +10036,150 @@ ${endMarker}`;
|
|
|
9927
10036
|
}
|
|
9928
10037
|
};
|
|
9929
10038
|
|
|
9930
|
-
// apps/cli/src/application/useCases/
|
|
10039
|
+
// apps/cli/src/application/useCases/InstallUseCase.ts
|
|
9931
10040
|
var fs5 = __toESM(require("fs/promises"));
|
|
9932
10041
|
var path7 = __toESM(require("path"));
|
|
9933
|
-
|
|
9934
|
-
|
|
9935
|
-
|
|
9936
|
-
|
|
10042
|
+
|
|
10043
|
+
// apps/cli/src/application/utils/normalizePackageSlugs.ts
|
|
10044
|
+
async function normalizePackageSlugs(slugs, spaceService) {
|
|
10045
|
+
const hasUnprefixed = slugs.some((s) => !s.startsWith("@"));
|
|
10046
|
+
if (!hasUnprefixed) return slugs;
|
|
10047
|
+
const spaces = await spaceService.getSpaces();
|
|
10048
|
+
if (spaces.length > 1) {
|
|
10049
|
+
throw new Error(
|
|
10050
|
+
`Your organization has multiple spaces. Please specify the space for each package using the @space/package format (e.g. @${spaces[0].slug}/my-package).`
|
|
10051
|
+
);
|
|
10052
|
+
}
|
|
10053
|
+
const defaultSpace = await spaceService.getDefaultSpace();
|
|
10054
|
+
return slugs.map(
|
|
10055
|
+
(slug3) => slug3.startsWith("@") ? slug3 : `@${defaultSpace.slug}/${slug3}`
|
|
10056
|
+
);
|
|
10057
|
+
}
|
|
10058
|
+
|
|
10059
|
+
// apps/cli/src/application/useCases/InstallUseCase.ts
|
|
10060
|
+
var InstallUseCase = class {
|
|
10061
|
+
constructor(packmindGateway, lockFileRepository, configFileRepository, spaceService) {
|
|
10062
|
+
this.packmindGateway = packmindGateway;
|
|
10063
|
+
this.lockFileRepository = lockFileRepository;
|
|
10064
|
+
this.configFileRepository = configFileRepository;
|
|
10065
|
+
this.spaceService = spaceService;
|
|
9937
10066
|
}
|
|
9938
10067
|
async execute(command33) {
|
|
9939
10068
|
const baseDirectory = command33.baseDirectory || process.cwd();
|
|
9940
10069
|
const result = {
|
|
9941
10070
|
filesCreated: 0,
|
|
9942
10071
|
filesUpdated: 0,
|
|
10072
|
+
filesDeleted: 0,
|
|
10073
|
+
contentFilesChanged: 0,
|
|
9943
10074
|
errors: [],
|
|
9944
|
-
|
|
9945
|
-
|
|
9946
|
-
|
|
10075
|
+
recipesCount: 0,
|
|
10076
|
+
standardsCount: 0,
|
|
10077
|
+
commandsCount: 0,
|
|
10078
|
+
skillsCount: 0,
|
|
10079
|
+
recipesRemoved: 0,
|
|
10080
|
+
standardsRemoved: 0,
|
|
10081
|
+
commandsRemoved: 0,
|
|
10082
|
+
skillsRemoved: 0,
|
|
10083
|
+
skillDirectoriesDeleted: 0,
|
|
10084
|
+
missingAccess: []
|
|
9947
10085
|
};
|
|
9948
|
-
const
|
|
9949
|
-
const
|
|
9950
|
-
const
|
|
9951
|
-
|
|
9952
|
-
|
|
9953
|
-
|
|
9954
|
-
|
|
10086
|
+
const hasExplicitPackages = command33.packages && command33.packages.length > 0;
|
|
10087
|
+
const lockFile = await this.lockFileRepository.read(baseDirectory);
|
|
10088
|
+
const config = await this.configFileRepository.readConfig(baseDirectory);
|
|
10089
|
+
if (!config && !hasExplicitPackages) {
|
|
10090
|
+
const configFileExists = await this.configFileRepository.configExists(baseDirectory);
|
|
10091
|
+
if (configFileExists) {
|
|
10092
|
+
throw new Error(
|
|
10093
|
+
"packmind.json exists but could not be parsed. Please fix the JSON syntax errors and try again."
|
|
10094
|
+
);
|
|
9955
10095
|
}
|
|
9956
|
-
|
|
9957
|
-
|
|
9958
|
-
|
|
9959
|
-
|
|
9960
|
-
|
|
9961
|
-
|
|
9962
|
-
|
|
9963
|
-
|
|
9964
|
-
|
|
9965
|
-
|
|
10096
|
+
throw new Error(
|
|
10097
|
+
"No packmind.json found in this directory. Run `packmind-cli install <@space/package>` first to install your packages."
|
|
10098
|
+
);
|
|
10099
|
+
}
|
|
10100
|
+
const effectiveLockFile = lockFile ?? {
|
|
10101
|
+
lockfileVersion: 1,
|
|
10102
|
+
packageSlugs: [],
|
|
10103
|
+
agents: [],
|
|
10104
|
+
installedAt: (/* @__PURE__ */ new Date()).toISOString(),
|
|
10105
|
+
artifacts: {}
|
|
10106
|
+
};
|
|
10107
|
+
let packagesSlugs;
|
|
10108
|
+
let normalizedPackages = [];
|
|
10109
|
+
if (hasExplicitPackages) {
|
|
10110
|
+
normalizedPackages = await this.normalizePackageSlugs(command33.packages);
|
|
10111
|
+
await this.validatePackageAccess(normalizedPackages);
|
|
10112
|
+
const normalizedConfigPackages = config ? await this.normalizeAndSaveConfigPackages(baseDirectory, config) : [];
|
|
10113
|
+
packagesSlugs = [
|
|
10114
|
+
.../* @__PURE__ */ new Set([...normalizedConfigPackages, ...normalizedPackages])
|
|
10115
|
+
];
|
|
10116
|
+
} else {
|
|
10117
|
+
packagesSlugs = await this.normalizeAndSaveConfigPackages(
|
|
10118
|
+
baseDirectory,
|
|
10119
|
+
config
|
|
10120
|
+
);
|
|
10121
|
+
}
|
|
10122
|
+
if (packagesSlugs.length === 0) {
|
|
10123
|
+
try {
|
|
10124
|
+
for (const entry of Object.values(effectiveLockFile.artifacts)) {
|
|
10125
|
+
for (const file of entry.files) {
|
|
10126
|
+
await this.deleteFile(baseDirectory, file.path, result);
|
|
10127
|
+
}
|
|
9966
10128
|
}
|
|
10129
|
+
await this.deleteFile(baseDirectory, "packmind-lock.json", result);
|
|
10130
|
+
} catch (error) {
|
|
10131
|
+
const errorMsg = error instanceof Error ? error.message : String(error);
|
|
10132
|
+
result.errors.push(`Failed to clean up artifacts: ${errorMsg}`);
|
|
10133
|
+
}
|
|
10134
|
+
return result;
|
|
10135
|
+
}
|
|
10136
|
+
const response = await this.packmindGateway.deployment.install({
|
|
10137
|
+
packagesSlugs,
|
|
10138
|
+
packmindLockFile: effectiveLockFile,
|
|
10139
|
+
agents: config?.agents
|
|
10140
|
+
});
|
|
10141
|
+
result.missingAccess = response.missingAccess;
|
|
10142
|
+
if (result.missingAccess.length > 0) {
|
|
10143
|
+
result.joinSpaceUrl = await this.computeJoinSpaceUrl(
|
|
10144
|
+
result.missingAccess
|
|
10145
|
+
);
|
|
10146
|
+
}
|
|
10147
|
+
const filteredCreateOrUpdate = response.fileUpdates.createOrUpdate.filter(
|
|
10148
|
+
(file) => file.path !== "packmind.json"
|
|
10149
|
+
);
|
|
10150
|
+
const uniqueFilesMap = /* @__PURE__ */ new Map();
|
|
10151
|
+
for (const file of filteredCreateOrUpdate) {
|
|
10152
|
+
uniqueFilesMap.set(file.path, file);
|
|
10153
|
+
}
|
|
10154
|
+
const uniqueFiles = Array.from(uniqueFilesMap.values());
|
|
10155
|
+
for (const file of uniqueFiles) {
|
|
10156
|
+
if (file.path.includes(".packmind/recipes/") && file.path.endsWith(".md")) {
|
|
10157
|
+
result.recipesCount++;
|
|
10158
|
+
} else if (file.path.includes(".packmind/standards/") && file.path.endsWith(".md")) {
|
|
10159
|
+
result.standardsCount++;
|
|
10160
|
+
} else if (file.path.includes(".packmind/commands/") && file.path.endsWith(".md")) {
|
|
10161
|
+
result.commandsCount++;
|
|
10162
|
+
} else if (file.path.includes(".packmind/skills/") && file.path.endsWith(".md")) {
|
|
10163
|
+
result.skillsCount++;
|
|
9967
10164
|
}
|
|
9968
10165
|
}
|
|
9969
10166
|
try {
|
|
9970
|
-
|
|
10167
|
+
result.skillDirectoriesDeleted = await this.deleteSkillFolders(
|
|
10168
|
+
baseDirectory,
|
|
10169
|
+
response.skillFolders
|
|
10170
|
+
);
|
|
10171
|
+
for (const file of uniqueFiles) {
|
|
9971
10172
|
try {
|
|
9972
|
-
|
|
9973
|
-
|
|
9974
|
-
|
|
9975
|
-
|
|
9976
|
-
|
|
9977
|
-
|
|
9978
|
-
|
|
9979
|
-
|
|
9980
|
-
|
|
9981
|
-
if (fileAlreadyInstalled) {
|
|
9982
|
-
const paths = incompatibleInstalledMap.get(skillName) ?? [];
|
|
9983
|
-
paths.push(file.path);
|
|
9984
|
-
incompatibleInstalledMap.set(skillName, paths);
|
|
9985
|
-
} else {
|
|
9986
|
-
if (!result.skippedIncompatibleSkillNames.includes(skillName)) {
|
|
9987
|
-
result.skippedIncompatibleSkillNames.push(skillName);
|
|
9988
|
-
}
|
|
9989
|
-
}
|
|
9990
|
-
continue;
|
|
10173
|
+
const changesBefore = result.filesCreated + result.filesUpdated;
|
|
10174
|
+
await this.createOrUpdateFile(
|
|
10175
|
+
baseDirectory,
|
|
10176
|
+
file,
|
|
10177
|
+
result,
|
|
10178
|
+
file.skillFilePermissions
|
|
10179
|
+
);
|
|
10180
|
+
if (result.filesCreated + result.filesUpdated > changesBefore && this.isContentFile(file.path)) {
|
|
10181
|
+
result.contentFilesChanged++;
|
|
9991
10182
|
}
|
|
9992
|
-
await this.createOrUpdateFile(baseDirectory, file, result);
|
|
9993
10183
|
} catch (error) {
|
|
9994
10184
|
const errorMsg = error instanceof Error ? error.message : String(error);
|
|
9995
10185
|
result.errors.push(
|
|
@@ -9997,44 +10187,489 @@ var InstallDefaultSkillsUseCase = class {
|
|
|
9997
10187
|
);
|
|
9998
10188
|
}
|
|
9999
10189
|
}
|
|
10190
|
+
for (const file of response.fileUpdates.delete) {
|
|
10191
|
+
try {
|
|
10192
|
+
const deletedBefore = result.filesDeleted;
|
|
10193
|
+
await this.deleteFile(baseDirectory, file.path, result);
|
|
10194
|
+
if (result.filesDeleted > deletedBefore) {
|
|
10195
|
+
if (file.path.includes(".packmind/standards/") && file.path.endsWith(".md")) {
|
|
10196
|
+
result.standardsRemoved++;
|
|
10197
|
+
result.contentFilesChanged++;
|
|
10198
|
+
} else if (file.path.includes(".packmind/commands/") && file.path.endsWith(".md")) {
|
|
10199
|
+
result.commandsRemoved++;
|
|
10200
|
+
result.contentFilesChanged++;
|
|
10201
|
+
} else if (file.path.includes(".packmind/skills/") && file.path.endsWith(".md")) {
|
|
10202
|
+
result.skillsRemoved++;
|
|
10203
|
+
result.contentFilesChanged++;
|
|
10204
|
+
} else if (file.path.includes(".packmind/recipes/") && file.path.endsWith(".md")) {
|
|
10205
|
+
result.recipesRemoved++;
|
|
10206
|
+
result.contentFilesChanged++;
|
|
10207
|
+
}
|
|
10208
|
+
}
|
|
10209
|
+
} catch (error) {
|
|
10210
|
+
const errorMsg = error instanceof Error ? error.message : String(error);
|
|
10211
|
+
result.errors.push(`Failed to delete ${file.path}: ${errorMsg}`);
|
|
10212
|
+
}
|
|
10213
|
+
}
|
|
10000
10214
|
} catch (error) {
|
|
10001
10215
|
const errorMsg = error instanceof Error ? error.message : String(error);
|
|
10002
|
-
result.errors.push(`Failed to install
|
|
10216
|
+
result.errors.push(`Failed to install packages: ${errorMsg}`);
|
|
10217
|
+
}
|
|
10218
|
+
if (normalizedPackages.length > 0) {
|
|
10219
|
+
await this.configFileRepository.addPackagesToConfig(
|
|
10220
|
+
baseDirectory,
|
|
10221
|
+
normalizedPackages
|
|
10222
|
+
);
|
|
10003
10223
|
}
|
|
10004
|
-
result.incompatibleInstalledSkills = Array.from(
|
|
10005
|
-
incompatibleInstalledMap.entries()
|
|
10006
|
-
).map(
|
|
10007
|
-
([skillName, filePaths]) => ({
|
|
10008
|
-
skillName,
|
|
10009
|
-
filePaths
|
|
10010
|
-
})
|
|
10011
|
-
);
|
|
10012
10224
|
return result;
|
|
10013
10225
|
}
|
|
10014
|
-
async
|
|
10226
|
+
async normalizePackageSlugs(slugs) {
|
|
10227
|
+
return normalizePackageSlugs(slugs, this.spaceService);
|
|
10228
|
+
}
|
|
10229
|
+
async normalizeAndSaveConfigPackages(baseDirectory, config) {
|
|
10230
|
+
const originalSlugs = Object.keys(config.packages);
|
|
10231
|
+
if (originalSlugs.length === 0) return [];
|
|
10232
|
+
const normalizedSlugs = await this.normalizePackageSlugs(originalSlugs);
|
|
10233
|
+
const hasChanges = normalizedSlugs.some(
|
|
10234
|
+
(slug3, i) => slug3 !== originalSlugs[i]
|
|
10235
|
+
);
|
|
10236
|
+
if (hasChanges) {
|
|
10237
|
+
const normalizedPackagesMap = {};
|
|
10238
|
+
for (let i = 0; i < normalizedSlugs.length; i++) {
|
|
10239
|
+
normalizedPackagesMap[normalizedSlugs[i]] = config.packages[originalSlugs[i]];
|
|
10240
|
+
}
|
|
10241
|
+
await this.configFileRepository.updateConfig(
|
|
10242
|
+
baseDirectory,
|
|
10243
|
+
"packages",
|
|
10244
|
+
normalizedPackagesMap
|
|
10245
|
+
);
|
|
10246
|
+
}
|
|
10247
|
+
return normalizedSlugs;
|
|
10248
|
+
}
|
|
10249
|
+
async validatePackageAccess(packages) {
|
|
10250
|
+
const userSpaces = await this.spaceService.getSpaces();
|
|
10251
|
+
const userSpaceSlugs = new Set(userSpaces.map((s) => s.slug));
|
|
10252
|
+
const { host } = this.spaceService.getApiContext();
|
|
10253
|
+
const errors = [];
|
|
10254
|
+
for (const pkg of packages) {
|
|
10255
|
+
const spaceSlug = pkg.startsWith("@") ? pkg.slice(1).split("/")[0] : null;
|
|
10256
|
+
if (!spaceSlug || userSpaceSlugs.has(spaceSlug)) continue;
|
|
10257
|
+
const space = await this.spaceService.getSpaceBySlug(spaceSlug);
|
|
10258
|
+
if (!space || space.type === "private" /* private */) {
|
|
10259
|
+
errors.push(`Package ${pkg} does not exist.`);
|
|
10260
|
+
} else {
|
|
10261
|
+
const organization = await this.packmindGateway.organization.getOrganization();
|
|
10262
|
+
const joinUrl = `${host}/org/${organization.slug}/spaces/${spaceSlug}/join`;
|
|
10263
|
+
errors.push(
|
|
10264
|
+
`You don't have access to space @${spaceSlug}. It is a public space \u2014 you can join at: ${joinUrl}`
|
|
10265
|
+
);
|
|
10266
|
+
}
|
|
10267
|
+
}
|
|
10268
|
+
if (errors.length > 0) {
|
|
10269
|
+
throw new Error(errors.join("\n"));
|
|
10270
|
+
}
|
|
10271
|
+
}
|
|
10272
|
+
async computeJoinSpaceUrl(missingAccessSlugs) {
|
|
10273
|
+
const spaceSlugs = /* @__PURE__ */ new Set();
|
|
10274
|
+
for (const slug3 of missingAccessSlugs) {
|
|
10275
|
+
if (slug3.startsWith("@")) {
|
|
10276
|
+
const spaceSlug2 = slug3.slice(1).split("/")[0];
|
|
10277
|
+
spaceSlugs.add(spaceSlug2);
|
|
10278
|
+
}
|
|
10279
|
+
}
|
|
10280
|
+
if (spaceSlugs.size !== 1) return void 0;
|
|
10281
|
+
const [spaceSlug] = spaceSlugs;
|
|
10282
|
+
const space = await this.spaceService.getSpaceBySlug(spaceSlug);
|
|
10283
|
+
if (!space || space.type !== "open" /* open */) return void 0;
|
|
10284
|
+
const organization = await this.packmindGateway.organization.getOrganization();
|
|
10285
|
+
const { host } = this.spaceService.getApiContext();
|
|
10286
|
+
return `${host}/org/${organization.slug}/spaces/${spaceSlug}/join`;
|
|
10287
|
+
}
|
|
10288
|
+
async createOrUpdateFile(baseDirectory, file, result, skillFilePermissions) {
|
|
10015
10289
|
const fullPath = path7.join(baseDirectory, file.path);
|
|
10016
10290
|
const directory = path7.dirname(fullPath);
|
|
10017
10291
|
await fs5.mkdir(directory, { recursive: true });
|
|
10018
10292
|
const fileExists = await this.fileExists(fullPath);
|
|
10293
|
+
if (file.content !== void 0) {
|
|
10294
|
+
await this.handleFullContentUpdate(
|
|
10295
|
+
fullPath,
|
|
10296
|
+
file.content,
|
|
10297
|
+
fileExists,
|
|
10298
|
+
result,
|
|
10299
|
+
file.isBase64
|
|
10300
|
+
);
|
|
10301
|
+
} else if (file.sections !== void 0) {
|
|
10302
|
+
await this.handleSectionsUpdate(
|
|
10303
|
+
fullPath,
|
|
10304
|
+
file.sections,
|
|
10305
|
+
fileExists,
|
|
10306
|
+
result,
|
|
10307
|
+
baseDirectory
|
|
10308
|
+
);
|
|
10309
|
+
}
|
|
10310
|
+
if (skillFilePermissions && supportsUnixPermissions()) {
|
|
10311
|
+
await fs5.chmod(fullPath, parsePermissionString(skillFilePermissions));
|
|
10312
|
+
}
|
|
10313
|
+
}
|
|
10314
|
+
async handleFullContentUpdate(fullPath, content, fileExists, result, isBase64) {
|
|
10315
|
+
if (isBase64) {
|
|
10316
|
+
const buffer = Buffer.from(content, "base64");
|
|
10317
|
+
await fs5.writeFile(fullPath, buffer);
|
|
10318
|
+
if (fileExists) {
|
|
10319
|
+
result.filesUpdated++;
|
|
10320
|
+
} else {
|
|
10321
|
+
result.filesCreated++;
|
|
10322
|
+
}
|
|
10323
|
+
return;
|
|
10324
|
+
}
|
|
10019
10325
|
if (fileExists) {
|
|
10020
10326
|
const existingContent = await fs5.readFile(fullPath, "utf-8");
|
|
10021
|
-
|
|
10022
|
-
|
|
10327
|
+
const commentMarker = this.extractCommentMarker(content);
|
|
10328
|
+
let finalContent;
|
|
10329
|
+
if (!commentMarker) {
|
|
10330
|
+
finalContent = content;
|
|
10331
|
+
} else {
|
|
10332
|
+
finalContent = this.mergeContentWithMarkers(
|
|
10333
|
+
existingContent,
|
|
10334
|
+
content,
|
|
10335
|
+
commentMarker
|
|
10336
|
+
);
|
|
10337
|
+
}
|
|
10338
|
+
if (existingContent !== finalContent) {
|
|
10339
|
+
await fs5.writeFile(fullPath, finalContent, "utf-8");
|
|
10023
10340
|
result.filesUpdated++;
|
|
10024
10341
|
}
|
|
10025
10342
|
} else {
|
|
10026
|
-
await fs5.writeFile(fullPath,
|
|
10343
|
+
await fs5.writeFile(fullPath, content, "utf-8");
|
|
10027
10344
|
result.filesCreated++;
|
|
10028
10345
|
}
|
|
10029
10346
|
}
|
|
10030
|
-
async fileExists
|
|
10031
|
-
|
|
10347
|
+
async handleSectionsUpdate(fullPath, sections, fileExists, result, baseDirectory) {
|
|
10348
|
+
let currentContent = "";
|
|
10349
|
+
if (fileExists) {
|
|
10350
|
+
currentContent = await fs5.readFile(fullPath, "utf-8");
|
|
10351
|
+
}
|
|
10352
|
+
const mergedContent = mergeSectionsIntoFileContent(
|
|
10353
|
+
currentContent,
|
|
10354
|
+
sections
|
|
10355
|
+
);
|
|
10356
|
+
if (currentContent !== mergedContent) {
|
|
10357
|
+
if (this.isEffectivelyEmpty(mergedContent) && fileExists) {
|
|
10358
|
+
await fs5.unlink(fullPath);
|
|
10359
|
+
result.filesDeleted++;
|
|
10360
|
+
await this.removeEmptyParentDirectories(fullPath, baseDirectory);
|
|
10361
|
+
} else {
|
|
10362
|
+
await fs5.writeFile(fullPath, mergedContent, "utf-8");
|
|
10363
|
+
if (fileExists) {
|
|
10364
|
+
result.filesUpdated++;
|
|
10365
|
+
} else {
|
|
10366
|
+
result.filesCreated++;
|
|
10367
|
+
}
|
|
10368
|
+
}
|
|
10369
|
+
}
|
|
10370
|
+
}
|
|
10371
|
+
async deleteFile(baseDirectory, filePath, result) {
|
|
10372
|
+
const fullPath = path7.join(baseDirectory, filePath);
|
|
10373
|
+
const stat9 = await fs5.stat(fullPath).catch(() => null);
|
|
10374
|
+
if (stat9?.isDirectory()) {
|
|
10375
|
+
await fs5.rm(fullPath, { recursive: true, force: true });
|
|
10376
|
+
result.filesDeleted++;
|
|
10377
|
+
await this.removeEmptyParentDirectories(fullPath, baseDirectory);
|
|
10378
|
+
} else if (stat9?.isFile()) {
|
|
10379
|
+
await fs5.unlink(fullPath);
|
|
10380
|
+
result.filesDeleted++;
|
|
10381
|
+
await this.removeEmptyParentDirectories(fullPath, baseDirectory);
|
|
10382
|
+
}
|
|
10383
|
+
}
|
|
10384
|
+
isContentFile(filePath) {
|
|
10385
|
+
return (filePath.includes(".packmind/standards/") || filePath.includes(".packmind/commands/") || filePath.includes(".packmind/skills/") || filePath.includes(".packmind/recipes/")) && filePath.endsWith(".md");
|
|
10386
|
+
}
|
|
10387
|
+
async fileExists(filePath) {
|
|
10388
|
+
try {
|
|
10032
10389
|
await fs5.access(filePath);
|
|
10033
10390
|
return true;
|
|
10034
10391
|
} catch {
|
|
10035
10392
|
return false;
|
|
10036
10393
|
}
|
|
10037
10394
|
}
|
|
10395
|
+
extractCommentMarker(content) {
|
|
10396
|
+
const startMarkerPattern = /<!--\s*start:\s*([^-]+?)\s*-->/;
|
|
10397
|
+
const match = content.match(startMarkerPattern);
|
|
10398
|
+
return match ? match[1].trim() : null;
|
|
10399
|
+
}
|
|
10400
|
+
mergeContentWithMarkers(existingContent, newContent, commentMarker) {
|
|
10401
|
+
const startMarker = `<!-- start: ${commentMarker} -->`;
|
|
10402
|
+
const endMarker = `<!-- end: ${commentMarker} -->`;
|
|
10403
|
+
const newSectionPattern = new RegExp(
|
|
10404
|
+
`${this.escapeRegex(startMarker)}([\\s\\S]*?)${this.escapeRegex(endMarker)}`
|
|
10405
|
+
);
|
|
10406
|
+
const newSectionMatch = newContent.match(newSectionPattern);
|
|
10407
|
+
const newSectionContent = newSectionMatch ? newSectionMatch[1].trim() : newContent;
|
|
10408
|
+
const existingSectionPattern = new RegExp(
|
|
10409
|
+
`${this.escapeRegex(startMarker)}[\\s\\S]*?${this.escapeRegex(endMarker)}`,
|
|
10410
|
+
"g"
|
|
10411
|
+
);
|
|
10412
|
+
if (existingSectionPattern.test(existingContent)) {
|
|
10413
|
+
return existingContent.replace(
|
|
10414
|
+
existingSectionPattern,
|
|
10415
|
+
`${startMarker}
|
|
10416
|
+
${newSectionContent}
|
|
10417
|
+
${endMarker}`
|
|
10418
|
+
);
|
|
10419
|
+
} else {
|
|
10420
|
+
return `${existingContent}
|
|
10421
|
+
${startMarker}
|
|
10422
|
+
${newSectionContent}
|
|
10423
|
+
${endMarker}`;
|
|
10424
|
+
}
|
|
10425
|
+
}
|
|
10426
|
+
isEffectivelyEmpty(content) {
|
|
10427
|
+
const withoutEmptySections = content.replace(
|
|
10428
|
+
/<!--\s*start:\s*[^-]+?\s*-->\s*<!--\s*end:\s*[^-]+?\s*-->/g,
|
|
10429
|
+
""
|
|
10430
|
+
);
|
|
10431
|
+
return withoutEmptySections.trim() === "";
|
|
10432
|
+
}
|
|
10433
|
+
escapeRegex(str) {
|
|
10434
|
+
return str.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
10435
|
+
}
|
|
10436
|
+
async deleteSkillFolders(baseDirectory, folders) {
|
|
10437
|
+
let deletedFilesCount = 0;
|
|
10438
|
+
for (const folder of folders) {
|
|
10439
|
+
const fullPath = path7.join(baseDirectory, folder);
|
|
10440
|
+
try {
|
|
10441
|
+
await fs5.access(fullPath);
|
|
10442
|
+
const fileCount = await this.countFilesInDirectory(fullPath);
|
|
10443
|
+
await fs5.rm(fullPath, { recursive: true, force: true });
|
|
10444
|
+
deletedFilesCount += fileCount;
|
|
10445
|
+
await this.removeEmptyParentDirectories(fullPath, baseDirectory);
|
|
10446
|
+
} catch {
|
|
10447
|
+
}
|
|
10448
|
+
}
|
|
10449
|
+
return deletedFilesCount;
|
|
10450
|
+
}
|
|
10451
|
+
async countFilesInDirectory(dirPath) {
|
|
10452
|
+
let count = 0;
|
|
10453
|
+
const entries = await fs5.readdir(dirPath, { withFileTypes: true });
|
|
10454
|
+
for (const entry of entries) {
|
|
10455
|
+
const entryPath = path7.join(dirPath, entry.name);
|
|
10456
|
+
if (entry.isDirectory()) {
|
|
10457
|
+
count += await this.countFilesInDirectory(entryPath);
|
|
10458
|
+
} else {
|
|
10459
|
+
count++;
|
|
10460
|
+
}
|
|
10461
|
+
}
|
|
10462
|
+
return count;
|
|
10463
|
+
}
|
|
10464
|
+
async isDirectoryEmpty(dirPath) {
|
|
10465
|
+
try {
|
|
10466
|
+
const entries = await fs5.readdir(dirPath);
|
|
10467
|
+
return entries.length === 0;
|
|
10468
|
+
} catch {
|
|
10469
|
+
return false;
|
|
10470
|
+
}
|
|
10471
|
+
}
|
|
10472
|
+
async removeEmptyParentDirectories(fullPath, baseDirectory) {
|
|
10473
|
+
const normalizedBase = path7.resolve(baseDirectory);
|
|
10474
|
+
let currentDir = path7.dirname(path7.resolve(fullPath));
|
|
10475
|
+
while (currentDir.startsWith(normalizedBase + path7.sep) && currentDir !== normalizedBase) {
|
|
10476
|
+
const isEmpty = await this.isDirectoryEmpty(currentDir);
|
|
10477
|
+
if (!isEmpty) break;
|
|
10478
|
+
try {
|
|
10479
|
+
await fs5.rmdir(currentDir);
|
|
10480
|
+
} catch {
|
|
10481
|
+
break;
|
|
10482
|
+
}
|
|
10483
|
+
currentDir = path7.dirname(currentDir);
|
|
10484
|
+
}
|
|
10485
|
+
}
|
|
10486
|
+
};
|
|
10487
|
+
|
|
10488
|
+
// apps/cli/src/application/useCases/UninstallUseCase.ts
|
|
10489
|
+
var UninstallUseCase = class {
|
|
10490
|
+
constructor(configFileRepository, spaceService, installUseCase) {
|
|
10491
|
+
this.configFileRepository = configFileRepository;
|
|
10492
|
+
this.spaceService = spaceService;
|
|
10493
|
+
this.installUseCase = installUseCase;
|
|
10494
|
+
}
|
|
10495
|
+
async execute(command33) {
|
|
10496
|
+
const baseDirectory = command33.baseDirectory || process.cwd();
|
|
10497
|
+
const config = await this.configFileRepository.readConfig(baseDirectory);
|
|
10498
|
+
if (!config) {
|
|
10499
|
+
const configFileExists = await this.configFileRepository.configExists(baseDirectory);
|
|
10500
|
+
if (configFileExists) {
|
|
10501
|
+
throw new Error(
|
|
10502
|
+
"packmind.json exists but could not be parsed. Please fix the JSON syntax errors and try again."
|
|
10503
|
+
);
|
|
10504
|
+
}
|
|
10505
|
+
throw new Error(
|
|
10506
|
+
"No packmind.json found in this directory. Run `packmind-cli install <@space/package>` first to install your packages."
|
|
10507
|
+
);
|
|
10508
|
+
}
|
|
10509
|
+
const normalized = await normalizePackageSlugs(
|
|
10510
|
+
command33.packages,
|
|
10511
|
+
this.spaceService
|
|
10512
|
+
);
|
|
10513
|
+
const notInstalled = normalized.filter((pkg) => !(pkg in config.packages));
|
|
10514
|
+
if (notInstalled.length > 0) {
|
|
10515
|
+
const pkgList = notInstalled.map((p) => ` - ${p}`).join("\n");
|
|
10516
|
+
throw new Error(
|
|
10517
|
+
`The following package${notInstalled.length > 1 ? "s are" : " is"} not installed:
|
|
10518
|
+
${pkgList}`
|
|
10519
|
+
);
|
|
10520
|
+
}
|
|
10521
|
+
const updatedPackages = { ...config.packages };
|
|
10522
|
+
for (const pkg of normalized) {
|
|
10523
|
+
delete updatedPackages[pkg];
|
|
10524
|
+
}
|
|
10525
|
+
await this.configFileRepository.updateConfig(
|
|
10526
|
+
baseDirectory,
|
|
10527
|
+
"packages",
|
|
10528
|
+
updatedPackages
|
|
10529
|
+
);
|
|
10530
|
+
try {
|
|
10531
|
+
return await this.installUseCase.execute({ baseDirectory });
|
|
10532
|
+
} catch (error) {
|
|
10533
|
+
await this.configFileRepository.updateConfig(
|
|
10534
|
+
baseDirectory,
|
|
10535
|
+
"packages",
|
|
10536
|
+
config.packages
|
|
10537
|
+
);
|
|
10538
|
+
throw error;
|
|
10539
|
+
}
|
|
10540
|
+
}
|
|
10541
|
+
};
|
|
10542
|
+
|
|
10543
|
+
// apps/cli/src/application/useCases/InstallDefaultSkillsUseCase.ts
|
|
10544
|
+
var fs6 = __toESM(require("fs/promises"));
|
|
10545
|
+
var path8 = __toESM(require("path"));
|
|
10546
|
+
var import_semver = __toESM(require("semver"));
|
|
10547
|
+
var InstallDefaultSkillsUseCase = class {
|
|
10548
|
+
constructor(repositories) {
|
|
10549
|
+
this.repositories = repositories;
|
|
10550
|
+
}
|
|
10551
|
+
async execute(command33) {
|
|
10552
|
+
const baseDirectory = command33.baseDirectory || process.cwd();
|
|
10553
|
+
const result = {
|
|
10554
|
+
filesCreated: 0,
|
|
10555
|
+
filesUpdated: 0,
|
|
10556
|
+
errors: [],
|
|
10557
|
+
skippedSkillsCount: 0,
|
|
10558
|
+
skippedIncompatibleSkillNames: [],
|
|
10559
|
+
incompatibleInstalledSkills: []
|
|
10560
|
+
};
|
|
10561
|
+
const config = await this.repositories.configFileRepository.readConfig(baseDirectory);
|
|
10562
|
+
const agents = config?.agents;
|
|
10563
|
+
const response = await this.repositories.packmindGateway.skills.getDefaults(
|
|
10564
|
+
{
|
|
10565
|
+
cliVersion: command33.cliVersion,
|
|
10566
|
+
includeBeta: command33.includeBeta,
|
|
10567
|
+
agents
|
|
10568
|
+
}
|
|
10569
|
+
);
|
|
10570
|
+
result.skippedSkillsCount = response.skippedSkillsCount;
|
|
10571
|
+
const incompatibleInstalledMap = /* @__PURE__ */ new Map();
|
|
10572
|
+
const incompatibleSkillDirs = /* @__PURE__ */ new Map();
|
|
10573
|
+
if (command33.cliVersion) {
|
|
10574
|
+
for (const file of response.fileUpdates.createOrUpdate) {
|
|
10575
|
+
if (path8.basename(file.path) === "SKILL.md" && file.content && this.isVersionConstraintViolated(file.content, command33.cliVersion)) {
|
|
10576
|
+
const dir = path8.dirname(file.path);
|
|
10577
|
+
const skillName = this.getSkillName(file.content) ?? path8.basename(dir);
|
|
10578
|
+
incompatibleSkillDirs.set(dir, skillName);
|
|
10579
|
+
}
|
|
10580
|
+
}
|
|
10581
|
+
}
|
|
10582
|
+
try {
|
|
10583
|
+
for (const file of response.fileUpdates.createOrUpdate) {
|
|
10584
|
+
try {
|
|
10585
|
+
if (!file.content) continue;
|
|
10586
|
+
const isIncompatible = command33.cliVersion && (this.isVersionConstraintViolated(
|
|
10587
|
+
file.content,
|
|
10588
|
+
command33.cliVersion
|
|
10589
|
+
) || this.isUnderIncompatibleSkillDir(
|
|
10590
|
+
file.path,
|
|
10591
|
+
incompatibleSkillDirs
|
|
10592
|
+
));
|
|
10593
|
+
if (isIncompatible) {
|
|
10594
|
+
const skillName = this.getSkillName(file.content) ?? this.getSkillNameForPath(file.path, incompatibleSkillDirs) ?? path8.basename(file.path);
|
|
10595
|
+
const fullPath = path8.join(baseDirectory, file.path);
|
|
10596
|
+
const fileAlreadyInstalled = await this.fileExists(fullPath);
|
|
10597
|
+
if (fileAlreadyInstalled) {
|
|
10598
|
+
const paths = incompatibleInstalledMap.get(skillName) ?? [];
|
|
10599
|
+
paths.push(file.path);
|
|
10600
|
+
incompatibleInstalledMap.set(skillName, paths);
|
|
10601
|
+
} else {
|
|
10602
|
+
if (!result.skippedIncompatibleSkillNames.includes(skillName)) {
|
|
10603
|
+
result.skippedIncompatibleSkillNames.push(skillName);
|
|
10604
|
+
}
|
|
10605
|
+
}
|
|
10606
|
+
continue;
|
|
10607
|
+
}
|
|
10608
|
+
await this.createOrUpdateFile(baseDirectory, file, result);
|
|
10609
|
+
} catch (error) {
|
|
10610
|
+
const errorMsg = error instanceof Error ? error.message : String(error);
|
|
10611
|
+
result.errors.push(
|
|
10612
|
+
`Failed to create/update ${file.path}: ${errorMsg}`
|
|
10613
|
+
);
|
|
10614
|
+
}
|
|
10615
|
+
}
|
|
10616
|
+
} catch (error) {
|
|
10617
|
+
const errorMsg = error instanceof Error ? error.message : String(error);
|
|
10618
|
+
result.errors.push(`Failed to install default skills: ${errorMsg}`);
|
|
10619
|
+
}
|
|
10620
|
+
result.incompatibleInstalledSkills = Array.from(
|
|
10621
|
+
incompatibleInstalledMap.entries()
|
|
10622
|
+
).map(
|
|
10623
|
+
([skillName, filePaths]) => ({
|
|
10624
|
+
skillName,
|
|
10625
|
+
filePaths
|
|
10626
|
+
})
|
|
10627
|
+
);
|
|
10628
|
+
return result;
|
|
10629
|
+
}
|
|
10630
|
+
async createOrUpdateFile(baseDirectory, file, result) {
|
|
10631
|
+
const fullPath = path8.join(baseDirectory, file.path);
|
|
10632
|
+
const directory = path8.dirname(fullPath);
|
|
10633
|
+
await fs6.mkdir(directory, { recursive: true });
|
|
10634
|
+
const fileExists = await this.fileExists(fullPath);
|
|
10635
|
+
if (fileExists) {
|
|
10636
|
+
const existingContent = await fs6.readFile(fullPath, "utf-8");
|
|
10637
|
+
if (existingContent !== file.content) {
|
|
10638
|
+
await fs6.writeFile(fullPath, file.content, "utf-8");
|
|
10639
|
+
result.filesUpdated++;
|
|
10640
|
+
}
|
|
10641
|
+
} else {
|
|
10642
|
+
await fs6.writeFile(fullPath, file.content, "utf-8");
|
|
10643
|
+
result.filesCreated++;
|
|
10644
|
+
}
|
|
10645
|
+
}
|
|
10646
|
+
async fileExists(filePath) {
|
|
10647
|
+
try {
|
|
10648
|
+
await fs6.access(filePath);
|
|
10649
|
+
return true;
|
|
10650
|
+
} catch {
|
|
10651
|
+
return false;
|
|
10652
|
+
}
|
|
10653
|
+
}
|
|
10654
|
+
/**
|
|
10655
|
+
* Returns true if the given file path is inside one of the incompatible skill
|
|
10656
|
+
* directories, including nested subdirectories (e.g. `scripts/`).
|
|
10657
|
+
*/
|
|
10658
|
+
isUnderIncompatibleSkillDir(filePath, incompatibleSkillDirs) {
|
|
10659
|
+
return this.getSkillNameForPath(filePath, incompatibleSkillDirs) !== null;
|
|
10660
|
+
}
|
|
10661
|
+
/**
|
|
10662
|
+
* Returns the skill name for the given file path by finding the incompatible
|
|
10663
|
+
* skill directory that contains it (including nested subdirectories).
|
|
10664
|
+
*/
|
|
10665
|
+
getSkillNameForPath(filePath, incompatibleSkillDirs) {
|
|
10666
|
+
for (const [dir, skillName] of incompatibleSkillDirs.entries()) {
|
|
10667
|
+
if (filePath === dir || filePath.startsWith(dir + "/") || filePath.startsWith(dir + path8.sep)) {
|
|
10668
|
+
return skillName;
|
|
10669
|
+
}
|
|
10670
|
+
}
|
|
10671
|
+
return null;
|
|
10672
|
+
}
|
|
10038
10673
|
/**
|
|
10039
10674
|
* Returns true if the skill's `metadata.packmind-cli-version` constraint
|
|
10040
10675
|
* is present AND the given CLI version does NOT satisfy it (i.e. the skill
|
|
@@ -10148,13 +10783,13 @@ var EnvCredentialsProvider = class {
|
|
|
10148
10783
|
};
|
|
10149
10784
|
|
|
10150
10785
|
// apps/cli/src/infra/utils/credentials/FileCredentialsProvider.ts
|
|
10151
|
-
var
|
|
10152
|
-
var
|
|
10786
|
+
var fs7 = __toESM(require("fs"));
|
|
10787
|
+
var path9 = __toESM(require("path"));
|
|
10153
10788
|
var os2 = __toESM(require("os"));
|
|
10154
10789
|
var CREDENTIALS_DIR = ".packmind";
|
|
10155
10790
|
var CREDENTIALS_FILE = "credentials.json";
|
|
10156
10791
|
function getCredentialsPath() {
|
|
10157
|
-
return
|
|
10792
|
+
return path9.join(os2.homedir(), CREDENTIALS_DIR, CREDENTIALS_FILE);
|
|
10158
10793
|
}
|
|
10159
10794
|
var FileCredentialsProvider = class {
|
|
10160
10795
|
getSourceName() {
|
|
@@ -10162,11 +10797,11 @@ var FileCredentialsProvider = class {
|
|
|
10162
10797
|
}
|
|
10163
10798
|
hasCredentials() {
|
|
10164
10799
|
const credentialsPath = getCredentialsPath();
|
|
10165
|
-
if (!
|
|
10800
|
+
if (!fs7.existsSync(credentialsPath)) {
|
|
10166
10801
|
return false;
|
|
10167
10802
|
}
|
|
10168
10803
|
try {
|
|
10169
|
-
const content =
|
|
10804
|
+
const content = fs7.readFileSync(credentialsPath, "utf-8");
|
|
10170
10805
|
const credentials = JSON.parse(content);
|
|
10171
10806
|
return !!credentials.apiKey;
|
|
10172
10807
|
} catch {
|
|
@@ -10175,11 +10810,11 @@ var FileCredentialsProvider = class {
|
|
|
10175
10810
|
}
|
|
10176
10811
|
loadCredentials() {
|
|
10177
10812
|
const credentialsPath = getCredentialsPath();
|
|
10178
|
-
if (!
|
|
10813
|
+
if (!fs7.existsSync(credentialsPath)) {
|
|
10179
10814
|
return null;
|
|
10180
10815
|
}
|
|
10181
10816
|
try {
|
|
10182
|
-
const content =
|
|
10817
|
+
const content = fs7.readFileSync(credentialsPath, "utf-8");
|
|
10183
10818
|
const credentials = JSON.parse(content);
|
|
10184
10819
|
if (!credentials.apiKey) {
|
|
10185
10820
|
return null;
|
|
@@ -10202,13 +10837,13 @@ var FileCredentialsProvider = class {
|
|
|
10202
10837
|
}
|
|
10203
10838
|
};
|
|
10204
10839
|
function saveCredentials(apiKey) {
|
|
10205
|
-
const credentialsDir =
|
|
10206
|
-
if (!
|
|
10207
|
-
|
|
10840
|
+
const credentialsDir = path9.join(os2.homedir(), CREDENTIALS_DIR);
|
|
10841
|
+
if (!fs7.existsSync(credentialsDir)) {
|
|
10842
|
+
fs7.mkdirSync(credentialsDir, { recursive: true, mode: 448 });
|
|
10208
10843
|
}
|
|
10209
10844
|
const credentialsPath = getCredentialsPath();
|
|
10210
10845
|
const credentials = { apiKey };
|
|
10211
|
-
|
|
10846
|
+
fs7.writeFileSync(credentialsPath, JSON.stringify(credentials, null, 2), {
|
|
10212
10847
|
mode: 384
|
|
10213
10848
|
});
|
|
10214
10849
|
}
|
|
@@ -10279,10 +10914,10 @@ async function defaultPromptForCode() {
|
|
|
10279
10914
|
input: process.stdin,
|
|
10280
10915
|
output: process.stdout
|
|
10281
10916
|
});
|
|
10282
|
-
return new Promise((
|
|
10917
|
+
return new Promise((resolve15) => {
|
|
10283
10918
|
rl.question("Enter the login code from the browser: ", (answer) => {
|
|
10284
10919
|
rl.close();
|
|
10285
|
-
|
|
10920
|
+
resolve15(answer.trim());
|
|
10286
10921
|
});
|
|
10287
10922
|
});
|
|
10288
10923
|
}
|
|
@@ -10316,7 +10951,7 @@ async function defaultExchangeCodeForApiKey(code, host) {
|
|
|
10316
10951
|
return await response.json();
|
|
10317
10952
|
}
|
|
10318
10953
|
function defaultStartCallbackServer() {
|
|
10319
|
-
return new Promise((
|
|
10954
|
+
return new Promise((resolve15, reject) => {
|
|
10320
10955
|
let timeoutId = null;
|
|
10321
10956
|
const server = http.createServer((req, res) => {
|
|
10322
10957
|
res.setHeader("Access-Control-Allow-Origin", "*");
|
|
@@ -10329,7 +10964,7 @@ function defaultStartCallbackServer() {
|
|
|
10329
10964
|
if (timeoutId) {
|
|
10330
10965
|
clearTimeout(timeoutId);
|
|
10331
10966
|
}
|
|
10332
|
-
|
|
10967
|
+
resolve15(code);
|
|
10333
10968
|
setImmediate(() => {
|
|
10334
10969
|
server.close();
|
|
10335
10970
|
});
|
|
@@ -10400,14 +11035,14 @@ var LoginUseCase = class {
|
|
|
10400
11035
|
};
|
|
10401
11036
|
|
|
10402
11037
|
// apps/cli/src/application/useCases/LogoutUseCase.ts
|
|
10403
|
-
var
|
|
11038
|
+
var fs8 = __toESM(require("fs"));
|
|
10404
11039
|
var ENV_VAR_NAME2 = "PACKMIND_API_KEY_V3";
|
|
10405
11040
|
var LogoutUseCase = class {
|
|
10406
11041
|
constructor(deps) {
|
|
10407
11042
|
this.deps = {
|
|
10408
11043
|
getCredentialsPath: deps?.getCredentialsPath ?? getCredentialsPath,
|
|
10409
|
-
fileExists: deps?.fileExists ?? ((
|
|
10410
|
-
deleteFile: deps?.deleteFile ?? ((
|
|
11044
|
+
fileExists: deps?.fileExists ?? ((path37) => fs8.existsSync(path37)),
|
|
11045
|
+
deleteFile: deps?.deleteFile ?? ((path37) => fs8.unlinkSync(path37)),
|
|
10411
11046
|
hasEnvVar: deps?.hasEnvVar ?? (() => !!process.env[ENV_VAR_NAME2])
|
|
10412
11047
|
};
|
|
10413
11048
|
}
|
|
@@ -10756,8 +11391,8 @@ var SetupMcpUseCase = class {
|
|
|
10756
11391
|
};
|
|
10757
11392
|
|
|
10758
11393
|
// apps/cli/src/application/services/McpConfigService.ts
|
|
10759
|
-
var
|
|
10760
|
-
var
|
|
11394
|
+
var fs9 = __toESM(require("fs"));
|
|
11395
|
+
var path11 = __toESM(require("path"));
|
|
10761
11396
|
var os3 = __toESM(require("os"));
|
|
10762
11397
|
var import_child_process3 = require("child_process");
|
|
10763
11398
|
var McpConfigService = class {
|
|
@@ -10804,11 +11439,11 @@ var McpConfigService = class {
|
|
|
10804
11439
|
}
|
|
10805
11440
|
installCursorMcp(config) {
|
|
10806
11441
|
try {
|
|
10807
|
-
const cursorConfigPath =
|
|
11442
|
+
const cursorConfigPath = path11.join(os3.homedir(), ".cursor", "mcp.json");
|
|
10808
11443
|
const cursorConfig = this.buildCursorConfig(config);
|
|
10809
11444
|
const existingConfig = this.readExistingJsonConfig(cursorConfigPath);
|
|
10810
11445
|
const mergedConfig = this.mergeConfig(existingConfig, cursorConfig);
|
|
10811
|
-
|
|
11446
|
+
fs9.writeFileSync(cursorConfigPath, JSON.stringify(mergedConfig, null, 2));
|
|
10812
11447
|
return { success: true };
|
|
10813
11448
|
} catch (error) {
|
|
10814
11449
|
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
@@ -10817,15 +11452,15 @@ var McpConfigService = class {
|
|
|
10817
11452
|
}
|
|
10818
11453
|
installVSCodeMcp(config) {
|
|
10819
11454
|
try {
|
|
10820
|
-
const vscodeDir =
|
|
10821
|
-
if (!
|
|
10822
|
-
|
|
11455
|
+
const vscodeDir = path11.join(this.projectDir, ".vscode");
|
|
11456
|
+
if (!fs9.existsSync(vscodeDir)) {
|
|
11457
|
+
fs9.mkdirSync(vscodeDir, { recursive: true });
|
|
10823
11458
|
}
|
|
10824
|
-
const vscodeConfigPath =
|
|
11459
|
+
const vscodeConfigPath = path11.join(vscodeDir, "mcp.json");
|
|
10825
11460
|
const vscodeConfig = this.buildVSCodeConfig(config);
|
|
10826
11461
|
const existingConfig = this.readExistingJsonConfig(vscodeConfigPath);
|
|
10827
11462
|
const mergedConfig = this.mergeVSCodeConfig(existingConfig, vscodeConfig);
|
|
10828
|
-
|
|
11463
|
+
fs9.writeFileSync(vscodeConfigPath, JSON.stringify(mergedConfig, null, 2));
|
|
10829
11464
|
return { success: true };
|
|
10830
11465
|
} catch (error) {
|
|
10831
11466
|
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
@@ -10834,14 +11469,14 @@ var McpConfigService = class {
|
|
|
10834
11469
|
}
|
|
10835
11470
|
installContinueMcp(config) {
|
|
10836
11471
|
try {
|
|
10837
|
-
const continueDir =
|
|
10838
|
-
const mcpServersDir =
|
|
10839
|
-
if (!
|
|
10840
|
-
|
|
11472
|
+
const continueDir = path11.join(this.projectDir, ".continue");
|
|
11473
|
+
const mcpServersDir = path11.join(continueDir, "mcpServers");
|
|
11474
|
+
if (!fs9.existsSync(mcpServersDir)) {
|
|
11475
|
+
fs9.mkdirSync(mcpServersDir, { recursive: true });
|
|
10841
11476
|
}
|
|
10842
|
-
const continueConfigPath =
|
|
11477
|
+
const continueConfigPath = path11.join(mcpServersDir, "packmind.yaml");
|
|
10843
11478
|
const continueConfig = this.buildContinueYamlConfig(config);
|
|
10844
|
-
|
|
11479
|
+
fs9.writeFileSync(continueConfigPath, continueConfig);
|
|
10845
11480
|
return { success: true };
|
|
10846
11481
|
} catch (error) {
|
|
10847
11482
|
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
@@ -10889,8 +11524,8 @@ mcpServers:
|
|
|
10889
11524
|
}
|
|
10890
11525
|
readExistingJsonConfig(filePath) {
|
|
10891
11526
|
try {
|
|
10892
|
-
if (
|
|
10893
|
-
const content =
|
|
11527
|
+
if (fs9.existsSync(filePath)) {
|
|
11528
|
+
const content = fs9.readFileSync(filePath, "utf-8");
|
|
10894
11529
|
return JSON.parse(content);
|
|
10895
11530
|
}
|
|
10896
11531
|
} catch {
|
|
@@ -10923,8 +11558,8 @@ mcpServers:
|
|
|
10923
11558
|
};
|
|
10924
11559
|
|
|
10925
11560
|
// apps/cli/src/infra/repositories/ConfigFileRepository.ts
|
|
10926
|
-
var
|
|
10927
|
-
var
|
|
11561
|
+
var fs10 = __toESM(require("fs/promises"));
|
|
11562
|
+
var path12 = __toESM(require("path"));
|
|
10928
11563
|
var ConfigFileRepository = class {
|
|
10929
11564
|
constructor() {
|
|
10930
11565
|
this.CONFIG_FILENAME = "packmind.json";
|
|
@@ -10945,7 +11580,7 @@ var ConfigFileRepository = class {
|
|
|
10945
11580
|
async configExists(baseDirectory) {
|
|
10946
11581
|
const configPath = this.getConfigPath(baseDirectory);
|
|
10947
11582
|
try {
|
|
10948
|
-
await
|
|
11583
|
+
await fs10.access(configPath);
|
|
10949
11584
|
return true;
|
|
10950
11585
|
} catch {
|
|
10951
11586
|
return false;
|
|
@@ -10954,7 +11589,7 @@ var ConfigFileRepository = class {
|
|
|
10954
11589
|
async readConfig(baseDirectory) {
|
|
10955
11590
|
const configPath = this.getConfigPath(baseDirectory);
|
|
10956
11591
|
try {
|
|
10957
|
-
const configContent = await
|
|
11592
|
+
const configContent = await fs10.readFile(configPath, "utf-8");
|
|
10958
11593
|
const rawConfig = JSON.parse(configContent);
|
|
10959
11594
|
if (!rawConfig.packages || typeof rawConfig.packages !== "object") {
|
|
10960
11595
|
throw new Error(
|
|
@@ -10988,18 +11623,18 @@ var ConfigFileRepository = class {
|
|
|
10988
11623
|
}
|
|
10989
11624
|
}
|
|
10990
11625
|
getConfigPath(directory) {
|
|
10991
|
-
return
|
|
11626
|
+
return path12.join(directory, this.CONFIG_FILENAME);
|
|
10992
11627
|
}
|
|
10993
11628
|
async writeConfigToPath(configPath, config) {
|
|
10994
11629
|
const configContent = JSON.stringify(config, null, 2) + "\n";
|
|
10995
|
-
await
|
|
11630
|
+
await fs10.writeFile(configPath, configContent, "utf-8");
|
|
10996
11631
|
}
|
|
10997
11632
|
/**
|
|
10998
11633
|
* Recursively finds all directories containing packmind.json in descendant folders.
|
|
10999
11634
|
* Excludes common build/dependency directories (node_modules, .git, dist, etc.)
|
|
11000
11635
|
*/
|
|
11001
11636
|
async findDescendantConfigs(directory) {
|
|
11002
|
-
const normalizedDir = normalizePath2(
|
|
11637
|
+
const normalizedDir = normalizePath2(path12.resolve(directory));
|
|
11003
11638
|
return this.searchDescendantsRecursively(normalizedDir);
|
|
11004
11639
|
}
|
|
11005
11640
|
async searchDescendantsRecursively(currentDir) {
|
|
@@ -11012,7 +11647,7 @@ var ConfigFileRepository = class {
|
|
|
11012
11647
|
if (!entry.isDirectory() || this.isExcludedDirectory(entry.name)) {
|
|
11013
11648
|
continue;
|
|
11014
11649
|
}
|
|
11015
|
-
const entryPath = normalizePath2(
|
|
11650
|
+
const entryPath = normalizePath2(path12.join(currentDir, entry.name));
|
|
11016
11651
|
const config = await this.readConfig(entryPath);
|
|
11017
11652
|
if (config) {
|
|
11018
11653
|
results.push(entryPath);
|
|
@@ -11024,7 +11659,7 @@ var ConfigFileRepository = class {
|
|
|
11024
11659
|
}
|
|
11025
11660
|
async tryReadDirectory(directory) {
|
|
11026
11661
|
try {
|
|
11027
|
-
return await
|
|
11662
|
+
return await fs10.readdir(directory, { withFileTypes: true });
|
|
11028
11663
|
} catch {
|
|
11029
11664
|
return null;
|
|
11030
11665
|
}
|
|
@@ -11043,21 +11678,21 @@ var ConfigFileRepository = class {
|
|
|
11043
11678
|
async readHierarchicalConfig(startDirectory, stopDirectory) {
|
|
11044
11679
|
const configs = [];
|
|
11045
11680
|
const configPaths = [];
|
|
11046
|
-
const normalizedStart = normalizePath2(
|
|
11047
|
-
const normalizedStop = stopDirectory ? normalizePath2(
|
|
11681
|
+
const normalizedStart = normalizePath2(path12.resolve(startDirectory));
|
|
11682
|
+
const normalizedStop = stopDirectory ? normalizePath2(path12.resolve(stopDirectory)) : null;
|
|
11048
11683
|
let currentDir = normalizedStart;
|
|
11049
11684
|
while (true) {
|
|
11050
11685
|
const config = await this.readConfig(currentDir);
|
|
11051
11686
|
if (config) {
|
|
11052
11687
|
configs.push(config);
|
|
11053
11688
|
configPaths.push(
|
|
11054
|
-
normalizePath2(
|
|
11689
|
+
normalizePath2(path12.join(currentDir, this.CONFIG_FILENAME))
|
|
11055
11690
|
);
|
|
11056
11691
|
}
|
|
11057
11692
|
if (normalizedStop !== null && currentDir === normalizedStop) {
|
|
11058
11693
|
break;
|
|
11059
11694
|
}
|
|
11060
|
-
const parentDir = normalizePath2(
|
|
11695
|
+
const parentDir = normalizePath2(path12.dirname(currentDir));
|
|
11061
11696
|
if (parentDir === currentDir) {
|
|
11062
11697
|
break;
|
|
11063
11698
|
}
|
|
@@ -11082,8 +11717,8 @@ var ConfigFileRepository = class {
|
|
|
11082
11717
|
* and returns each config with its target path.
|
|
11083
11718
|
*/
|
|
11084
11719
|
async findAllConfigsInTree(startDirectory, stopDirectory) {
|
|
11085
|
-
const normalizedStart = normalizePath2(
|
|
11086
|
-
const normalizedStop = stopDirectory ? normalizePath2(
|
|
11720
|
+
const normalizedStart = normalizePath2(path12.resolve(startDirectory));
|
|
11721
|
+
const normalizedStop = stopDirectory ? normalizePath2(path12.resolve(stopDirectory)) : null;
|
|
11087
11722
|
const basePath = normalizedStop ?? normalizedStart;
|
|
11088
11723
|
const searchRoot = normalizedStop ?? normalizedStart;
|
|
11089
11724
|
const configsMap = /* @__PURE__ */ new Map();
|
|
@@ -11109,7 +11744,7 @@ var ConfigFileRepository = class {
|
|
|
11109
11744
|
if (stopDir !== null && currentDir === stopDir) {
|
|
11110
11745
|
break;
|
|
11111
11746
|
}
|
|
11112
|
-
const parentDir = normalizePath2(
|
|
11747
|
+
const parentDir = normalizePath2(path12.dirname(currentDir));
|
|
11113
11748
|
if (parentDir === currentDir) {
|
|
11114
11749
|
break;
|
|
11115
11750
|
}
|
|
@@ -11240,7 +11875,7 @@ var ConfigFileRepository = class {
|
|
|
11240
11875
|
}
|
|
11241
11876
|
async tryReadFile(filePath) {
|
|
11242
11877
|
try {
|
|
11243
|
-
return await
|
|
11878
|
+
return await fs10.readFile(filePath, "utf-8");
|
|
11244
11879
|
} catch (error) {
|
|
11245
11880
|
if (error.code === "ENOENT") {
|
|
11246
11881
|
return null;
|
|
@@ -11258,8 +11893,8 @@ var ConfigFileRepository = class {
|
|
|
11258
11893
|
};
|
|
11259
11894
|
|
|
11260
11895
|
// apps/cli/src/infra/repositories/LockFileRepository.ts
|
|
11261
|
-
var
|
|
11262
|
-
var
|
|
11896
|
+
var fs11 = __toESM(require("fs/promises"));
|
|
11897
|
+
var path13 = __toESM(require("path"));
|
|
11263
11898
|
var LockFileRepository = class {
|
|
11264
11899
|
constructor() {
|
|
11265
11900
|
this.LOCK_FILENAME = "packmind-lock.json";
|
|
@@ -11267,7 +11902,7 @@ var LockFileRepository = class {
|
|
|
11267
11902
|
async read(baseDirectory) {
|
|
11268
11903
|
const lockFilePath = this.getLockFilePath(baseDirectory);
|
|
11269
11904
|
try {
|
|
11270
|
-
const content = await
|
|
11905
|
+
const content = await fs11.readFile(lockFilePath, "utf-8");
|
|
11271
11906
|
const parsed = JSON.parse(content);
|
|
11272
11907
|
if (!this.isValidLockFile(parsed)) {
|
|
11273
11908
|
logWarningConsole(`Malformed lock file: ${lockFilePath}`);
|
|
@@ -11293,7 +11928,7 @@ var LockFileRepository = class {
|
|
|
11293
11928
|
return typeof obj.installedAt === "string" && Array.isArray(obj.packageSlugs) && Array.isArray(obj.agents) && (obj.targetId === void 0 || typeof obj.targetId === "string") && typeof obj.artifacts === "object" && obj.artifacts !== null && !Array.isArray(obj.artifacts);
|
|
11294
11929
|
}
|
|
11295
11930
|
getLockFilePath(baseDirectory) {
|
|
11296
|
-
return
|
|
11931
|
+
return path13.join(baseDirectory, this.LOCK_FILENAME);
|
|
11297
11932
|
}
|
|
11298
11933
|
};
|
|
11299
11934
|
|
|
@@ -11308,17 +11943,12 @@ var ListStandardsUseCase = class {
|
|
|
11308
11943
|
const response = await this.packmindGateway.standards.list({
|
|
11309
11944
|
spaceId: command33.spaceId
|
|
11310
11945
|
});
|
|
11311
|
-
return response.standards
|
|
11312
|
-
...s,
|
|
11313
|
-
spaceId: command33.spaceId
|
|
11314
|
-
}));
|
|
11946
|
+
return response.standards;
|
|
11315
11947
|
}
|
|
11316
11948
|
const spaces = await this.spaceService.getSpaces();
|
|
11317
11949
|
const results = await Promise.all(
|
|
11318
11950
|
spaces.map(
|
|
11319
|
-
(space) => this.packmindGateway.standards.list({ spaceId: space.id }).then(
|
|
11320
|
-
(r) => r.standards.map((s) => ({ ...s, spaceId: space.id }))
|
|
11321
|
-
)
|
|
11951
|
+
(space) => this.packmindGateway.standards.list({ spaceId: space.id }).then((r) => r.standards)
|
|
11322
11952
|
)
|
|
11323
11953
|
);
|
|
11324
11954
|
return results.flat();
|
|
@@ -11363,7 +11993,7 @@ var ListSkillsUseCase = class {
|
|
|
11363
11993
|
slug: s.slug,
|
|
11364
11994
|
name: s.name,
|
|
11365
11995
|
description: s.description,
|
|
11366
|
-
spaceId:
|
|
11996
|
+
spaceId: s.spaceId
|
|
11367
11997
|
}));
|
|
11368
11998
|
}
|
|
11369
11999
|
const spaces = await this.spaceService.getSpaces();
|
|
@@ -11394,7 +12024,7 @@ function normalizeLineEndings(content) {
|
|
|
11394
12024
|
}
|
|
11395
12025
|
|
|
11396
12026
|
// apps/cli/src/infra/utils/binaryDetection.ts
|
|
11397
|
-
var
|
|
12027
|
+
var path14 = __toESM(require("path"));
|
|
11398
12028
|
var BINARY_EXTENSIONS = /* @__PURE__ */ new Set([
|
|
11399
12029
|
// Images
|
|
11400
12030
|
".png",
|
|
@@ -11452,7 +12082,7 @@ var BINARY_EXTENSIONS = /* @__PURE__ */ new Set([
|
|
|
11452
12082
|
".sqlite3"
|
|
11453
12083
|
]);
|
|
11454
12084
|
function isBinaryExtension(filePath) {
|
|
11455
|
-
const ext =
|
|
12085
|
+
const ext = path14.extname(filePath).toLowerCase();
|
|
11456
12086
|
return BINARY_EXTENSIONS.has(ext);
|
|
11457
12087
|
}
|
|
11458
12088
|
function isBinaryBuffer(buffer) {
|
|
@@ -11472,7 +12102,11 @@ function normalizePath3(filePath) {
|
|
|
11472
12102
|
}
|
|
11473
12103
|
var MAX_FILE_SIZE_BYTES = 10 * 1024 * 1024;
|
|
11474
12104
|
var MAX_FILE_SIZE_MB = 10;
|
|
11475
|
-
var BLACKLIST_PATTERNS = [
|
|
12105
|
+
var BLACKLIST_PATTERNS = [
|
|
12106
|
+
"**/.DS_Store",
|
|
12107
|
+
"**/node_modules",
|
|
12108
|
+
"**/node_modules/**"
|
|
12109
|
+
];
|
|
11476
12110
|
function isBlacklisted(relativePath) {
|
|
11477
12111
|
const normalizedPath = relativePath.replace(/\\/g, "/");
|
|
11478
12112
|
return BLACKLIST_PATTERNS.some(
|
|
@@ -11594,17 +12228,17 @@ ${spaceList}`
|
|
|
11594
12228
|
|
|
11595
12229
|
// apps/cli/src/application/useCases/diffStrategies/CommandDiffStrategy.ts
|
|
11596
12230
|
var import_diff2 = require("diff");
|
|
11597
|
-
var
|
|
11598
|
-
var
|
|
12231
|
+
var fs13 = __toESM(require("fs/promises"));
|
|
12232
|
+
var path16 = __toESM(require("path"));
|
|
11599
12233
|
var CommandDiffStrategy = class {
|
|
11600
12234
|
supports(file) {
|
|
11601
12235
|
return file.artifactType === "command";
|
|
11602
12236
|
}
|
|
11603
12237
|
async diff(file, baseDirectory) {
|
|
11604
|
-
const fullPath =
|
|
12238
|
+
const fullPath = path16.join(baseDirectory, file.path);
|
|
11605
12239
|
let localContent;
|
|
11606
12240
|
try {
|
|
11607
|
-
localContent = await
|
|
12241
|
+
localContent = await fs13.readFile(fullPath, "utf-8");
|
|
11608
12242
|
} catch {
|
|
11609
12243
|
return [];
|
|
11610
12244
|
}
|
|
@@ -11634,8 +12268,8 @@ var CommandDiffStrategy = class {
|
|
|
11634
12268
|
|
|
11635
12269
|
// apps/cli/src/application/useCases/diffStrategies/SkillDiffStrategy.ts
|
|
11636
12270
|
var import_diff3 = require("diff");
|
|
11637
|
-
var
|
|
11638
|
-
var
|
|
12271
|
+
var fs14 = __toESM(require("fs/promises"));
|
|
12272
|
+
var path17 = __toESM(require("path"));
|
|
11639
12273
|
|
|
11640
12274
|
// apps/cli/src/application/utils/stripFrontmatter.ts
|
|
11641
12275
|
var FRONTMATTER_DELIMITER2 = "---";
|
|
@@ -11670,7 +12304,7 @@ var SkillDiffStrategy = class {
|
|
|
11670
12304
|
async diffNewFiles(skillFolders, serverFiles, baseDirectory) {
|
|
11671
12305
|
const diffs = [];
|
|
11672
12306
|
for (const folder of skillFolders) {
|
|
11673
|
-
const folderPath =
|
|
12307
|
+
const folderPath = path17.join(baseDirectory, folder);
|
|
11674
12308
|
const localFiles = await this.listFilesRecursively(folderPath);
|
|
11675
12309
|
const serverPathsInFolder = new Set(
|
|
11676
12310
|
serverFiles.filter((f) => f.path.startsWith(folder + "/")).map((f) => f.path)
|
|
@@ -11689,7 +12323,7 @@ var SkillDiffStrategy = class {
|
|
|
11689
12323
|
if (serverPathsInFolder.has(filePath)) {
|
|
11690
12324
|
continue;
|
|
11691
12325
|
}
|
|
11692
|
-
const fullPath =
|
|
12326
|
+
const fullPath = path17.join(baseDirectory, filePath);
|
|
11693
12327
|
const localRead = await this.tryReadFileBinaryAware(fullPath);
|
|
11694
12328
|
if (localRead === null) {
|
|
11695
12329
|
continue;
|
|
@@ -11716,7 +12350,7 @@ var SkillDiffStrategy = class {
|
|
|
11716
12350
|
return diffs;
|
|
11717
12351
|
}
|
|
11718
12352
|
async diffSkillMd(file, baseDirectory) {
|
|
11719
|
-
const fullPath =
|
|
12353
|
+
const fullPath = path17.join(baseDirectory, file.path);
|
|
11720
12354
|
const localContent = await this.tryReadFile(fullPath);
|
|
11721
12355
|
if (localContent === null) {
|
|
11722
12356
|
return [];
|
|
@@ -11773,7 +12407,7 @@ var SkillDiffStrategy = class {
|
|
|
11773
12407
|
return [];
|
|
11774
12408
|
}
|
|
11775
12409
|
const skillFileId = createSkillFileId(file.skillFileId);
|
|
11776
|
-
const fullPath =
|
|
12410
|
+
const fullPath = path17.join(baseDirectory, file.path);
|
|
11777
12411
|
const localRead = await this.tryReadFileBinaryAware(fullPath);
|
|
11778
12412
|
const fileRelativePath = this.computeRelativePath(file.path, skillFolders);
|
|
11779
12413
|
if (localRead === null) {
|
|
@@ -11983,14 +12617,14 @@ var SkillDiffStrategy = class {
|
|
|
11983
12617
|
}
|
|
11984
12618
|
async tryReadFile(filePath) {
|
|
11985
12619
|
try {
|
|
11986
|
-
return await
|
|
12620
|
+
return await fs14.readFile(filePath, "utf-8");
|
|
11987
12621
|
} catch {
|
|
11988
12622
|
return null;
|
|
11989
12623
|
}
|
|
11990
12624
|
}
|
|
11991
12625
|
async tryReadFileBinaryAware(filePath) {
|
|
11992
12626
|
try {
|
|
11993
|
-
const buffer = await
|
|
12627
|
+
const buffer = await fs14.readFile(filePath);
|
|
11994
12628
|
if (isBinaryFile(filePath, buffer)) {
|
|
11995
12629
|
return { content: buffer.toString("base64"), isBase64: true };
|
|
11996
12630
|
}
|
|
@@ -12002,13 +12636,13 @@ var SkillDiffStrategy = class {
|
|
|
12002
12636
|
async listFilesRecursively(dirPath, prefix = "") {
|
|
12003
12637
|
let entries;
|
|
12004
12638
|
try {
|
|
12005
|
-
entries = await
|
|
12639
|
+
entries = await fs14.readdir(dirPath);
|
|
12006
12640
|
} catch {
|
|
12007
12641
|
return [];
|
|
12008
12642
|
}
|
|
12009
12643
|
const files = [];
|
|
12010
12644
|
for (const entry of entries) {
|
|
12011
|
-
const fullPath =
|
|
12645
|
+
const fullPath = path17.join(dirPath, entry);
|
|
12012
12646
|
const stat9 = await this.tryStatFile(fullPath);
|
|
12013
12647
|
if (!stat9) {
|
|
12014
12648
|
continue;
|
|
@@ -12028,7 +12662,7 @@ var SkillDiffStrategy = class {
|
|
|
12028
12662
|
}
|
|
12029
12663
|
async tryStatFile(filePath) {
|
|
12030
12664
|
try {
|
|
12031
|
-
const stat9 = await
|
|
12665
|
+
const stat9 = await fs14.stat(filePath);
|
|
12032
12666
|
return { isDirectory: stat9.isDirectory() };
|
|
12033
12667
|
} catch {
|
|
12034
12668
|
return null;
|
|
@@ -12036,7 +12670,7 @@ var SkillDiffStrategy = class {
|
|
|
12036
12670
|
}
|
|
12037
12671
|
async tryGetPermissions(filePath) {
|
|
12038
12672
|
try {
|
|
12039
|
-
const stat9 = await
|
|
12673
|
+
const stat9 = await fs14.stat(filePath);
|
|
12040
12674
|
return modeToPermissionStringOrDefault(stat9.mode);
|
|
12041
12675
|
} catch {
|
|
12042
12676
|
return null;
|
|
@@ -12052,8 +12686,8 @@ var SkillDiffStrategy = class {
|
|
|
12052
12686
|
};
|
|
12053
12687
|
|
|
12054
12688
|
// apps/cli/src/application/useCases/diffStrategies/StandardDiffStrategy.ts
|
|
12055
|
-
var
|
|
12056
|
-
var
|
|
12689
|
+
var fs15 = __toESM(require("fs/promises"));
|
|
12690
|
+
var path18 = __toESM(require("path"));
|
|
12057
12691
|
|
|
12058
12692
|
// apps/cli/src/application/utils/parseStandardMd.ts
|
|
12059
12693
|
var DEPLOYER_PARSERS = [
|
|
@@ -12361,10 +12995,10 @@ var StandardDiffStrategy = class {
|
|
|
12361
12995
|
return file.artifactType === "standard";
|
|
12362
12996
|
}
|
|
12363
12997
|
async diff(file, baseDirectory) {
|
|
12364
|
-
const fullPath =
|
|
12998
|
+
const fullPath = path18.join(baseDirectory, file.path);
|
|
12365
12999
|
let localContent;
|
|
12366
13000
|
try {
|
|
12367
|
-
localContent = await
|
|
13001
|
+
localContent = await fs15.readFile(fullPath, "utf-8");
|
|
12368
13002
|
} catch {
|
|
12369
13003
|
return [];
|
|
12370
13004
|
}
|
|
@@ -12728,6 +13362,149 @@ var SpaceService = class {
|
|
|
12728
13362
|
}
|
|
12729
13363
|
return defaultSpace;
|
|
12730
13364
|
}
|
|
13365
|
+
async getSpaceBySlug(slug3) {
|
|
13366
|
+
return this.spaceGateway.getSpaceBySlug(slug3);
|
|
13367
|
+
}
|
|
13368
|
+
getApiContext() {
|
|
13369
|
+
return this.spaceGateway.getApiContext();
|
|
13370
|
+
}
|
|
13371
|
+
};
|
|
13372
|
+
|
|
13373
|
+
// apps/cli/src/infra/repositories/CliOutput.ts
|
|
13374
|
+
init_source();
|
|
13375
|
+
var import_log_update = __toESM(require("log-update"));
|
|
13376
|
+
var CLI_PREFIX2 = "packmind-cli";
|
|
13377
|
+
var CliFormatter = class {
|
|
13378
|
+
static success(message) {
|
|
13379
|
+
return `${source_default.bgGreen.bold(CLI_PREFIX2)} ${source_default.green.bold(message)}`;
|
|
13380
|
+
}
|
|
13381
|
+
static info(message) {
|
|
13382
|
+
return `${source_default.bgBlue.bold(CLI_PREFIX2)} ${source_default.blue(message)}`;
|
|
13383
|
+
}
|
|
13384
|
+
static warning(message) {
|
|
13385
|
+
return `${source_default.bgYellow.bold(CLI_PREFIX2)} ${source_default.yellow.bold(message)}`;
|
|
13386
|
+
}
|
|
13387
|
+
static error(message) {
|
|
13388
|
+
return `${source_default.bgRed.bold(CLI_PREFIX2)} ${source_default.red(message)}`;
|
|
13389
|
+
}
|
|
13390
|
+
static command(command33) {
|
|
13391
|
+
return source_default.yellow(command33);
|
|
13392
|
+
}
|
|
13393
|
+
static loader(text) {
|
|
13394
|
+
return source_default.dim.italic(text);
|
|
13395
|
+
}
|
|
13396
|
+
static header(title) {
|
|
13397
|
+
return source_default.bold.underline(title);
|
|
13398
|
+
}
|
|
13399
|
+
static subHeader(title) {
|
|
13400
|
+
return source_default.bold(title);
|
|
13401
|
+
}
|
|
13402
|
+
static slug(slug3) {
|
|
13403
|
+
return source_default.blue.bold(slug3);
|
|
13404
|
+
}
|
|
13405
|
+
static label(label) {
|
|
13406
|
+
return source_default.dim(label);
|
|
13407
|
+
}
|
|
13408
|
+
};
|
|
13409
|
+
var CliOutput = class {
|
|
13410
|
+
constructor(logger2 = console) {
|
|
13411
|
+
this.logger = logger2;
|
|
13412
|
+
}
|
|
13413
|
+
notifySuccess(message, help) {
|
|
13414
|
+
this.notifyMessage(
|
|
13415
|
+
CliFormatter.success(message),
|
|
13416
|
+
(msg) => this.logger.log(msg),
|
|
13417
|
+
help
|
|
13418
|
+
);
|
|
13419
|
+
}
|
|
13420
|
+
notifyInfo(message, help) {
|
|
13421
|
+
this.notifyMessage(
|
|
13422
|
+
CliFormatter.info(message),
|
|
13423
|
+
(msg) => this.logger.log(msg),
|
|
13424
|
+
help
|
|
13425
|
+
);
|
|
13426
|
+
}
|
|
13427
|
+
notifyWarning(message, help) {
|
|
13428
|
+
this.notifyMessage(
|
|
13429
|
+
CliFormatter.warning(message),
|
|
13430
|
+
(msg) => this.logger.warn(msg),
|
|
13431
|
+
help
|
|
13432
|
+
);
|
|
13433
|
+
}
|
|
13434
|
+
notifyError(message, help) {
|
|
13435
|
+
this.notifyMessage(
|
|
13436
|
+
CliFormatter.error(message),
|
|
13437
|
+
(msg) => this.logger.error(msg),
|
|
13438
|
+
help
|
|
13439
|
+
);
|
|
13440
|
+
}
|
|
13441
|
+
showLoader(message) {
|
|
13442
|
+
this.logger.log(CliFormatter.loader(message));
|
|
13443
|
+
}
|
|
13444
|
+
async withLoader(message, loader) {
|
|
13445
|
+
(0, import_log_update.default)(CliFormatter.loader(message));
|
|
13446
|
+
try {
|
|
13447
|
+
return loader();
|
|
13448
|
+
} finally {
|
|
13449
|
+
import_log_update.default.clear();
|
|
13450
|
+
}
|
|
13451
|
+
}
|
|
13452
|
+
showArtefact(artefact, help) {
|
|
13453
|
+
this.logger.log(CliFormatter.label(artefact.slug));
|
|
13454
|
+
this.logger.log(CliFormatter.header(artefact.title));
|
|
13455
|
+
if (artefact.url) {
|
|
13456
|
+
this.logger.log(CliFormatter.label(artefact.url));
|
|
13457
|
+
}
|
|
13458
|
+
this.logger.log("");
|
|
13459
|
+
if (artefact.description) {
|
|
13460
|
+
this.logger.log(artefact.description);
|
|
13461
|
+
}
|
|
13462
|
+
this.logger.log("");
|
|
13463
|
+
this.displayHelp((msg) => this.logger.log(msg), help);
|
|
13464
|
+
}
|
|
13465
|
+
listArtefacts(title, artefacts, help) {
|
|
13466
|
+
this.logger.log(CliFormatter.header(title));
|
|
13467
|
+
this.logger.log("");
|
|
13468
|
+
this.displayList(artefacts);
|
|
13469
|
+
this.displayHelp((msg) => this.logger.log(msg), help);
|
|
13470
|
+
}
|
|
13471
|
+
listScopedArtefacts(title, scopedArtefacts, help) {
|
|
13472
|
+
this.logger.log(CliFormatter.header(title));
|
|
13473
|
+
this.logger.log("");
|
|
13474
|
+
for (const { title: title2, artefacts } of scopedArtefacts) {
|
|
13475
|
+
this.logger.log(CliFormatter.subHeader(title2));
|
|
13476
|
+
this.logger.log("");
|
|
13477
|
+
this.displayList(artefacts);
|
|
13478
|
+
}
|
|
13479
|
+
this.displayHelp((msg) => this.logger.log(msg), help);
|
|
13480
|
+
}
|
|
13481
|
+
notifyMessage(message, output, help) {
|
|
13482
|
+
output(message);
|
|
13483
|
+
this.displayHelp(output, help);
|
|
13484
|
+
}
|
|
13485
|
+
displayList(artefacts) {
|
|
13486
|
+
for (const artefact of artefacts) {
|
|
13487
|
+
this.logger.log(`- ${CliFormatter.label(artefact.slug)}`);
|
|
13488
|
+
this.logger.log(` Name: ${CliFormatter.header(artefact.title)}`);
|
|
13489
|
+
if (artefact.url) {
|
|
13490
|
+
this.logger.log(` ${CliFormatter.label(artefact.url)}`);
|
|
13491
|
+
}
|
|
13492
|
+
this.logger.log("");
|
|
13493
|
+
}
|
|
13494
|
+
}
|
|
13495
|
+
displayHelp(output, help) {
|
|
13496
|
+
if (help) {
|
|
13497
|
+
output(help.content);
|
|
13498
|
+
if (help.exampleCommand) {
|
|
13499
|
+
output(`
|
|
13500
|
+
Example: ${CliFormatter.command(help.exampleCommand)}`);
|
|
13501
|
+
}
|
|
13502
|
+
if (help.command) {
|
|
13503
|
+
output(`
|
|
13504
|
+
${CliFormatter.command(help.command)}`);
|
|
13505
|
+
}
|
|
13506
|
+
}
|
|
13507
|
+
}
|
|
12731
13508
|
};
|
|
12732
13509
|
|
|
12733
13510
|
// apps/cli/src/PackmindCliHexaFactory.ts
|
|
@@ -12736,7 +13513,8 @@ var PackmindCliHexaFactory = class {
|
|
|
12736
13513
|
this.repositories = {
|
|
12737
13514
|
packmindGateway: new PackmindGateway(loadApiKey()),
|
|
12738
13515
|
configFileRepository: new ConfigFileRepository(),
|
|
12739
|
-
lockFileRepository: new LockFileRepository()
|
|
13516
|
+
lockFileRepository: new LockFileRepository(),
|
|
13517
|
+
output: new CliOutput()
|
|
12740
13518
|
};
|
|
12741
13519
|
this.services = {
|
|
12742
13520
|
listFiles: new ListFiles(),
|
|
@@ -12745,6 +13523,12 @@ var PackmindCliHexaFactory = class {
|
|
|
12745
13523
|
diffViolationFilterService: new DiffViolationFilterService(),
|
|
12746
13524
|
spaceService: new SpaceService(this.repositories.packmindGateway.spaces)
|
|
12747
13525
|
};
|
|
13526
|
+
const installUseCase = new InstallUseCase(
|
|
13527
|
+
this.repositories.packmindGateway,
|
|
13528
|
+
this.repositories.lockFileRepository,
|
|
13529
|
+
this.repositories.configFileRepository,
|
|
13530
|
+
this.services.spaceService
|
|
13531
|
+
);
|
|
12748
13532
|
this.useCases = {
|
|
12749
13533
|
executeSingleFileAst: new ExecuteSingleFileAstUseCase(
|
|
12750
13534
|
this.services.linterExecutionUseCase
|
|
@@ -12762,6 +13546,12 @@ var PackmindCliHexaFactory = class {
|
|
|
12762
13546
|
installPackages: new InstallPackagesUseCase(
|
|
12763
13547
|
this.repositories.packmindGateway
|
|
12764
13548
|
),
|
|
13549
|
+
install: installUseCase,
|
|
13550
|
+
uninstall: new UninstallUseCase(
|
|
13551
|
+
this.repositories.configFileRepository,
|
|
13552
|
+
this.services.spaceService,
|
|
13553
|
+
installUseCase
|
|
13554
|
+
),
|
|
12765
13555
|
installDefaultSkills: new InstallDefaultSkillsUseCase(this.repositories),
|
|
12766
13556
|
listPackages: new ListPackagesUseCase(
|
|
12767
13557
|
this.repositories.packmindGateway,
|
|
@@ -12813,6 +13603,11 @@ var PackmindCliHexa = class {
|
|
|
12813
13603
|
command33
|
|
12814
13604
|
);
|
|
12815
13605
|
};
|
|
13606
|
+
this.notifyArtefactsDistribution = async (command33) => {
|
|
13607
|
+
return this.hexa.repositories.packmindGateway.deployment.notifyArtefactsDistribution(
|
|
13608
|
+
command33
|
|
13609
|
+
);
|
|
13610
|
+
};
|
|
12816
13611
|
this.logger = logger2;
|
|
12817
13612
|
try {
|
|
12818
13613
|
this.hexa = new PackmindCliHexaFactory();
|
|
@@ -12830,6 +13625,9 @@ var PackmindCliHexa = class {
|
|
|
12830
13625
|
this.logger.info("Destroying PackmindCliHexa");
|
|
12831
13626
|
this.logger.info("PackmindCliHexa destroyed");
|
|
12832
13627
|
}
|
|
13628
|
+
get output() {
|
|
13629
|
+
return this.hexa.repositories.output;
|
|
13630
|
+
}
|
|
12833
13631
|
async getGitRemoteUrl(command33) {
|
|
12834
13632
|
return this.hexa.useCases.getGitRemoteUrl.execute(command33);
|
|
12835
13633
|
}
|
|
@@ -12845,6 +13643,12 @@ var PackmindCliHexa = class {
|
|
|
12845
13643
|
async installPackages(command33) {
|
|
12846
13644
|
return this.hexa.useCases.installPackages.execute(command33);
|
|
12847
13645
|
}
|
|
13646
|
+
async install(command33) {
|
|
13647
|
+
return this.hexa.useCases.install.execute(command33);
|
|
13648
|
+
}
|
|
13649
|
+
async uninstall(command33) {
|
|
13650
|
+
return this.hexa.useCases.uninstall.execute(command33);
|
|
13651
|
+
}
|
|
12848
13652
|
async diffArtefacts(command33) {
|
|
12849
13653
|
return this.hexa.useCases.diffArtefacts.execute(command33);
|
|
12850
13654
|
}
|
|
@@ -13103,31 +13907,31 @@ var HumanReadableLogger = class {
|
|
|
13103
13907
|
var pathModule2 = __toESM(require("path"));
|
|
13104
13908
|
|
|
13105
13909
|
// apps/cli/src/infra/commands/lintHandler.ts
|
|
13106
|
-
var
|
|
13910
|
+
var fs17 = __toESM(require("fs/promises"));
|
|
13107
13911
|
var pathModule = __toESM(require("path"));
|
|
13108
13912
|
|
|
13109
13913
|
// apps/cli/src/application/services/PackmindIgnoreReader.ts
|
|
13110
|
-
var
|
|
13111
|
-
var
|
|
13914
|
+
var fs16 = __toESM(require("fs/promises"));
|
|
13915
|
+
var path19 = __toESM(require("path"));
|
|
13112
13916
|
var IGNORE_FILENAME = ".packmindignore";
|
|
13113
13917
|
var PackmindIgnoreReader = class {
|
|
13114
13918
|
async readIgnorePatterns(startDirectory, stopDirectory) {
|
|
13115
13919
|
const patterns = [];
|
|
13116
|
-
const normalizedStart =
|
|
13117
|
-
const normalizedStop = stopDirectory ?
|
|
13920
|
+
const normalizedStart = path19.resolve(startDirectory);
|
|
13921
|
+
const normalizedStop = stopDirectory ? path19.resolve(stopDirectory) : null;
|
|
13118
13922
|
if (normalizedStop === null) {
|
|
13119
|
-
const ignoreFile =
|
|
13923
|
+
const ignoreFile = path19.join(normalizedStart, IGNORE_FILENAME);
|
|
13120
13924
|
return this.parseIgnoreFile(ignoreFile);
|
|
13121
13925
|
}
|
|
13122
13926
|
let currentDir = normalizedStart;
|
|
13123
13927
|
while (true) {
|
|
13124
|
-
const ignoreFile =
|
|
13928
|
+
const ignoreFile = path19.join(currentDir, IGNORE_FILENAME);
|
|
13125
13929
|
const filePatterns = await this.parseIgnoreFile(ignoreFile);
|
|
13126
13930
|
patterns.push(...filePatterns);
|
|
13127
13931
|
if (currentDir === normalizedStop) {
|
|
13128
13932
|
break;
|
|
13129
13933
|
}
|
|
13130
|
-
const parentDir =
|
|
13934
|
+
const parentDir = path19.dirname(currentDir);
|
|
13131
13935
|
if (parentDir === currentDir) {
|
|
13132
13936
|
break;
|
|
13133
13937
|
}
|
|
@@ -13138,7 +13942,7 @@ var PackmindIgnoreReader = class {
|
|
|
13138
13942
|
async parseIgnoreFile(filePath) {
|
|
13139
13943
|
let content;
|
|
13140
13944
|
try {
|
|
13141
|
-
content = await
|
|
13945
|
+
content = await fs16.readFile(filePath, "utf-8");
|
|
13142
13946
|
} catch (err) {
|
|
13143
13947
|
if (err.code === "ENOENT") {
|
|
13144
13948
|
return [];
|
|
@@ -13159,7 +13963,7 @@ function isNotLoggedInError(error) {
|
|
|
13159
13963
|
}
|
|
13160
13964
|
async function lintHandler(args2, deps) {
|
|
13161
13965
|
const {
|
|
13162
|
-
path:
|
|
13966
|
+
path: path37,
|
|
13163
13967
|
draft,
|
|
13164
13968
|
rule,
|
|
13165
13969
|
language,
|
|
@@ -13181,11 +13985,11 @@ async function lintHandler(args2, deps) {
|
|
|
13181
13985
|
throw new Error("option --rule is required to use --draft mode");
|
|
13182
13986
|
}
|
|
13183
13987
|
const startedAt = Date.now();
|
|
13184
|
-
const targetPath =
|
|
13988
|
+
const targetPath = path37 ?? ".";
|
|
13185
13989
|
const absolutePath = resolvePath(targetPath);
|
|
13186
13990
|
let stats;
|
|
13187
13991
|
try {
|
|
13188
|
-
stats = await
|
|
13992
|
+
stats = await fs17.stat(absolutePath);
|
|
13189
13993
|
} catch (err) {
|
|
13190
13994
|
const isNotFound = err.code === "ENOENT";
|
|
13191
13995
|
const message = isNotFound ? `File or directory "${absolutePath}" does not exist` : `Cannot access "${absolutePath}": ${err.message}`;
|
|
@@ -13503,72 +14307,15 @@ function extractWasmFiles() {
|
|
|
13503
14307
|
|
|
13504
14308
|
// apps/cli/src/main.ts
|
|
13505
14309
|
var import_dotenv = require("dotenv");
|
|
13506
|
-
var
|
|
13507
|
-
var
|
|
14310
|
+
var fs28 = __toESM(require("fs"));
|
|
14311
|
+
var path36 = __toESM(require("path"));
|
|
13508
14312
|
|
|
13509
14313
|
// apps/cli/src/infra/commands/InstallCommand.ts
|
|
13510
14314
|
var import_cmd_ts2 = __toESM(require_cjs());
|
|
14315
|
+
var path20 = __toESM(require("path"));
|
|
14316
|
+
var fs18 = __toESM(require("fs"));
|
|
13511
14317
|
|
|
13512
14318
|
// apps/cli/src/infra/commands/installPackagesHandler.ts
|
|
13513
|
-
var fs17 = __toESM(require("fs/promises"));
|
|
13514
|
-
var path19 = __toESM(require("path"));
|
|
13515
|
-
var { version: CLI_VERSION } = require_package();
|
|
13516
|
-
async function notifyDistributionIfInGitRepo(params) {
|
|
13517
|
-
const { packmindCliHexa, cwd, packages, log, agents } = params;
|
|
13518
|
-
const resolvedGitRoot = params.gitRoot ?? await packmindCliHexa.tryGetGitRepositoryRoot(cwd);
|
|
13519
|
-
if (!resolvedGitRoot) {
|
|
13520
|
-
return false;
|
|
13521
|
-
}
|
|
13522
|
-
try {
|
|
13523
|
-
const gitRemoteUrl = packmindCliHexa.getGitRemoteUrlFromPath(resolvedGitRoot);
|
|
13524
|
-
const gitBranch = packmindCliHexa.getCurrentBranch(resolvedGitRoot);
|
|
13525
|
-
let relativePath = cwd.startsWith(resolvedGitRoot) ? cwd.slice(resolvedGitRoot.length) : "/";
|
|
13526
|
-
if (!relativePath.startsWith("/")) {
|
|
13527
|
-
relativePath = "/" + relativePath;
|
|
13528
|
-
}
|
|
13529
|
-
if (!relativePath.endsWith("/")) {
|
|
13530
|
-
relativePath = relativePath + "/";
|
|
13531
|
-
}
|
|
13532
|
-
await packmindCliHexa.notifyDistribution({
|
|
13533
|
-
distributedPackages: packages,
|
|
13534
|
-
gitRemoteUrl,
|
|
13535
|
-
gitBranch,
|
|
13536
|
-
relativePath,
|
|
13537
|
-
agents
|
|
13538
|
-
});
|
|
13539
|
-
log("Successfully notified Packmind of the new distribution");
|
|
13540
|
-
return true;
|
|
13541
|
-
} catch {
|
|
13542
|
-
return false;
|
|
13543
|
-
}
|
|
13544
|
-
}
|
|
13545
|
-
async function installDefaultSkillsIfAtGitRoot(params) {
|
|
13546
|
-
const { packmindCliHexa, cwd, log } = params;
|
|
13547
|
-
const gitRoot = await packmindCliHexa.tryGetGitRepositoryRoot(cwd);
|
|
13548
|
-
if (!gitRoot || cwd !== gitRoot) {
|
|
13549
|
-
return;
|
|
13550
|
-
}
|
|
13551
|
-
try {
|
|
13552
|
-
log("\nInstalling default skills...");
|
|
13553
|
-
const skillsResult = await packmindCliHexa.installDefaultSkills({
|
|
13554
|
-
cliVersion: CLI_VERSION
|
|
13555
|
-
});
|
|
13556
|
-
if (skillsResult.errors.length > 0) {
|
|
13557
|
-
skillsResult.errors.forEach((err) => {
|
|
13558
|
-
log(` Warning: ${err}`);
|
|
13559
|
-
});
|
|
13560
|
-
}
|
|
13561
|
-
const totalSkillFiles = skillsResult.filesCreated + skillsResult.filesUpdated;
|
|
13562
|
-
if (totalSkillFiles > 0) {
|
|
13563
|
-
log(
|
|
13564
|
-
`Default skills: added ${skillsResult.filesCreated} files, changed ${skillsResult.filesUpdated} files`
|
|
13565
|
-
);
|
|
13566
|
-
} else if (skillsResult.errors.length === 0) {
|
|
13567
|
-
log("Default skills are already up to date");
|
|
13568
|
-
}
|
|
13569
|
-
} catch {
|
|
13570
|
-
}
|
|
13571
|
-
}
|
|
13572
14319
|
function formatOverviewRow(configPath, packages, pathColumnWidth) {
|
|
13573
14320
|
const paddedPath = configPath.padEnd(pathColumnWidth);
|
|
13574
14321
|
if (packages.length === 0) {
|
|
@@ -13641,1150 +14388,340 @@ ${uniqueCount} unique ${packageWord} currently installed.`);
|
|
|
13641
14388
|
};
|
|
13642
14389
|
}
|
|
13643
14390
|
}
|
|
13644
|
-
|
|
13645
|
-
|
|
13646
|
-
|
|
13647
|
-
|
|
14391
|
+
|
|
14392
|
+
// apps/cli/src/infra/commands/InstallCommand.ts
|
|
14393
|
+
var { version: CLI_VERSION } = require_package();
|
|
14394
|
+
function findSubDirectoriesWithPackmindJson(dirPath, recursive) {
|
|
14395
|
+
const result = [];
|
|
14396
|
+
let entries;
|
|
13648
14397
|
try {
|
|
13649
|
-
|
|
13650
|
-
|
|
13651
|
-
|
|
13652
|
-
configAgents = fullConfig.agents;
|
|
13653
|
-
} else {
|
|
13654
|
-
configPackages = [];
|
|
13655
|
-
}
|
|
13656
|
-
} catch (err) {
|
|
13657
|
-
const errorMessage = err instanceof Error ? err.message : String(err);
|
|
13658
|
-
return {
|
|
13659
|
-
success: false,
|
|
13660
|
-
filesCreated: 0,
|
|
13661
|
-
filesUpdated: 0,
|
|
13662
|
-
filesDeleted: 0,
|
|
13663
|
-
notificationSent: false,
|
|
13664
|
-
errorMessage: `Failed to parse packmind.json: ${errorMessage}`
|
|
13665
|
-
};
|
|
13666
|
-
}
|
|
13667
|
-
if (configPackages.length === 0) {
|
|
13668
|
-
return {
|
|
13669
|
-
success: true,
|
|
13670
|
-
filesCreated: 0,
|
|
13671
|
-
filesUpdated: 0,
|
|
13672
|
-
filesDeleted: 0,
|
|
13673
|
-
notificationSent: false
|
|
13674
|
-
};
|
|
14398
|
+
entries = fs18.readdirSync(dirPath, { withFileTypes: true });
|
|
14399
|
+
} catch {
|
|
14400
|
+
return result;
|
|
13675
14401
|
}
|
|
13676
|
-
const
|
|
13677
|
-
|
|
13678
|
-
|
|
13679
|
-
|
|
13680
|
-
|
|
13681
|
-
|
|
13682
|
-
|
|
13683
|
-
|
|
13684
|
-
gitBranch = packmindCliHexa.getCurrentBranch(gitRoot);
|
|
13685
|
-
relativePath = directory.startsWith(gitRoot) ? directory.slice(gitRoot.length) : "/";
|
|
13686
|
-
if (!relativePath.startsWith("/")) {
|
|
13687
|
-
relativePath = "/" + relativePath;
|
|
13688
|
-
}
|
|
13689
|
-
if (!relativePath.endsWith("/")) {
|
|
13690
|
-
relativePath = relativePath + "/";
|
|
13691
|
-
}
|
|
13692
|
-
} catch {
|
|
14402
|
+
for (const entry of entries) {
|
|
14403
|
+
if (!entry.isDirectory()) continue;
|
|
14404
|
+
const subDir = path20.join(dirPath, entry.name);
|
|
14405
|
+
if (fs18.existsSync(path20.join(subDir, "packmind.json"))) {
|
|
14406
|
+
result.push(subDir);
|
|
14407
|
+
}
|
|
14408
|
+
if (recursive) {
|
|
14409
|
+
result.push(...findSubDirectoriesWithPackmindJson(subDir, true));
|
|
13693
14410
|
}
|
|
13694
14411
|
}
|
|
14412
|
+
return result;
|
|
14413
|
+
}
|
|
14414
|
+
function mergeInstallResults(results) {
|
|
14415
|
+
const merged = {
|
|
14416
|
+
filesCreated: 0,
|
|
14417
|
+
filesUpdated: 0,
|
|
14418
|
+
filesDeleted: 0,
|
|
14419
|
+
contentFilesChanged: 0,
|
|
14420
|
+
errors: [],
|
|
14421
|
+
recipesCount: 0,
|
|
14422
|
+
standardsCount: 0,
|
|
14423
|
+
commandsCount: 0,
|
|
14424
|
+
skillsCount: 0,
|
|
14425
|
+
recipesRemoved: 0,
|
|
14426
|
+
standardsRemoved: 0,
|
|
14427
|
+
commandsRemoved: 0,
|
|
14428
|
+
skillsRemoved: 0,
|
|
14429
|
+
skillDirectoriesDeleted: 0,
|
|
14430
|
+
missingAccess: [],
|
|
14431
|
+
joinSpaceUrl: void 0
|
|
14432
|
+
};
|
|
14433
|
+
for (const r of results) {
|
|
14434
|
+
merged.filesCreated += r.filesCreated;
|
|
14435
|
+
merged.filesUpdated += r.filesUpdated;
|
|
14436
|
+
merged.filesDeleted += r.filesDeleted;
|
|
14437
|
+
merged.contentFilesChanged += r.contentFilesChanged;
|
|
14438
|
+
merged.errors.push(...r.errors);
|
|
14439
|
+
merged.recipesCount += r.recipesCount;
|
|
14440
|
+
merged.standardsCount += r.standardsCount;
|
|
14441
|
+
merged.commandsCount += r.commandsCount;
|
|
14442
|
+
merged.skillsCount += r.skillsCount;
|
|
14443
|
+
merged.recipesRemoved += r.recipesRemoved;
|
|
14444
|
+
merged.standardsRemoved += r.standardsRemoved;
|
|
14445
|
+
merged.commandsRemoved += r.commandsRemoved;
|
|
14446
|
+
merged.skillsRemoved += r.skillsRemoved;
|
|
14447
|
+
merged.skillDirectoriesDeleted += r.skillDirectoriesDeleted;
|
|
14448
|
+
merged.missingAccess.push(...r.missingAccess);
|
|
14449
|
+
}
|
|
14450
|
+
merged.missingAccess = [...new Set(merged.missingAccess)];
|
|
14451
|
+
const urlsFromResultsWithMissingAccess = results.filter((r) => r.missingAccess.length > 0).map((r) => r.joinSpaceUrl);
|
|
14452
|
+
const uniqueUrls = new Set(urlsFromResultsWithMissingAccess.filter(Boolean));
|
|
14453
|
+
if (uniqueUrls.size === 1 && !urlsFromResultsWithMissingAccess.some((u) => u === void 0)) {
|
|
14454
|
+
merged.joinSpaceUrl = [...uniqueUrls][0];
|
|
14455
|
+
}
|
|
14456
|
+
return merged;
|
|
14457
|
+
}
|
|
14458
|
+
function buildInstallSummary(result) {
|
|
14459
|
+
const contentParts = [
|
|
14460
|
+
result.standardsCount > 0 ? `${result.standardsCount} ${result.standardsCount === 1 ? "standard" : "standards"}` : null,
|
|
14461
|
+
result.commandsCount > 0 ? `${result.commandsCount} ${result.commandsCount === 1 ? "command" : "commands"}` : null,
|
|
14462
|
+
result.skillsCount > 0 ? `${result.skillsCount} ${result.skillsCount === 1 ? "skill" : "skills"}` : null,
|
|
14463
|
+
result.recipesCount > 0 ? `${result.recipesCount} ${result.recipesCount === 1 ? "recipe" : "recipes"}` : null
|
|
14464
|
+
].filter(Boolean);
|
|
14465
|
+
const contentChanged = result.contentFilesChanged > 0;
|
|
14466
|
+
if (!contentChanged && contentParts.length === 0) {
|
|
14467
|
+
return "\u2705 Nothing to install";
|
|
14468
|
+
}
|
|
14469
|
+
if (!contentChanged) {
|
|
14470
|
+
return `\u2705 Already up to date \u2014 ${contentParts.join(", ")}`;
|
|
14471
|
+
}
|
|
14472
|
+
if (contentParts.length === 0) {
|
|
14473
|
+
return "\u2705 Packages removed";
|
|
14474
|
+
}
|
|
14475
|
+
return `\u2705 Synced ${contentParts.join(", ")}`;
|
|
14476
|
+
}
|
|
14477
|
+
async function notifyArtefactsDistributionIfInGitRepo(params) {
|
|
14478
|
+
const { packmindCliHexa, dir } = params;
|
|
13695
14479
|
try {
|
|
13696
|
-
const
|
|
13697
|
-
|
|
13698
|
-
|
|
13699
|
-
|
|
13700
|
-
);
|
|
13701
|
-
const
|
|
13702
|
-
|
|
13703
|
-
|
|
13704
|
-
|
|
13705
|
-
|
|
14480
|
+
const gitRoot = await packmindCliHexa.tryGetGitRepositoryRoot(dir);
|
|
14481
|
+
if (!gitRoot) return;
|
|
14482
|
+
const lockFilePath = path20.join(dir, "packmind-lock.json");
|
|
14483
|
+
const content = fs18.readFileSync(lockFilePath, "utf-8");
|
|
14484
|
+
const packmindLockFile = JSON.parse(content);
|
|
14485
|
+
const gitRemoteUrl = packmindCliHexa.getGitRemoteUrlFromPath(gitRoot);
|
|
14486
|
+
const gitBranch = packmindCliHexa.getCurrentBranch(gitRoot);
|
|
14487
|
+
let relativePath = dir.startsWith(gitRoot) ? dir.slice(gitRoot.length) : "/";
|
|
14488
|
+
if (!relativePath.startsWith("/")) {
|
|
14489
|
+
relativePath = "/" + relativePath;
|
|
14490
|
+
}
|
|
14491
|
+
if (!relativePath.endsWith("/")) {
|
|
14492
|
+
relativePath = relativePath + "/";
|
|
14493
|
+
}
|
|
14494
|
+
await packmindCliHexa.notifyArtefactsDistribution({
|
|
13706
14495
|
gitRemoteUrl,
|
|
13707
14496
|
gitBranch,
|
|
13708
14497
|
relativePath,
|
|
13709
|
-
|
|
13710
|
-
// Pass agents from config if present
|
|
14498
|
+
packmindLockFile
|
|
13711
14499
|
});
|
|
13712
|
-
|
|
13713
|
-
if (result.recipesCount > 0) parts.push(`${result.recipesCount} commands`);
|
|
13714
|
-
if (result.standardsCount > 0)
|
|
13715
|
-
parts.push(`${result.standardsCount} standards`);
|
|
13716
|
-
if (result.skillsCount > 0) parts.push(`${result.skillsCount} skills`);
|
|
13717
|
-
log(` Installing ${parts.join(", ") || "artifacts"}...`);
|
|
13718
|
-
log(
|
|
13719
|
-
` added ${result.filesCreated} files, changed ${result.filesUpdated} files, removed ${result.filesDeleted} files`
|
|
13720
|
-
);
|
|
13721
|
-
if (result.errors.length > 0) {
|
|
13722
|
-
return {
|
|
13723
|
-
success: false,
|
|
13724
|
-
filesCreated: result.filesCreated,
|
|
13725
|
-
filesUpdated: result.filesUpdated,
|
|
13726
|
-
filesDeleted: result.filesDeleted,
|
|
13727
|
-
notificationSent: false,
|
|
13728
|
-
errorMessage: result.errors.join(", ")
|
|
13729
|
-
};
|
|
13730
|
-
}
|
|
13731
|
-
const configSlugsWereNormalized = configPackages.some(
|
|
13732
|
-
(slug3, i) => slug3 !== normalizedConfigPackages[i]
|
|
13733
|
-
);
|
|
13734
|
-
if (configSlugsWereNormalized) {
|
|
13735
|
-
await packmindCliHexa.writeConfig(directory, normalizedConfigPackages);
|
|
13736
|
-
}
|
|
13737
|
-
const skillDirsDeleted = result.skillDirectoriesDeleted || 0;
|
|
13738
|
-
let notificationSent = false;
|
|
13739
|
-
if (result.filesCreated > 0 || result.filesUpdated > 0 || result.filesDeleted > 0 || skillDirsDeleted > 0) {
|
|
13740
|
-
notificationSent = await notifyDistributionIfInGitRepo({
|
|
13741
|
-
packmindCliHexa,
|
|
13742
|
-
cwd: directory,
|
|
13743
|
-
packages: normalizedConfigPackages,
|
|
13744
|
-
agents: configAgents,
|
|
13745
|
-
log: () => {
|
|
13746
|
-
},
|
|
13747
|
-
gitRoot: gitRoot ?? void 0
|
|
13748
|
-
});
|
|
13749
|
-
}
|
|
13750
|
-
return {
|
|
13751
|
-
success: true,
|
|
13752
|
-
filesCreated: result.filesCreated,
|
|
13753
|
-
filesUpdated: result.filesUpdated,
|
|
13754
|
-
filesDeleted: result.filesDeleted + skillDirsDeleted,
|
|
13755
|
-
notificationSent
|
|
13756
|
-
};
|
|
13757
|
-
} catch (err) {
|
|
13758
|
-
const errorMessage = err instanceof Error ? err.message : String(err);
|
|
13759
|
-
return {
|
|
13760
|
-
success: false,
|
|
13761
|
-
filesCreated: 0,
|
|
13762
|
-
filesUpdated: 0,
|
|
13763
|
-
filesDeleted: 0,
|
|
13764
|
-
notificationSent: false,
|
|
13765
|
-
errorMessage
|
|
13766
|
-
};
|
|
14500
|
+
} catch {
|
|
13767
14501
|
}
|
|
13768
14502
|
}
|
|
13769
|
-
async function
|
|
13770
|
-
const { packmindCliHexa,
|
|
13771
|
-
const
|
|
13772
|
-
|
|
13773
|
-
|
|
13774
|
-
if (args2.path) {
|
|
13775
|
-
const resolvedPath = path19.resolve(rawCwd, args2.path);
|
|
13776
|
-
try {
|
|
13777
|
-
const stat9 = await fs17.stat(resolvedPath);
|
|
13778
|
-
if (!stat9.isDirectory()) {
|
|
13779
|
-
logErrorConsole(`Path is not a directory: ${resolvedPath}`);
|
|
13780
|
-
exit(1);
|
|
13781
|
-
return {
|
|
13782
|
-
filesCreated: 0,
|
|
13783
|
-
filesUpdated: 0,
|
|
13784
|
-
filesDeleted: 0,
|
|
13785
|
-
notificationSent: false
|
|
13786
|
-
};
|
|
13787
|
-
}
|
|
13788
|
-
cwd = resolvedPath;
|
|
13789
|
-
} catch {
|
|
13790
|
-
logErrorConsole(`Path does not exist: ${resolvedPath}`);
|
|
13791
|
-
exit(1);
|
|
13792
|
-
return {
|
|
13793
|
-
filesCreated: 0,
|
|
13794
|
-
filesUpdated: 0,
|
|
13795
|
-
filesDeleted: 0,
|
|
13796
|
-
notificationSent: false
|
|
13797
|
-
};
|
|
13798
|
-
}
|
|
13799
|
-
const relativeToCwd = path19.relative(rawCwd, resolvedPath);
|
|
13800
|
-
const displayPath = relativeToCwd ? `./${relativeToCwd}/packmind.json` : `./packmind.json`;
|
|
13801
|
-
log(`Installing in ${displayPath}...`);
|
|
14503
|
+
async function installDefaultSkillsIfAtGitRoot(params) {
|
|
14504
|
+
const { packmindCliHexa, cwd } = params;
|
|
14505
|
+
const gitRoot = await packmindCliHexa.tryGetGitRepositoryRoot(cwd);
|
|
14506
|
+
if (!gitRoot || cwd !== gitRoot) {
|
|
14507
|
+
return;
|
|
13802
14508
|
}
|
|
13803
|
-
let configPackages;
|
|
13804
|
-
let configAgents;
|
|
13805
|
-
let configFileExists = false;
|
|
13806
14509
|
try {
|
|
13807
|
-
|
|
13808
|
-
const
|
|
13809
|
-
|
|
13810
|
-
|
|
13811
|
-
|
|
13812
|
-
|
|
13813
|
-
|
|
13814
|
-
logWarningConsole(
|
|
13815
|
-
|
|
13816
|
-
);
|
|
13817
|
-
}
|
|
13818
|
-
configPackages = Object.keys(fullConfig.packages);
|
|
13819
|
-
configAgents = fullConfig.agents;
|
|
13820
|
-
} else {
|
|
13821
|
-
configPackages = [];
|
|
14510
|
+
logConsole("\nInstalling default skills...");
|
|
14511
|
+
const skillsResult = await packmindCliHexa.installDefaultSkills({
|
|
14512
|
+
cliVersion: CLI_VERSION,
|
|
14513
|
+
baseDirectory: cwd
|
|
14514
|
+
});
|
|
14515
|
+
if (skillsResult.errors.length > 0) {
|
|
14516
|
+
skillsResult.errors.forEach((err) => {
|
|
14517
|
+
logWarningConsole(`Warning: ${err}`);
|
|
14518
|
+
});
|
|
13822
14519
|
}
|
|
13823
|
-
|
|
13824
|
-
|
|
13825
|
-
|
|
13826
|
-
|
|
13827
|
-
|
|
13828
|
-
|
|
14520
|
+
const totalSkillFiles = skillsResult.filesCreated + skillsResult.filesUpdated;
|
|
14521
|
+
if (totalSkillFiles > 0) {
|
|
14522
|
+
logConsole(
|
|
14523
|
+
`Default skills: added ${skillsResult.filesCreated} files, changed ${skillsResult.filesUpdated} files`
|
|
14524
|
+
);
|
|
14525
|
+
} else if (skillsResult.errors.length === 0) {
|
|
14526
|
+
logConsole("Default skills are already up to date");
|
|
13829
14527
|
}
|
|
13830
|
-
|
|
13831
|
-
exit(1);
|
|
13832
|
-
return {
|
|
13833
|
-
filesCreated: 0,
|
|
13834
|
-
filesUpdated: 0,
|
|
13835
|
-
filesDeleted: 0,
|
|
13836
|
-
notificationSent: false
|
|
13837
|
-
};
|
|
14528
|
+
} catch {
|
|
13838
14529
|
}
|
|
13839
|
-
|
|
13840
|
-
|
|
13841
|
-
|
|
13842
|
-
|
|
13843
|
-
|
|
13844
|
-
|
|
13845
|
-
|
|
13846
|
-
|
|
13847
|
-
|
|
13848
|
-
|
|
13849
|
-
|
|
13850
|
-
|
|
13851
|
-
|
|
14530
|
+
}
|
|
14531
|
+
async function installHandler({
|
|
14532
|
+
installPath,
|
|
14533
|
+
packages,
|
|
14534
|
+
list,
|
|
14535
|
+
show,
|
|
14536
|
+
status
|
|
14537
|
+
}) {
|
|
14538
|
+
const packmindLogger = new PackmindLogger("PackmindCLI", "info" /* INFO */);
|
|
14539
|
+
const packmindCliHexa = new PackmindCliHexa(packmindLogger);
|
|
14540
|
+
if (status) {
|
|
14541
|
+
const deps = {
|
|
14542
|
+
packmindCliHexa,
|
|
14543
|
+
exit: process.exit,
|
|
14544
|
+
getCwd: () => process.cwd(),
|
|
14545
|
+
log: console.log,
|
|
14546
|
+
error: console.error
|
|
13852
14547
|
};
|
|
14548
|
+
await statusHandler({}, deps);
|
|
14549
|
+
return;
|
|
13853
14550
|
}
|
|
13854
|
-
|
|
13855
|
-
|
|
13856
|
-
|
|
13857
|
-
|
|
13858
|
-
if (configFileExists) {
|
|
13859
|
-
logWarningConsole(
|
|
13860
|
-
"config packmind.json is empty, no packages to install"
|
|
13861
|
-
);
|
|
13862
|
-
} else {
|
|
13863
|
-
logWarningConsole("config packmind.json not found");
|
|
13864
|
-
}
|
|
13865
|
-
log("Usage: packmind-cli install <package-slug> [package-slug...]");
|
|
13866
|
-
log(" packmind-cli install --list");
|
|
13867
|
-
log("");
|
|
13868
|
-
log("Examples:");
|
|
13869
|
-
log(" packmind-cli install backend");
|
|
13870
|
-
log(" packmind-cli install backend frontend");
|
|
13871
|
-
log(" packmind-cli install --list # Show available packages");
|
|
13872
|
-
log("");
|
|
13873
|
-
log("Install commands and standards from the specified packages.");
|
|
13874
|
-
exit(0);
|
|
13875
|
-
return {
|
|
13876
|
-
filesCreated: 0,
|
|
13877
|
-
filesUpdated: 0,
|
|
13878
|
-
filesDeleted: 0,
|
|
13879
|
-
notificationSent: false
|
|
13880
|
-
};
|
|
13881
|
-
}
|
|
13882
|
-
if (!configFileExists && packagesSlugs.length > 0) {
|
|
13883
|
-
log("INFO initializing packmind.json");
|
|
13884
|
-
}
|
|
13885
|
-
try {
|
|
13886
|
-
const packageCount = allPackages.length;
|
|
13887
|
-
const packageWord = packageCount === 1 ? "package" : "packages";
|
|
13888
|
-
log(
|
|
13889
|
-
`Fetching ${packageCount} ${packageWord}: ${allPackages.join(", ")}...`
|
|
13890
|
-
);
|
|
13891
|
-
let gitRemoteUrl;
|
|
13892
|
-
let gitBranch;
|
|
13893
|
-
let relativePath;
|
|
13894
|
-
const gitRoot = await packmindCliHexa.tryGetGitRepositoryRoot(cwd);
|
|
13895
|
-
if (gitRoot) {
|
|
13896
|
-
try {
|
|
13897
|
-
gitRemoteUrl = packmindCliHexa.getGitRemoteUrlFromPath(gitRoot);
|
|
13898
|
-
gitBranch = packmindCliHexa.getCurrentBranch(gitRoot);
|
|
13899
|
-
relativePath = cwd.startsWith(gitRoot) ? cwd.slice(gitRoot.length) : "/";
|
|
13900
|
-
if (!relativePath.startsWith("/")) {
|
|
13901
|
-
relativePath = "/" + relativePath;
|
|
13902
|
-
}
|
|
13903
|
-
if (!relativePath.endsWith("/")) {
|
|
13904
|
-
relativePath = relativePath + "/";
|
|
13905
|
-
}
|
|
13906
|
-
} catch {
|
|
13907
|
-
}
|
|
13908
|
-
}
|
|
13909
|
-
const result = await packmindCliHexa.installPackages({
|
|
13910
|
-
baseDirectory: cwd,
|
|
13911
|
-
packagesSlugs: allPackages,
|
|
13912
|
-
previousPackagesSlugs: normalizedConfigSlugs,
|
|
13913
|
-
// Pass previous config for change detection
|
|
13914
|
-
gitRemoteUrl,
|
|
13915
|
-
gitBranch,
|
|
13916
|
-
relativePath,
|
|
13917
|
-
agents: configAgents
|
|
13918
|
-
// Pass agents from config if present (overrides org-level)
|
|
13919
|
-
});
|
|
13920
|
-
const parts = [];
|
|
13921
|
-
if (result.recipesCount > 0) parts.push(`${result.recipesCount} commands`);
|
|
13922
|
-
if (result.standardsCount > 0)
|
|
13923
|
-
parts.push(`${result.standardsCount} standards`);
|
|
13924
|
-
if (result.skillsCount > 0) parts.push(`${result.skillsCount} skills`);
|
|
13925
|
-
log(`Installing ${parts.join(", ") || "artifacts"}...`);
|
|
13926
|
-
const skillDirsDeleted = result.skillDirectoriesDeleted || 0;
|
|
13927
|
-
const totalDeleted = result.filesDeleted + skillDirsDeleted;
|
|
13928
|
-
log(
|
|
13929
|
-
`
|
|
13930
|
-
added ${result.filesCreated} files, changed ${result.filesUpdated} files, removed ${totalDeleted} files`
|
|
13931
|
-
);
|
|
13932
|
-
if (result.errors.length > 0) {
|
|
13933
|
-
log("\n\u26A0\uFE0F Errors encountered:");
|
|
13934
|
-
result.errors.forEach((err) => {
|
|
13935
|
-
log(` - ${err}`);
|
|
13936
|
-
});
|
|
13937
|
-
exit(1);
|
|
13938
|
-
return {
|
|
13939
|
-
filesCreated: result.filesCreated,
|
|
13940
|
-
filesUpdated: result.filesUpdated,
|
|
13941
|
-
filesDeleted: totalDeleted,
|
|
13942
|
-
notificationSent: false
|
|
13943
|
-
};
|
|
13944
|
-
}
|
|
13945
|
-
const configSlugsWereNormalized = configPackages.some(
|
|
13946
|
-
(slug3, i) => slug3 !== normalizedConfigSlugs[i]
|
|
13947
|
-
);
|
|
13948
|
-
const newPackages = normalizedNewSlugs.filter(
|
|
13949
|
-
(slug3) => !normalizedConfigSlugs.includes(slug3)
|
|
13950
|
-
);
|
|
13951
|
-
if (configSlugsWereNormalized) {
|
|
13952
|
-
await packmindCliHexa.writeConfig(cwd, allPackages);
|
|
13953
|
-
} else if (newPackages.length > 0) {
|
|
13954
|
-
await packmindCliHexa.addPackagesToConfig(cwd, newPackages);
|
|
13955
|
-
}
|
|
13956
|
-
let notificationSent = false;
|
|
13957
|
-
if (result.filesCreated > 0 || result.filesUpdated > 0 || result.filesDeleted > 0 || skillDirsDeleted > 0) {
|
|
13958
|
-
notificationSent = await notifyDistributionIfInGitRepo({
|
|
13959
|
-
packmindCliHexa,
|
|
13960
|
-
cwd,
|
|
13961
|
-
packages: allPackages,
|
|
13962
|
-
agents: configAgents,
|
|
13963
|
-
log
|
|
13964
|
-
});
|
|
13965
|
-
}
|
|
13966
|
-
await installDefaultSkillsIfAtGitRoot({
|
|
13967
|
-
packmindCliHexa,
|
|
13968
|
-
cwd,
|
|
13969
|
-
log
|
|
13970
|
-
});
|
|
13971
|
-
if (deps.playbookLocalRepository) {
|
|
13972
|
-
deps.playbookLocalRepository.clearAll();
|
|
13973
|
-
}
|
|
13974
|
-
return {
|
|
13975
|
-
filesCreated: result.filesCreated,
|
|
13976
|
-
filesUpdated: result.filesUpdated,
|
|
13977
|
-
filesDeleted: totalDeleted,
|
|
13978
|
-
notificationSent
|
|
13979
|
-
};
|
|
13980
|
-
} catch (err) {
|
|
13981
|
-
error("\n\u274C Failed to install content:");
|
|
13982
|
-
if (err instanceof Error) {
|
|
13983
|
-
const errorObj = err;
|
|
13984
|
-
if (errorObj.statusCode === 400) {
|
|
13985
|
-
error(` ${errorObj.message}`);
|
|
13986
|
-
error("\n\u{1F4A1} This is a validation error. Please check:");
|
|
13987
|
-
error(" - The command syntax is correct");
|
|
13988
|
-
error(" - You have provided at least one package slug");
|
|
13989
|
-
error(" - Your packmind.json file contains valid package slugs");
|
|
13990
|
-
} else if (errorObj.statusCode === 404) {
|
|
13991
|
-
error(` ${errorObj.message}`);
|
|
13992
|
-
if (configFileExists && configPackages.length > 0) {
|
|
13993
|
-
const missingPackages = allPackages.filter(
|
|
13994
|
-
(pkg) => configPackages.includes(pkg)
|
|
13995
|
-
);
|
|
13996
|
-
if (missingPackages.length > 0) {
|
|
13997
|
-
error(
|
|
13998
|
-
"\n\u{1F4A1} Either remove the following package(s) from packmind.json:"
|
|
13999
|
-
);
|
|
14000
|
-
missingPackages.forEach((pkg) => {
|
|
14001
|
-
error(` "${pkg}"`);
|
|
14002
|
-
});
|
|
14003
|
-
error(" Or ensure that:");
|
|
14004
|
-
error(" - The package slug exists and is correctly spelled");
|
|
14005
|
-
error(" - The package exists in your organization");
|
|
14006
|
-
error(" - You have the correct API key configured");
|
|
14007
|
-
} else {
|
|
14008
|
-
error("\n\u{1F4A1} Troubleshooting tips:");
|
|
14009
|
-
error(
|
|
14010
|
-
" - Check if the package slug exists and is correctly spelled"
|
|
14011
|
-
);
|
|
14012
|
-
error(" - Check that the package exists in your organization");
|
|
14013
|
-
error(" - Ensure you have the correct API key configured");
|
|
14014
|
-
}
|
|
14015
|
-
} else {
|
|
14016
|
-
error("\n\u{1F4A1} Troubleshooting tips:");
|
|
14017
|
-
error(
|
|
14018
|
-
" - Check if the package slug exists and is correctly spelled"
|
|
14019
|
-
);
|
|
14020
|
-
error(" - Check that the package exists in your organization");
|
|
14021
|
-
error(" - Ensure you have the correct API key configured");
|
|
14022
|
-
}
|
|
14023
|
-
} else {
|
|
14024
|
-
error(` ${errorObj.message}`);
|
|
14025
|
-
const apiErrorObj = err;
|
|
14026
|
-
if (apiErrorObj.response?.data?.message) {
|
|
14027
|
-
error(`
|
|
14028
|
-
Details: ${apiErrorObj.response.data.message}`);
|
|
14029
|
-
}
|
|
14030
|
-
error("\n\u{1F4A1} Troubleshooting tips:");
|
|
14031
|
-
error(" - Verify that the package slugs are correct");
|
|
14032
|
-
error(" - Check that the packages exist in your organization");
|
|
14033
|
-
error(" - Ensure you have the correct API key configured");
|
|
14034
|
-
}
|
|
14035
|
-
} else {
|
|
14036
|
-
error(` ${String(err)}`);
|
|
14037
|
-
}
|
|
14038
|
-
exit(1);
|
|
14039
|
-
return {
|
|
14040
|
-
filesCreated: 0,
|
|
14041
|
-
filesUpdated: 0,
|
|
14042
|
-
filesDeleted: 0,
|
|
14043
|
-
notificationSent: false
|
|
14044
|
-
};
|
|
14045
|
-
}
|
|
14046
|
-
}
|
|
14047
|
-
async function uninstallPackagesHandler(args2, deps) {
|
|
14048
|
-
const { packmindCliHexa, exit, getCwd, log, error } = deps;
|
|
14049
|
-
const { packagesSlugs } = args2;
|
|
14050
|
-
const cwd = getCwd();
|
|
14051
|
-
if (!packagesSlugs || packagesSlugs.length === 0) {
|
|
14052
|
-
error("\u274C No packages specified.");
|
|
14053
|
-
log("");
|
|
14054
|
-
log("Usage: packmind-cli uninstall <package-slug> [package-slug...]");
|
|
14055
|
-
log(" packmind-cli remove <package-slug> [package-slug...]");
|
|
14056
|
-
log("");
|
|
14057
|
-
log("Examples:");
|
|
14058
|
-
log(" packmind-cli uninstall backend");
|
|
14059
|
-
log(" packmind-cli remove backend frontend");
|
|
14060
|
-
exit(1);
|
|
14061
|
-
return {
|
|
14062
|
-
filesDeleted: 0,
|
|
14063
|
-
packagesUninstalled: []
|
|
14064
|
-
};
|
|
14065
|
-
}
|
|
14066
|
-
let configPackages;
|
|
14067
|
-
let configAgents;
|
|
14068
|
-
let configFileExists = false;
|
|
14069
|
-
try {
|
|
14070
|
-
configFileExists = await packmindCliHexa.configExists(cwd);
|
|
14071
|
-
const fullConfig = await packmindCliHexa.readFullConfig(cwd);
|
|
14072
|
-
if (fullConfig) {
|
|
14073
|
-
configPackages = fullConfig.packages;
|
|
14074
|
-
configAgents = fullConfig.agents;
|
|
14075
|
-
} else {
|
|
14076
|
-
configPackages = {};
|
|
14077
|
-
}
|
|
14078
|
-
} catch (err) {
|
|
14079
|
-
error("\u274C Failed to read packmind.json");
|
|
14080
|
-
if (err instanceof Error) {
|
|
14081
|
-
error(` ${err.message}`);
|
|
14082
|
-
} else {
|
|
14083
|
-
error(` ${String(err)}`);
|
|
14084
|
-
}
|
|
14085
|
-
error("\n\u{1F4A1} Please fix the packmind.json file or delete it to continue.");
|
|
14086
|
-
exit(1);
|
|
14087
|
-
return {
|
|
14088
|
-
filesDeleted: 0,
|
|
14089
|
-
packagesUninstalled: []
|
|
14090
|
-
};
|
|
14091
|
-
}
|
|
14092
|
-
if (Object.keys(configPackages).length === 0) {
|
|
14093
|
-
if (configFileExists) {
|
|
14094
|
-
error("\u274C packmind.json is empty.");
|
|
14095
|
-
} else {
|
|
14096
|
-
error("\u274C No packmind.json found in current directory.");
|
|
14097
|
-
}
|
|
14098
|
-
log("");
|
|
14099
|
-
log("\u{1F4A1} There are no packages to uninstall.");
|
|
14100
|
-
log(" To install packages, run: packmind-cli install <package-slug>");
|
|
14101
|
-
exit(1);
|
|
14102
|
-
return {
|
|
14103
|
-
filesDeleted: 0,
|
|
14104
|
-
packagesUninstalled: []
|
|
14105
|
-
};
|
|
14106
|
-
}
|
|
14107
|
-
let normalizedRequestedSlugs;
|
|
14108
|
-
let normalizedConfigSlugs;
|
|
14109
|
-
try {
|
|
14110
|
-
normalizedRequestedSlugs = await packmindCliHexa.normalizePackageSlugs(packagesSlugs);
|
|
14111
|
-
normalizedConfigSlugs = await packmindCliHexa.normalizePackageSlugs(
|
|
14112
|
-
Object.keys(configPackages)
|
|
14113
|
-
);
|
|
14114
|
-
} catch (err) {
|
|
14115
|
-
error(`\u274C ${err instanceof Error ? err.message : String(err)}`);
|
|
14116
|
-
exit(1);
|
|
14117
|
-
return {
|
|
14118
|
-
filesDeleted: 0,
|
|
14119
|
-
packagesUninstalled: []
|
|
14120
|
-
};
|
|
14121
|
-
}
|
|
14122
|
-
const normalizedToOriginalConfigKey = /* @__PURE__ */ new Map();
|
|
14123
|
-
Object.keys(configPackages).forEach((originalKey, index) => {
|
|
14124
|
-
normalizedToOriginalConfigKey.set(
|
|
14125
|
-
normalizedConfigSlugs[index],
|
|
14126
|
-
originalKey
|
|
14127
|
-
);
|
|
14128
|
-
});
|
|
14129
|
-
const packagesToUninstall = normalizedRequestedSlugs.filter((slug3) => normalizedToOriginalConfigKey.has(slug3)).map((slug3) => normalizedToOriginalConfigKey.get(slug3));
|
|
14130
|
-
const notInstalledPackages = packagesSlugs.filter(
|
|
14131
|
-
(_, i) => !normalizedToOriginalConfigKey.has(normalizedRequestedSlugs[i])
|
|
14132
|
-
);
|
|
14133
|
-
if (notInstalledPackages.length > 0) {
|
|
14134
|
-
const packageWord = notInstalledPackages.length === 1 ? "package" : "packages";
|
|
14135
|
-
log(
|
|
14136
|
-
`\u26A0\uFE0F Warning: The following ${packageWord} ${notInstalledPackages.length === 1 ? "is" : "are"} not installed:`
|
|
14137
|
-
);
|
|
14138
|
-
notInstalledPackages.forEach((pkg) => {
|
|
14139
|
-
log(` - ${pkg}`);
|
|
14140
|
-
});
|
|
14141
|
-
log("");
|
|
14142
|
-
}
|
|
14143
|
-
if (packagesToUninstall.length === 0) {
|
|
14144
|
-
error("\u274C No packages to uninstall.");
|
|
14145
|
-
exit(1);
|
|
14146
|
-
return {
|
|
14147
|
-
filesDeleted: 0,
|
|
14148
|
-
packagesUninstalled: []
|
|
14149
|
-
};
|
|
14150
|
-
}
|
|
14151
|
-
try {
|
|
14152
|
-
const packageCount = packagesToUninstall.length;
|
|
14153
|
-
const packageWord = packageCount === 1 ? "package" : "packages";
|
|
14154
|
-
log(
|
|
14155
|
-
`Uninstalling ${packageCount} ${packageWord}: ${packagesToUninstall.join(", ")}...`
|
|
14156
|
-
);
|
|
14157
|
-
const remainingPackages = Object.keys(configPackages).filter(
|
|
14158
|
-
(pkg) => !packagesToUninstall.includes(pkg)
|
|
14159
|
-
);
|
|
14160
|
-
let filesDeleted = 0;
|
|
14161
|
-
if (remainingPackages.length === 0) {
|
|
14162
|
-
log("Removing all packages and cleaning up...");
|
|
14163
|
-
const result = await packmindCliHexa.installPackages({
|
|
14164
|
-
baseDirectory: cwd,
|
|
14165
|
-
packagesSlugs: [],
|
|
14166
|
-
previousPackagesSlugs: Object.keys(configPackages),
|
|
14167
|
-
agents: configAgents
|
|
14168
|
-
});
|
|
14169
|
-
log(`
|
|
14170
|
-
removed ${result.filesDeleted} files`);
|
|
14171
|
-
if (result.errors.length > 0) {
|
|
14172
|
-
log("\n\u26A0\uFE0F Errors encountered:");
|
|
14173
|
-
result.errors.forEach((err) => {
|
|
14174
|
-
log(` - ${err}`);
|
|
14175
|
-
});
|
|
14176
|
-
exit(1);
|
|
14177
|
-
return {
|
|
14178
|
-
filesDeleted: result.filesDeleted,
|
|
14179
|
-
packagesUninstalled: packagesToUninstall
|
|
14180
|
-
};
|
|
14181
|
-
}
|
|
14182
|
-
filesDeleted = result.filesDeleted;
|
|
14183
|
-
} else {
|
|
14184
|
-
const result = await packmindCliHexa.installPackages({
|
|
14185
|
-
baseDirectory: cwd,
|
|
14186
|
-
packagesSlugs: remainingPackages,
|
|
14187
|
-
previousPackagesSlugs: Object.keys(configPackages),
|
|
14188
|
-
agents: configAgents
|
|
14189
|
-
});
|
|
14190
|
-
if (result.recipesCount > 0 || result.standardsCount > 0) {
|
|
14191
|
-
log(
|
|
14192
|
-
`Removing ${result.recipesCount} commands and ${result.standardsCount} standards...`
|
|
14193
|
-
);
|
|
14194
|
-
}
|
|
14195
|
-
log(`
|
|
14196
|
-
removed ${result.filesDeleted} files`);
|
|
14197
|
-
if (result.errors.length > 0) {
|
|
14198
|
-
log("\n\u26A0\uFE0F Errors encountered:");
|
|
14199
|
-
result.errors.forEach((err) => {
|
|
14200
|
-
log(` - ${err}`);
|
|
14201
|
-
});
|
|
14202
|
-
exit(1);
|
|
14203
|
-
return {
|
|
14204
|
-
filesDeleted: result.filesDeleted,
|
|
14205
|
-
packagesUninstalled: packagesToUninstall
|
|
14206
|
-
};
|
|
14207
|
-
}
|
|
14208
|
-
filesDeleted = result.filesDeleted;
|
|
14209
|
-
}
|
|
14210
|
-
await packmindCliHexa.writeConfig(cwd, remainingPackages);
|
|
14211
|
-
await notifyDistributionIfInGitRepo({
|
|
14212
|
-
packmindCliHexa,
|
|
14213
|
-
cwd,
|
|
14214
|
-
packages: remainingPackages,
|
|
14215
|
-
log
|
|
14216
|
-
});
|
|
14217
|
-
log("");
|
|
14218
|
-
if (packagesToUninstall.length === 1) {
|
|
14219
|
-
log(`\u2713 Package '${packagesToUninstall[0]}' has been uninstalled.`);
|
|
14220
|
-
} else {
|
|
14221
|
-
log(`\u2713 ${packagesToUninstall.length} packages have been uninstalled.`);
|
|
14222
|
-
}
|
|
14223
|
-
if (remainingPackages.length === 0) {
|
|
14224
|
-
log("");
|
|
14225
|
-
log("\u{1F4A1} All packages have been uninstalled.");
|
|
14226
|
-
log(" Your packmind.json still exists but contains no packages.");
|
|
14227
|
-
}
|
|
14228
|
-
return {
|
|
14229
|
-
filesDeleted,
|
|
14230
|
-
packagesUninstalled: packagesToUninstall
|
|
14231
|
-
};
|
|
14232
|
-
} catch (err) {
|
|
14233
|
-
error("\n\u274C Failed to uninstall packages:");
|
|
14234
|
-
if (err instanceof Error) {
|
|
14235
|
-
error(` ${err.message}`);
|
|
14236
|
-
} else {
|
|
14237
|
-
error(` ${String(err)}`);
|
|
14238
|
-
}
|
|
14239
|
-
exit(1);
|
|
14240
|
-
return {
|
|
14241
|
-
filesDeleted: 0,
|
|
14242
|
-
packagesUninstalled: []
|
|
14243
|
-
};
|
|
14244
|
-
}
|
|
14245
|
-
}
|
|
14246
|
-
async function recursiveInstallHandler(args2, deps) {
|
|
14247
|
-
const { packmindCliHexa, exit, getCwd, log, error } = deps;
|
|
14248
|
-
const cwd = getCwd();
|
|
14249
|
-
const result = {
|
|
14250
|
-
directoriesProcessed: 0,
|
|
14251
|
-
totalFilesCreated: 0,
|
|
14252
|
-
totalFilesUpdated: 0,
|
|
14253
|
-
totalFilesDeleted: 0,
|
|
14254
|
-
totalNotifications: 0,
|
|
14255
|
-
errors: []
|
|
14256
|
-
};
|
|
14257
|
-
let startDirectory = cwd;
|
|
14258
|
-
if (args2.path) {
|
|
14259
|
-
const resolvedPath = path19.resolve(cwd, args2.path);
|
|
14260
|
-
try {
|
|
14261
|
-
const stat9 = await fs17.stat(resolvedPath);
|
|
14262
|
-
if (!stat9.isDirectory()) {
|
|
14263
|
-
logErrorConsole(`Path is not a directory: ${resolvedPath}`);
|
|
14264
|
-
exit(1);
|
|
14265
|
-
return result;
|
|
14266
|
-
}
|
|
14267
|
-
startDirectory = resolvedPath;
|
|
14268
|
-
} catch {
|
|
14269
|
-
logErrorConsole(`Path does not exist: ${resolvedPath}`);
|
|
14270
|
-
exit(1);
|
|
14271
|
-
return result;
|
|
14272
|
-
}
|
|
14273
|
-
}
|
|
14274
|
-
try {
|
|
14275
|
-
const gitRoot = await packmindCliHexa.tryGetGitRepositoryRoot(cwd);
|
|
14276
|
-
const basePath = args2.path ? startDirectory : gitRoot ?? cwd;
|
|
14277
|
-
const allConfigs = await packmindCliHexa.findAllConfigsInTree(
|
|
14278
|
-
startDirectory,
|
|
14279
|
-
basePath
|
|
14280
|
-
);
|
|
14281
|
-
if (!allConfigs.hasConfigs) {
|
|
14282
|
-
log("No packmind.json files found in this repository.");
|
|
14283
|
-
log("");
|
|
14284
|
-
log("Usage: packmind-cli install");
|
|
14285
|
-
log("");
|
|
14286
|
-
log(
|
|
14287
|
-
"This command requires at least one packmind.json file in the repository."
|
|
14288
|
-
);
|
|
14289
|
-
log("Create a packmind.json file first:");
|
|
14290
|
-
log("");
|
|
14291
|
-
log(" packmind-cli install <package-slug>");
|
|
14292
|
-
exit(0);
|
|
14293
|
-
return result;
|
|
14294
|
-
}
|
|
14295
|
-
const sortedConfigs = [...allConfigs.configs].sort(
|
|
14296
|
-
(a, b) => a.targetPath.localeCompare(b.targetPath)
|
|
14297
|
-
);
|
|
14298
|
-
log(`Found ${sortedConfigs.length} packmind.json file(s) to process
|
|
14299
|
-
`);
|
|
14300
|
-
for (const config of sortedConfigs) {
|
|
14301
|
-
const displayPath = args2.path ? computeDisplayPath(
|
|
14302
|
-
config.absoluteTargetPath === cwd ? "/" : config.absoluteTargetPath.startsWith(cwd + "/") ? config.absoluteTargetPath.slice(cwd.length) : config.targetPath
|
|
14303
|
-
) : computeDisplayPath(config.targetPath);
|
|
14304
|
-
log(`Installing in ${displayPath}...`);
|
|
14305
|
-
const installResult = await executeInstallForDirectory(
|
|
14306
|
-
config.absoluteTargetPath,
|
|
14307
|
-
{ packmindCliHexa, getCwd, log, error }
|
|
14308
|
-
);
|
|
14309
|
-
result.directoriesProcessed++;
|
|
14310
|
-
result.totalFilesCreated += installResult.filesCreated;
|
|
14311
|
-
result.totalFilesUpdated += installResult.filesUpdated;
|
|
14312
|
-
result.totalFilesDeleted += installResult.filesDeleted;
|
|
14313
|
-
if (installResult.notificationSent) {
|
|
14314
|
-
result.totalNotifications++;
|
|
14315
|
-
}
|
|
14316
|
-
if (!installResult.success && installResult.errorMessage) {
|
|
14317
|
-
result.errors.push({
|
|
14318
|
-
directory: displayPath,
|
|
14319
|
-
message: installResult.errorMessage
|
|
14320
|
-
});
|
|
14321
|
-
error(` Error: ${installResult.errorMessage}`);
|
|
14322
|
-
}
|
|
14323
|
-
log("");
|
|
14324
|
-
}
|
|
14325
|
-
const dirWord = result.directoriesProcessed === 1 ? "directory" : "directories";
|
|
14326
|
-
log(
|
|
14327
|
-
`Summary: ${result.directoriesProcessed} ${dirWord} processed, ${result.totalFilesCreated} files added, ${result.totalFilesUpdated} changed, ${result.totalFilesDeleted} removed`
|
|
14328
|
-
);
|
|
14329
|
-
if (result.totalNotifications > 0) {
|
|
14330
|
-
const distWord = result.totalNotifications === 1 ? "distribution" : "distributions";
|
|
14331
|
-
log(`Notified Packmind of ${result.totalNotifications} ${distWord}`);
|
|
14332
|
-
}
|
|
14333
|
-
if (result.errors.length > 0) {
|
|
14334
|
-
log("");
|
|
14335
|
-
log(`\u26A0\uFE0F ${result.errors.length} error(s) encountered:`);
|
|
14336
|
-
result.errors.forEach((err) => {
|
|
14337
|
-
log(` - ${err.directory}: ${err.message}`);
|
|
14338
|
-
});
|
|
14339
|
-
exit(1);
|
|
14340
|
-
return result;
|
|
14341
|
-
}
|
|
14342
|
-
if (deps.playbookLocalRepository) {
|
|
14343
|
-
deps.playbookLocalRepository.clearAll();
|
|
14344
|
-
}
|
|
14345
|
-
exit(0);
|
|
14346
|
-
return result;
|
|
14347
|
-
} catch (err) {
|
|
14348
|
-
error("\n\u274C Failed to run recursive install:");
|
|
14349
|
-
if (err instanceof Error) {
|
|
14350
|
-
error(` ${err.message}`);
|
|
14351
|
-
} else {
|
|
14352
|
-
error(` ${String(err)}`);
|
|
14353
|
-
}
|
|
14354
|
-
exit(1);
|
|
14355
|
-
return result;
|
|
14356
|
-
}
|
|
14357
|
-
}
|
|
14358
|
-
|
|
14359
|
-
// apps/cli/src/infra/utils/spaceFilterUtils.ts
|
|
14360
|
-
function resolveSpaceFromArgs(spaceArg, spaces) {
|
|
14361
|
-
if (!spaceArg) return null;
|
|
14362
|
-
const slug3 = spaceArg.startsWith("@") ? spaceArg.slice(1) : spaceArg;
|
|
14363
|
-
return spaces.find((s) => s.slug === slug3) ?? null;
|
|
14364
|
-
}
|
|
14365
|
-
|
|
14366
|
-
// apps/cli/src/infra/utils/urlBuilderUtils.ts
|
|
14367
|
-
function resolveUrlBuilder(buildArtifactPath) {
|
|
14368
|
-
const apiKey = loadApiKey();
|
|
14369
|
-
if (!apiKey) return () => null;
|
|
14370
|
-
const decoded = decodeApiKey(apiKey);
|
|
14371
|
-
const orgSlug = decoded?.jwt?.organization?.slug;
|
|
14372
|
-
if (!decoded?.host || !orgSlug) return () => null;
|
|
14373
|
-
return (spaceSlug, artifactId) => `${decoded.host}/org/${orgSlug}/space/${spaceSlug}/${buildArtifactPath(artifactId)}`;
|
|
14374
|
-
}
|
|
14375
|
-
|
|
14376
|
-
// apps/cli/src/infra/commands/packages/listPackagesHandler.ts
|
|
14377
|
-
function logPackageEntry(pkg, fullSlug, spaceSlug, buildUrl) {
|
|
14378
|
-
logConsole(`- ${formatSlug(fullSlug)}`);
|
|
14379
|
-
logConsole(` ${formatLabel("Name:")} ${pkg.name}`);
|
|
14380
|
-
const url = buildUrl(spaceSlug, pkg.id);
|
|
14381
|
-
if (url) {
|
|
14382
|
-
logConsole(` ${formatLabel("Link:")} ${url}`);
|
|
14383
|
-
}
|
|
14384
|
-
if (pkg.description) {
|
|
14385
|
-
const lines = pkg.description.trim().split("\n").map((l) => l.trim()).filter((l) => l.length > 0);
|
|
14386
|
-
const [first, ...rest] = lines;
|
|
14387
|
-
logConsole(` ${formatLabel("Description:")} ${first}`);
|
|
14388
|
-
rest.forEach((l) => logConsole(` ${l}`));
|
|
14389
|
-
}
|
|
14390
|
-
}
|
|
14391
|
-
function groupPackagesBySpace(packages, spaces) {
|
|
14392
|
-
const spaceMap = new Map(
|
|
14393
|
-
spaces.map((s) => [s.id, s])
|
|
14394
|
-
);
|
|
14395
|
-
const groupsMap = /* @__PURE__ */ new Map();
|
|
14396
|
-
for (const pkg of packages) {
|
|
14397
|
-
const space = spaceMap.get(pkg.spaceId);
|
|
14398
|
-
if (!space) {
|
|
14399
|
-
continue;
|
|
14400
|
-
}
|
|
14401
|
-
let group = groupsMap.get(space.id);
|
|
14402
|
-
if (!group) {
|
|
14403
|
-
group = { space, pkgs: [] };
|
|
14404
|
-
groupsMap.set(space.id, group);
|
|
14405
|
-
}
|
|
14406
|
-
group.pkgs.push(pkg);
|
|
14551
|
+
if (list) {
|
|
14552
|
+
logErrorConsole('Command "packmind-cli install --list" has been removed.');
|
|
14553
|
+
logConsole(`Use ${formatCommand("packmind-cli packages list")} instead.`);
|
|
14554
|
+
process.exit(1);
|
|
14407
14555
|
}
|
|
14408
|
-
|
|
14409
|
-
|
|
14410
|
-
|
|
14411
|
-
}
|
|
14412
|
-
|
|
14413
|
-
const groups = groupPackagesBySpace(packages, spaces);
|
|
14414
|
-
let firstSlug = null;
|
|
14415
|
-
for (const { space, pkgs } of groups) {
|
|
14416
|
-
logConsole(`Space "${space.name}":
|
|
14417
|
-
`);
|
|
14418
|
-
for (const pkg of [...pkgs].sort((a, b) => a.slug.localeCompare(b.slug))) {
|
|
14419
|
-
const fullSlug = `@${space.slug}/${pkg.slug}`;
|
|
14420
|
-
firstSlug ??= fullSlug;
|
|
14421
|
-
logPackageEntry(pkg, fullSlug, space.slug, buildUrl);
|
|
14422
|
-
logConsole("");
|
|
14423
|
-
}
|
|
14556
|
+
if (show) {
|
|
14557
|
+
const showCommand = `packmind-cli packages show ${show}`;
|
|
14558
|
+
logErrorConsole('Command "packmind-cli install --show" has been removed.');
|
|
14559
|
+
logConsole(`Use ${formatCommand(showCommand)} instead.`);
|
|
14560
|
+
process.exit(1);
|
|
14424
14561
|
}
|
|
14425
|
-
|
|
14426
|
-
|
|
14427
|
-
|
|
14428
|
-
|
|
14429
|
-
|
|
14430
|
-
logInfoConsole("Fetching available packages...");
|
|
14431
|
-
const allSpaces = await packmindCliHexa.getSpaces();
|
|
14432
|
-
if (!allSpaces || allSpaces.length === 0) {
|
|
14433
|
-
throw new Error("Unable to list organization spaces.");
|
|
14434
|
-
}
|
|
14435
|
-
const matchedSpace = resolveSpaceFromArgs(args2.space, allSpaces);
|
|
14436
|
-
if (args2.space && !matchedSpace) {
|
|
14437
|
-
logErrorConsole(`Space "@${args2.space}" not found.`);
|
|
14438
|
-
logInfoConsole(
|
|
14439
|
-
`Available spaces: ${allSpaces.map((s) => `@${s.slug}`).join(", ")}`
|
|
14440
|
-
);
|
|
14441
|
-
exit(1);
|
|
14562
|
+
const cwd = installPath ? path20.resolve(process.cwd(), installPath) : process.cwd();
|
|
14563
|
+
if (installPath) {
|
|
14564
|
+
if (!fs18.existsSync(cwd)) {
|
|
14565
|
+
logErrorConsole(`Path does not exist: ${cwd}`);
|
|
14566
|
+
process.exit(1);
|
|
14442
14567
|
return;
|
|
14443
14568
|
}
|
|
14444
|
-
|
|
14445
|
-
|
|
14446
|
-
|
|
14447
|
-
const spaces = matchedSpace ? [matchedSpace] : allSpaces;
|
|
14448
|
-
if (packages.length === 0) {
|
|
14449
|
-
logConsole(
|
|
14450
|
-
matchedSpace ? `No packages found in space "@${matchedSpace.slug}".` : "No packages found."
|
|
14451
|
-
);
|
|
14452
|
-
exit(0);
|
|
14569
|
+
if (!fs18.statSync(cwd).isDirectory()) {
|
|
14570
|
+
logErrorConsole(`Path is not a directory: ${cwd}`);
|
|
14571
|
+
process.exit(1);
|
|
14453
14572
|
return;
|
|
14454
14573
|
}
|
|
14455
|
-
const buildUrl = resolveUrlBuilder((id) => `packages/${id}`);
|
|
14456
|
-
logConsole("\nAvailable packages:\n");
|
|
14457
|
-
const exampleSlug = displayGroupedPackages(packages, spaces, buildUrl);
|
|
14458
|
-
logConsole("How to install a package:\n");
|
|
14459
|
-
logConsole(` ${formatCommand(`packmind-cli install ${exampleSlug}`)}`);
|
|
14460
|
-
exit(0);
|
|
14461
|
-
} catch (err) {
|
|
14462
|
-
logErrorConsole("Failed to list packages:");
|
|
14463
|
-
if (err instanceof Error) {
|
|
14464
|
-
logErrorConsole(err.message);
|
|
14465
|
-
} else {
|
|
14466
|
-
logErrorConsole(String(err));
|
|
14467
|
-
}
|
|
14468
|
-
exit(1);
|
|
14469
|
-
}
|
|
14470
|
-
}
|
|
14471
|
-
|
|
14472
|
-
// apps/cli/src/infra/utils/packageSlugUtils.ts
|
|
14473
|
-
function parsePackageSlug(slug3) {
|
|
14474
|
-
if (!slug3.startsWith("@")) return null;
|
|
14475
|
-
const slash = slug3.indexOf("/", 1);
|
|
14476
|
-
if (slash === -1) return null;
|
|
14477
|
-
return { spaceSlug: slug3.slice(1, slash), pkgSlug: slug3.slice(slash + 1) };
|
|
14478
|
-
}
|
|
14479
|
-
|
|
14480
|
-
// apps/cli/src/infra/commands/packages/showPackageHandler.ts
|
|
14481
|
-
function isNotFoundError(err) {
|
|
14482
|
-
return err instanceof Error && err.message.includes("does not exist");
|
|
14483
|
-
}
|
|
14484
|
-
async function resolvePackage(slug3, packmindCliHexa) {
|
|
14485
|
-
const allSpaces = await packmindCliHexa.getSpaces();
|
|
14486
|
-
const parsed = parsePackageSlug(slug3);
|
|
14487
|
-
if (parsed) {
|
|
14488
|
-
const { spaceSlug, pkgSlug } = parsed;
|
|
14489
|
-
const matchedSpace = allSpaces.find((s) => s.slug === spaceSlug);
|
|
14490
|
-
if (!matchedSpace) {
|
|
14491
|
-
throw new Error(`Space '@${spaceSlug}' not found.`);
|
|
14492
|
-
}
|
|
14493
|
-
let pkg;
|
|
14494
|
-
try {
|
|
14495
|
-
pkg = await packmindCliHexa.getPackageBySlug({
|
|
14496
|
-
slug: pkgSlug,
|
|
14497
|
-
spaceId: matchedSpace.id
|
|
14498
|
-
});
|
|
14499
|
-
} catch (err) {
|
|
14500
|
-
if (isNotFoundError(err)) {
|
|
14501
|
-
throw new Error(
|
|
14502
|
-
`Package '${pkgSlug}' not found in space '@${spaceSlug}'.`
|
|
14503
|
-
);
|
|
14504
|
-
}
|
|
14505
|
-
throw err;
|
|
14506
|
-
}
|
|
14507
|
-
return { pkg, fullSlug: `@${spaceSlug}/${pkgSlug}` };
|
|
14508
14574
|
}
|
|
14509
|
-
|
|
14510
|
-
|
|
14511
|
-
|
|
14512
|
-
|
|
14513
|
-
|
|
14514
|
-
|
|
14515
|
-
|
|
14516
|
-
|
|
14517
|
-
|
|
14518
|
-
const matches = results.filter(
|
|
14519
|
-
(r) => r.status === "fulfilled"
|
|
14520
|
-
).map((r) => r.value);
|
|
14521
|
-
if (matches.length === 0) {
|
|
14522
|
-
const realError = results.filter((r) => r.status === "rejected").find((r) => !isNotFoundError(r.reason));
|
|
14523
|
-
if (realError) {
|
|
14524
|
-
throw realError.reason;
|
|
14575
|
+
let targetDirs;
|
|
14576
|
+
if (installPath) {
|
|
14577
|
+
targetDirs = findSubDirectoriesWithPackmindJson(cwd, false);
|
|
14578
|
+
} else if (packages.length > 0) {
|
|
14579
|
+
targetDirs = [cwd];
|
|
14580
|
+
} else {
|
|
14581
|
+
targetDirs = [];
|
|
14582
|
+
if (fs18.existsSync(path20.join(cwd, "packmind.json"))) {
|
|
14583
|
+
targetDirs.push(cwd);
|
|
14525
14584
|
}
|
|
14526
|
-
|
|
14585
|
+
targetDirs.push(...findSubDirectoriesWithPackmindJson(cwd, true));
|
|
14527
14586
|
}
|
|
14528
|
-
if (
|
|
14529
|
-
|
|
14530
|
-
throw new Error(
|
|
14531
|
-
`Package '${slug3}' exists in multiple spaces (${matches.map((m) => `@${m.spaceSlug}`).join(", ")}). Please specify the space using the @space/package format (e.g. ${example}).`
|
|
14532
|
-
);
|
|
14587
|
+
if (targetDirs.length === 0) {
|
|
14588
|
+
targetDirs = [cwd];
|
|
14533
14589
|
}
|
|
14534
|
-
|
|
14535
|
-
|
|
14536
|
-
|
|
14537
|
-
|
|
14538
|
-
|
|
14539
|
-
|
|
14540
|
-
|
|
14541
|
-
|
|
14542
|
-
logInfoConsole(`Fetching package details for '${args2.slug}'...`);
|
|
14543
|
-
const { pkg, fullSlug } = await resolvePackage(args2.slug, packmindCliHexa);
|
|
14544
|
-
logConsole(`
|
|
14545
|
-
${pkg.name} (${fullSlug}):
|
|
14546
|
-
`);
|
|
14547
|
-
if (pkg.description) {
|
|
14548
|
-
logConsole(`${pkg.description}
|
|
14549
|
-
`);
|
|
14550
|
-
}
|
|
14551
|
-
if (pkg.standards && pkg.standards.length > 0) {
|
|
14552
|
-
logConsole("Standards:");
|
|
14553
|
-
pkg.standards.forEach((standard) => {
|
|
14554
|
-
if (standard.summary) {
|
|
14555
|
-
logConsole(` - ${standard.name}: ${standard.summary}`);
|
|
14556
|
-
} else {
|
|
14557
|
-
logConsole(` - ${standard.name}`);
|
|
14558
|
-
}
|
|
14559
|
-
});
|
|
14560
|
-
logConsole("");
|
|
14561
|
-
}
|
|
14562
|
-
if (pkg.recipes && pkg.recipes.length > 0) {
|
|
14563
|
-
logConsole("Commands:");
|
|
14564
|
-
pkg.recipes.forEach((recipe) => {
|
|
14565
|
-
if (recipe.summary) {
|
|
14566
|
-
logConsole(` - ${recipe.name}: ${recipe.summary}`);
|
|
14567
|
-
} else {
|
|
14568
|
-
logConsole(` - ${recipe.name}`);
|
|
14569
|
-
}
|
|
14590
|
+
const results = [];
|
|
14591
|
+
const thrownErrors = [];
|
|
14592
|
+
const multiDir = targetDirs.length > 1;
|
|
14593
|
+
for (const dir of targetDirs) {
|
|
14594
|
+
try {
|
|
14595
|
+
const result = await packmindCliHexa.install({
|
|
14596
|
+
baseDirectory: dir,
|
|
14597
|
+
packages: packages.length > 0 ? packages : void 0
|
|
14570
14598
|
});
|
|
14571
|
-
|
|
14572
|
-
|
|
14573
|
-
|
|
14574
|
-
|
|
14575
|
-
pkg.skills.forEach((skill) => {
|
|
14576
|
-
if (skill.summary) {
|
|
14577
|
-
logConsole(` - ${skill.name}: ${skill.summary}`);
|
|
14578
|
-
} else {
|
|
14579
|
-
logConsole(` - ${skill.name}`);
|
|
14580
|
-
}
|
|
14599
|
+
results.push(result);
|
|
14600
|
+
await notifyArtefactsDistributionIfInGitRepo({
|
|
14601
|
+
packmindCliHexa,
|
|
14602
|
+
dir
|
|
14581
14603
|
});
|
|
14582
|
-
|
|
14583
|
-
|
|
14584
|
-
|
|
14585
|
-
|
|
14586
|
-
|
|
14587
|
-
if (err instanceof Error) {
|
|
14588
|
-
logErrorConsole(err.message);
|
|
14589
|
-
} else {
|
|
14590
|
-
logErrorConsole(String(err));
|
|
14604
|
+
} catch (error) {
|
|
14605
|
+
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
14606
|
+
thrownErrors.push(
|
|
14607
|
+
multiDir ? `[${dir}] install failed: ${errorMessage}` : `install failed: ${errorMessage}`
|
|
14608
|
+
);
|
|
14591
14609
|
}
|
|
14592
|
-
exit(1);
|
|
14593
14610
|
}
|
|
14594
|
-
|
|
14611
|
+
const combined = mergeInstallResults(results);
|
|
14612
|
+
if (combined.missingAccess.length > 0) {
|
|
14613
|
+
let warning = `\u26A0\uFE0F You don't have access to the following packages (their artifacts were preserved from the lock file):
|
|
14614
|
+
` + combined.missingAccess.map((s) => ` - ${s}`).join("\n");
|
|
14615
|
+
if (combined.joinSpaceUrl) {
|
|
14616
|
+
warning += `
|
|
14595
14617
|
|
|
14596
|
-
|
|
14597
|
-
var crypto = __toESM(require("crypto"));
|
|
14598
|
-
var fs18 = __toESM(require("fs"));
|
|
14599
|
-
var os4 = __toESM(require("os"));
|
|
14600
|
-
var path20 = __toESM(require("path"));
|
|
14601
|
-
var yaml = __toESM(require("yaml"));
|
|
14602
|
-
var PlaybookLocalRepository = class {
|
|
14603
|
-
constructor(repoRoot) {
|
|
14604
|
-
const normalized = this.normalizeRepoRoot(repoRoot);
|
|
14605
|
-
const hash = crypto.createHash("md5").update(normalized).digest("hex");
|
|
14606
|
-
this.storagePath = path20.join(
|
|
14607
|
-
os4.homedir(),
|
|
14608
|
-
".packmind",
|
|
14609
|
-
hash,
|
|
14610
|
-
"playbook.yaml"
|
|
14611
|
-
);
|
|
14612
|
-
}
|
|
14613
|
-
addChange(entry) {
|
|
14614
|
-
const data = this.readYaml();
|
|
14615
|
-
const existingIndex = data.changes.findIndex(
|
|
14616
|
-
(c) => c.filePath === entry.filePath && c.spaceId === entry.spaceId
|
|
14617
|
-
);
|
|
14618
|
-
if (existingIndex >= 0) {
|
|
14619
|
-
data.changes[existingIndex] = entry;
|
|
14620
|
-
} else {
|
|
14621
|
-
data.changes.push(entry);
|
|
14618
|
+
\u{1F449} Join the space to get access: ${combined.joinSpaceUrl}`;
|
|
14622
14619
|
}
|
|
14623
|
-
|
|
14620
|
+
logWarningConsole(warning);
|
|
14624
14621
|
}
|
|
14625
|
-
|
|
14626
|
-
|
|
14627
|
-
|
|
14628
|
-
|
|
14629
|
-
|
|
14630
|
-
);
|
|
14631
|
-
if (data.changes.length === initialLength) {
|
|
14632
|
-
return false;
|
|
14633
|
-
}
|
|
14634
|
-
this.writeYaml(data);
|
|
14635
|
-
return true;
|
|
14636
|
-
}
|
|
14637
|
-
getChanges() {
|
|
14638
|
-
return this.readYaml().changes;
|
|
14622
|
+
logConsole(buildInstallSummary(combined));
|
|
14623
|
+
await installDefaultSkillsIfAtGitRoot({ packmindCliHexa, cwd });
|
|
14624
|
+
const allErrors = [...combined.errors, ...thrownErrors];
|
|
14625
|
+
if (allErrors.length > 0) {
|
|
14626
|
+
logWarningConsole(`Encountered ${allErrors.length} error(s):`);
|
|
14627
|
+
allErrors.forEach((err) => logErrorConsole(` - ${err}`));
|
|
14639
14628
|
}
|
|
14640
|
-
|
|
14641
|
-
|
|
14642
|
-
(c) => c.filePath === filePath && c.spaceId === spaceId
|
|
14643
|
-
) ?? null;
|
|
14644
|
-
}
|
|
14645
|
-
clearAll() {
|
|
14646
|
-
this.writeYaml({ version: 1, changes: [] });
|
|
14647
|
-
}
|
|
14648
|
-
normalizeRepoRoot(repoRoot) {
|
|
14649
|
-
let normalized = repoRoot.replace(/\\/g, "/");
|
|
14650
|
-
normalized = normalized.replace(/\/$/, "");
|
|
14651
|
-
return normalized;
|
|
14652
|
-
}
|
|
14653
|
-
readYaml() {
|
|
14654
|
-
if (!fs18.existsSync(this.storagePath)) {
|
|
14655
|
-
return { version: 1, changes: [] };
|
|
14656
|
-
}
|
|
14657
|
-
try {
|
|
14658
|
-
const content = fs18.readFileSync(this.storagePath, "utf-8");
|
|
14659
|
-
const parsed = yaml.parse(content);
|
|
14660
|
-
if (!parsed || !Array.isArray(parsed.changes)) {
|
|
14661
|
-
return { version: 1, changes: [] };
|
|
14662
|
-
}
|
|
14663
|
-
return { version: 1, changes: parsed.changes };
|
|
14664
|
-
} catch {
|
|
14665
|
-
logWarningConsole(
|
|
14666
|
-
`Corrupted playbook file: ${this.storagePath}. Treating as empty.`
|
|
14667
|
-
);
|
|
14668
|
-
return { version: 1, changes: [] };
|
|
14669
|
-
}
|
|
14670
|
-
}
|
|
14671
|
-
writeYaml(data) {
|
|
14672
|
-
const dir = path20.dirname(this.storagePath);
|
|
14673
|
-
fs18.mkdirSync(dir, { recursive: true });
|
|
14674
|
-
fs18.writeFileSync(this.storagePath, yaml.stringify(data), "utf-8");
|
|
14629
|
+
if (thrownErrors.length > 0) {
|
|
14630
|
+
process.exit(1);
|
|
14675
14631
|
}
|
|
14676
|
-
}
|
|
14677
|
-
|
|
14678
|
-
// apps/cli/src/infra/commands/InstallCommand.ts
|
|
14632
|
+
}
|
|
14679
14633
|
var installCommand = (0, import_cmd_ts2.command)({
|
|
14680
14634
|
name: "install",
|
|
14681
|
-
description: "Install packages and save their artifacts locally",
|
|
14682
14635
|
aliases: ["pull"],
|
|
14636
|
+
description: "Install packages and save their artifacts locally",
|
|
14683
14637
|
args: {
|
|
14684
|
-
|
|
14685
|
-
|
|
14686
|
-
|
|
14638
|
+
installPath: (0, import_cmd_ts2.option)({
|
|
14639
|
+
type: import_cmd_ts2.string,
|
|
14640
|
+
short: "p",
|
|
14641
|
+
long: "path",
|
|
14642
|
+
defaultValue: () => "",
|
|
14643
|
+
description: "Run install in the specified directory instead of the current directory"
|
|
14644
|
+
}),
|
|
14645
|
+
packages: (0, import_cmd_ts2.restPositionals)({
|
|
14646
|
+
type: import_cmd_ts2.string,
|
|
14647
|
+
displayName: "packages",
|
|
14648
|
+
description: "Package slugs to install (e.g. @my-space/my-package)"
|
|
14687
14649
|
}),
|
|
14688
14650
|
status: (0, import_cmd_ts2.flag)({
|
|
14689
14651
|
long: "status",
|
|
14690
14652
|
description: "Show status of all packmind.json files and their packages in the workspace"
|
|
14691
14653
|
}),
|
|
14692
|
-
|
|
14693
|
-
|
|
14694
|
-
|
|
14695
|
-
description: "[Deprecated] Install is now recursive by default. This flag will be removed in a future version."
|
|
14696
|
-
}),
|
|
14697
|
-
path: (0, import_cmd_ts2.option)({
|
|
14698
|
-
type: import_cmd_ts2.string,
|
|
14699
|
-
short: "p",
|
|
14700
|
-
long: "path",
|
|
14701
|
-
defaultValue: () => "",
|
|
14702
|
-
description: "Run install in the specified directory (recursive within that path)"
|
|
14654
|
+
list: (0, import_cmd_ts2.flag)({
|
|
14655
|
+
long: "list",
|
|
14656
|
+
description: "[Deprecated] List available packages"
|
|
14703
14657
|
}),
|
|
14704
14658
|
show: (0, import_cmd_ts2.option)({
|
|
14705
14659
|
type: import_cmd_ts2.string,
|
|
14706
14660
|
long: "show",
|
|
14707
|
-
description: "Show details of a specific package",
|
|
14661
|
+
description: "[Deprecated] Show details of a specific package",
|
|
14708
14662
|
defaultValue: () => ""
|
|
14709
|
-
}),
|
|
14710
|
-
packagesSlugs: (0, import_cmd_ts2.restPositionals)({
|
|
14711
|
-
type: import_cmd_ts2.string,
|
|
14712
|
-
displayName: "packages",
|
|
14713
|
-
description: "Package slugs to install (e.g., backend frontend)"
|
|
14714
14663
|
})
|
|
14715
14664
|
},
|
|
14716
|
-
handler:
|
|
14717
|
-
const packmindLogger = new PackmindLogger("PackmindCLI", "info" /* INFO */);
|
|
14718
|
-
const packmindCliHexa = new PackmindCliHexa(packmindLogger);
|
|
14719
|
-
const repoRoot = await packmindCliHexa.tryGetGitRepositoryRoot(
|
|
14720
|
-
process.cwd()
|
|
14721
|
-
);
|
|
14722
|
-
const playbookLocalRepository = repoRoot ? new PlaybookLocalRepository(repoRoot) : void 0;
|
|
14723
|
-
const deps = {
|
|
14724
|
-
packmindCliHexa,
|
|
14725
|
-
exit: process.exit,
|
|
14726
|
-
getCwd: () => process.cwd(),
|
|
14727
|
-
log: console.log,
|
|
14728
|
-
error: console.error,
|
|
14729
|
-
playbookLocalRepository
|
|
14730
|
-
};
|
|
14731
|
-
if (list) {
|
|
14732
|
-
await listPackagesHandler({}, deps);
|
|
14733
|
-
return;
|
|
14734
|
-
}
|
|
14735
|
-
if (status) {
|
|
14736
|
-
await statusHandler({}, deps);
|
|
14737
|
-
return;
|
|
14738
|
-
}
|
|
14739
|
-
if (show) {
|
|
14740
|
-
await showPackageHandler(
|
|
14741
|
-
{ slug: show },
|
|
14742
|
-
{ packmindCliHexa, exit: process.exit }
|
|
14743
|
-
);
|
|
14744
|
-
return;
|
|
14745
|
-
}
|
|
14746
|
-
if (recursive) {
|
|
14747
|
-
logWarningConsole(
|
|
14748
|
-
"\u26A0\uFE0F The --recursive flag is deprecated. Install is now recursive by default."
|
|
14749
|
-
);
|
|
14750
|
-
await recursiveInstallHandler({ path: path36 || void 0 }, deps);
|
|
14751
|
-
return;
|
|
14752
|
-
}
|
|
14753
|
-
if (packagesSlugs.length > 0) {
|
|
14754
|
-
await installPackagesHandler(
|
|
14755
|
-
{ packagesSlugs, path: path36 || void 0 },
|
|
14756
|
-
deps
|
|
14757
|
-
);
|
|
14758
|
-
return;
|
|
14759
|
-
}
|
|
14760
|
-
await recursiveInstallHandler({ path: path36 || void 0 }, deps);
|
|
14761
|
-
}
|
|
14665
|
+
handler: installHandler
|
|
14762
14666
|
});
|
|
14763
14667
|
|
|
14764
14668
|
// apps/cli/src/infra/commands/UninstallCommand.ts
|
|
14765
14669
|
var import_cmd_ts3 = __toESM(require_cjs());
|
|
14670
|
+
function buildUninstallSummary(result) {
|
|
14671
|
+
const removedParts = [
|
|
14672
|
+
result.standardsRemoved > 0 ? `${result.standardsRemoved} ${result.standardsRemoved === 1 ? "standard" : "standards"}` : null,
|
|
14673
|
+
result.commandsRemoved > 0 ? `${result.commandsRemoved} ${result.commandsRemoved === 1 ? "command" : "commands"}` : null,
|
|
14674
|
+
result.skillsRemoved > 0 ? `${result.skillsRemoved} ${result.skillsRemoved === 1 ? "skill" : "skills"}` : null,
|
|
14675
|
+
result.recipesRemoved > 0 ? `${result.recipesRemoved} ${result.recipesRemoved === 1 ? "recipe" : "recipes"}` : null
|
|
14676
|
+
].filter(Boolean);
|
|
14677
|
+
if (removedParts.length === 0) {
|
|
14678
|
+
return "\u2705 Package removed";
|
|
14679
|
+
}
|
|
14680
|
+
return `\u2705 Removed ${removedParts.join(", ")}`;
|
|
14681
|
+
}
|
|
14766
14682
|
var uninstallCommand = (0, import_cmd_ts3.command)({
|
|
14767
14683
|
name: "uninstall",
|
|
14768
|
-
description: "Uninstall packages and
|
|
14684
|
+
description: "Uninstall packages and sync artifacts. Specify package slugs (e.g. @my-space/my-package) to uninstall.",
|
|
14769
14685
|
aliases: ["remove"],
|
|
14770
14686
|
args: {
|
|
14771
|
-
|
|
14687
|
+
packages: (0, import_cmd_ts3.restPositionals)({
|
|
14772
14688
|
type: import_cmd_ts3.string,
|
|
14773
14689
|
displayName: "packages",
|
|
14774
|
-
description: "Package slugs to uninstall (e.g
|
|
14690
|
+
description: "Package slugs to uninstall (e.g. @my-space/my-package)"
|
|
14775
14691
|
})
|
|
14776
14692
|
},
|
|
14777
|
-
handler: async ({
|
|
14693
|
+
handler: async ({ packages }) => {
|
|
14694
|
+
if (packages.length === 0) {
|
|
14695
|
+
logErrorConsole("Please specify at least one package to uninstall.");
|
|
14696
|
+
process.exit(1);
|
|
14697
|
+
}
|
|
14778
14698
|
const packmindLogger = new PackmindLogger("PackmindCLI", "info" /* INFO */);
|
|
14779
14699
|
const packmindCliHexa = new PackmindCliHexa(packmindLogger);
|
|
14780
|
-
|
|
14781
|
-
packmindCliHexa
|
|
14782
|
-
|
|
14783
|
-
|
|
14784
|
-
|
|
14785
|
-
|
|
14786
|
-
|
|
14787
|
-
|
|
14700
|
+
try {
|
|
14701
|
+
const result = await packmindCliHexa.uninstall({
|
|
14702
|
+
baseDirectory: process.cwd(),
|
|
14703
|
+
packages
|
|
14704
|
+
});
|
|
14705
|
+
if (result.missingAccess.length > 0) {
|
|
14706
|
+
let warning = `\u26A0\uFE0F You don't have access to the following packages (their artifacts were preserved from the lock file):
|
|
14707
|
+
` + result.missingAccess.map((s) => ` - ${s}`).join("\n");
|
|
14708
|
+
if (result.joinSpaceUrl) {
|
|
14709
|
+
warning += `
|
|
14710
|
+
|
|
14711
|
+
\u{1F449} Join the space to get access: ${result.joinSpaceUrl}`;
|
|
14712
|
+
}
|
|
14713
|
+
logWarningConsole(warning);
|
|
14714
|
+
}
|
|
14715
|
+
logConsole(buildUninstallSummary(result));
|
|
14716
|
+
if (result.errors.length > 0) {
|
|
14717
|
+
logWarningConsole(`Encountered ${result.errors.length} error(s):`);
|
|
14718
|
+
result.errors.forEach((err) => logErrorConsole(` - ${err}`));
|
|
14719
|
+
}
|
|
14720
|
+
} catch (error) {
|
|
14721
|
+
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
14722
|
+
logErrorConsole(`uninstall failed: ${errorMessage}`);
|
|
14723
|
+
process.exit(1);
|
|
14724
|
+
}
|
|
14788
14725
|
}
|
|
14789
14726
|
});
|
|
14790
14727
|
|
|
@@ -14980,7 +14917,7 @@ var inquirer = __toESM(require("inquirer"));
|
|
|
14980
14917
|
// apps/cli/src/application/services/AgentDetectionService.ts
|
|
14981
14918
|
var fs19 = __toESM(require("fs"));
|
|
14982
14919
|
var path21 = __toESM(require("path"));
|
|
14983
|
-
var
|
|
14920
|
+
var os4 = __toESM(require("os"));
|
|
14984
14921
|
var import_child_process4 = require("child_process");
|
|
14985
14922
|
var AgentDetectionService = class {
|
|
14986
14923
|
constructor(projectDir = process.cwd()) {
|
|
@@ -15006,7 +14943,7 @@ var AgentDetectionService = class {
|
|
|
15006
14943
|
return this.isCommandAvailable("claude");
|
|
15007
14944
|
}
|
|
15008
14945
|
isCursorAvailable() {
|
|
15009
|
-
const cursorConfigDir = path21.join(
|
|
14946
|
+
const cursorConfigDir = path21.join(os4.homedir(), ".cursor");
|
|
15010
14947
|
return fs19.existsSync(cursorConfigDir);
|
|
15011
14948
|
}
|
|
15012
14949
|
isVSCodeAvailable() {
|
|
@@ -15073,7 +15010,7 @@ async function promptAgentsWithReadline(choices) {
|
|
|
15073
15010
|
output.write("\n");
|
|
15074
15011
|
const preselected = choices.map((c, i) => c.checked ? i + 1 : null).filter((i) => i !== null);
|
|
15075
15012
|
const defaultValue = preselected.length > 0 ? preselected.join(",") : "1,2,3";
|
|
15076
|
-
return new Promise((
|
|
15013
|
+
return new Promise((resolve15) => {
|
|
15077
15014
|
rl.question(
|
|
15078
15015
|
`Enter numbers separated by commas (default: ${defaultValue}): `,
|
|
15079
15016
|
(answer) => {
|
|
@@ -15084,7 +15021,7 @@ async function promptAgentsWithReadline(choices) {
|
|
|
15084
15021
|
const numbersStr = trimmed === "" ? defaultValue : trimmed;
|
|
15085
15022
|
const numbers = numbersStr.split(",").map((s) => parseInt(s.trim(), 10)).filter((n) => !isNaN(n) && n >= 1 && n <= choices.length);
|
|
15086
15023
|
const selectedAgents = numbers.map((n) => choices[n - 1].value);
|
|
15087
|
-
|
|
15024
|
+
resolve15(selectedAgents);
|
|
15088
15025
|
}
|
|
15089
15026
|
);
|
|
15090
15027
|
});
|
|
@@ -15258,9 +15195,14 @@ var addSkillCommand = (0, import_cmd_ts9.command)({
|
|
|
15258
15195
|
originSkill: originSkillOption
|
|
15259
15196
|
},
|
|
15260
15197
|
handler: async () => {
|
|
15261
|
-
|
|
15262
|
-
|
|
15263
|
-
|
|
15198
|
+
const packmindLogger = new PackmindLogger("PackmindCLI", "info" /* INFO */);
|
|
15199
|
+
const packmindCliHexa = new PackmindCliHexa(packmindLogger);
|
|
15200
|
+
packmindCliHexa.output.notifyError(
|
|
15201
|
+
'Command "packmind-cli skills add" has been removed.',
|
|
15202
|
+
{
|
|
15203
|
+
content: 'Use the "playbook add" command instead:',
|
|
15204
|
+
exampleCommand: "packmind-cli playbook add .packmind/commands/my-command.md"
|
|
15205
|
+
}
|
|
15264
15206
|
);
|
|
15265
15207
|
process.exit(1);
|
|
15266
15208
|
}
|
|
@@ -15340,13 +15282,6 @@ var installDefaultSkillsCommand = (0, import_cmd_ts10.command)({
|
|
|
15340
15282
|
`${result.skippedSkillsCount} skill(s) were skipped because they require a newer version of packmind-cli. Run "${formatCommand("packmind-cli update")}" to get the latest version.`
|
|
15341
15283
|
);
|
|
15342
15284
|
}
|
|
15343
|
-
if (result.skippedIncompatibleSkillNames.length > 0) {
|
|
15344
|
-
for (const skillName of result.skippedIncompatibleSkillNames) {
|
|
15345
|
-
logWarningConsole(
|
|
15346
|
-
`Skill "${skillName}" was not installed because it is not compatible with this version of packmind-cli.`
|
|
15347
|
-
);
|
|
15348
|
-
}
|
|
15349
|
-
}
|
|
15350
15285
|
if (result.incompatibleInstalledSkills.length > 0) {
|
|
15351
15286
|
await handleIncompatibleInstalledSkillsWithPrompt(
|
|
15352
15287
|
result.incompatibleInstalledSkills,
|
|
@@ -15393,10 +15328,10 @@ async function promptConfirmation(question) {
|
|
|
15393
15328
|
input: process.stdin,
|
|
15394
15329
|
output: process.stdout
|
|
15395
15330
|
});
|
|
15396
|
-
return new Promise((
|
|
15331
|
+
return new Promise((resolve15) => {
|
|
15397
15332
|
rl.question(question, (answer) => {
|
|
15398
15333
|
rl.close();
|
|
15399
|
-
|
|
15334
|
+
resolve15(answer.trim().toLowerCase() === "y");
|
|
15400
15335
|
});
|
|
15401
15336
|
});
|
|
15402
15337
|
}
|
|
@@ -15404,93 +15339,95 @@ async function promptConfirmation(question) {
|
|
|
15404
15339
|
// apps/cli/src/infra/commands/ListSkillsCommand.ts
|
|
15405
15340
|
var import_cmd_ts11 = __toESM(require_cjs());
|
|
15406
15341
|
|
|
15407
|
-
// apps/cli/src/infra/
|
|
15408
|
-
function
|
|
15409
|
-
|
|
15342
|
+
// apps/cli/src/infra/utils/spaceFilterUtils.ts
|
|
15343
|
+
function resolveSpaceFromArgs(spaceArg, spaces) {
|
|
15344
|
+
if (!spaceArg) return null;
|
|
15345
|
+
const slug3 = spaceArg.startsWith("@") ? spaceArg.slice(1) : spaceArg;
|
|
15346
|
+
return spaces.find((s) => s.slug === slug3) ?? null;
|
|
15347
|
+
}
|
|
15348
|
+
|
|
15349
|
+
// apps/cli/src/infra/utils/urlBuilderUtils.ts
|
|
15350
|
+
function resolveUrlBuilder(buildArtifactPath) {
|
|
15351
|
+
const apiKey = loadApiKey();
|
|
15352
|
+
if (!apiKey) return () => null;
|
|
15353
|
+
const decoded = decodeApiKey(apiKey);
|
|
15354
|
+
const orgSlug = decoded?.jwt?.organization?.slug;
|
|
15355
|
+
if (!decoded?.host || !orgSlug) return () => null;
|
|
15356
|
+
return (spaceSlug, artifactId) => `${decoded.host}/org/${orgSlug}/space/${spaceSlug}/${buildArtifactPath(artifactId)}`;
|
|
15357
|
+
}
|
|
15358
|
+
|
|
15359
|
+
// apps/cli/src/infra/utils/groupArtefactsBySpaces.ts
|
|
15360
|
+
function groupArtefactBySpaces(artefacts, spaces) {
|
|
15361
|
+
const spacesById = new Map(
|
|
15410
15362
|
spaces.map((s) => [s.id, s])
|
|
15411
15363
|
);
|
|
15412
|
-
const
|
|
15413
|
-
|
|
15414
|
-
|
|
15415
|
-
|
|
15416
|
-
|
|
15417
|
-
|
|
15418
|
-
|
|
15419
|
-
|
|
15420
|
-
let group = groupsMap.get(space.id);
|
|
15421
|
-
if (!group) {
|
|
15422
|
-
group = { space, items: [] };
|
|
15423
|
-
groupsMap.set(space.id, group);
|
|
15424
|
-
}
|
|
15425
|
-
group.items.push(skill);
|
|
15426
|
-
}
|
|
15427
|
-
const groups = [...groupsMap.values()].sort(
|
|
15428
|
-
(a, b) => a.space.name.localeCompare(b.space.name)
|
|
15429
|
-
);
|
|
15430
|
-
return { groups, orphaned };
|
|
15431
|
-
}
|
|
15432
|
-
function displayGroupedSkills(skills, spaces, buildUrl) {
|
|
15433
|
-
const { groups, orphaned } = groupSkillsBySpace(skills, spaces);
|
|
15434
|
-
for (const { space, items } of groups) {
|
|
15435
|
-
logConsole(`Space "${space.name}":
|
|
15436
|
-
`);
|
|
15437
|
-
for (const skill of [...items].sort(
|
|
15438
|
-
(a, b) => a.slug.localeCompare(b.slug)
|
|
15439
|
-
)) {
|
|
15440
|
-
logConsole(` ${formatSlug(skill.slug)}`);
|
|
15441
|
-
logConsole(` ${formatLabel("Name:")} ${skill.name}`);
|
|
15442
|
-
if (skill.description) {
|
|
15443
|
-
const descriptionLines = skill.description.trim().split("\n").map((line) => line.trim()).filter((line) => line.length > 0);
|
|
15444
|
-
const firstLine = descriptionLines[0];
|
|
15445
|
-
if (firstLine) {
|
|
15446
|
-
const truncated = firstLine.length > 80 ? firstLine.slice(0, 77) + "..." : firstLine;
|
|
15447
|
-
logConsole(` ${formatLabel("Desc:")} ${truncated}`);
|
|
15448
|
-
}
|
|
15449
|
-
}
|
|
15450
|
-
const url = buildUrl(space.slug, skill.slug);
|
|
15451
|
-
if (url) {
|
|
15452
|
-
logConsole(` ${formatLabel("Link:")} ${url}`);
|
|
15453
|
-
}
|
|
15454
|
-
logConsole("");
|
|
15364
|
+
const groupedArtefacts = artefacts.reduce((acc, artefact) => {
|
|
15365
|
+
const space = spacesById.get(artefact.spaceId);
|
|
15366
|
+
if (space) {
|
|
15367
|
+
const group = acc.get(artefact.spaceId) ?? { space, artefacts: [] };
|
|
15368
|
+
acc.set(artefact.spaceId, {
|
|
15369
|
+
space,
|
|
15370
|
+
artefacts: [...group.artefacts, artefact]
|
|
15371
|
+
});
|
|
15455
15372
|
}
|
|
15456
|
-
|
|
15457
|
-
|
|
15458
|
-
|
|
15459
|
-
|
|
15460
|
-
|
|
15461
|
-
|
|
15462
|
-
logConsole("");
|
|
15463
|
-
}
|
|
15373
|
+
return acc;
|
|
15374
|
+
}, /* @__PURE__ */ new Map());
|
|
15375
|
+
return [...groupedArtefacts.values()].map(({ space, artefacts: artefacts2 }) => ({
|
|
15376
|
+
space,
|
|
15377
|
+
artefacts: [...artefacts2].sort((a, b) => a.slug.localeCompare(b.slug))
|
|
15378
|
+
})).sort((a, b) => a.space.name.localeCompare(b.space.name));
|
|
15464
15379
|
}
|
|
15380
|
+
|
|
15381
|
+
// apps/cli/src/infra/commands/skills/listSkillsHandler.ts
|
|
15465
15382
|
async function listSkillsHandler(args2, deps) {
|
|
15466
15383
|
const { packmindCliHexa, exit } = deps;
|
|
15467
15384
|
try {
|
|
15468
|
-
|
|
15469
|
-
|
|
15385
|
+
const spaces = await packmindCliHexa.output.withLoader(
|
|
15386
|
+
"Fetching spaces",
|
|
15387
|
+
() => packmindCliHexa.getSpaces()
|
|
15388
|
+
);
|
|
15470
15389
|
const matchedSpace = resolveSpaceFromArgs(args2.space, spaces);
|
|
15471
15390
|
if (args2.space && !matchedSpace) {
|
|
15472
|
-
|
|
15391
|
+
const availableSpaces = spaces.map((s) => ` - @${s.slug}`).join("\n");
|
|
15392
|
+
packmindCliHexa.output.notifyError(`Space "@${args2.space}" not found.`, {
|
|
15393
|
+
content: `Available spaces:
|
|
15394
|
+
${availableSpaces}`
|
|
15395
|
+
});
|
|
15473
15396
|
exit(1);
|
|
15474
15397
|
return;
|
|
15475
15398
|
}
|
|
15476
|
-
const skills = await packmindCliHexa.
|
|
15477
|
-
|
|
15399
|
+
const skills = await packmindCliHexa.output.withLoader(
|
|
15400
|
+
"Fetching skills",
|
|
15401
|
+
() => packmindCliHexa.listSkills(
|
|
15402
|
+
matchedSpace ? { spaceId: matchedSpace.id } : {}
|
|
15403
|
+
)
|
|
15478
15404
|
);
|
|
15479
15405
|
if (skills.length === 0) {
|
|
15480
|
-
|
|
15406
|
+
packmindCliHexa.output.notifyInfo(
|
|
15481
15407
|
matchedSpace ? `No skills found in space "@${matchedSpace.slug}".` : "No skills found."
|
|
15482
15408
|
);
|
|
15483
15409
|
exit(0);
|
|
15484
15410
|
return;
|
|
15485
15411
|
}
|
|
15486
|
-
logConsole(formatHeader(`\u{1F4CB} Skills (${skills.length})
|
|
15487
|
-
`));
|
|
15488
15412
|
const buildUrl = resolveUrlBuilder((slug3) => `skills/${slug3}/files`);
|
|
15489
|
-
|
|
15413
|
+
const groups = groupArtefactBySpaces(skills, spaces);
|
|
15414
|
+
packmindCliHexa.output.listScopedArtefacts(
|
|
15415
|
+
`\u{1F4CB} Skills (${skills.length})`,
|
|
15416
|
+
groups.map(({ space, artefacts }) => ({
|
|
15417
|
+
title: `Space: ${space.name}`,
|
|
15418
|
+
artefacts: artefacts.map((skill) => ({
|
|
15419
|
+
title: skill.name,
|
|
15420
|
+
slug: skill.slug,
|
|
15421
|
+
description: skill.description ?? void 0,
|
|
15422
|
+
url: buildUrl(space.slug, skill.slug)
|
|
15423
|
+
}))
|
|
15424
|
+
}))
|
|
15425
|
+
);
|
|
15490
15426
|
exit(0);
|
|
15491
15427
|
} catch (err) {
|
|
15492
|
-
|
|
15493
|
-
|
|
15428
|
+
packmindCliHexa.output.notifyError("Failed to list skills:", {
|
|
15429
|
+
content: err instanceof Error ? err.message : String(err)
|
|
15430
|
+
});
|
|
15494
15431
|
exit(1);
|
|
15495
15432
|
}
|
|
15496
15433
|
}
|
|
@@ -15552,11 +15489,14 @@ var createStandardCommand = (0, import_cmd_ts13.command)({
|
|
|
15552
15489
|
originSkill: originSkillOption
|
|
15553
15490
|
},
|
|
15554
15491
|
handler: async () => {
|
|
15555
|
-
|
|
15556
|
-
|
|
15557
|
-
|
|
15558
|
-
|
|
15559
|
-
|
|
15492
|
+
const packmindLogger = new PackmindLogger("PackmindCLI", "info" /* INFO */);
|
|
15493
|
+
const packmindCliHexa = new PackmindCliHexa(packmindLogger);
|
|
15494
|
+
packmindCliHexa.output.notifyError(
|
|
15495
|
+
'Command "packmind-cli standards create" has been removed.',
|
|
15496
|
+
{
|
|
15497
|
+
content: 'Use the "playbook add" command instead:',
|
|
15498
|
+
exampleCommand: "packmind-cli playbook add .packmind/standards/my-standard.md"
|
|
15499
|
+
}
|
|
15560
15500
|
);
|
|
15561
15501
|
process.exit(1);
|
|
15562
15502
|
}
|
|
@@ -15566,92 +15506,55 @@ var createStandardCommand = (0, import_cmd_ts13.command)({
|
|
|
15566
15506
|
var import_cmd_ts14 = __toESM(require_cjs());
|
|
15567
15507
|
|
|
15568
15508
|
// apps/cli/src/infra/commands/standards/listStandardsHandler.ts
|
|
15569
|
-
function groupStandardsBySpace(standards, spaces) {
|
|
15570
|
-
const spaceMap = new Map(
|
|
15571
|
-
spaces.map((s) => [s.id, s])
|
|
15572
|
-
);
|
|
15573
|
-
const groupsMap = /* @__PURE__ */ new Map();
|
|
15574
|
-
const orphaned = [];
|
|
15575
|
-
for (const standard of standards) {
|
|
15576
|
-
const space = spaceMap.get(standard.spaceId);
|
|
15577
|
-
if (!space) {
|
|
15578
|
-
orphaned.push(standard);
|
|
15579
|
-
continue;
|
|
15580
|
-
}
|
|
15581
|
-
let group = groupsMap.get(space.id);
|
|
15582
|
-
if (!group) {
|
|
15583
|
-
group = { space, items: [] };
|
|
15584
|
-
groupsMap.set(space.id, group);
|
|
15585
|
-
}
|
|
15586
|
-
group.items.push(standard);
|
|
15587
|
-
}
|
|
15588
|
-
const groups = [...groupsMap.values()].sort(
|
|
15589
|
-
(a, b) => a.space.name.localeCompare(b.space.name)
|
|
15590
|
-
);
|
|
15591
|
-
return { groups, orphaned };
|
|
15592
|
-
}
|
|
15593
|
-
function displayGroupedStandards(standards, spaces, buildUrl) {
|
|
15594
|
-
const { groups, orphaned } = groupStandardsBySpace(standards, spaces);
|
|
15595
|
-
for (const { space, items } of groups) {
|
|
15596
|
-
logConsole(`Space "${space.name}":
|
|
15597
|
-
`);
|
|
15598
|
-
for (const standard of [...items].sort(
|
|
15599
|
-
(a, b) => a.slug.localeCompare(b.slug)
|
|
15600
|
-
)) {
|
|
15601
|
-
logConsole(` ${formatSlug(standard.slug)}`);
|
|
15602
|
-
logConsole(` ${formatLabel("Name:")} ${standard.name}`);
|
|
15603
|
-
if (standard.description) {
|
|
15604
|
-
const descriptionLines = standard.description.trim().split("\n").map((line) => line.trim()).filter((line) => line.length > 0);
|
|
15605
|
-
const firstLine = descriptionLines[0];
|
|
15606
|
-
if (firstLine) {
|
|
15607
|
-
const truncated = firstLine.length > 80 ? firstLine.slice(0, 77) + "..." : firstLine;
|
|
15608
|
-
logConsole(` ${formatLabel("Desc:")} ${truncated}`);
|
|
15609
|
-
}
|
|
15610
|
-
}
|
|
15611
|
-
const url = buildUrl(space.slug, standard.id);
|
|
15612
|
-
if (url) {
|
|
15613
|
-
logConsole(` ${formatLabel("Link:")} ${url}`);
|
|
15614
|
-
}
|
|
15615
|
-
logConsole("");
|
|
15616
|
-
}
|
|
15617
|
-
}
|
|
15618
|
-
for (const standard of [...orphaned].sort(
|
|
15619
|
-
(a, b) => a.slug.localeCompare(b.slug)
|
|
15620
|
-
)) {
|
|
15621
|
-
logConsole(` ${formatSlug(standard.slug)}`);
|
|
15622
|
-
logConsole(` ${formatLabel("Name:")} ${standard.name}`);
|
|
15623
|
-
logConsole("");
|
|
15624
|
-
}
|
|
15625
|
-
}
|
|
15626
15509
|
async function listStandardsHandler(args2, deps) {
|
|
15627
15510
|
const { packmindCliHexa, exit } = deps;
|
|
15628
15511
|
try {
|
|
15629
|
-
|
|
15630
|
-
|
|
15512
|
+
const spaces = await packmindCliHexa.output.withLoader(
|
|
15513
|
+
"Fetching spaces",
|
|
15514
|
+
() => packmindCliHexa.getSpaces()
|
|
15515
|
+
);
|
|
15631
15516
|
const matchedSpace = resolveSpaceFromArgs(args2.space, spaces);
|
|
15632
15517
|
if (args2.space && !matchedSpace) {
|
|
15633
|
-
|
|
15518
|
+
const availableSpaces = spaces.map((space) => ` - @${space.slug}`).join("\n");
|
|
15519
|
+
packmindCliHexa.output.notifyError(`Space "@${args2.space}" not found.`, {
|
|
15520
|
+
content: `Available spaces:
|
|
15521
|
+
${availableSpaces}`
|
|
15522
|
+
});
|
|
15634
15523
|
exit(1);
|
|
15635
15524
|
return;
|
|
15636
15525
|
}
|
|
15637
|
-
const standards = await packmindCliHexa.
|
|
15638
|
-
|
|
15526
|
+
const standards = await packmindCliHexa.output.withLoader(
|
|
15527
|
+
"Fetching standards",
|
|
15528
|
+
() => packmindCliHexa.listStandards(
|
|
15529
|
+
matchedSpace ? { spaceId: matchedSpace.id } : {}
|
|
15530
|
+
)
|
|
15639
15531
|
);
|
|
15640
15532
|
if (standards.length === 0) {
|
|
15641
|
-
|
|
15533
|
+
packmindCliHexa.output.notifyInfo(
|
|
15642
15534
|
matchedSpace ? `No standards found in space "@${matchedSpace.slug}".` : "No standards found."
|
|
15643
15535
|
);
|
|
15644
15536
|
exit(0);
|
|
15645
15537
|
return;
|
|
15646
15538
|
}
|
|
15647
|
-
|
|
15648
|
-
`));
|
|
15539
|
+
const groupedStandards = groupArtefactBySpaces(standards, spaces);
|
|
15649
15540
|
const buildUrl = resolveUrlBuilder((id) => `standards/${id}/summary`);
|
|
15650
|
-
|
|
15541
|
+
const scopedArtefacts = groupedStandards.map(({ space, artefacts }) => ({
|
|
15542
|
+
title: `Space: ${space.name}`,
|
|
15543
|
+
artefacts: artefacts.map((s) => ({
|
|
15544
|
+
title: s.name,
|
|
15545
|
+
slug: s.slug,
|
|
15546
|
+
url: buildUrl(space.slug, s.id)
|
|
15547
|
+
}))
|
|
15548
|
+
}));
|
|
15549
|
+
packmindCliHexa.output.listScopedArtefacts(
|
|
15550
|
+
`\u{1F4CB} Standards (${standards.length})`,
|
|
15551
|
+
scopedArtefacts
|
|
15552
|
+
);
|
|
15651
15553
|
exit(0);
|
|
15652
15554
|
} catch (err) {
|
|
15653
|
-
|
|
15654
|
-
|
|
15555
|
+
packmindCliHexa.output.notifyError("Failed to list standards:", {
|
|
15556
|
+
content: err instanceof Error ? err.message : String(err)
|
|
15557
|
+
});
|
|
15655
15558
|
exit(1);
|
|
15656
15559
|
}
|
|
15657
15560
|
}
|
|
@@ -15712,9 +15615,14 @@ var createCommandCommand = (0, import_cmd_ts16.command)({
|
|
|
15712
15615
|
originSkill: originSkillOption
|
|
15713
15616
|
},
|
|
15714
15617
|
handler: async () => {
|
|
15715
|
-
|
|
15716
|
-
|
|
15717
|
-
|
|
15618
|
+
const packmindLogger = new PackmindLogger("PackmindCLI", "info" /* INFO */);
|
|
15619
|
+
const packmindCliHexa = new PackmindCliHexa(packmindLogger);
|
|
15620
|
+
packmindCliHexa.output.notifyError(
|
|
15621
|
+
'Command "packmind-cli commands create" has been removed.',
|
|
15622
|
+
{
|
|
15623
|
+
content: 'Use the "playbook add" command instead:',
|
|
15624
|
+
exampleCommand: "packmind-cli playbook add .packmind/commands/my-command.md"
|
|
15625
|
+
}
|
|
15718
15626
|
);
|
|
15719
15627
|
process.exit(1);
|
|
15720
15628
|
}
|
|
@@ -15724,86 +15632,54 @@ var createCommandCommand = (0, import_cmd_ts16.command)({
|
|
|
15724
15632
|
var import_cmd_ts17 = __toESM(require_cjs());
|
|
15725
15633
|
|
|
15726
15634
|
// apps/cli/src/infra/commands/commands/listCommandsHandler.ts
|
|
15727
|
-
function groupCommandsBySpace(commands, spaces) {
|
|
15728
|
-
const spaceMap = new Map(
|
|
15729
|
-
spaces.map((s) => [s.id, s])
|
|
15730
|
-
);
|
|
15731
|
-
const groupsMap = /* @__PURE__ */ new Map();
|
|
15732
|
-
const orphaned = [];
|
|
15733
|
-
for (const cmd of commands) {
|
|
15734
|
-
const space = spaceMap.get(cmd.spaceId);
|
|
15735
|
-
if (!space) {
|
|
15736
|
-
orphaned.push(cmd);
|
|
15737
|
-
continue;
|
|
15738
|
-
}
|
|
15739
|
-
let group = groupsMap.get(space.id);
|
|
15740
|
-
if (!group) {
|
|
15741
|
-
group = { space, cmds: [] };
|
|
15742
|
-
groupsMap.set(space.id, group);
|
|
15743
|
-
}
|
|
15744
|
-
group.cmds.push(cmd);
|
|
15745
|
-
}
|
|
15746
|
-
const groups = [...groupsMap.values()].sort(
|
|
15747
|
-
(a, b) => a.space.name.localeCompare(b.space.name)
|
|
15748
|
-
);
|
|
15749
|
-
return { groups, orphaned };
|
|
15750
|
-
}
|
|
15751
|
-
function displayGroupedCommands(commands, spaces, buildUrl) {
|
|
15752
|
-
const { groups, orphaned } = groupCommandsBySpace(commands, spaces);
|
|
15753
|
-
for (const { space, cmds } of groups) {
|
|
15754
|
-
logConsole(`Space "${space.name}":
|
|
15755
|
-
`);
|
|
15756
|
-
for (const cmd of [...cmds].sort((a, b) => a.slug.localeCompare(b.slug))) {
|
|
15757
|
-
logConsole(` ${formatSlug(cmd.slug)}`);
|
|
15758
|
-
logConsole(` ${formatLabel("Name:")} ${cmd.name}`);
|
|
15759
|
-
const url = buildUrl(space.slug, cmd.id);
|
|
15760
|
-
if (url) {
|
|
15761
|
-
logConsole(` ${formatLabel("Link:")} ${url}`);
|
|
15762
|
-
}
|
|
15763
|
-
logConsole("");
|
|
15764
|
-
}
|
|
15765
|
-
}
|
|
15766
|
-
for (const cmd of [...orphaned].sort(
|
|
15767
|
-
(a, b) => a.slug.localeCompare(b.slug)
|
|
15768
|
-
)) {
|
|
15769
|
-
logConsole(` ${formatSlug(cmd.slug)}`);
|
|
15770
|
-
logConsole(` ${formatLabel("Name:")} ${cmd.name}`);
|
|
15771
|
-
logConsole("");
|
|
15772
|
-
}
|
|
15773
|
-
}
|
|
15774
15635
|
async function listCommandsHandler(args2, deps) {
|
|
15775
15636
|
const { packmindCliHexa, exit } = deps;
|
|
15776
15637
|
try {
|
|
15777
|
-
|
|
15778
|
-
|
|
15638
|
+
const spaces = await packmindCliHexa.output.withLoader(
|
|
15639
|
+
"Fetching spaces",
|
|
15640
|
+
() => packmindCliHexa.getSpaces()
|
|
15641
|
+
);
|
|
15779
15642
|
const matchedSpace = resolveSpaceFromArgs(args2.space, spaces);
|
|
15780
15643
|
if (args2.space && !matchedSpace) {
|
|
15781
|
-
|
|
15644
|
+
const availableSpaces = spaces.map((space) => ` - @${space.slug}`).join("\n");
|
|
15645
|
+
packmindCliHexa.output.notifyError(`Space "@${args2.space}" not found.`, {
|
|
15646
|
+
content: `Available spaces:
|
|
15647
|
+
${availableSpaces}`
|
|
15648
|
+
});
|
|
15782
15649
|
exit(1);
|
|
15783
15650
|
return;
|
|
15784
15651
|
}
|
|
15785
|
-
const commands = await packmindCliHexa.
|
|
15786
|
-
|
|
15652
|
+
const commands = await packmindCliHexa.output.withLoader(
|
|
15653
|
+
"Fetching commands",
|
|
15654
|
+
() => packmindCliHexa.listCommands(
|
|
15655
|
+
matchedSpace ? { spaceId: matchedSpace.id } : {}
|
|
15656
|
+
)
|
|
15787
15657
|
);
|
|
15788
15658
|
if (commands.length === 0) {
|
|
15789
|
-
|
|
15659
|
+
packmindCliHexa.output.notifyInfo(
|
|
15790
15660
|
matchedSpace ? `No commands found in space "@${matchedSpace.slug}".` : "No commands found."
|
|
15791
15661
|
);
|
|
15792
15662
|
exit(0);
|
|
15793
15663
|
return;
|
|
15794
15664
|
}
|
|
15795
|
-
|
|
15796
|
-
`));
|
|
15665
|
+
const groupedCommands = groupArtefactBySpaces(commands, spaces);
|
|
15797
15666
|
const buildUrl = resolveUrlBuilder((id) => `commands/${id}`);
|
|
15798
|
-
|
|
15667
|
+
packmindCliHexa.output.listScopedArtefacts(
|
|
15668
|
+
`\u{1F4CB} Commands (${commands.length})`,
|
|
15669
|
+
groupedCommands.map(({ space, artefacts }) => ({
|
|
15670
|
+
title: `Space: ${space.name}`,
|
|
15671
|
+
artefacts: artefacts.map((cmd) => ({
|
|
15672
|
+
title: cmd.name,
|
|
15673
|
+
slug: cmd.slug,
|
|
15674
|
+
url: buildUrl(space.slug, cmd.id)
|
|
15675
|
+
}))
|
|
15676
|
+
}))
|
|
15677
|
+
);
|
|
15799
15678
|
exit(0);
|
|
15800
15679
|
} catch (err) {
|
|
15801
|
-
|
|
15802
|
-
|
|
15803
|
-
|
|
15804
|
-
} else {
|
|
15805
|
-
logErrorConsole(String(err));
|
|
15806
|
-
}
|
|
15680
|
+
packmindCliHexa.output.notifyError("Failed to list commands:", {
|
|
15681
|
+
content: err instanceof Error ? err.message : String(err)
|
|
15682
|
+
});
|
|
15807
15683
|
exit(1);
|
|
15808
15684
|
}
|
|
15809
15685
|
}
|
|
@@ -16011,6 +15887,21 @@ async function findTargetDirectories(searchPath, packmindCliHexa) {
|
|
|
16011
15887
|
targets.push(dir);
|
|
16012
15888
|
}
|
|
16013
15889
|
}
|
|
15890
|
+
if (targets.length === 0) {
|
|
15891
|
+
let currentDir = nodePath.dirname(searchPath);
|
|
15892
|
+
while (true) {
|
|
15893
|
+
const ancestorExists = await packmindCliHexa.configExists(currentDir);
|
|
15894
|
+
if (ancestorExists) {
|
|
15895
|
+
targets.push(currentDir);
|
|
15896
|
+
break;
|
|
15897
|
+
}
|
|
15898
|
+
const parentDir = nodePath.dirname(currentDir);
|
|
15899
|
+
if (parentDir === currentDir) {
|
|
15900
|
+
break;
|
|
15901
|
+
}
|
|
15902
|
+
currentDir = parentDir;
|
|
15903
|
+
}
|
|
15904
|
+
}
|
|
16014
15905
|
return targets;
|
|
16015
15906
|
}
|
|
16016
15907
|
function computeRelativePath(targetAbsDir, gitRoot) {
|
|
@@ -16193,7 +16084,11 @@ async function diffArtefactsHandler(deps) {
|
|
|
16193
16084
|
relativePath,
|
|
16194
16085
|
agents: config.agents
|
|
16195
16086
|
});
|
|
16196
|
-
|
|
16087
|
+
const filterPrefix = nodePath.relative(targetDir, searchPath);
|
|
16088
|
+
const filteredDiffs = filterPrefix !== "" && !filterPrefix.startsWith("..") ? diffs.filter(
|
|
16089
|
+
(d) => d.filePath === filterPrefix || d.filePath.startsWith(filterPrefix + "/")
|
|
16090
|
+
) : diffs;
|
|
16091
|
+
targetResults.push({ targetRelativePath, diffs: filteredDiffs });
|
|
16197
16092
|
}
|
|
16198
16093
|
if (targetResults.length === 0) {
|
|
16199
16094
|
log("No packages configured in any target.");
|
|
@@ -16285,7 +16180,7 @@ var diffCommand = (0, import_cmd_ts19.command)({
|
|
|
16285
16180
|
description: "Subcommand and arguments (e.g., add <path>, remove <path>)"
|
|
16286
16181
|
})
|
|
16287
16182
|
},
|
|
16288
|
-
handler: async ({ submit, includeSubmitted, message, path:
|
|
16183
|
+
handler: async ({ submit, includeSubmitted, message, path: path37, positionals }) => {
|
|
16289
16184
|
const packmindLogger = new PackmindLogger("PackmindCLI", "info" /* INFO */);
|
|
16290
16185
|
const packmindCliHexa = new PackmindCliHexa(packmindLogger);
|
|
16291
16186
|
if (submit) {
|
|
@@ -16301,7 +16196,7 @@ var diffCommand = (0, import_cmd_ts19.command)({
|
|
|
16301
16196
|
process.exit(1);
|
|
16302
16197
|
}
|
|
16303
16198
|
if (positionals[0] === "add") {
|
|
16304
|
-
const addFilePath =
|
|
16199
|
+
const addFilePath = path37 && positionals[1] ? `${path37}/${positionals[1]}`.replace(/\/+/g, "/") : positionals[1];
|
|
16305
16200
|
const addCommand = `packmind-cli playbook add ${addFilePath}`;
|
|
16306
16201
|
logErrorConsole("Deprecated: `packmind-cli diff add` has been removed");
|
|
16307
16202
|
logInfoConsole("Use the following command instead:");
|
|
@@ -16309,7 +16204,7 @@ var diffCommand = (0, import_cmd_ts19.command)({
|
|
|
16309
16204
|
process.exit(1);
|
|
16310
16205
|
}
|
|
16311
16206
|
if (positionals[0] === "remove" || positionals[0] === "rm") {
|
|
16312
|
-
const removeFilePath =
|
|
16207
|
+
const removeFilePath = path37 && positionals[1] ? `${path37}/${positionals[1]}`.replace(/\/+/g, "/") : positionals[1];
|
|
16313
16208
|
const removeCommand = `packmind-cli playbook remove ${removeFilePath}`;
|
|
16314
16209
|
logErrorConsole(
|
|
16315
16210
|
"Deprecated: `packmind-cli diff remove` has been removed"
|
|
@@ -16318,7 +16213,7 @@ var diffCommand = (0, import_cmd_ts19.command)({
|
|
|
16318
16213
|
logInfoConsole(` ${formatCommand(removeCommand)}`);
|
|
16319
16214
|
process.exit(1);
|
|
16320
16215
|
}
|
|
16321
|
-
const diffCommand3 = `packmind-cli playbook diff${includeSubmitted ? " --include-submitted" : ""}${
|
|
16216
|
+
const diffCommand3 = `packmind-cli playbook diff${includeSubmitted ? " --include-submitted" : ""}${path37 ? ` --path ${path37}` : ""}`;
|
|
16322
16217
|
logErrorConsole("Deprecated: `packmind-cli diff` will be removed");
|
|
16323
16218
|
logInfoConsole("Use the following command instead:");
|
|
16324
16219
|
logInfoConsole(` ${formatCommand(diffCommand3)}`);
|
|
@@ -16328,7 +16223,7 @@ var diffCommand = (0, import_cmd_ts19.command)({
|
|
|
16328
16223
|
getCwd: () => process.cwd(),
|
|
16329
16224
|
log: console.log,
|
|
16330
16225
|
includeSubmitted,
|
|
16331
|
-
path:
|
|
16226
|
+
path: path37
|
|
16332
16227
|
});
|
|
16333
16228
|
}
|
|
16334
16229
|
});
|
|
@@ -16608,6 +16503,14 @@ var AddToPackageUseCase = class {
|
|
|
16608
16503
|
}
|
|
16609
16504
|
};
|
|
16610
16505
|
|
|
16506
|
+
// apps/cli/src/infra/utils/packageSlugUtils.ts
|
|
16507
|
+
function parsePackageSlug(slug3) {
|
|
16508
|
+
if (!slug3.startsWith("@")) return null;
|
|
16509
|
+
const slash = slug3.indexOf("/", 1);
|
|
16510
|
+
if (slash === -1) return null;
|
|
16511
|
+
return { spaceSlug: slug3.slice(1, slash), pkgSlug: slug3.slice(slash + 1) };
|
|
16512
|
+
}
|
|
16513
|
+
|
|
16611
16514
|
// apps/cli/src/infra/commands/packages/addToPackageHandler.ts
|
|
16612
16515
|
function pluralize(singular, count) {
|
|
16613
16516
|
return count === 1 ? singular : `${singular}s`;
|
|
@@ -16749,24 +16652,90 @@ var addToPackageCommand = (0, import_cmd_ts21.command)({
|
|
|
16749
16652
|
);
|
|
16750
16653
|
process.exit(1);
|
|
16751
16654
|
}
|
|
16752
|
-
if (itemTypes.length > 1) {
|
|
16753
|
-
logErrorConsole(
|
|
16754
|
-
"Cannot add standards, commands, and skills simultaneously. Use dedicated commands for each artefact."
|
|
16655
|
+
if (itemTypes.length > 1) {
|
|
16656
|
+
logErrorConsole(
|
|
16657
|
+
"Cannot add standards, commands, and skills simultaneously. Use dedicated commands for each artefact."
|
|
16658
|
+
);
|
|
16659
|
+
process.exit(1);
|
|
16660
|
+
}
|
|
16661
|
+
const { type: itemType, slugs: itemSlugs } = itemTypes[0];
|
|
16662
|
+
const packmindLogger = new PackmindLogger("PackmindCLI", "info" /* INFO */);
|
|
16663
|
+
const hexa = new PackmindCliHexa(packmindLogger);
|
|
16664
|
+
await addToPackageHandler(
|
|
16665
|
+
{ to, itemType, itemSlugs, originSkill },
|
|
16666
|
+
{ hexa, exit: process.exit }
|
|
16667
|
+
);
|
|
16668
|
+
}
|
|
16669
|
+
});
|
|
16670
|
+
|
|
16671
|
+
// apps/cli/src/infra/commands/listPackagesCommand.ts
|
|
16672
|
+
var import_cmd_ts22 = __toESM(require_cjs());
|
|
16673
|
+
|
|
16674
|
+
// apps/cli/src/infra/commands/packages/listPackagesHandler.ts
|
|
16675
|
+
async function listPackagesHandler(args2, deps) {
|
|
16676
|
+
const { packmindCliHexa, exit } = deps;
|
|
16677
|
+
try {
|
|
16678
|
+
const allSpaces = await packmindCliHexa.output.withLoader(
|
|
16679
|
+
"Fetching spaces",
|
|
16680
|
+
() => packmindCliHexa.getSpaces()
|
|
16681
|
+
);
|
|
16682
|
+
if (!allSpaces || allSpaces.length === 0) {
|
|
16683
|
+
throw new Error("Unable to list organization spaces.");
|
|
16684
|
+
}
|
|
16685
|
+
const matchedSpace = resolveSpaceFromArgs(args2.space, allSpaces);
|
|
16686
|
+
if (args2.space && !matchedSpace) {
|
|
16687
|
+
const availableSpaces = allSpaces.map((s) => ` - @${s.slug}`).join("\n");
|
|
16688
|
+
packmindCliHexa.output.notifyError(`Space "@${args2.space}" not found.`, {
|
|
16689
|
+
content: `Available spaces:
|
|
16690
|
+
${availableSpaces}`
|
|
16691
|
+
});
|
|
16692
|
+
exit(1);
|
|
16693
|
+
return;
|
|
16694
|
+
}
|
|
16695
|
+
const packages = await packmindCliHexa.output.withLoader(
|
|
16696
|
+
"Fetching packages",
|
|
16697
|
+
() => packmindCliHexa.listPackages(
|
|
16698
|
+
matchedSpace ? { spaceId: matchedSpace.id } : {}
|
|
16699
|
+
)
|
|
16700
|
+
);
|
|
16701
|
+
const spaces = matchedSpace ? [matchedSpace] : allSpaces;
|
|
16702
|
+
if (packages.length === 0) {
|
|
16703
|
+
packmindCliHexa.output.notifyInfo(
|
|
16704
|
+
matchedSpace ? `No packages found in space "@${matchedSpace.slug}".` : "No packages found."
|
|
16755
16705
|
);
|
|
16756
|
-
|
|
16706
|
+
exit(0);
|
|
16707
|
+
return;
|
|
16757
16708
|
}
|
|
16758
|
-
const
|
|
16759
|
-
const
|
|
16760
|
-
const
|
|
16761
|
-
|
|
16762
|
-
|
|
16763
|
-
|
|
16709
|
+
const buildUrl = resolveUrlBuilder((id) => `packages/${id}`);
|
|
16710
|
+
const groups = groupArtefactBySpaces(packages, spaces);
|
|
16711
|
+
const scopedArtefacts = groups.map(({ space, artefacts }) => ({
|
|
16712
|
+
title: `Space: ${space.name}`,
|
|
16713
|
+
artefacts: artefacts.map((pkg) => ({
|
|
16714
|
+
title: pkg.name,
|
|
16715
|
+
slug: `@${space.slug}/${pkg.slug}`,
|
|
16716
|
+
description: pkg.description,
|
|
16717
|
+
url: buildUrl(space.slug, pkg.id)
|
|
16718
|
+
}))
|
|
16719
|
+
}));
|
|
16720
|
+
const firstSlug = scopedArtefacts[0]?.artefacts[0]?.slug ?? `@${packages[0].slug}`;
|
|
16721
|
+
packmindCliHexa.output.listScopedArtefacts(
|
|
16722
|
+
`\u{1F4E6} Packages (${packages.length})`,
|
|
16723
|
+
scopedArtefacts,
|
|
16724
|
+
{
|
|
16725
|
+
content: "How to install a package:",
|
|
16726
|
+
exampleCommand: `packmind-cli install ${firstSlug}`
|
|
16727
|
+
}
|
|
16764
16728
|
);
|
|
16729
|
+
exit(0);
|
|
16730
|
+
} catch (err) {
|
|
16731
|
+
packmindCliHexa.output.notifyError("Failed to list packages:", {
|
|
16732
|
+
content: err instanceof Error ? err.message : String(err)
|
|
16733
|
+
});
|
|
16734
|
+
exit(1);
|
|
16765
16735
|
}
|
|
16766
|
-
}
|
|
16736
|
+
}
|
|
16767
16737
|
|
|
16768
16738
|
// apps/cli/src/infra/commands/listPackagesCommand.ts
|
|
16769
|
-
var import_cmd_ts22 = __toESM(require_cjs());
|
|
16770
16739
|
var listPackagesCommand = (0, import_cmd_ts22.command)({
|
|
16771
16740
|
name: "list",
|
|
16772
16741
|
description: "List available packages",
|
|
@@ -16790,6 +16759,124 @@ var listPackagesCommand = (0, import_cmd_ts22.command)({
|
|
|
16790
16759
|
|
|
16791
16760
|
// apps/cli/src/infra/commands/packages/showPackageCommand.ts
|
|
16792
16761
|
var import_cmd_ts23 = __toESM(require_cjs());
|
|
16762
|
+
|
|
16763
|
+
// apps/cli/src/infra/commands/packages/showPackageHandler.ts
|
|
16764
|
+
function isNotFoundError(err) {
|
|
16765
|
+
return err instanceof Error && err.message.includes("does not exist");
|
|
16766
|
+
}
|
|
16767
|
+
async function resolvePackage(slug3, packmindCliHexa) {
|
|
16768
|
+
const allSpaces = await packmindCliHexa.getSpaces();
|
|
16769
|
+
const parsed = parsePackageSlug(slug3);
|
|
16770
|
+
if (parsed) {
|
|
16771
|
+
const { spaceSlug, pkgSlug } = parsed;
|
|
16772
|
+
const matchedSpace = allSpaces.find((s) => s.slug === spaceSlug);
|
|
16773
|
+
if (!matchedSpace) {
|
|
16774
|
+
throw new Error(`Space '@${spaceSlug}' not found.`);
|
|
16775
|
+
}
|
|
16776
|
+
let pkg;
|
|
16777
|
+
try {
|
|
16778
|
+
pkg = await packmindCliHexa.getPackageBySlug({
|
|
16779
|
+
slug: pkgSlug,
|
|
16780
|
+
spaceId: matchedSpace.id
|
|
16781
|
+
});
|
|
16782
|
+
} catch (err) {
|
|
16783
|
+
if (isNotFoundError(err)) {
|
|
16784
|
+
throw new Error(
|
|
16785
|
+
`Package '${pkgSlug}' not found in space '@${spaceSlug}'.`
|
|
16786
|
+
);
|
|
16787
|
+
}
|
|
16788
|
+
throw err;
|
|
16789
|
+
}
|
|
16790
|
+
return { pkg, fullSlug: `@${spaceSlug}/${pkgSlug}` };
|
|
16791
|
+
}
|
|
16792
|
+
const results = await Promise.allSettled(
|
|
16793
|
+
allSpaces.map(async (space) => ({
|
|
16794
|
+
pkg: await packmindCliHexa.getPackageBySlug({
|
|
16795
|
+
slug: slug3,
|
|
16796
|
+
spaceId: space.id
|
|
16797
|
+
}),
|
|
16798
|
+
spaceSlug: space.slug
|
|
16799
|
+
}))
|
|
16800
|
+
);
|
|
16801
|
+
const matches = results.filter(
|
|
16802
|
+
(r) => r.status === "fulfilled"
|
|
16803
|
+
).map((r) => r.value);
|
|
16804
|
+
if (matches.length === 0) {
|
|
16805
|
+
const realError = results.filter((r) => r.status === "rejected").find((r) => !isNotFoundError(r.reason));
|
|
16806
|
+
if (realError) {
|
|
16807
|
+
throw realError.reason;
|
|
16808
|
+
}
|
|
16809
|
+
throw new Error(`Package '${slug3}' not found in any space.`);
|
|
16810
|
+
}
|
|
16811
|
+
if (matches.length > 1) {
|
|
16812
|
+
const example = `@${matches[0].spaceSlug}/${slug3}`;
|
|
16813
|
+
throw new Error(
|
|
16814
|
+
`Package '${slug3}' exists in multiple spaces (${matches.map((m) => `@${m.spaceSlug}`).join(", ")}). Please specify the space using the @space/package format (e.g. ${example}).`
|
|
16815
|
+
);
|
|
16816
|
+
}
|
|
16817
|
+
return {
|
|
16818
|
+
pkg: matches[0].pkg,
|
|
16819
|
+
fullSlug: `@${matches[0].spaceSlug}/${slug3}`
|
|
16820
|
+
};
|
|
16821
|
+
}
|
|
16822
|
+
async function showPackageHandler(args2, deps) {
|
|
16823
|
+
const { packmindCliHexa, exit } = deps;
|
|
16824
|
+
try {
|
|
16825
|
+
logInfoConsole(`Fetching package details for '${args2.slug}'...`);
|
|
16826
|
+
const { pkg, fullSlug } = await resolvePackage(args2.slug, packmindCliHexa);
|
|
16827
|
+
logConsole(`
|
|
16828
|
+
${pkg.name} (${fullSlug}):
|
|
16829
|
+
`);
|
|
16830
|
+
if (pkg.description) {
|
|
16831
|
+
logConsole(`${pkg.description}
|
|
16832
|
+
`);
|
|
16833
|
+
}
|
|
16834
|
+
if (pkg.standards && pkg.standards.length > 0) {
|
|
16835
|
+
logConsole("Standards:");
|
|
16836
|
+
pkg.standards.forEach((standard) => {
|
|
16837
|
+
if (standard.summary) {
|
|
16838
|
+
logConsole(` - ${standard.name}: ${standard.summary}`);
|
|
16839
|
+
} else {
|
|
16840
|
+
logConsole(` - ${standard.name}`);
|
|
16841
|
+
}
|
|
16842
|
+
});
|
|
16843
|
+
logConsole("");
|
|
16844
|
+
}
|
|
16845
|
+
if (pkg.recipes && pkg.recipes.length > 0) {
|
|
16846
|
+
logConsole("Commands:");
|
|
16847
|
+
pkg.recipes.forEach((recipe) => {
|
|
16848
|
+
if (recipe.summary) {
|
|
16849
|
+
logConsole(` - ${recipe.name}: ${recipe.summary}`);
|
|
16850
|
+
} else {
|
|
16851
|
+
logConsole(` - ${recipe.name}`);
|
|
16852
|
+
}
|
|
16853
|
+
});
|
|
16854
|
+
logConsole("");
|
|
16855
|
+
}
|
|
16856
|
+
if (pkg.skills && pkg.skills.length > 0) {
|
|
16857
|
+
logConsole("Skills:");
|
|
16858
|
+
pkg.skills.forEach((skill) => {
|
|
16859
|
+
if (skill.summary) {
|
|
16860
|
+
logConsole(` - ${skill.name}: ${skill.summary}`);
|
|
16861
|
+
} else {
|
|
16862
|
+
logConsole(` - ${skill.name}`);
|
|
16863
|
+
}
|
|
16864
|
+
});
|
|
16865
|
+
logConsole("");
|
|
16866
|
+
}
|
|
16867
|
+
exit(0);
|
|
16868
|
+
} catch (err) {
|
|
16869
|
+
logErrorConsole("Failed to fetch package details:");
|
|
16870
|
+
if (err instanceof Error) {
|
|
16871
|
+
logErrorConsole(err.message);
|
|
16872
|
+
} else {
|
|
16873
|
+
logErrorConsole(String(err));
|
|
16874
|
+
}
|
|
16875
|
+
exit(1);
|
|
16876
|
+
}
|
|
16877
|
+
}
|
|
16878
|
+
|
|
16879
|
+
// apps/cli/src/infra/commands/packages/showPackageCommand.ts
|
|
16793
16880
|
var showPackageCommand = (0, import_cmd_ts23.command)({
|
|
16794
16881
|
name: "show",
|
|
16795
16882
|
description: "Show details of a specific package",
|
|
@@ -16826,14 +16913,96 @@ var import_cmd_ts31 = __toESM(require_cjs());
|
|
|
16826
16913
|
var import_fs21 = require("fs");
|
|
16827
16914
|
var import_cmd_ts25 = __toESM(require_cjs());
|
|
16828
16915
|
|
|
16829
|
-
// apps/cli/src/infra/
|
|
16916
|
+
// apps/cli/src/infra/repositories/PlaybookLocalRepository.ts
|
|
16917
|
+
var crypto = __toESM(require("crypto"));
|
|
16830
16918
|
var fs23 = __toESM(require("fs"));
|
|
16831
|
-
var
|
|
16919
|
+
var os5 = __toESM(require("os"));
|
|
16920
|
+
var path23 = __toESM(require("path"));
|
|
16921
|
+
var yaml = __toESM(require("yaml"));
|
|
16922
|
+
var PlaybookLocalRepository = class {
|
|
16923
|
+
constructor(repoRoot) {
|
|
16924
|
+
const normalized = this.normalizeRepoRoot(repoRoot);
|
|
16925
|
+
const hash = crypto.createHash("md5").update(normalized).digest("hex");
|
|
16926
|
+
this.storagePath = path23.join(
|
|
16927
|
+
os5.homedir(),
|
|
16928
|
+
".packmind",
|
|
16929
|
+
hash,
|
|
16930
|
+
"playbook.yaml"
|
|
16931
|
+
);
|
|
16932
|
+
}
|
|
16933
|
+
addChange(entry) {
|
|
16934
|
+
const data = this.readYaml();
|
|
16935
|
+
const existingIndex = data.changes.findIndex(
|
|
16936
|
+
(c) => c.filePath === entry.filePath && c.spaceId === entry.spaceId
|
|
16937
|
+
);
|
|
16938
|
+
if (existingIndex >= 0) {
|
|
16939
|
+
data.changes[existingIndex] = entry;
|
|
16940
|
+
} else {
|
|
16941
|
+
data.changes.push(entry);
|
|
16942
|
+
}
|
|
16943
|
+
this.writeYaml(data);
|
|
16944
|
+
}
|
|
16945
|
+
removeChange(filePath, spaceId) {
|
|
16946
|
+
const data = this.readYaml();
|
|
16947
|
+
const initialLength = data.changes.length;
|
|
16948
|
+
data.changes = data.changes.filter(
|
|
16949
|
+
(c) => !(c.filePath === filePath && c.spaceId === spaceId)
|
|
16950
|
+
);
|
|
16951
|
+
if (data.changes.length === initialLength) {
|
|
16952
|
+
return false;
|
|
16953
|
+
}
|
|
16954
|
+
this.writeYaml(data);
|
|
16955
|
+
return true;
|
|
16956
|
+
}
|
|
16957
|
+
getChanges() {
|
|
16958
|
+
return this.readYaml().changes;
|
|
16959
|
+
}
|
|
16960
|
+
getChange(filePath, spaceId) {
|
|
16961
|
+
return this.readYaml().changes.find(
|
|
16962
|
+
(c) => c.filePath === filePath && c.spaceId === spaceId
|
|
16963
|
+
) ?? null;
|
|
16964
|
+
}
|
|
16965
|
+
clearAll() {
|
|
16966
|
+
this.writeYaml({ version: 1, changes: [] });
|
|
16967
|
+
}
|
|
16968
|
+
normalizeRepoRoot(repoRoot) {
|
|
16969
|
+
let normalized = repoRoot.replace(/\\/g, "/");
|
|
16970
|
+
normalized = normalized.replace(/\/$/, "");
|
|
16971
|
+
return normalized;
|
|
16972
|
+
}
|
|
16973
|
+
readYaml() {
|
|
16974
|
+
if (!fs23.existsSync(this.storagePath)) {
|
|
16975
|
+
return { version: 1, changes: [] };
|
|
16976
|
+
}
|
|
16977
|
+
try {
|
|
16978
|
+
const content = fs23.readFileSync(this.storagePath, "utf-8");
|
|
16979
|
+
const parsed = yaml.parse(content);
|
|
16980
|
+
if (!parsed || !Array.isArray(parsed.changes)) {
|
|
16981
|
+
return { version: 1, changes: [] };
|
|
16982
|
+
}
|
|
16983
|
+
return { version: 1, changes: parsed.changes };
|
|
16984
|
+
} catch {
|
|
16985
|
+
logWarningConsole(
|
|
16986
|
+
`Corrupted playbook file: ${this.storagePath}. Treating as empty.`
|
|
16987
|
+
);
|
|
16988
|
+
return { version: 1, changes: [] };
|
|
16989
|
+
}
|
|
16990
|
+
}
|
|
16991
|
+
writeYaml(data) {
|
|
16992
|
+
const dir = path23.dirname(this.storagePath);
|
|
16993
|
+
fs23.mkdirSync(dir, { recursive: true });
|
|
16994
|
+
fs23.writeFileSync(this.storagePath, yaml.stringify(data), "utf-8");
|
|
16995
|
+
}
|
|
16996
|
+
};
|
|
16997
|
+
|
|
16998
|
+
// apps/cli/src/infra/commands/playbook/addHandler.ts
|
|
16999
|
+
var fs24 = __toESM(require("fs"));
|
|
17000
|
+
var path27 = __toESM(require("path"));
|
|
16832
17001
|
var yaml2 = __toESM(require("yaml"));
|
|
16833
17002
|
var import_slug = __toESM(require("slug"));
|
|
16834
17003
|
|
|
16835
17004
|
// apps/cli/src/application/utils/parseCommandFile.ts
|
|
16836
|
-
var
|
|
17005
|
+
var path24 = __toESM(require("path"));
|
|
16837
17006
|
var FRONTMATTER_DELIMITER3 = "---";
|
|
16838
17007
|
function parseCommandFile(content, filePath) {
|
|
16839
17008
|
content = normalizeLineEndings(content);
|
|
@@ -16889,7 +17058,7 @@ function stripYamlQuotes2(value) {
|
|
|
16889
17058
|
return value;
|
|
16890
17059
|
}
|
|
16891
17060
|
function extractFilenameSlug(filePath) {
|
|
16892
|
-
let basename4 =
|
|
17061
|
+
let basename4 = path24.basename(filePath);
|
|
16893
17062
|
if (basename4.endsWith(".prompt.md")) {
|
|
16894
17063
|
basename4 = basename4.slice(0, -".prompt.md".length);
|
|
16895
17064
|
} else if (basename4.endsWith(".md")) {
|
|
@@ -17056,7 +17225,7 @@ function parseSkillDirectory(files) {
|
|
|
17056
17225
|
}
|
|
17057
17226
|
|
|
17058
17227
|
// apps/cli/src/application/utils/findNearestConfigDir.ts
|
|
17059
|
-
var
|
|
17228
|
+
var path25 = __toESM(require("path"));
|
|
17060
17229
|
async function findNearestConfigDir(startDir, packmindCliHexa) {
|
|
17061
17230
|
let current = startDir;
|
|
17062
17231
|
while (true) {
|
|
@@ -17064,7 +17233,7 @@ async function findNearestConfigDir(startDir, packmindCliHexa) {
|
|
|
17064
17233
|
if (exists) {
|
|
17065
17234
|
return current;
|
|
17066
17235
|
}
|
|
17067
|
-
const parent =
|
|
17236
|
+
const parent = path25.dirname(current);
|
|
17068
17237
|
if (parent === current) {
|
|
17069
17238
|
return null;
|
|
17070
17239
|
}
|
|
@@ -17073,7 +17242,7 @@ async function findNearestConfigDir(startDir, packmindCliHexa) {
|
|
|
17073
17242
|
}
|
|
17074
17243
|
|
|
17075
17244
|
// apps/cli/src/application/utils/resolveDeployedContext.ts
|
|
17076
|
-
var
|
|
17245
|
+
var path26 = __toESM(require("path"));
|
|
17077
17246
|
async function resolveDeployedContext(packmindCliHexa, targetDir) {
|
|
17078
17247
|
try {
|
|
17079
17248
|
const space = await packmindCliHexa.getDefaultSpace();
|
|
@@ -17085,7 +17254,7 @@ async function resolveDeployedContext(packmindCliHexa, targetDir) {
|
|
|
17085
17254
|
}
|
|
17086
17255
|
const gitRemoteUrl = packmindCliHexa.getGitRemoteUrlFromPath(gitRoot);
|
|
17087
17256
|
const gitBranch = packmindCliHexa.getCurrentBranch(gitRoot);
|
|
17088
|
-
const rel =
|
|
17257
|
+
const rel = path26.relative(gitRoot, targetDir);
|
|
17089
17258
|
const relativePath = rel.startsWith("..") ? "/" : rel ? `/${rel}/` : "/";
|
|
17090
17259
|
const deployedContent = await packmindCliHexa.getPackmindGateway().deployment.getDeployed({
|
|
17091
17260
|
packagesSlugs: configPackages,
|
|
@@ -17150,19 +17319,19 @@ async function fetchDeployedFiles(gateway, lockFile) {
|
|
|
17150
17319
|
|
|
17151
17320
|
// apps/cli/src/infra/commands/playbook/addHandler.ts
|
|
17152
17321
|
async function tryStageRemovedFromLockFile(resolvedPath, deps) {
|
|
17153
|
-
const fileDir =
|
|
17322
|
+
const fileDir = path27.dirname(resolvedPath);
|
|
17154
17323
|
const targetDir = await findNearestConfigDir(fileDir, deps.packmindCliHexa);
|
|
17155
17324
|
if (!targetDir) return false;
|
|
17156
17325
|
const lockFile = await deps.lockFileRepository.read(targetDir);
|
|
17157
17326
|
if (!lockFile) return false;
|
|
17158
|
-
const normalizedPath = normalizePath2(
|
|
17327
|
+
const normalizedPath = normalizePath2(path27.relative(targetDir, resolvedPath));
|
|
17159
17328
|
const lockEntry = findLockFileEntryForPath(
|
|
17160
17329
|
normalizedPath,
|
|
17161
17330
|
lockFile.artifacts
|
|
17162
17331
|
);
|
|
17163
17332
|
if (!lockEntry) return false;
|
|
17164
17333
|
const gitRoot = await deps.packmindCliHexa.tryGetGitRepositoryRoot(targetDir);
|
|
17165
|
-
const configDir = gitRoot ? normalizePath2(
|
|
17334
|
+
const configDir = gitRoot ? normalizePath2(path27.relative(gitRoot, targetDir)) : "";
|
|
17166
17335
|
const deployedContext = await resolveDeployedContext(
|
|
17167
17336
|
deps.packmindCliHexa,
|
|
17168
17337
|
targetDir
|
|
@@ -17194,22 +17363,22 @@ async function tryStageRemovedFromLockFile(resolvedPath, deps) {
|
|
|
17194
17363
|
}
|
|
17195
17364
|
function resolveSkillDirectoryRoot(absolutePath) {
|
|
17196
17365
|
if (absolutePath.endsWith("SKILL.md")) {
|
|
17197
|
-
return
|
|
17366
|
+
return path27.dirname(absolutePath);
|
|
17198
17367
|
}
|
|
17199
17368
|
try {
|
|
17200
|
-
if (
|
|
17369
|
+
if (fs24.statSync(absolutePath).isDirectory()) {
|
|
17201
17370
|
return absolutePath;
|
|
17202
17371
|
}
|
|
17203
17372
|
} catch {
|
|
17204
17373
|
return absolutePath;
|
|
17205
17374
|
}
|
|
17206
|
-
let current =
|
|
17207
|
-
const root =
|
|
17375
|
+
let current = path27.dirname(absolutePath);
|
|
17376
|
+
const root = path27.parse(current).root;
|
|
17208
17377
|
while (current !== root) {
|
|
17209
|
-
if (
|
|
17378
|
+
if (fs24.existsSync(path27.join(current, "SKILL.md"))) {
|
|
17210
17379
|
return current;
|
|
17211
17380
|
}
|
|
17212
|
-
current =
|
|
17381
|
+
current = path27.dirname(current);
|
|
17213
17382
|
}
|
|
17214
17383
|
return absolutePath;
|
|
17215
17384
|
}
|
|
@@ -17220,7 +17389,7 @@ async function playbookAddHandler(deps) {
|
|
|
17220
17389
|
spaceSlug,
|
|
17221
17390
|
exit,
|
|
17222
17391
|
cwd,
|
|
17223
|
-
readFile:
|
|
17392
|
+
readFile: readFile11,
|
|
17224
17393
|
readSkillDirectory: readSkillDirectory2,
|
|
17225
17394
|
playbookLocalRepository,
|
|
17226
17395
|
lockFileRepository
|
|
@@ -17232,17 +17401,17 @@ async function playbookAddHandler(deps) {
|
|
|
17232
17401
|
exit(1);
|
|
17233
17402
|
return;
|
|
17234
17403
|
}
|
|
17235
|
-
const absolutePath =
|
|
17404
|
+
const absolutePath = path27.resolve(cwd, filePath);
|
|
17236
17405
|
let artifactType;
|
|
17237
17406
|
let codingAgent;
|
|
17238
17407
|
const earlyTargetDir = await findNearestConfigDir(
|
|
17239
|
-
|
|
17408
|
+
path27.dirname(absolutePath),
|
|
17240
17409
|
packmindCliHexa
|
|
17241
17410
|
);
|
|
17242
17411
|
const earlyLockFile = earlyTargetDir ? await lockFileRepository.read(earlyTargetDir) : null;
|
|
17243
17412
|
if (earlyLockFile && earlyTargetDir) {
|
|
17244
17413
|
const normalizedForLookup = normalizePath2(
|
|
17245
|
-
|
|
17414
|
+
path27.relative(earlyTargetDir, absolutePath)
|
|
17246
17415
|
);
|
|
17247
17416
|
const lockResult = findLockFileEntryAndFileForPath(
|
|
17248
17417
|
normalizedForLookup,
|
|
@@ -17322,7 +17491,7 @@ async function playbookAddHandler(deps) {
|
|
|
17322
17491
|
localContent = skillMdFile?.content ?? serializedContent;
|
|
17323
17492
|
} else {
|
|
17324
17493
|
try {
|
|
17325
|
-
localContent =
|
|
17494
|
+
localContent = readFile11(absolutePath);
|
|
17326
17495
|
} catch (err) {
|
|
17327
17496
|
const staged = await tryStageRemovedFromLockFile(absolutePath, {
|
|
17328
17497
|
packmindCliHexa,
|
|
@@ -17376,7 +17545,7 @@ Content goes here...`
|
|
|
17376
17545
|
return;
|
|
17377
17546
|
}
|
|
17378
17547
|
const gitRoot = await packmindCliHexa.tryGetGitRepositoryRoot(targetDir);
|
|
17379
|
-
const configDir = gitRoot ? normalizePath2(
|
|
17548
|
+
const configDir = gitRoot ? normalizePath2(path27.relative(gitRoot, targetDir)) : "";
|
|
17380
17549
|
const deployedContext = await resolveDeployedContext(
|
|
17381
17550
|
packmindCliHexa,
|
|
17382
17551
|
targetDir
|
|
@@ -17384,7 +17553,7 @@ Content goes here...`
|
|
|
17384
17553
|
const targetId = deployedContext?.targetId ?? earlyLockFile?.targetId;
|
|
17385
17554
|
const normalizedFilePath = (() => {
|
|
17386
17555
|
const refPath = artifactType === "skill" && skillDirPath ? skillDirPath : absolutePath;
|
|
17387
|
-
return normalizePath2(
|
|
17556
|
+
return normalizePath2(path27.relative(targetDir, refPath));
|
|
17388
17557
|
})();
|
|
17389
17558
|
let spaceId;
|
|
17390
17559
|
let spaceName;
|
|
@@ -17499,7 +17668,7 @@ Run ${formatLabel("packmind-cli install")} to update before making changes.`
|
|
|
17499
17668
|
);
|
|
17500
17669
|
const allMatch = skillDeployedFiles.length > 0 && skillDeployedFiles.length === skillFiles.length && skillDeployedFiles.every((deployed) => {
|
|
17501
17670
|
const localFile = skillFiles.find(
|
|
17502
|
-
(f) => normalizePath2(
|
|
17671
|
+
(f) => normalizePath2(path27.join(normalizedFilePath, f.relativePath)) === normalizePath2(deployed.path)
|
|
17503
17672
|
);
|
|
17504
17673
|
return localFile && deployed.content?.trim() === localFile.content.trim() && (!deployed.skillFilePermissions || deployed.skillFilePermissions === localFile.permissions);
|
|
17505
17674
|
});
|
|
@@ -17611,8 +17780,8 @@ var addPlaybookCommand = (0, import_cmd_ts25.command)({
|
|
|
17611
17780
|
var import_cmd_ts26 = __toESM(require_cjs());
|
|
17612
17781
|
|
|
17613
17782
|
// apps/cli/src/infra/commands/playbook/rmHandler.ts
|
|
17614
|
-
var
|
|
17615
|
-
var
|
|
17783
|
+
var fs25 = __toESM(require("fs"));
|
|
17784
|
+
var path28 = __toESM(require("path"));
|
|
17616
17785
|
function isSkillSupportFile(absolutePath) {
|
|
17617
17786
|
const normalized = absolutePath.replace(/\\/g, "/");
|
|
17618
17787
|
const skillDirMatch = normalized.match(/\/skills\/[^/]+\//);
|
|
@@ -17639,14 +17808,14 @@ async function playbookRmHandler(deps) {
|
|
|
17639
17808
|
exit(1);
|
|
17640
17809
|
return;
|
|
17641
17810
|
}
|
|
17642
|
-
const absolutePath =
|
|
17643
|
-
if (!
|
|
17811
|
+
const absolutePath = path28.resolve(getCwd(), filePath);
|
|
17812
|
+
if (!fs25.existsSync(absolutePath)) {
|
|
17644
17813
|
logErrorConsole(`File not found: "${filePath}"`);
|
|
17645
17814
|
exit(1);
|
|
17646
17815
|
return;
|
|
17647
17816
|
}
|
|
17648
17817
|
const targetDir = await findNearestConfigDir(
|
|
17649
|
-
|
|
17818
|
+
path28.dirname(absolutePath),
|
|
17650
17819
|
packmindCliHexa
|
|
17651
17820
|
);
|
|
17652
17821
|
if (!targetDir) {
|
|
@@ -17663,7 +17832,7 @@ async function playbookRmHandler(deps) {
|
|
|
17663
17832
|
return;
|
|
17664
17833
|
}
|
|
17665
17834
|
const normalizedForLookup = normalizePath2(
|
|
17666
|
-
|
|
17835
|
+
path28.relative(targetDir, absolutePath)
|
|
17667
17836
|
);
|
|
17668
17837
|
const lockResult = findLockFileEntryAndFileForPath(
|
|
17669
17838
|
normalizedForLookup,
|
|
@@ -17685,7 +17854,7 @@ async function playbookRmHandler(deps) {
|
|
|
17685
17854
|
}
|
|
17686
17855
|
const resolvedAbsolutePath = artifactType === "skill" ? resolveSkillDirPath(absolutePath) : absolutePath;
|
|
17687
17856
|
const normalizedFilePath = normalizePath2(
|
|
17688
|
-
|
|
17857
|
+
path28.relative(targetDir, resolvedAbsolutePath)
|
|
17689
17858
|
);
|
|
17690
17859
|
const lockEntry = findLockFileEntryAndFileForPath(normalizedFilePath, lockFile.artifacts)?.entry ?? lockResult.entry;
|
|
17691
17860
|
if (!lockEntry) {
|
|
@@ -17713,7 +17882,7 @@ async function playbookRmHandler(deps) {
|
|
|
17713
17882
|
}
|
|
17714
17883
|
const spaceName = matchingSpace.name;
|
|
17715
17884
|
const gitRoot = await packmindCliHexa.tryGetGitRepositoryRoot(targetDir);
|
|
17716
|
-
const configDir = gitRoot ? normalizePath2(
|
|
17885
|
+
const configDir = gitRoot ? normalizePath2(path28.relative(gitRoot, targetDir)) : "";
|
|
17717
17886
|
const deployedContext = await resolveDeployedContext(
|
|
17718
17887
|
packmindCliHexa,
|
|
17719
17888
|
targetDir
|
|
@@ -17774,7 +17943,7 @@ var rmPlaybookCommand = (0, import_cmd_ts26.command)({
|
|
|
17774
17943
|
var import_cmd_ts27 = __toESM(require_cjs());
|
|
17775
17944
|
|
|
17776
17945
|
// apps/cli/src/infra/commands/playbook/unstageHandler.ts
|
|
17777
|
-
var
|
|
17946
|
+
var path29 = __toESM(require("path"));
|
|
17778
17947
|
async function playbookUnstageHandler(deps) {
|
|
17779
17948
|
const {
|
|
17780
17949
|
packmindCliHexa,
|
|
@@ -17792,10 +17961,10 @@ async function playbookUnstageHandler(deps) {
|
|
|
17792
17961
|
return;
|
|
17793
17962
|
}
|
|
17794
17963
|
const cwd = getCwd();
|
|
17795
|
-
const absolutePath =
|
|
17964
|
+
const absolutePath = path29.resolve(cwd, filePath);
|
|
17796
17965
|
const resolvedPath = resolveSkillDirPath(absolutePath);
|
|
17797
17966
|
const configDir = await findNearestConfigDir(
|
|
17798
|
-
|
|
17967
|
+
path29.dirname(resolvedPath),
|
|
17799
17968
|
packmindCliHexa
|
|
17800
17969
|
);
|
|
17801
17970
|
if (!configDir) {
|
|
@@ -17808,10 +17977,10 @@ async function playbookUnstageHandler(deps) {
|
|
|
17808
17977
|
const gitRoot = await packmindCliHexa.tryGetGitRepositoryRoot(cwd);
|
|
17809
17978
|
const baseDir = gitRoot ?? configDir;
|
|
17810
17979
|
const normalizedFilePath = normalizePath2(
|
|
17811
|
-
|
|
17980
|
+
path29.relative(baseDir, resolvedPath)
|
|
17812
17981
|
);
|
|
17813
17982
|
const matchingEntries = playbookLocalRepository.getChanges().filter((c) => {
|
|
17814
|
-
const fullEntryPath = c.configDir ? normalizePath2(
|
|
17983
|
+
const fullEntryPath = c.configDir ? normalizePath2(path29.join(c.configDir, c.filePath)) : c.filePath;
|
|
17815
17984
|
return fullEntryPath === normalizedFilePath;
|
|
17816
17985
|
});
|
|
17817
17986
|
if (matchingEntries.length === 0) {
|
|
@@ -17895,15 +18064,15 @@ var import_cmd_ts28 = __toESM(require_cjs());
|
|
|
17895
18064
|
|
|
17896
18065
|
// apps/cli/src/infra/utils/listDirectoryFiles.ts
|
|
17897
18066
|
var import_fs22 = require("fs");
|
|
17898
|
-
var
|
|
18067
|
+
var path30 = __toESM(require("path"));
|
|
17899
18068
|
function listDirectoryFiles(dirPath) {
|
|
17900
18069
|
const results = [];
|
|
17901
18070
|
const entries = (0, import_fs22.readdirSync)(dirPath, { withFileTypes: true });
|
|
17902
18071
|
for (const entry of entries) {
|
|
17903
|
-
const fullPath =
|
|
18072
|
+
const fullPath = path30.join(dirPath, entry.name);
|
|
17904
18073
|
if (entry.isDirectory()) {
|
|
17905
18074
|
for (const nested of listDirectoryFiles(fullPath)) {
|
|
17906
|
-
results.push(
|
|
18075
|
+
results.push(path30.join(entry.name, nested));
|
|
17907
18076
|
}
|
|
17908
18077
|
} else if (entry.isFile()) {
|
|
17909
18078
|
results.push(entry.name);
|
|
@@ -17913,7 +18082,7 @@ function listDirectoryFiles(dirPath) {
|
|
|
17913
18082
|
}
|
|
17914
18083
|
|
|
17915
18084
|
// apps/cli/src/infra/commands/playbook/statusHandler.ts
|
|
17916
|
-
var
|
|
18085
|
+
var path31 = __toESM(require("path"));
|
|
17917
18086
|
|
|
17918
18087
|
// apps/cli/src/infra/utils/stringUtils.ts
|
|
17919
18088
|
function capitalize(s) {
|
|
@@ -17948,7 +18117,7 @@ function groupStagedChanges(changes, cwd, gitRoot) {
|
|
|
17948
18117
|
const changeType = change.changeType ?? "updated";
|
|
17949
18118
|
const key = `${change.artifactType}:${change.artifactName}:${changeType}`;
|
|
17950
18119
|
const rootRelativePath = change.configDir ? `${change.configDir}/${change.filePath}` : change.filePath;
|
|
17951
|
-
const displayPath = gitRoot ? normalizePath2(
|
|
18120
|
+
const displayPath = gitRoot ? normalizePath2(path31.relative(cwd, path31.join(gitRoot, rootRelativePath))) : rootRelativePath;
|
|
17952
18121
|
const existing = groups.get(key);
|
|
17953
18122
|
if (existing) {
|
|
17954
18123
|
existing.filePaths.push(displayPath);
|
|
@@ -17989,7 +18158,7 @@ async function playbookStatusHandler(deps) {
|
|
|
17989
18158
|
lockFileRepository,
|
|
17990
18159
|
cwd,
|
|
17991
18160
|
exit,
|
|
17992
|
-
readFile:
|
|
18161
|
+
readFile: readFile11,
|
|
17993
18162
|
listDirectoryFiles: listDirectoryFiles2,
|
|
17994
18163
|
getFileMode
|
|
17995
18164
|
} = deps;
|
|
@@ -18006,12 +18175,12 @@ async function playbookStatusHandler(deps) {
|
|
|
18006
18175
|
const fallbackConfigDir = await findNearestConfigDir(cwd, packmindCliHexa);
|
|
18007
18176
|
const configDirs = /* @__PURE__ */ new Set([...stagedByConfigDir.keys()]);
|
|
18008
18177
|
if (fallbackConfigDir && !configDirs.has("__cwd__")) {
|
|
18009
|
-
const rel = gitRoot ? normalizePath2(
|
|
18178
|
+
const rel = gitRoot ? normalizePath2(path31.relative(gitRoot, fallbackConfigDir)) : "";
|
|
18010
18179
|
if (!configDirs.has(rel)) configDirs.add(rel);
|
|
18011
18180
|
}
|
|
18012
18181
|
const descendantDirs = await packmindCliHexa.findDescendantConfigs(cwd);
|
|
18013
18182
|
for (const descendantDir of descendantDirs) {
|
|
18014
|
-
const rel = gitRoot ? normalizePath2(
|
|
18183
|
+
const rel = gitRoot ? normalizePath2(path31.relative(gitRoot, descendantDir)) : normalizePath2(path31.relative(cwd, descendantDir));
|
|
18015
18184
|
if (!configDirs.has(rel)) configDirs.add(rel);
|
|
18016
18185
|
}
|
|
18017
18186
|
for (const configDirKey of configDirs) {
|
|
@@ -18019,7 +18188,7 @@ async function playbookStatusHandler(deps) {
|
|
|
18019
18188
|
if (configDirKey === "__cwd__") {
|
|
18020
18189
|
projectDir = fallbackConfigDir;
|
|
18021
18190
|
} else if (gitRoot) {
|
|
18022
|
-
projectDir =
|
|
18191
|
+
projectDir = path31.join(gitRoot, configDirKey);
|
|
18023
18192
|
} else {
|
|
18024
18193
|
continue;
|
|
18025
18194
|
}
|
|
@@ -18044,11 +18213,11 @@ async function playbookStatusHandler(deps) {
|
|
|
18044
18213
|
continue;
|
|
18045
18214
|
}
|
|
18046
18215
|
const displayPath = normalizePath2(
|
|
18047
|
-
|
|
18216
|
+
path31.relative(cwd, path31.join(projectDir, deployedFile.path))
|
|
18048
18217
|
);
|
|
18049
18218
|
let localContent;
|
|
18050
18219
|
try {
|
|
18051
|
-
localContent =
|
|
18220
|
+
localContent = readFile11(path31.join(projectDir, deployedFile.path));
|
|
18052
18221
|
} catch {
|
|
18053
18222
|
const artifact = findArtifactForFile(
|
|
18054
18223
|
deployedFile.path,
|
|
@@ -18077,7 +18246,7 @@ async function playbookStatusHandler(deps) {
|
|
|
18077
18246
|
});
|
|
18078
18247
|
}
|
|
18079
18248
|
} else if (deployedFile.skillFilePermissions && getFileMode) {
|
|
18080
|
-
const localMode = getFileMode(
|
|
18249
|
+
const localMode = getFileMode(path31.join(projectDir, deployedFile.path));
|
|
18081
18250
|
if (localMode !== null) {
|
|
18082
18251
|
const localPermissions = modeToPermissionStringOrDefault(localMode);
|
|
18083
18252
|
if (localPermissions !== deployedFile.skillFilePermissions) {
|
|
@@ -18106,13 +18275,13 @@ async function playbookStatusHandler(deps) {
|
|
|
18106
18275
|
(f) => normalizePath2(f.path).endsWith("/SKILL.md")
|
|
18107
18276
|
);
|
|
18108
18277
|
if (!skillMdFile) continue;
|
|
18109
|
-
const skillDir = normalizePath2(
|
|
18278
|
+
const skillDir = normalizePath2(path31.dirname(skillMdFile.path));
|
|
18110
18279
|
if (targetStagedPaths.has(skillDir) || targetSkillDirPaths.some(
|
|
18111
18280
|
(staged) => skillDir === staged || skillDir.startsWith(staged + "/")
|
|
18112
18281
|
)) {
|
|
18113
18282
|
continue;
|
|
18114
18283
|
}
|
|
18115
|
-
const absoluteSkillDir =
|
|
18284
|
+
const absoluteSkillDir = path31.join(projectDir, skillDir);
|
|
18116
18285
|
let localFiles;
|
|
18117
18286
|
try {
|
|
18118
18287
|
localFiles = listDirectoryFiles2(absoluteSkillDir);
|
|
@@ -18121,11 +18290,11 @@ async function playbookStatusHandler(deps) {
|
|
|
18121
18290
|
}
|
|
18122
18291
|
for (const localRelPath of localFiles) {
|
|
18123
18292
|
const normalizedLocalPath = normalizePath2(
|
|
18124
|
-
|
|
18293
|
+
path31.join(skillDir, localRelPath)
|
|
18125
18294
|
);
|
|
18126
18295
|
if (!deployedPathSet.has(normalizedLocalPath)) {
|
|
18127
18296
|
const displayPath = normalizePath2(
|
|
18128
|
-
|
|
18297
|
+
path31.relative(cwd, path31.join(projectDir, normalizedLocalPath))
|
|
18129
18298
|
);
|
|
18130
18299
|
untrackedChanges.push({
|
|
18131
18300
|
artifactName: entry.name,
|
|
@@ -18213,7 +18382,7 @@ var import_path5 = require("path");
|
|
|
18213
18382
|
var import_cmd_ts29 = __toESM(require_cjs());
|
|
18214
18383
|
|
|
18215
18384
|
// apps/cli/src/infra/commands/playbook/submitHandler.ts
|
|
18216
|
-
var
|
|
18385
|
+
var path33 = __toESM(require("path"));
|
|
18217
18386
|
|
|
18218
18387
|
// apps/cli/src/infra/commands/playbook/submit/duplicateNameChecker.ts
|
|
18219
18388
|
var import_slug2 = __toESM(require("slug"));
|
|
@@ -18275,7 +18444,7 @@ async function checkForDuplicateNames(createdEntries, packmindGateway) {
|
|
|
18275
18444
|
}
|
|
18276
18445
|
|
|
18277
18446
|
// apps/cli/src/infra/commands/playbook/submit/targetContextResolver.ts
|
|
18278
|
-
var
|
|
18447
|
+
var path32 = __toESM(require("path"));
|
|
18279
18448
|
async function createTargetContextResolver(deps) {
|
|
18280
18449
|
const { lockFileRepository, cwd, packmindCliHexa } = deps;
|
|
18281
18450
|
const gitRoot = await packmindCliHexa.tryGetGitRepositoryRoot(cwd);
|
|
@@ -18286,7 +18455,7 @@ async function createTargetContextResolver(deps) {
|
|
|
18286
18455
|
if (cache.has(key)) return cache.get(key);
|
|
18287
18456
|
let projectDir;
|
|
18288
18457
|
if (entry.configDir !== void 0 && gitRoot) {
|
|
18289
|
-
projectDir =
|
|
18458
|
+
projectDir = path32.join(gitRoot, entry.configDir);
|
|
18290
18459
|
} else {
|
|
18291
18460
|
projectDir = await findNearestConfigDir(cwd, packmindCliHexa);
|
|
18292
18461
|
}
|
|
@@ -19234,7 +19403,7 @@ Only one agent version can be submitted at a time. Use "playbook unstage" to rem
|
|
|
19234
19403
|
const entryCtx = resolver.getCachedContext(entry.configDir);
|
|
19235
19404
|
if (!entryCtx?.projectDir) continue;
|
|
19236
19405
|
try {
|
|
19237
|
-
const fullPath =
|
|
19406
|
+
const fullPath = path33.join(entryCtx.projectDir, entry.filePath);
|
|
19238
19407
|
if (entry.artifactType === "skill") {
|
|
19239
19408
|
deps.rmSync(fullPath, { recursive: true });
|
|
19240
19409
|
} else {
|
|
@@ -19262,7 +19431,7 @@ Only one agent version can be submitted at a time. Use "playbook unstage" to rem
|
|
|
19262
19431
|
const entryCtx = resolver.getCachedContext(entry.configDir);
|
|
19263
19432
|
if (!entryCtx?.projectDir) continue;
|
|
19264
19433
|
try {
|
|
19265
|
-
const fullPath =
|
|
19434
|
+
const fullPath = path33.join(entryCtx.projectDir, entry.filePath);
|
|
19266
19435
|
if (entry.artifactType === "skill") {
|
|
19267
19436
|
deps.rmSync(fullPath, { recursive: true });
|
|
19268
19437
|
} else {
|
|
@@ -19384,7 +19553,7 @@ var diffCommand2 = (0, import_cmd_ts30.command)({
|
|
|
19384
19553
|
type: (0, import_cmd_ts30.optional)(import_cmd_ts30.string)
|
|
19385
19554
|
})
|
|
19386
19555
|
},
|
|
19387
|
-
handler: async ({ includeSubmitted, path:
|
|
19556
|
+
handler: async ({ includeSubmitted, path: path37 }) => {
|
|
19388
19557
|
const packmindLogger = new PackmindLogger("PackmindCLI", "info" /* INFO */);
|
|
19389
19558
|
const packmindCliHexa = new PackmindCliHexa(packmindLogger);
|
|
19390
19559
|
await diffArtefactsHandler({
|
|
@@ -19393,7 +19562,7 @@ var diffCommand2 = (0, import_cmd_ts30.command)({
|
|
|
19393
19562
|
getCwd: () => process.cwd(),
|
|
19394
19563
|
log: console.log,
|
|
19395
19564
|
includeSubmitted,
|
|
19396
|
-
path:
|
|
19565
|
+
path: path37
|
|
19397
19566
|
});
|
|
19398
19567
|
}
|
|
19399
19568
|
});
|
|
@@ -19482,8 +19651,8 @@ var import_cmd_ts39 = __toESM(require_cjs());
|
|
|
19482
19651
|
var import_cmd_ts38 = __toESM(require_cjs());
|
|
19483
19652
|
|
|
19484
19653
|
// apps/cli/src/application/services/AgentArtifactDetectionService.ts
|
|
19485
|
-
var
|
|
19486
|
-
var
|
|
19654
|
+
var fs26 = __toESM(require("fs/promises"));
|
|
19655
|
+
var path34 = __toESM(require("path"));
|
|
19487
19656
|
var AGENT_ARTIFACT_CHECKS = [
|
|
19488
19657
|
{ agent: "claude", paths: [".claude"] },
|
|
19489
19658
|
{ agent: "cursor", paths: [".cursor"] },
|
|
@@ -19512,7 +19681,7 @@ var AgentArtifactDetectionService = class {
|
|
|
19512
19681
|
}
|
|
19513
19682
|
} else {
|
|
19514
19683
|
for (const relativePath of check.paths) {
|
|
19515
|
-
const fullPath =
|
|
19684
|
+
const fullPath = path34.join(baseDirectory, relativePath);
|
|
19516
19685
|
const exists = await this.pathExists(fullPath);
|
|
19517
19686
|
if (exists) {
|
|
19518
19687
|
detected.push({
|
|
@@ -19528,7 +19697,7 @@ var AgentArtifactDetectionService = class {
|
|
|
19528
19697
|
}
|
|
19529
19698
|
async pathExists(filePath) {
|
|
19530
19699
|
try {
|
|
19531
|
-
await
|
|
19700
|
+
await fs26.access(filePath);
|
|
19532
19701
|
return true;
|
|
19533
19702
|
} catch {
|
|
19534
19703
|
return false;
|
|
@@ -19539,16 +19708,16 @@ var AgentArtifactDetectionService = class {
|
|
|
19539
19708
|
while (queue.length > 0) {
|
|
19540
19709
|
const currentDir = queue.shift();
|
|
19541
19710
|
for (const targetPath of targetPaths) {
|
|
19542
|
-
const fullPath =
|
|
19711
|
+
const fullPath = path34.join(currentDir, targetPath);
|
|
19543
19712
|
if (await this.pathExists(fullPath)) {
|
|
19544
19713
|
return fullPath;
|
|
19545
19714
|
}
|
|
19546
19715
|
}
|
|
19547
19716
|
try {
|
|
19548
|
-
const entries = await
|
|
19717
|
+
const entries = await fs26.readdir(currentDir, { withFileTypes: true });
|
|
19549
19718
|
for (const entry of entries) {
|
|
19550
19719
|
if (entry.isDirectory() && !entry.name.startsWith(".") && entry.name !== "node_modules") {
|
|
19551
|
-
queue.push(
|
|
19720
|
+
queue.push(path34.join(currentDir, entry.name));
|
|
19552
19721
|
}
|
|
19553
19722
|
}
|
|
19554
19723
|
} catch {
|
|
@@ -19563,18 +19732,18 @@ var readline4 = __toESM(require("readline"));
|
|
|
19563
19732
|
var inquirer2 = __toESM(require("inquirer"));
|
|
19564
19733
|
|
|
19565
19734
|
// apps/cli/src/infra/commands/config/agents/agentsHandlerUtils.ts
|
|
19566
|
-
var
|
|
19567
|
-
var
|
|
19735
|
+
var path35 = __toESM(require("path"));
|
|
19736
|
+
var fs27 = __toESM(require("fs/promises"));
|
|
19568
19737
|
function getRelativePath(dir, startDirectory) {
|
|
19569
19738
|
if (dir === startDirectory) return "./packmind.json";
|
|
19570
|
-
return "./" +
|
|
19739
|
+
return "./" + path35.relative(startDirectory, dir) + "/packmind.json";
|
|
19571
19740
|
}
|
|
19572
19741
|
async function resolveStartDirectory(args2, getCwd, exit) {
|
|
19573
19742
|
let startDirectory = getCwd();
|
|
19574
19743
|
if (args2.path) {
|
|
19575
|
-
const resolvedPath =
|
|
19744
|
+
const resolvedPath = path35.resolve(getCwd(), args2.path);
|
|
19576
19745
|
try {
|
|
19577
|
-
const stat9 = await
|
|
19746
|
+
const stat9 = await fs27.stat(resolvedPath);
|
|
19578
19747
|
if (!stat9.isDirectory()) {
|
|
19579
19748
|
logErrorConsole(`Path is not a directory: ${resolvedPath}`);
|
|
19580
19749
|
exit(1);
|
|
@@ -19685,7 +19854,7 @@ async function promptAgentsWithReadline2(choices) {
|
|
|
19685
19854
|
output.write("\n");
|
|
19686
19855
|
const preselected = choices.map((c, i) => c.checked ? i + 1 : null).filter((i) => i !== null);
|
|
19687
19856
|
const defaultValue = preselected.length > 0 ? preselected.join(",") : "1,2,3";
|
|
19688
|
-
return new Promise((
|
|
19857
|
+
return new Promise((resolve15) => {
|
|
19689
19858
|
rl.question(
|
|
19690
19859
|
`Enter numbers separated by commas (default: ${defaultValue}): `,
|
|
19691
19860
|
(answer) => {
|
|
@@ -19694,7 +19863,7 @@ async function promptAgentsWithReadline2(choices) {
|
|
|
19694
19863
|
const numbersStr = trimmed === "" ? defaultValue : trimmed;
|
|
19695
19864
|
const numbers = numbersStr.split(",").map((s) => parseInt(s.trim(), 10)).filter((n) => !isNaN(n) && n >= 1 && n <= choices.length);
|
|
19696
19865
|
const selectedAgents = numbers.map((n) => choices[n - 1].value);
|
|
19697
|
-
|
|
19866
|
+
resolve15(selectedAgents);
|
|
19698
19867
|
}
|
|
19699
19868
|
);
|
|
19700
19869
|
});
|
|
@@ -19841,14 +20010,14 @@ To restore organization settings later, remove all local agents with: packmind-c
|
|
|
19841
20010
|
|
|
19842
20011
|
// apps/cli/src/infra/commands/config/ConfigAgentsAddCommand.ts
|
|
19843
20012
|
function createPromptConfirm() {
|
|
19844
|
-
return (message) => new Promise((
|
|
20013
|
+
return (message) => new Promise((resolve15) => {
|
|
19845
20014
|
const rl = readline5.createInterface({
|
|
19846
20015
|
input: process.stdin,
|
|
19847
20016
|
output: process.stdout
|
|
19848
20017
|
});
|
|
19849
20018
|
rl.question(`${message} (y/N) `, (answer) => {
|
|
19850
20019
|
rl.close();
|
|
19851
|
-
|
|
20020
|
+
resolve15(answer.toLowerCase() === "y");
|
|
19852
20021
|
});
|
|
19853
20022
|
});
|
|
19854
20023
|
}
|
|
@@ -20263,20 +20432,20 @@ function findEnvFile() {
|
|
|
20263
20432
|
const currentDir = process.cwd();
|
|
20264
20433
|
const gitService = new GitService();
|
|
20265
20434
|
const gitRoot = gitService.getGitRepositoryRootSync(currentDir);
|
|
20266
|
-
const filesystemRoot =
|
|
20435
|
+
const filesystemRoot = path36.parse(currentDir).root;
|
|
20267
20436
|
const stopDir = gitRoot ?? filesystemRoot;
|
|
20268
20437
|
let searchDir = currentDir;
|
|
20269
|
-
let parentDir =
|
|
20438
|
+
let parentDir = path36.dirname(searchDir);
|
|
20270
20439
|
while (searchDir !== parentDir) {
|
|
20271
|
-
const envPath2 =
|
|
20272
|
-
if (
|
|
20440
|
+
const envPath2 = path36.join(searchDir, ".env");
|
|
20441
|
+
if (fs28.existsSync(envPath2)) {
|
|
20273
20442
|
return envPath2;
|
|
20274
20443
|
}
|
|
20275
20444
|
if (searchDir === stopDir) {
|
|
20276
20445
|
return null;
|
|
20277
20446
|
}
|
|
20278
20447
|
searchDir = parentDir;
|
|
20279
|
-
parentDir =
|
|
20448
|
+
parentDir = path36.dirname(searchDir);
|
|
20280
20449
|
}
|
|
20281
20450
|
return null;
|
|
20282
20451
|
}
|