@unbrained/pm-cli 2026.5.11 → 2026.5.14
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/AGENTS.md +3 -116
- package/CHANGELOG.md +18 -0
- package/PRD.md +18 -39
- package/README.md +8 -5
- package/dist/cli/commander-usage.js +27 -0
- package/dist/cli/commander-usage.js.map +1 -1
- package/dist/cli/commands/activity.js +19 -4
- package/dist/cli/commands/activity.js.map +1 -1
- package/dist/cli/commands/calendar.js +5 -2
- package/dist/cli/commands/calendar.js.map +1 -1
- package/dist/cli/commands/contracts.js +63 -19
- package/dist/cli/commands/contracts.js.map +1 -1
- package/dist/cli/commands/create.js +58 -3
- package/dist/cli/commands/create.js.map +1 -1
- package/dist/cli/commands/extension.d.ts +14 -3
- package/dist/cli/commands/extension.js +481 -95
- package/dist/cli/commands/extension.js.map +1 -1
- package/dist/cli/commands/index.d.ts +1 -8
- package/dist/cli/commands/index.js +1 -8
- package/dist/cli/commands/index.js.map +1 -1
- package/dist/cli/commands/reindex.d.ts +8 -0
- package/dist/cli/commands/reindex.js +96 -23
- package/dist/cli/commands/reindex.js.map +1 -1
- package/dist/cli/commands/search.js +51 -25
- package/dist/cli/commands/search.js.map +1 -1
- package/dist/cli/commands/test.js +14 -6
- package/dist/cli/commands/test.js.map +1 -1
- package/dist/cli/commands/upgrade.d.ts +63 -0
- package/dist/cli/commands/upgrade.js +260 -0
- package/dist/cli/commands/upgrade.js.map +1 -0
- package/dist/cli/guide-topics.js +18 -16
- package/dist/cli/guide-topics.js.map +1 -1
- package/dist/cli/help-content.js +57 -18
- package/dist/cli/help-content.js.map +1 -1
- package/dist/cli/main.js +73 -7
- package/dist/cli/main.js.map +1 -1
- package/dist/cli/register-list-query.js +24 -142
- package/dist/cli/register-list-query.js.map +1 -1
- package/dist/cli/register-mutation.js +49 -257
- package/dist/cli/register-mutation.js.map +1 -1
- package/dist/cli/register-operations.js +29 -198
- package/dist/cli/register-operations.js.map +1 -1
- package/dist/cli/register-setup.js +181 -204
- package/dist/cli/register-setup.js.map +1 -1
- package/dist/cli/registration-helpers.d.ts +2 -2
- package/dist/cli/registration-helpers.js +1 -19
- package/dist/cli/registration-helpers.js.map +1 -1
- package/dist/core/extensions/loader.js +7 -1
- package/dist/core/extensions/loader.js.map +1 -1
- package/dist/core/packages/manifest.d.ts +38 -0
- package/dist/core/packages/manifest.js +221 -0
- package/dist/core/packages/manifest.js.map +1 -0
- package/dist/core/search/embedding-batches.d.ts +13 -1
- package/dist/core/search/embedding-batches.js +19 -1
- package/dist/core/search/embedding-batches.js.map +1 -1
- package/dist/core/store/front-matter-cache.d.ts +8 -1
- package/dist/core/store/front-matter-cache.js +20 -11
- package/dist/core/store/front-matter-cache.js.map +1 -1
- package/dist/mcp/server.d.ts +8 -0
- package/dist/mcp/server.js +100 -43
- package/dist/mcp/server.js.map +1 -1
- package/dist/sdk/cli-contracts/commander-mutation-options.d.ts +7 -0
- package/dist/sdk/cli-contracts/commander-mutation-options.js +477 -0
- package/dist/sdk/cli-contracts/commander-mutation-options.js.map +1 -0
- package/dist/sdk/cli-contracts/commander-types.d.ts +21 -0
- package/dist/sdk/cli-contracts/commander-types.js +92 -0
- package/dist/sdk/cli-contracts/commander-types.js.map +1 -0
- package/dist/sdk/cli-contracts.d.ts +22 -32
- package/dist/sdk/cli-contracts.js +155 -296
- package/dist/sdk/cli-contracts.js.map +1 -1
- package/dist/sdk/index.d.ts +2 -0
- package/dist/sdk/index.js +2 -0
- package/dist/sdk/index.js.map +1 -1
- package/dist/sdk/runtime.d.ts +29 -0
- package/dist/sdk/runtime.js +28 -0
- package/dist/sdk/runtime.js.map +1 -0
- package/docs/ARCHITECTURE.md +1 -1
- package/docs/COMMANDS.md +17 -1
- package/docs/EXTENSIONS.md +169 -61
- package/docs/QUICKSTART.md +11 -2
- package/docs/README.md +4 -6
- package/docs/RELEASING.md +4 -2
- package/docs/SDK.md +79 -438
- package/package.json +6 -23
- package/packages/pm-beads/README.md +10 -0
- package/packages/pm-beads/extensions/beads/index.js +113 -0
- package/{.agents/pm/extensions/beads/index.js → packages/pm-beads/extensions/beads/index.ts} +42 -20
- package/{.agents/pm → packages/pm-beads}/extensions/beads/runtime.js +2 -17
- package/{.agents/pm → packages/pm-beads}/extensions/beads/runtime.ts +41 -18
- package/packages/pm-beads/package.json +50 -0
- package/packages/pm-calendar/README.md +13 -0
- package/packages/pm-calendar/extensions/calendar/index.js +56 -0
- package/packages/pm-calendar/extensions/calendar/index.ts +62 -0
- package/packages/pm-calendar/extensions/calendar/manifest.json +7 -0
- package/packages/pm-calendar/extensions/calendar/runtime.js +95 -0
- package/packages/pm-calendar/extensions/calendar/runtime.ts +104 -0
- package/packages/pm-calendar/package.json +51 -0
- package/packages/pm-governance-audit/README.md +23 -0
- package/packages/pm-governance-audit/extensions/governance-audit/index.js +117 -0
- package/packages/pm-governance-audit/extensions/governance-audit/index.ts +118 -0
- package/packages/pm-governance-audit/extensions/governance-audit/manifest.json +7 -0
- package/packages/pm-governance-audit/extensions/governance-audit/runtime.js +159 -0
- package/packages/pm-governance-audit/extensions/governance-audit/runtime.ts +176 -0
- package/packages/pm-governance-audit/package.json +52 -0
- package/packages/pm-guide-shell/README.md +23 -0
- package/packages/pm-guide-shell/extensions/guide-shell/index.js +76 -0
- package/packages/pm-guide-shell/extensions/guide-shell/index.ts +81 -0
- package/packages/pm-guide-shell/extensions/guide-shell/manifest.json +7 -0
- package/packages/pm-guide-shell/extensions/guide-shell/runtime.js +263 -0
- package/packages/pm-guide-shell/extensions/guide-shell/runtime.ts +327 -0
- package/packages/pm-guide-shell/package.json +52 -0
- package/packages/pm-linked-test-adapters/README.md +24 -0
- package/packages/pm-linked-test-adapters/extensions/linked-test-adapters/index.js +101 -0
- package/packages/pm-linked-test-adapters/extensions/linked-test-adapters/index.ts +102 -0
- package/packages/pm-linked-test-adapters/extensions/linked-test-adapters/manifest.json +7 -0
- package/packages/pm-linked-test-adapters/extensions/linked-test-adapters/runtime.js +142 -0
- package/packages/pm-linked-test-adapters/extensions/linked-test-adapters/runtime.ts +173 -0
- package/packages/pm-linked-test-adapters/package.json +53 -0
- package/packages/pm-search-advanced/README.md +27 -0
- package/packages/pm-search-advanced/extensions/search-advanced/index.js +93 -0
- package/packages/pm-search-advanced/extensions/search-advanced/index.ts +94 -0
- package/packages/pm-search-advanced/extensions/search-advanced/manifest.json +7 -0
- package/packages/pm-search-advanced/extensions/search-advanced/runtime.js +120 -0
- package/packages/pm-search-advanced/extensions/search-advanced/runtime.ts +144 -0
- package/packages/pm-search-advanced/package.json +54 -0
- package/packages/pm-templates/README.md +20 -0
- package/packages/pm-templates/extensions/templates/index.js +101 -0
- package/packages/pm-templates/extensions/templates/index.ts +109 -0
- package/packages/pm-templates/extensions/templates/manifest.json +7 -0
- package/packages/pm-templates/extensions/templates/runtime.js +226 -0
- package/packages/pm-templates/extensions/templates/runtime.ts +283 -0
- package/packages/pm-templates/package.json +50 -0
- package/packages/pm-todos/README.md +11 -0
- package/packages/pm-todos/extensions/todos/index.js +130 -0
- package/{.agents/pm/extensions/todos/index.js → packages/pm-todos/extensions/todos/index.ts} +47 -23
- package/{.agents/pm → packages/pm-todos}/extensions/todos/runtime.js +3 -18
- package/{.agents/pm → packages/pm-todos}/extensions/todos/runtime.ts +42 -20
- package/packages/pm-todos/package.json +51 -0
- package/plugins/pm-cli-claude/README.md +1 -2
- package/plugins/pm-cli-claude/hooks/session-start.mjs +4 -55
- package/plugins/pm-cli-claude/scripts/pm-mcp-server.mjs +4 -2
- package/plugins/pm-cli-codex/scripts/pm-mcp-server.mjs +4 -2
- package/.agents/pm/extensions/.managed-extensions.json +0 -42
- package/.agents/skills/HARNESS_COMPATIBILITY.md +0 -45
- package/.agents/skills/README.md +0 -21
- package/.agents/skills/pm-developer/SKILL.md +0 -73
- package/.agents/skills/pm-developer/references/COMMAND_PLAYBOOK.md +0 -48
- package/.agents/skills/pm-developer/references/PROMPTS.md +0 -17
- package/.agents/skills/pm-extensions/SKILL.md +0 -57
- package/.agents/skills/pm-extensions/references/LIFECYCLE.md +0 -40
- package/.agents/skills/pm-extensions/references/TROUBLESHOOTING.md +0 -25
- package/.agents/skills/pm-sdk/SKILL.md +0 -50
- package/.agents/skills/pm-sdk/references/INTEGRATION_CHECKLIST.md +0 -31
- package/.agents/skills/pm-sdk/references/PROMPTS.md +0 -13
- package/.agents/skills/pm-user/SKILL.md +0 -59
- package/.agents/skills/pm-user/references/PROMPTS.md +0 -17
- package/.agents/skills/pm-user/references/WORKFLOWS.md +0 -35
- package/.pi/README.md +0 -35
- package/.pi/agents/pm-triage-agent.md +0 -19
- package/.pi/agents/pm-verification-agent.md +0 -21
- package/.pi/chains/pm-native-delivery.chain.md +0 -11
- package/.pi/extensions/pm-cli/index.js +0 -387
- package/.pi/prompts/pm-workflow.md +0 -5
- package/.pi/skills/pm-native/SKILL.md +0 -44
- package/.pi/skills/pm-release/SKILL.md +0 -35
- package/dist/pi/native.d.ts +0 -5
- package/dist/pi/native.js +0 -236
- package/dist/pi/native.js.map +0 -1
- package/docs/PI_PACKAGE.md +0 -141
- /package/{.agents/pm → packages/pm-beads}/extensions/beads/manifest.json +0 -0
- /package/{.agents/pm → packages/pm-todos}/extensions/todos/manifest.json +0 -0
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
import path from "node:path";
|
|
2
|
+
import { fileURLToPath, pathToFileURL } from "node:url";
|
|
3
|
+
const PM_PACKAGE_ROOT_ENV = "PM_CLI_PACKAGE_ROOT";
|
|
4
|
+
const CURRENT_EXTENSION_ROOT = path.dirname(fileURLToPath(import.meta.url));
|
|
5
|
+
export const manifest = {
|
|
6
|
+
name: "builtin-todos-import-export",
|
|
7
|
+
version: "0.1.0",
|
|
8
|
+
entry: "./index.js",
|
|
9
|
+
priority: 0,
|
|
10
|
+
capabilities: ["commands", "schema"],
|
|
11
|
+
};
|
|
12
|
+
function asOptionalString(value) {
|
|
13
|
+
return typeof value === "string" ? value : undefined;
|
|
14
|
+
}
|
|
15
|
+
function toImportOptions(options) {
|
|
16
|
+
return {
|
|
17
|
+
folder: asOptionalString(options.folder),
|
|
18
|
+
author: asOptionalString(options.author),
|
|
19
|
+
message: asOptionalString(options.message),
|
|
20
|
+
};
|
|
21
|
+
}
|
|
22
|
+
function toExportOptions(options) {
|
|
23
|
+
return {
|
|
24
|
+
folder: asOptionalString(options.folder),
|
|
25
|
+
};
|
|
26
|
+
}
|
|
27
|
+
function resolvePackageRootCandidates() {
|
|
28
|
+
const candidates = [];
|
|
29
|
+
const envRoot = process.env[PM_PACKAGE_ROOT_ENV];
|
|
30
|
+
if (typeof envRoot === "string" && envRoot.trim().length > 0) {
|
|
31
|
+
candidates.push(path.resolve(envRoot.trim()));
|
|
32
|
+
}
|
|
33
|
+
const argvEntry = typeof process.argv[1] === "string" ? process.argv[1].trim() : "";
|
|
34
|
+
if (argvEntry.length > 0) {
|
|
35
|
+
const resolvedEntry = path.resolve(argvEntry);
|
|
36
|
+
const entryDir = path.dirname(resolvedEntry);
|
|
37
|
+
candidates.push(path.resolve(entryDir, ".."));
|
|
38
|
+
candidates.push(path.resolve(entryDir, "../.."));
|
|
39
|
+
candidates.push(path.resolve(entryDir, "../../.."));
|
|
40
|
+
}
|
|
41
|
+
return [...new Set(candidates)];
|
|
42
|
+
}
|
|
43
|
+
async function loadRuntimeModule() {
|
|
44
|
+
const attempted = [];
|
|
45
|
+
for (const packageRoot of resolvePackageRootCandidates()) {
|
|
46
|
+
const modulePaths = [
|
|
47
|
+
path.join(packageRoot, ".agents", "pm", "extensions", "todos", "runtime.js"),
|
|
48
|
+
path.join(packageRoot, "packages", "pm-todos", "extensions", "todos", "runtime.js"),
|
|
49
|
+
];
|
|
50
|
+
for (const modulePath of modulePaths) {
|
|
51
|
+
attempted.push(modulePath);
|
|
52
|
+
try {
|
|
53
|
+
return await import(pathToFileURL(modulePath).href);
|
|
54
|
+
}
|
|
55
|
+
catch {
|
|
56
|
+
// Try the next package-root candidate.
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
const localRuntimePath = path.join(CURRENT_EXTENSION_ROOT, "runtime.js");
|
|
61
|
+
attempted.push(localRuntimePath);
|
|
62
|
+
try {
|
|
63
|
+
return await import(pathToFileURL(localRuntimePath).href);
|
|
64
|
+
}
|
|
65
|
+
catch {
|
|
66
|
+
// Fall through to the diagnostic below.
|
|
67
|
+
}
|
|
68
|
+
throw new Error("Unable to resolve packaged todos extension runtime module. " +
|
|
69
|
+
`Tried: ${attempted.join(", ")}. Ensure the installed extension includes runtime.js or PM_CLI_PACKAGE_ROOT points to an installed pm package root.`);
|
|
70
|
+
}
|
|
71
|
+
async function runTodosImportFromRuntime(options, global) {
|
|
72
|
+
const runtime = await loadRuntimeModule();
|
|
73
|
+
if (typeof runtime.runTodosImport !== "function") {
|
|
74
|
+
throw new Error("Bundled todos runtime module is missing runTodosImport().");
|
|
75
|
+
}
|
|
76
|
+
return runtime.runTodosImport(options, global);
|
|
77
|
+
}
|
|
78
|
+
async function runTodosExportFromRuntime(options, global) {
|
|
79
|
+
const runtime = await loadRuntimeModule();
|
|
80
|
+
if (typeof runtime.runTodosExport !== "function") {
|
|
81
|
+
throw new Error("Bundled todos runtime module is missing runTodosExport().");
|
|
82
|
+
}
|
|
83
|
+
return runtime.runTodosExport(options, global);
|
|
84
|
+
}
|
|
85
|
+
export function activate(api) {
|
|
86
|
+
api.registerCommand({
|
|
87
|
+
name: "todos import",
|
|
88
|
+
action: "todos-import",
|
|
89
|
+
description: "Import Todo markdown files into pm items.",
|
|
90
|
+
flags: [
|
|
91
|
+
{
|
|
92
|
+
long: "--folder",
|
|
93
|
+
value_name: "path",
|
|
94
|
+
value_type: "string",
|
|
95
|
+
description: "Source folder containing Todo markdown files.",
|
|
96
|
+
},
|
|
97
|
+
{
|
|
98
|
+
long: "--author",
|
|
99
|
+
value_name: "author",
|
|
100
|
+
value_type: "string",
|
|
101
|
+
description: "Override import mutation author.",
|
|
102
|
+
},
|
|
103
|
+
{
|
|
104
|
+
long: "--message",
|
|
105
|
+
value_name: "text",
|
|
106
|
+
value_type: "string",
|
|
107
|
+
description: "Override import history message.",
|
|
108
|
+
},
|
|
109
|
+
],
|
|
110
|
+
run: async (context) => runTodosImportFromRuntime(toImportOptions(context.options), context.global),
|
|
111
|
+
});
|
|
112
|
+
api.registerCommand({
|
|
113
|
+
name: "todos export",
|
|
114
|
+
action: "todos-export",
|
|
115
|
+
description: "Export pm items into Todo markdown files.",
|
|
116
|
+
flags: [
|
|
117
|
+
{
|
|
118
|
+
long: "--folder",
|
|
119
|
+
value_name: "path",
|
|
120
|
+
value_type: "string",
|
|
121
|
+
description: "Destination folder for exported Todo markdown files.",
|
|
122
|
+
},
|
|
123
|
+
],
|
|
124
|
+
run: async (context) => runTodosExportFromRuntime(toExportOptions(context.options), context.global),
|
|
125
|
+
});
|
|
126
|
+
}
|
|
127
|
+
export default {
|
|
128
|
+
manifest,
|
|
129
|
+
activate,
|
|
130
|
+
};
|
package/{.agents/pm/extensions/todos/index.js → packages/pm-todos/extensions/todos/index.ts}
RENAMED
|
@@ -1,7 +1,10 @@
|
|
|
1
1
|
import path from "node:path";
|
|
2
|
-
import { pathToFileURL } from "node:url";
|
|
2
|
+
import { fileURLToPath, pathToFileURL } from "node:url";
|
|
3
|
+
import type { CommandDefinition, ExtensionApi, GlobalOptions } from "../../../../src/sdk/index.js";
|
|
4
|
+
import type { TodosExportOptions, TodosExportResult, TodosImportOptions, TodosImportResult } from "./runtime.js";
|
|
3
5
|
|
|
4
6
|
const PM_PACKAGE_ROOT_ENV = "PM_CLI_PACKAGE_ROOT";
|
|
7
|
+
const CURRENT_EXTENSION_ROOT = path.dirname(fileURLToPath(import.meta.url));
|
|
5
8
|
|
|
6
9
|
export const manifest = {
|
|
7
10
|
name: "builtin-todos-import-export",
|
|
@@ -11,11 +14,16 @@ export const manifest = {
|
|
|
11
14
|
capabilities: ["commands", "schema"],
|
|
12
15
|
};
|
|
13
16
|
|
|
14
|
-
|
|
17
|
+
type RuntimeModule = {
|
|
18
|
+
runTodosImport?: (options: TodosImportOptions, global: GlobalOptions) => Promise<TodosImportResult>;
|
|
19
|
+
runTodosExport?: (options: TodosExportOptions, global: GlobalOptions) => Promise<TodosExportResult>;
|
|
20
|
+
};
|
|
21
|
+
|
|
22
|
+
function asOptionalString(value: unknown): string | undefined {
|
|
15
23
|
return typeof value === "string" ? value : undefined;
|
|
16
24
|
}
|
|
17
25
|
|
|
18
|
-
function toImportOptions(options) {
|
|
26
|
+
function toImportOptions(options: Record<string, unknown>): TodosImportOptions {
|
|
19
27
|
return {
|
|
20
28
|
folder: asOptionalString(options.folder),
|
|
21
29
|
author: asOptionalString(options.author),
|
|
@@ -23,14 +31,14 @@ function toImportOptions(options) {
|
|
|
23
31
|
};
|
|
24
32
|
}
|
|
25
33
|
|
|
26
|
-
function toExportOptions(options) {
|
|
34
|
+
function toExportOptions(options: Record<string, unknown>): TodosExportOptions {
|
|
27
35
|
return {
|
|
28
36
|
folder: asOptionalString(options.folder),
|
|
29
37
|
};
|
|
30
38
|
}
|
|
31
39
|
|
|
32
|
-
function resolvePackageRootCandidates() {
|
|
33
|
-
const candidates = [];
|
|
40
|
+
function resolvePackageRootCandidates(): string[] {
|
|
41
|
+
const candidates: string[] = [];
|
|
34
42
|
const envRoot = process.env[PM_PACKAGE_ROOT_ENV];
|
|
35
43
|
if (typeof envRoot === "string" && envRoot.trim().length > 0) {
|
|
36
44
|
candidates.push(path.resolve(envRoot.trim()));
|
|
@@ -46,42 +54,57 @@ function resolvePackageRootCandidates() {
|
|
|
46
54
|
return [...new Set(candidates)];
|
|
47
55
|
}
|
|
48
56
|
|
|
49
|
-
async function loadRuntimeModule() {
|
|
50
|
-
const attempted = [];
|
|
57
|
+
async function loadRuntimeModule(): Promise<RuntimeModule> {
|
|
58
|
+
const attempted: string[] = [];
|
|
51
59
|
for (const packageRoot of resolvePackageRootCandidates()) {
|
|
52
|
-
const
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
60
|
+
const modulePaths = [
|
|
61
|
+
path.join(packageRoot, ".agents", "pm", "extensions", "todos", "runtime.js"),
|
|
62
|
+
path.join(packageRoot, "packages", "pm-todos", "extensions", "todos", "runtime.js"),
|
|
63
|
+
];
|
|
64
|
+
for (const modulePath of modulePaths) {
|
|
65
|
+
attempted.push(modulePath);
|
|
66
|
+
try {
|
|
67
|
+
return await import(pathToFileURL(modulePath).href) as RuntimeModule;
|
|
68
|
+
} catch {
|
|
69
|
+
// Try the next package-root candidate.
|
|
70
|
+
}
|
|
58
71
|
}
|
|
59
72
|
}
|
|
73
|
+
|
|
74
|
+
const localRuntimePath = path.join(CURRENT_EXTENSION_ROOT, "runtime.js");
|
|
75
|
+
attempted.push(localRuntimePath);
|
|
76
|
+
try {
|
|
77
|
+
return await import(pathToFileURL(localRuntimePath).href) as RuntimeModule;
|
|
78
|
+
} catch {
|
|
79
|
+
// Fall through to the diagnostic below.
|
|
80
|
+
}
|
|
81
|
+
|
|
60
82
|
throw new Error(
|
|
61
|
-
"Unable to resolve
|
|
62
|
-
`Tried: ${attempted.join(", ")}. Ensure PM_CLI_PACKAGE_ROOT points to an installed pm package root.`,
|
|
83
|
+
"Unable to resolve packaged todos extension runtime module. " +
|
|
84
|
+
`Tried: ${attempted.join(", ")}. Ensure the installed extension includes runtime.js or PM_CLI_PACKAGE_ROOT points to an installed pm package root.`,
|
|
63
85
|
);
|
|
64
86
|
}
|
|
65
87
|
|
|
66
|
-
async function runTodosImportFromRuntime(options, global) {
|
|
88
|
+
async function runTodosImportFromRuntime(options: TodosImportOptions, global: GlobalOptions): Promise<TodosImportResult> {
|
|
67
89
|
const runtime = await loadRuntimeModule();
|
|
68
90
|
if (typeof runtime.runTodosImport !== "function") {
|
|
69
|
-
throw new Error(
|
|
91
|
+
throw new Error("Bundled todos runtime module is missing runTodosImport().");
|
|
70
92
|
}
|
|
71
93
|
return runtime.runTodosImport(options, global);
|
|
72
94
|
}
|
|
73
95
|
|
|
74
|
-
async function runTodosExportFromRuntime(options, global) {
|
|
96
|
+
async function runTodosExportFromRuntime(options: TodosExportOptions, global: GlobalOptions): Promise<TodosExportResult> {
|
|
75
97
|
const runtime = await loadRuntimeModule();
|
|
76
98
|
if (typeof runtime.runTodosExport !== "function") {
|
|
77
|
-
throw new Error(
|
|
99
|
+
throw new Error("Bundled todos runtime module is missing runTodosExport().");
|
|
78
100
|
}
|
|
79
101
|
return runtime.runTodosExport(options, global);
|
|
80
102
|
}
|
|
81
103
|
|
|
82
|
-
export function activate(api) {
|
|
104
|
+
export function activate(api: ExtensionApi): void {
|
|
83
105
|
api.registerCommand({
|
|
84
106
|
name: "todos import",
|
|
107
|
+
action: "todos-import",
|
|
85
108
|
description: "Import Todo markdown files into pm items.",
|
|
86
109
|
flags: [
|
|
87
110
|
{
|
|
@@ -104,9 +127,10 @@ export function activate(api) {
|
|
|
104
127
|
},
|
|
105
128
|
],
|
|
106
129
|
run: async (context) => runTodosImportFromRuntime(toImportOptions(context.options), context.global),
|
|
107
|
-
});
|
|
130
|
+
} satisfies CommandDefinition);
|
|
108
131
|
api.registerCommand({
|
|
109
132
|
name: "todos export",
|
|
133
|
+
action: "todos-export",
|
|
110
134
|
description: "Export pm items into Todo markdown files.",
|
|
111
135
|
flags: [
|
|
112
136
|
{
|
|
@@ -117,7 +141,7 @@ export function activate(api) {
|
|
|
117
141
|
},
|
|
118
142
|
],
|
|
119
143
|
run: async (context) => runTodosExportFromRuntime(toExportOptions(context.options), context.global),
|
|
120
|
-
});
|
|
144
|
+
} satisfies CommandDefinition);
|
|
121
145
|
}
|
|
122
146
|
|
|
123
147
|
export default {
|
|
@@ -1,22 +1,7 @@
|
|
|
1
1
|
import fs from "node:fs/promises";
|
|
2
2
|
import path from "node:path";
|
|
3
|
-
import { getActiveExtensionRegistrations, runActiveOnReadHooks, runActiveOnWriteHooks } from "../../../../dist/
|
|
4
|
-
|
|
5
|
-
import { appendHistoryEntry, createHistoryEntry } from "../../../../dist/core/history/history.js";
|
|
6
|
-
import { generateItemId, normalizeItemId } from "../../../../dist/core/item/id.js";
|
|
7
|
-
import { canonicalDocument, normalizeFrontMatter, serializeItemDocument, splitFrontMatter } from "../../../../dist/core/item/item-format.js";
|
|
8
|
-
import { normalizeStatusInput } from "../../../../dist/core/item/status.js";
|
|
9
|
-
import { resolveItemTypeRegistry } from "../../../../dist/core/item/type-registry.js";
|
|
10
|
-
import { parseTags } from "../../../../dist/core/item/parse.js";
|
|
11
|
-
import { acquireLock } from "../../../../dist/core/lock/lock.js";
|
|
12
|
-
import { EXIT_CODE } from "../../../../dist/core/shared/constants.js";
|
|
13
|
-
import { PmCliError } from "../../../../dist/core/shared/errors.js";
|
|
14
|
-
import { nowIso } from "../../../../dist/core/shared/time.js";
|
|
15
|
-
import { listAllFrontMatter, locateItem, readLocatedItem } from "../../../../dist/core/store/item-store.js";
|
|
16
|
-
import { getHistoryPath, getItemPath, getSettingsPath, resolvePmRoot } from "../../../../dist/core/store/paths.js";
|
|
17
|
-
import { readSettings } from "../../../../dist/core/store/settings.js";
|
|
18
|
-
import { CONFIDENCE_TEXT_VALUES, ISSUE_SEVERITY_VALUES, RISK_VALUES } from "../../../../dist/types/index.js";
|
|
19
|
-
const DEFAULT_TODOS_FOLDER = ".pi/todos";
|
|
3
|
+
import { CONFIDENCE_TEXT_VALUES, EXIT_CODE, ISSUE_SEVERITY_VALUES, PmCliError, RISK_VALUES, acquireLock, appendHistoryEntry, canonicalDocument, createHistoryEntry, generateItemId, getActiveExtensionRegistrations, getHistoryPath, getItemPath, getSettingsPath, listAllFrontMatter, locateItem, normalizeFrontMatter, normalizeItemId, normalizeStatusInput, nowIso, parseTags, pathExists, readLocatedItem, readSettings, removeFileIfExists, resolveItemTypeRegistry, resolvePmRoot, runActiveOnReadHooks, runActiveOnWriteHooks, serializeItemDocument, splitFrontMatter, writeFileAtomic, } from "../../../../dist/sdk/index.js";
|
|
4
|
+
const DEFAULT_TODOS_FOLDER = ".pm/todos";
|
|
20
5
|
function isRecord(value) {
|
|
21
6
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
22
7
|
}
|
|
@@ -467,4 +452,4 @@ export async function runTodosExport(options, global) {
|
|
|
467
452
|
ids,
|
|
468
453
|
warnings,
|
|
469
454
|
};
|
|
470
|
-
}
|
|
455
|
+
}
|
|
@@ -1,26 +1,48 @@
|
|
|
1
1
|
import fs from "node:fs/promises";
|
|
2
2
|
import type { Dirent } from "node:fs";
|
|
3
3
|
import path from "node:path";
|
|
4
|
-
import {
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
4
|
+
import {
|
|
5
|
+
CONFIDENCE_TEXT_VALUES,
|
|
6
|
+
EXIT_CODE,
|
|
7
|
+
ISSUE_SEVERITY_VALUES,
|
|
8
|
+
PmCliError,
|
|
9
|
+
RISK_VALUES,
|
|
10
|
+
acquireLock,
|
|
11
|
+
appendHistoryEntry,
|
|
12
|
+
canonicalDocument,
|
|
13
|
+
createHistoryEntry,
|
|
14
|
+
generateItemId,
|
|
15
|
+
getActiveExtensionRegistrations,
|
|
16
|
+
getHistoryPath,
|
|
17
|
+
getItemPath,
|
|
18
|
+
getSettingsPath,
|
|
19
|
+
listAllFrontMatter,
|
|
20
|
+
locateItem,
|
|
21
|
+
normalizeFrontMatter,
|
|
22
|
+
normalizeItemId,
|
|
23
|
+
normalizeStatusInput,
|
|
24
|
+
nowIso,
|
|
25
|
+
parseTags,
|
|
26
|
+
pathExists,
|
|
27
|
+
readLocatedItem,
|
|
28
|
+
readSettings,
|
|
29
|
+
removeFileIfExists,
|
|
30
|
+
resolveItemTypeRegistry,
|
|
31
|
+
resolvePmRoot,
|
|
32
|
+
runActiveOnReadHooks,
|
|
33
|
+
runActiveOnWriteHooks,
|
|
34
|
+
serializeItemDocument,
|
|
35
|
+
splitFrontMatter,
|
|
36
|
+
writeFileAtomic,
|
|
37
|
+
type GlobalOptions,
|
|
38
|
+
type ItemDocument,
|
|
39
|
+
type ItemMetadata,
|
|
40
|
+
type ItemStatus,
|
|
41
|
+
type ItemType,
|
|
42
|
+
type PmSettings,
|
|
43
|
+
} from "../../../../src/sdk/index.js";
|
|
44
|
+
|
|
45
|
+
const DEFAULT_TODOS_FOLDER = ".pm/todos";
|
|
24
46
|
|
|
25
47
|
export interface TodosImportOptions {
|
|
26
48
|
folder?: string;
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@unbrained/pm-package-todos",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"private": true,
|
|
5
|
+
"type": "module",
|
|
6
|
+
"description": "First-party pm package for Todo markdown import and export.",
|
|
7
|
+
"homepage": "https://github.com/unbraind/pm-cli/tree/main/packages/pm-todos#readme",
|
|
8
|
+
"repository": {
|
|
9
|
+
"type": "git",
|
|
10
|
+
"url": "git+https://github.com/unbraind/pm-cli.git",
|
|
11
|
+
"directory": "packages/pm-todos"
|
|
12
|
+
},
|
|
13
|
+
"bugs": {
|
|
14
|
+
"url": "https://github.com/unbraind/pm-cli/issues"
|
|
15
|
+
},
|
|
16
|
+
"keywords": [
|
|
17
|
+
"pm-package",
|
|
18
|
+
"project-management",
|
|
19
|
+
"todos"
|
|
20
|
+
],
|
|
21
|
+
"pm": {
|
|
22
|
+
"aliases": [
|
|
23
|
+
"todos"
|
|
24
|
+
],
|
|
25
|
+
"extensions": [
|
|
26
|
+
"extensions/todos"
|
|
27
|
+
],
|
|
28
|
+
"catalog": {
|
|
29
|
+
"display_name": "Todos Import/Export",
|
|
30
|
+
"category": "migration",
|
|
31
|
+
"summary": "Import and export Todo markdown tasks through pm package commands.",
|
|
32
|
+
"tags": [
|
|
33
|
+
"migration",
|
|
34
|
+
"todos",
|
|
35
|
+
"import",
|
|
36
|
+
"export"
|
|
37
|
+
],
|
|
38
|
+
"links": {
|
|
39
|
+
"docs": "https://github.com/unbraind/pm-cli/tree/main/packages/pm-todos#readme",
|
|
40
|
+
"repository": "https://github.com/unbraind/pm-cli/tree/main/packages/pm-todos",
|
|
41
|
+
"report": "https://github.com/unbraind/pm-cli/issues"
|
|
42
|
+
}
|
|
43
|
+
},
|
|
44
|
+
"docs": [
|
|
45
|
+
"README.md"
|
|
46
|
+
],
|
|
47
|
+
"examples": [
|
|
48
|
+
"README.md"
|
|
49
|
+
]
|
|
50
|
+
}
|
|
51
|
+
}
|
|
@@ -191,8 +191,7 @@ All skills and commands implement this pattern for every claimed item:
|
|
|
191
191
|
## Session Context Injection
|
|
192
192
|
|
|
193
193
|
At session start, the hook runs natively (no `pm` CLI required):
|
|
194
|
-
-
|
|
195
|
-
- Falls back to `npx @unbrained/pm-cli` if no local dist is found
|
|
194
|
+
- Uses `npx @unbrained/pm-cli` without requiring a global install
|
|
196
195
|
- Injects a compact summary of in-progress/open/blocked items
|
|
197
196
|
|
|
198
197
|
Example output:
|
|
@@ -3,14 +3,11 @@
|
|
|
3
3
|
* pm-cli Claude Code session-start hook.
|
|
4
4
|
*
|
|
5
5
|
* Injects a brief pm context summary into the session when pm is initialized
|
|
6
|
-
* in the current workspace. Uses
|
|
7
|
-
*
|
|
8
|
-
* be installed globally. Exits silently if pm is not set up.
|
|
6
|
+
* in the current workspace. Uses the published pm CLI through npx without
|
|
7
|
+
* requiring a global install. Exits silently if pm is not set up.
|
|
9
8
|
*/
|
|
10
|
-
import { access } from "node:fs/promises";
|
|
11
9
|
import { existsSync } from "node:fs";
|
|
12
|
-
import { join
|
|
13
|
-
import { fileURLToPath, pathToFileURL } from "node:url";
|
|
10
|
+
import { join } from "node:path";
|
|
14
11
|
import { execSync } from "node:child_process";
|
|
15
12
|
|
|
16
13
|
const workspace = process.cwd();
|
|
@@ -20,31 +17,6 @@ if (!existsSync(pmSettingsPath)) {
|
|
|
20
17
|
process.exit(0);
|
|
21
18
|
}
|
|
22
19
|
|
|
23
|
-
const here = dirname(fileURLToPath(import.meta.url));
|
|
24
|
-
|
|
25
|
-
async function pathExists(target) {
|
|
26
|
-
try {
|
|
27
|
-
await access(target);
|
|
28
|
-
return true;
|
|
29
|
-
} catch {
|
|
30
|
-
return false;
|
|
31
|
-
}
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
async function findNativeModule() {
|
|
35
|
-
let cursor = here;
|
|
36
|
-
for (let depth = 0; depth < 10; depth += 1) {
|
|
37
|
-
const candidate = join(cursor, "dist", "pi", "native.js");
|
|
38
|
-
if (await pathExists(candidate)) {
|
|
39
|
-
return candidate;
|
|
40
|
-
}
|
|
41
|
-
const parent = dirname(cursor);
|
|
42
|
-
if (parent === cursor) break;
|
|
43
|
-
cursor = parent;
|
|
44
|
-
}
|
|
45
|
-
return null;
|
|
46
|
-
}
|
|
47
|
-
|
|
48
20
|
function formatSummary(ctx) {
|
|
49
21
|
const { summary } = ctx;
|
|
50
22
|
if (!summary) return null;
|
|
@@ -68,29 +40,6 @@ function formatSummary(ctx) {
|
|
|
68
40
|
);
|
|
69
41
|
}
|
|
70
42
|
|
|
71
|
-
async function tryNativeContext() {
|
|
72
|
-
const nativePath = await findNativeModule();
|
|
73
|
-
if (!nativePath) return null;
|
|
74
|
-
|
|
75
|
-
try {
|
|
76
|
-
const { runNativePmAction } = await import(pathToFileURL(nativePath).href);
|
|
77
|
-
const result = await runNativePmAction({
|
|
78
|
-
action: "context",
|
|
79
|
-
cwd: workspace,
|
|
80
|
-
json: true,
|
|
81
|
-
options: { limit: "5" },
|
|
82
|
-
});
|
|
83
|
-
const text = Array.isArray(result?.content)
|
|
84
|
-
? result.content.find((p) => p?.type === "text")?.text ?? ""
|
|
85
|
-
: typeof result === "string"
|
|
86
|
-
? result
|
|
87
|
-
: JSON.stringify(result);
|
|
88
|
-
return JSON.parse(text);
|
|
89
|
-
} catch {
|
|
90
|
-
return null;
|
|
91
|
-
}
|
|
92
|
-
}
|
|
93
|
-
|
|
94
43
|
function tryNpxContext() {
|
|
95
44
|
try {
|
|
96
45
|
const raw = execSync(
|
|
@@ -109,7 +58,7 @@ function tryNpxContext() {
|
|
|
109
58
|
}
|
|
110
59
|
|
|
111
60
|
try {
|
|
112
|
-
const ctx =
|
|
61
|
+
const ctx = tryNpxContext();
|
|
113
62
|
if (!ctx) process.exit(0);
|
|
114
63
|
|
|
115
64
|
const message = formatSummary(ctx);
|
|
@@ -39,11 +39,13 @@ async function findRepoServer() {
|
|
|
39
39
|
|
|
40
40
|
const explicitServer = process.env.PM_CLI_MCP_SERVER;
|
|
41
41
|
if (explicitServer && (await exists(explicitServer))) {
|
|
42
|
-
await import(pathToFileURL(explicitServer).href);
|
|
42
|
+
const server = await import(pathToFileURL(explicitServer).href);
|
|
43
|
+
server.startMcpServer();
|
|
43
44
|
} else {
|
|
44
45
|
const repoServer = await findRepoServer();
|
|
45
46
|
if (repoServer) {
|
|
46
|
-
await import(pathToFileURL(repoServer).href);
|
|
47
|
+
const server = await import(pathToFileURL(repoServer).href);
|
|
48
|
+
server.startMcpServer();
|
|
47
49
|
} else {
|
|
48
50
|
const child = spawn("npx", ["-y", "--package=@unbrained/pm-cli@latest", "pm-mcp"], {
|
|
49
51
|
stdio: "inherit",
|
|
@@ -33,11 +33,13 @@ async function findRepoServer() {
|
|
|
33
33
|
|
|
34
34
|
const explicitServer = process.env.PM_CLI_MCP_SERVER;
|
|
35
35
|
if (explicitServer && await exists(explicitServer)) {
|
|
36
|
-
await import(pathToFileURL(explicitServer).href);
|
|
36
|
+
const server = await import(pathToFileURL(explicitServer).href);
|
|
37
|
+
server.startMcpServer();
|
|
37
38
|
} else {
|
|
38
39
|
const repoServer = await findRepoServer();
|
|
39
40
|
if (repoServer) {
|
|
40
|
-
await import(pathToFileURL(repoServer).href);
|
|
41
|
+
const server = await import(pathToFileURL(repoServer).href);
|
|
42
|
+
server.startMcpServer();
|
|
41
43
|
} else {
|
|
42
44
|
const child = spawn("npx", ["-y", "@unbrained/pm-cli@latest", "pm-mcp"], {
|
|
43
45
|
stdio: "inherit",
|
|
@@ -1,42 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"version": 1,
|
|
3
|
-
"updated_at": "2026-04-25T17:01:49.273Z",
|
|
4
|
-
"entries": [
|
|
5
|
-
{
|
|
6
|
-
"name": "builtin-beads-import",
|
|
7
|
-
"directory": "beads",
|
|
8
|
-
"scope": "project",
|
|
9
|
-
"manifest_version": "0.1.0",
|
|
10
|
-
"manifest_entry": "./index.js",
|
|
11
|
-
"capabilities": [
|
|
12
|
-
"commands",
|
|
13
|
-
"schema"
|
|
14
|
-
],
|
|
15
|
-
"installed_at": "2026-04-25T17:01:49.268Z",
|
|
16
|
-
"updated_at": "2026-04-25T17:01:49.268Z",
|
|
17
|
-
"source": {
|
|
18
|
-
"kind": "local",
|
|
19
|
-
"input": "builtin-beads-import",
|
|
20
|
-
"location": ".agents/pm/extensions/beads"
|
|
21
|
-
}
|
|
22
|
-
},
|
|
23
|
-
{
|
|
24
|
-
"name": "builtin-todos-import-export",
|
|
25
|
-
"directory": "todos",
|
|
26
|
-
"scope": "project",
|
|
27
|
-
"manifest_version": "0.1.0",
|
|
28
|
-
"manifest_entry": "./index.js",
|
|
29
|
-
"capabilities": [
|
|
30
|
-
"commands",
|
|
31
|
-
"schema"
|
|
32
|
-
],
|
|
33
|
-
"installed_at": "2026-04-25T17:01:49.268Z",
|
|
34
|
-
"updated_at": "2026-04-25T17:01:49.268Z",
|
|
35
|
-
"source": {
|
|
36
|
-
"kind": "local",
|
|
37
|
-
"input": "builtin-todos-import-export",
|
|
38
|
-
"location": ".agents/pm/extensions/todos"
|
|
39
|
-
}
|
|
40
|
-
}
|
|
41
|
-
]
|
|
42
|
-
}
|
|
@@ -1,45 +0,0 @@
|
|
|
1
|
-
# Harness Compatibility
|
|
2
|
-
|
|
3
|
-
This repository supports the following harnesses through shared docs and `.agents/skills` workflows only (no harness-specific runtime code):
|
|
4
|
-
|
|
5
|
-
- Pi coding agent
|
|
6
|
-
- OpenClaw
|
|
7
|
-
- Claude Code
|
|
8
|
-
- Codex CLI
|
|
9
|
-
- OpenCode
|
|
10
|
-
- Amp
|
|
11
|
-
- Droid
|
|
12
|
-
- Hermes
|
|
13
|
-
- Gemini CLI
|
|
14
|
-
|
|
15
|
-
## Progressive-Disclosure Route
|
|
16
|
-
|
|
17
|
-
Use the same low-token route in every harness:
|
|
18
|
-
|
|
19
|
-
1. `pm guide` (topic index)
|
|
20
|
-
2. `pm guide <topic>` (focused route)
|
|
21
|
-
3. `pm guide <topic> --depth standard|deep` (details only when needed)
|
|
22
|
-
4. `pm contracts --command <command> --flags-only --json` (strict machine flags)
|
|
23
|
-
|
|
24
|
-
## Harness Mapping
|
|
25
|
-
|
|
26
|
-
| Harness | Preferred prompt/doc entrypoint | Skill route |
|
|
27
|
-
|---------|----------------------------------|-------------|
|
|
28
|
-
| Pi coding agent | `AGENTS.md` + `pm guide workflows` | `.agents/skills/pm-developer/SKILL.md` |
|
|
29
|
-
| OpenClaw | repository docs + `pm guide` | `.agents/skills/pm-user/SKILL.md` |
|
|
30
|
-
| Claude Code | repository docs + `pm guide skills` | `.agents/skills/pm-developer/SKILL.md` |
|
|
31
|
-
| Codex CLI | repository docs + `pm guide commands` | `.agents/skills/pm-developer/SKILL.md` |
|
|
32
|
-
| OpenCode | repository docs + `pm guide quickstart` | `.agents/skills/pm-user/SKILL.md` |
|
|
33
|
-
| Amp | repository docs + `pm guide workflows` | `.agents/skills/pm-user/SKILL.md` |
|
|
34
|
-
| Droid | repository docs + `pm guide extensions` | `.agents/skills/pm-extensions/SKILL.md` |
|
|
35
|
-
| Hermes | repository docs + `pm guide sdk` | `.agents/skills/pm-sdk/SKILL.md` |
|
|
36
|
-
| Gemini CLI | repository docs + `pm guide commands` | `.agents/skills/pm-user/SKILL.md` |
|
|
37
|
-
|
|
38
|
-
## Verification
|
|
39
|
-
|
|
40
|
-
Before release, run:
|
|
41
|
-
|
|
42
|
-
```bash
|
|
43
|
-
pm guide skills --depth standard
|
|
44
|
-
node scripts/release/docs-skills-gate.mjs
|
|
45
|
-
```
|
package/.agents/skills/README.md
DELETED
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
# pm Agent Skills
|
|
2
|
-
|
|
3
|
-
This directory contains `agentskills.io`-style skills for `pm` workflows.
|
|
4
|
-
|
|
5
|
-
Start with:
|
|
6
|
-
|
|
7
|
-
```bash
|
|
8
|
-
pm guide skills
|
|
9
|
-
pm guide harnesses --depth standard
|
|
10
|
-
```
|
|
11
|
-
|
|
12
|
-
Skill bundles:
|
|
13
|
-
|
|
14
|
-
- `pm-developer` - implementation loop for coding agents.
|
|
15
|
-
- `pm-user` - operator workflow for planning and task routing.
|
|
16
|
-
- `pm-extensions` - extension lifecycle, diagnostics, and release-safe updates.
|
|
17
|
-
- `pm-sdk` - SDK and integration workflows.
|
|
18
|
-
|
|
19
|
-
Compatibility routing:
|
|
20
|
-
|
|
21
|
-
- [Harness compatibility matrix](HARNESS_COMPATIBILITY.md)
|