@codemation/agent-skills 0.1.6 → 0.1.7
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/CHANGELOG.md +33 -0
- package/README.md +20 -0
- package/bin/codemation-agent-skills.mjs +9 -162
- package/lib/agent-skills-extractor.d.ts +41 -0
- package/lib/agent-skills-extractor.mjs +178 -0
- package/package.json +9 -1
- package/skills/codemation-credential-development/references/credential-patterns.md +9 -0
- package/skills/codemation-workflow-dsl/SKILL.md +13 -0
- package/skills/codemation-workflow-dsl/references/builder-patterns.md +13 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,38 @@
|
|
|
1
1
|
# @codemation/agent-skills
|
|
2
2
|
|
|
3
|
+
## 0.1.7
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- [#77](https://github.com/MadeRelevant/codemation/pull/77) [`525a311`](https://github.com/MadeRelevant/codemation/commit/525a311fe7868772c923f92e268730dab422cf97) Thanks [@cblokland90](https://github.com/cblokland90)! - Expose the packaged agent skills extractor as an importable module and refresh `.agents/skills/extracted` automatically when running `codemation dev`, `codemation build`, `codemation serve web`, or `codemation dev:plugin`. Add `codemation skills sync` for manual or CI refreshes after upgrading the CLI.
|
|
8
|
+
|
|
9
|
+
- [#71](https://github.com/MadeRelevant/codemation/pull/71) [`3044e73`](https://github.com/MadeRelevant/codemation/commit/3044e73fd3cfb33f8e2cbc579c10baf97ed94658) Thanks [@cblokland90](https://github.com/cblokland90)! - Add inline callable agent tools to the workflow DSL.
|
|
10
|
+
|
|
11
|
+
This introduces `callableTool(...)` as a workflow-friendly helper for app-local agent tools, keeps
|
|
12
|
+
`CallableToolFactory.callableTool(...)` as a compatible factory entry point, teaches `AIAgentNode`
|
|
13
|
+
to execute callable tools with the same tracing and validation model as other tool kinds, and
|
|
14
|
+
updates docs, skills, and the test-dev sample to show the new path.
|
|
15
|
+
|
|
16
|
+
- [#73](https://github.com/MadeRelevant/codemation/pull/73) [`418434a`](https://github.com/MadeRelevant/codemation/commit/418434a6a2ad88a6254a94cb70e6f14b886df348) Thanks [@cblokland90](https://github.com/cblokland90)! - Improve credential UX and add extensible advanced field presentation.
|
|
17
|
+
- Run automatic credential health tests after create/save (including OAuth) and keep the dialog open when the test fails; auto-bind newly created credentials to empty workflow slots; auto-bind when picking an existing credential from the workflow slot dropdown while the slot is unbound.
|
|
18
|
+
- Add `CredentialFieldSchema.visibility` (`default` | `advanced`) and optional `CredentialTypeDefinition.advancedSection` (advanced fields always render in a collapsible block; section labels default when omitted). Next host uses stable test ids and fixes collapsible chevron styling.
|
|
19
|
+
- Credential dialog: title uses the credential type name (e.g. **Add …** / type display name on edit); hide the redundant type dropdown in edit mode.
|
|
20
|
+
- Gmail OAuth: group Client ID with Client secret, move scope preset and custom scopes under an **OAuth scopes** advanced section (collapsed by default).
|
|
21
|
+
- Documentation: `packages/core/docs/credential-ui-fields.md`, AGENTS.md, and credential development skill reference.
|
|
22
|
+
|
|
23
|
+
- [#74](https://github.com/MadeRelevant/codemation/pull/74) [`26ebe63`](https://github.com/MadeRelevant/codemation/commit/26ebe6346db0e9133a2133435a463c3dcd2dc537) Thanks [@cblokland90](https://github.com/cblokland90)! - Unify `workflow().agent()` message authoring with `AIAgent`.
|
|
24
|
+
|
|
25
|
+
`WorkflowAgentOptions` now takes `messages` (the same `AgentMessageConfig` as `AIAgent`) instead of
|
|
26
|
+
`prompt`. The workflow helper passes `messages` through unchanged. Docs, workflow DSL skills, and the
|
|
27
|
+
test-dev sample use `itemValue(...)` for per-item prompts; execution docs note `itemValue` on agent
|
|
28
|
+
`messages`.
|
|
29
|
+
|
|
30
|
+
## Unreleased
|
|
31
|
+
|
|
32
|
+
### Patch Changes
|
|
33
|
+
|
|
34
|
+
- Workflow DSL skill: document **`callableTool(...)`** for inline agent tools (with **`CallableToolFactory.callableTool(...)`** as the equivalent factory entry point).
|
|
35
|
+
|
|
3
36
|
## 0.1.6
|
|
4
37
|
|
|
5
38
|
### Patch Changes
|
package/README.md
CHANGED
|
@@ -6,6 +6,7 @@ Publishable Codemation agent skills packaged as `SKILL.md` directories.
|
|
|
6
6
|
|
|
7
7
|
- shared Codemation skills for CLI usage, workflow authoring, plugin development, credentials, and framework concepts
|
|
8
8
|
- a small extraction CLI that copies the packaged skills into a project-local `.agents/skills` directory
|
|
9
|
+
- a programmatic API (`@codemation/agent-skills`) used by `@codemation/cli` to refresh packaged skills on consumer workflows
|
|
9
10
|
|
|
10
11
|
## Install in a project
|
|
11
12
|
|
|
@@ -16,6 +17,25 @@ codemation-agent-skills extract --output .agents/skills/extracted
|
|
|
16
17
|
|
|
17
18
|
The starter templates call the extractor automatically after `pnpm install`.
|
|
18
19
|
|
|
20
|
+
## Framework-managed copy
|
|
21
|
+
|
|
22
|
+
The directory `.agents/skills/extracted` is **framework-managed**: Codemation overwrites packaged `codemation-*` skill folders there and removes stale packaged skill directories when you run `codemation dev`, `codemation build`, `codemation serve web`, or `codemation dev:plugin` (or `codemation skills sync`). Put project-local skills in sibling folders under `.agents/skills`, not inside `extracted`, unless you accept them being replaced.
|
|
23
|
+
|
|
24
|
+
## Programmatic use
|
|
25
|
+
|
|
26
|
+
```js
|
|
27
|
+
import { FileSystemGateway, SkillExtractor, resolveAgentSkillsPackageRoot } from "@codemation/agent-skills";
|
|
28
|
+
|
|
29
|
+
const consumerRoot = process.cwd();
|
|
30
|
+
const extractor = new SkillExtractor(
|
|
31
|
+
new FileSystemGateway(),
|
|
32
|
+
resolveAgentSkillsPackageRoot(),
|
|
33
|
+
consumerRoot,
|
|
34
|
+
process.stdout,
|
|
35
|
+
);
|
|
36
|
+
await extractor.extract(".agents/skills/extracted");
|
|
37
|
+
```
|
|
38
|
+
|
|
19
39
|
## Published layout
|
|
20
40
|
|
|
21
41
|
```text
|
|
@@ -2,171 +2,18 @@
|
|
|
2
2
|
|
|
3
3
|
import path from "node:path";
|
|
4
4
|
import process from "node:process";
|
|
5
|
-
import { cp, mkdir, readdir, rm, stat } from "node:fs/promises";
|
|
6
5
|
import { fileURLToPath } from "node:url";
|
|
7
6
|
|
|
8
|
-
export
|
|
7
|
+
export {
|
|
8
|
+
CodemationAgentSkillsCli,
|
|
9
|
+
CommandError,
|
|
10
|
+
CommandLineParser,
|
|
11
|
+
FileSystemGateway,
|
|
12
|
+
SkillExtractor,
|
|
13
|
+
resolveAgentSkillsPackageRoot,
|
|
14
|
+
} from "../lib/agent-skills-extractor.mjs";
|
|
9
15
|
|
|
10
|
-
|
|
11
|
-
async copyDirectory(sourcePath, destinationPath) {
|
|
12
|
-
await cp(sourcePath, destinationPath, { force: true, recursive: true });
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
async createDirectory(targetPath) {
|
|
16
|
-
await mkdir(targetPath, { recursive: true });
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
async listDirectoryEntries(targetPath) {
|
|
20
|
-
return readdir(targetPath, { withFileTypes: true });
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
async removePath(targetPath) {
|
|
24
|
-
await rm(targetPath, { force: true, recursive: true });
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
async statPath(targetPath) {
|
|
28
|
-
return stat(targetPath);
|
|
29
|
-
}
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
export class SkillExtractor {
|
|
33
|
-
constructor(fileSystem, packageRoot, cwd, stdout) {
|
|
34
|
-
this.fileSystem = fileSystem;
|
|
35
|
-
this.packageRoot = packageRoot;
|
|
36
|
-
this.cwd = cwd;
|
|
37
|
-
this.stdout = stdout;
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
async extract(outputArgument) {
|
|
41
|
-
const outputPath = path.resolve(this.cwd, outputArgument);
|
|
42
|
-
const skillsRoot = path.join(this.packageRoot, "skills");
|
|
43
|
-
|
|
44
|
-
await this.fileSystem.createDirectory(outputPath);
|
|
45
|
-
const packagedEntries = await this.fileSystem.listDirectoryEntries(skillsRoot);
|
|
46
|
-
const packagedSkillNames = new Set(
|
|
47
|
-
packagedEntries.filter((entry) => entry.isDirectory()).map((entry) => entry.name),
|
|
48
|
-
);
|
|
49
|
-
|
|
50
|
-
await this.#removeStaleSkillDirectories(outputPath, packagedSkillNames);
|
|
51
|
-
|
|
52
|
-
for (const skillName of packagedSkillNames) {
|
|
53
|
-
const sourcePath = path.join(skillsRoot, skillName);
|
|
54
|
-
const destinationPath = path.join(outputPath, skillName);
|
|
55
|
-
await this.fileSystem.removePath(destinationPath);
|
|
56
|
-
await this.fileSystem.copyDirectory(sourcePath, destinationPath);
|
|
57
|
-
this.stdout.write(`[codemation-agent-skills] extracted ${skillName}\n`);
|
|
58
|
-
}
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
async #removeStaleSkillDirectories(outputPath, packagedSkillNames) {
|
|
62
|
-
let existingEntries;
|
|
63
|
-
try {
|
|
64
|
-
existingEntries = await this.fileSystem.listDirectoryEntries(outputPath);
|
|
65
|
-
} catch {
|
|
66
|
-
return;
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
for (const entry of existingEntries) {
|
|
70
|
-
if (!entry.isDirectory()) {
|
|
71
|
-
continue;
|
|
72
|
-
}
|
|
73
|
-
if (!entry.name.startsWith("codemation-")) {
|
|
74
|
-
continue;
|
|
75
|
-
}
|
|
76
|
-
if (packagedSkillNames.has(entry.name)) {
|
|
77
|
-
continue;
|
|
78
|
-
}
|
|
79
|
-
await this.fileSystem.removePath(path.join(outputPath, entry.name));
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
}
|
|
83
|
-
|
|
84
|
-
export class CommandLineParser {
|
|
85
|
-
constructor(argv) {
|
|
86
|
-
this.argv = argv;
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
parse() {
|
|
90
|
-
const [command, ...rest] = this.argv;
|
|
91
|
-
if (!command || command === "--help" || command === "-h") {
|
|
92
|
-
return { command: "help" };
|
|
93
|
-
}
|
|
94
|
-
if (command !== "extract") {
|
|
95
|
-
throw new CommandError(`Unknown command "${command}".`);
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
let output = ".agents/skills/extracted";
|
|
99
|
-
for (let index = 0; index < rest.length; index += 1) {
|
|
100
|
-
const argument = rest[index];
|
|
101
|
-
if (argument === "--output") {
|
|
102
|
-
const value = rest[index + 1];
|
|
103
|
-
if (!value) {
|
|
104
|
-
throw new CommandError("Missing value for --output.");
|
|
105
|
-
}
|
|
106
|
-
output = value;
|
|
107
|
-
index += 1;
|
|
108
|
-
continue;
|
|
109
|
-
}
|
|
110
|
-
if (argument === "--help" || argument === "-h") {
|
|
111
|
-
return { command: "help" };
|
|
112
|
-
}
|
|
113
|
-
throw new CommandError(`Unknown argument "${argument}".`);
|
|
114
|
-
}
|
|
115
|
-
|
|
116
|
-
return { command: "extract", output };
|
|
117
|
-
}
|
|
118
|
-
}
|
|
119
|
-
|
|
120
|
-
export class CodemationAgentSkillsCli {
|
|
121
|
-
constructor(argv, cwd, stdout, stderr) {
|
|
122
|
-
this.argv = argv;
|
|
123
|
-
this.cwd = cwd;
|
|
124
|
-
this.stdout = stdout;
|
|
125
|
-
this.stderr = stderr;
|
|
126
|
-
this.fileSystem = new FileSystemGateway();
|
|
127
|
-
}
|
|
128
|
-
|
|
129
|
-
async run() {
|
|
130
|
-
try {
|
|
131
|
-
const parsed = new CommandLineParser(this.argv).parse();
|
|
132
|
-
if (parsed.command === "help") {
|
|
133
|
-
this.#writeHelp();
|
|
134
|
-
return;
|
|
135
|
-
}
|
|
136
|
-
|
|
137
|
-
const packageRoot = path.resolve(import.meta.dirname, "..");
|
|
138
|
-
const extractor = new SkillExtractor(this.fileSystem, packageRoot, this.cwd, this.stdout);
|
|
139
|
-
await extractor.extract(parsed.output);
|
|
140
|
-
} catch (error) {
|
|
141
|
-
if (error instanceof CommandError) {
|
|
142
|
-
this.stderr.write(`${error.message}\n\n`);
|
|
143
|
-
this.#writeHelp();
|
|
144
|
-
process.exitCode = 1;
|
|
145
|
-
return;
|
|
146
|
-
}
|
|
147
|
-
this.stderr.write(`${error instanceof Error ? error.message : String(error)}\n`);
|
|
148
|
-
process.exitCode = 1;
|
|
149
|
-
}
|
|
150
|
-
}
|
|
151
|
-
|
|
152
|
-
#writeHelp() {
|
|
153
|
-
this.stdout.write(
|
|
154
|
-
[
|
|
155
|
-
"codemation-agent-skills",
|
|
156
|
-
"",
|
|
157
|
-
"Usage:",
|
|
158
|
-
" codemation-agent-skills extract [--output <path>]",
|
|
159
|
-
"",
|
|
160
|
-
"Commands:",
|
|
161
|
-
" extract Copy packaged Codemation skills into a project directory.",
|
|
162
|
-
"",
|
|
163
|
-
"Options:",
|
|
164
|
-
" --output Destination directory. Defaults to .agents/skills/extracted.",
|
|
165
|
-
"",
|
|
166
|
-
].join("\n"),
|
|
167
|
-
);
|
|
168
|
-
}
|
|
169
|
-
}
|
|
16
|
+
import { CodemationAgentSkillsCli } from "../lib/agent-skills-extractor.mjs";
|
|
170
17
|
|
|
171
18
|
if (process.argv[1] && path.resolve(process.argv[1]) === fileURLToPath(import.meta.url)) {
|
|
172
19
|
await new CodemationAgentSkillsCli(process.argv.slice(2), process.cwd(), process.stdout, process.stderr).run();
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import type { Dirent } from "node:fs";
|
|
2
|
+
|
|
3
|
+
export class CommandError extends Error {}
|
|
4
|
+
|
|
5
|
+
export class FileSystemGateway {
|
|
6
|
+
copyDirectory(sourcePath: string, destinationPath: string): Promise<void>;
|
|
7
|
+
createDirectory(targetPath: string): Promise<void>;
|
|
8
|
+
listDirectoryEntries(targetPath: string): Promise<Dirent[]>;
|
|
9
|
+
removePath(targetPath: string): Promise<void>;
|
|
10
|
+
statPath(targetPath: string): Promise<import("node:fs").Stats>;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
export function resolveAgentSkillsPackageRoot(): string;
|
|
14
|
+
|
|
15
|
+
export class SkillExtractor {
|
|
16
|
+
constructor(
|
|
17
|
+
fileSystem: FileSystemGateway,
|
|
18
|
+
packageRoot: string,
|
|
19
|
+
cwd: string,
|
|
20
|
+
stdout: { write: (chunk: string) => void },
|
|
21
|
+
);
|
|
22
|
+
|
|
23
|
+
extract(outputArgument: string): Promise<void>;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
export class CommandLineParser {
|
|
27
|
+
constructor(argv: ReadonlyArray<string>);
|
|
28
|
+
|
|
29
|
+
parse(): { command: "help" } | { command: "extract"; output: string };
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
export class CodemationAgentSkillsCli {
|
|
33
|
+
constructor(
|
|
34
|
+
argv: ReadonlyArray<string>,
|
|
35
|
+
cwd: string,
|
|
36
|
+
stdout: { write: (chunk: string) => void },
|
|
37
|
+
stderr: { write: (chunk: string) => void },
|
|
38
|
+
);
|
|
39
|
+
|
|
40
|
+
run(): Promise<void>;
|
|
41
|
+
}
|
|
@@ -0,0 +1,178 @@
|
|
|
1
|
+
import path from "node:path";
|
|
2
|
+
import process from "node:process";
|
|
3
|
+
import { cp, mkdir, readdir, rm, stat } from "node:fs/promises";
|
|
4
|
+
import { fileURLToPath } from "node:url";
|
|
5
|
+
|
|
6
|
+
export class CommandError extends Error {}
|
|
7
|
+
|
|
8
|
+
export class FileSystemGateway {
|
|
9
|
+
async copyDirectory(sourcePath, destinationPath) {
|
|
10
|
+
await cp(sourcePath, destinationPath, { force: true, recursive: true });
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
async createDirectory(targetPath) {
|
|
14
|
+
await mkdir(targetPath, { recursive: true });
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
async listDirectoryEntries(targetPath) {
|
|
18
|
+
return readdir(targetPath, { withFileTypes: true });
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
async removePath(targetPath) {
|
|
22
|
+
await rm(targetPath, { force: true, recursive: true });
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
async statPath(targetPath) {
|
|
26
|
+
return stat(targetPath);
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* Resolves the root directory of the `@codemation/agent-skills` package (contains `skills/`).
|
|
32
|
+
*/
|
|
33
|
+
export function resolveAgentSkillsPackageRoot() {
|
|
34
|
+
const libDir = path.dirname(fileURLToPath(import.meta.url));
|
|
35
|
+
return path.resolve(libDir, "..");
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
export class SkillExtractor {
|
|
39
|
+
constructor(fileSystem, packageRoot, cwd, stdout) {
|
|
40
|
+
this.fileSystem = fileSystem;
|
|
41
|
+
this.packageRoot = packageRoot;
|
|
42
|
+
this.cwd = cwd;
|
|
43
|
+
this.stdout = stdout;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
/**
|
|
47
|
+
* @param {string} outputArgument relative or absolute path for extracted skills
|
|
48
|
+
*/
|
|
49
|
+
async extract(outputArgument) {
|
|
50
|
+
const outputPath = path.resolve(this.cwd, outputArgument);
|
|
51
|
+
const skillsRoot = path.join(this.packageRoot, "skills");
|
|
52
|
+
|
|
53
|
+
await this.fileSystem.createDirectory(outputPath);
|
|
54
|
+
const packagedEntries = await this.fileSystem.listDirectoryEntries(skillsRoot);
|
|
55
|
+
const packagedSkillNames = new Set(
|
|
56
|
+
packagedEntries.filter((entry) => entry.isDirectory()).map((entry) => entry.name),
|
|
57
|
+
);
|
|
58
|
+
|
|
59
|
+
await this.#removeStaleSkillDirectories(outputPath, packagedSkillNames);
|
|
60
|
+
|
|
61
|
+
for (const skillName of packagedSkillNames) {
|
|
62
|
+
const sourcePath = path.join(skillsRoot, skillName);
|
|
63
|
+
const destinationPath = path.join(outputPath, skillName);
|
|
64
|
+
await this.fileSystem.removePath(destinationPath);
|
|
65
|
+
await this.fileSystem.copyDirectory(sourcePath, destinationPath);
|
|
66
|
+
this.stdout.write(`[codemation-agent-skills] extracted ${skillName}\n`);
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
async #removeStaleSkillDirectories(outputPath, packagedSkillNames) {
|
|
71
|
+
let existingEntries;
|
|
72
|
+
try {
|
|
73
|
+
existingEntries = await this.fileSystem.listDirectoryEntries(outputPath);
|
|
74
|
+
} catch {
|
|
75
|
+
return;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
for (const entry of existingEntries) {
|
|
79
|
+
if (!entry.isDirectory()) {
|
|
80
|
+
continue;
|
|
81
|
+
}
|
|
82
|
+
if (!entry.name.startsWith("codemation-")) {
|
|
83
|
+
continue;
|
|
84
|
+
}
|
|
85
|
+
if (packagedSkillNames.has(entry.name)) {
|
|
86
|
+
continue;
|
|
87
|
+
}
|
|
88
|
+
await this.fileSystem.removePath(path.join(outputPath, entry.name));
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
export class CommandLineParser {
|
|
94
|
+
constructor(argv) {
|
|
95
|
+
this.argv = argv;
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
parse() {
|
|
99
|
+
const [command, ...rest] = this.argv;
|
|
100
|
+
if (!command || command === "--help" || command === "-h") {
|
|
101
|
+
return { command: "help" };
|
|
102
|
+
}
|
|
103
|
+
if (command !== "extract") {
|
|
104
|
+
throw new CommandError(`Unknown command "${command}".`);
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
let output = ".agents/skills/extracted";
|
|
108
|
+
for (let index = 0; index < rest.length; index += 1) {
|
|
109
|
+
const argument = rest[index];
|
|
110
|
+
if (argument === "--output") {
|
|
111
|
+
const value = rest[index + 1];
|
|
112
|
+
if (!value) {
|
|
113
|
+
throw new CommandError("Missing value for --output.");
|
|
114
|
+
}
|
|
115
|
+
output = value;
|
|
116
|
+
index += 1;
|
|
117
|
+
continue;
|
|
118
|
+
}
|
|
119
|
+
if (argument === "--help" || argument === "-h") {
|
|
120
|
+
return { command: "help" };
|
|
121
|
+
}
|
|
122
|
+
throw new CommandError(`Unknown argument "${argument}".`);
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
return { command: "extract", output };
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
export class CodemationAgentSkillsCli {
|
|
130
|
+
constructor(argv, cwd, stdout, stderr) {
|
|
131
|
+
this.argv = argv;
|
|
132
|
+
this.cwd = cwd;
|
|
133
|
+
this.stdout = stdout;
|
|
134
|
+
this.stderr = stderr;
|
|
135
|
+
this.fileSystem = new FileSystemGateway();
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
async run() {
|
|
139
|
+
try {
|
|
140
|
+
const parsed = new CommandLineParser(this.argv).parse();
|
|
141
|
+
if (parsed.command === "help") {
|
|
142
|
+
this.#writeHelp();
|
|
143
|
+
return;
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
const packageRoot = resolveAgentSkillsPackageRoot();
|
|
147
|
+
const extractor = new SkillExtractor(this.fileSystem, packageRoot, this.cwd, this.stdout);
|
|
148
|
+
await extractor.extract(parsed.output);
|
|
149
|
+
} catch (error) {
|
|
150
|
+
if (error instanceof CommandError) {
|
|
151
|
+
this.stderr.write(`${error.message}\n\n`);
|
|
152
|
+
this.#writeHelp();
|
|
153
|
+
process.exitCode = 1;
|
|
154
|
+
return;
|
|
155
|
+
}
|
|
156
|
+
this.stderr.write(`${error instanceof Error ? error.message : String(error)}\n`);
|
|
157
|
+
process.exitCode = 1;
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
#writeHelp() {
|
|
162
|
+
this.stdout.write(
|
|
163
|
+
[
|
|
164
|
+
"codemation-agent-skills",
|
|
165
|
+
"",
|
|
166
|
+
"Usage:",
|
|
167
|
+
" codemation-agent-skills extract [--output <path>]",
|
|
168
|
+
"",
|
|
169
|
+
"Commands:",
|
|
170
|
+
" extract Copy packaged Codemation skills into a project directory.",
|
|
171
|
+
"",
|
|
172
|
+
"Options:",
|
|
173
|
+
" --output Destination directory. Defaults to .agents/skills/extracted.",
|
|
174
|
+
"",
|
|
175
|
+
].join("\n"),
|
|
176
|
+
);
|
|
177
|
+
}
|
|
178
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@codemation/agent-skills",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.7",
|
|
4
4
|
"description": "Reusable agent skills for Codemation projects and plugin development.",
|
|
5
5
|
"publishConfig": {
|
|
6
6
|
"access": "public"
|
|
@@ -14,6 +14,13 @@
|
|
|
14
14
|
},
|
|
15
15
|
"license": "SEE LICENSE IN LICENSE",
|
|
16
16
|
"type": "module",
|
|
17
|
+
"exports": {
|
|
18
|
+
".": {
|
|
19
|
+
"types": "./lib/agent-skills-extractor.d.ts",
|
|
20
|
+
"import": "./lib/agent-skills-extractor.mjs",
|
|
21
|
+
"default": "./lib/agent-skills-extractor.mjs"
|
|
22
|
+
}
|
|
23
|
+
},
|
|
17
24
|
"bin": {
|
|
18
25
|
"codemation-agent-skills": "./bin/codemation-agent-skills.mjs"
|
|
19
26
|
},
|
|
@@ -34,6 +41,7 @@
|
|
|
34
41
|
"README.md",
|
|
35
42
|
"CHANGELOG.md",
|
|
36
43
|
"bin",
|
|
44
|
+
"lib",
|
|
37
45
|
"skills"
|
|
38
46
|
],
|
|
39
47
|
"scripts": {
|
|
@@ -31,6 +31,15 @@ credentials: {
|
|
|
31
31
|
|
|
32
32
|
Then the runtime can supply a typed session through the named slot.
|
|
33
33
|
|
|
34
|
+
## Advanced fields in the credential dialog
|
|
35
|
+
|
|
36
|
+
Optional or power-user fields (for example custom OAuth scopes) can be tucked behind a single collapsible section:
|
|
37
|
+
|
|
38
|
+
- Set `visibility: "advanced"` on each relevant `CredentialFieldSchema` entry in `publicFields` / `secretFields`.
|
|
39
|
+
- Optionally set `advancedSection: { title?, description?, defaultOpen? }` on `CredentialTypeDefinition` to customize the collapsible header (if omitted, the UI still wraps advanced fields in a collapsed section titled **Advanced**).
|
|
40
|
+
|
|
41
|
+
See **`packages/core/docs/credential-ui-fields.md`** in the repository root layout.
|
|
42
|
+
|
|
34
43
|
## Health and activation
|
|
35
44
|
|
|
36
45
|
- deploy the workflow and credential type
|
|
@@ -34,6 +34,19 @@ Do not use this skill for CLI-only troubleshooting or deep host architecture que
|
|
|
34
34
|
4. Add transformations or nodes in execution order.
|
|
35
35
|
5. End with `.build()`.
|
|
36
36
|
|
|
37
|
+
## Agent tools (callable helpers)
|
|
38
|
+
|
|
39
|
+
- For **inline** agent tools in workflow files (no separate `@tool()` class), use **`callableTool(...)`** from `@codemation/core`: supply `name`, Zod `inputSchema` / `outputSchema`, and `execute({ input, item, ctx, ... })`. **`CallableToolFactory.callableTool(...)`** is the same implementation if you prefer the factory style.
|
|
40
|
+
- Prefer **plugin `Tool` classes** when the tool is reusable across packages; use **`AgentToolFactory.asTool(...)`** when exposing an existing runnable node to the agent.
|
|
41
|
+
|
|
42
|
+
## Workflow agent authoring
|
|
43
|
+
|
|
44
|
+
- Use `.agent(...)` for fluent workflow-defined agent steps.
|
|
45
|
+
- Define agent messages with `messages`, not a workflow-specific prompt shortcut.
|
|
46
|
+
- Use a static `messages` array for fixed prompts.
|
|
47
|
+
- Use `itemValue(...)` when agent messages depend on the current item.
|
|
48
|
+
- `model` may be a provider string such as `"openai:gpt-4o-mini"` or a `ChatModelConfig`.
|
|
49
|
+
|
|
37
50
|
## Read next when needed
|
|
38
51
|
|
|
39
52
|
- Read `references/builder-patterns.md` for item-flow rules and fluent authoring patterns.
|
|
@@ -42,3 +42,16 @@ Promote inline callbacks into custom nodes when:
|
|
|
42
42
|
- the fluent DSL is the friendly authoring surface
|
|
43
43
|
- `@codemation/core` still owns planning, execution, continuation, and runtime contracts
|
|
44
44
|
- host and node packages add the surrounding product capabilities
|
|
45
|
+
|
|
46
|
+
## Inline callable agent tools
|
|
47
|
+
|
|
48
|
+
- import `callableTool` from `@codemation/core`
|
|
49
|
+
- build tools with `callableTool({ name, inputSchema, outputSchema, execute, credentialRequirements? })` (equivalent to `CallableToolFactory.callableTool(...)`)
|
|
50
|
+
- pass the result in `AIAgent` `tools: [...]` alongside other tool configs
|
|
51
|
+
|
|
52
|
+
## Fluent agent steps
|
|
53
|
+
|
|
54
|
+
- use `.agent(...)` for agent steps in fluent workflow definitions
|
|
55
|
+
- define agent prompts with `messages`
|
|
56
|
+
- use `itemValue(...)` when message content depends on `item.json`
|
|
57
|
+
- use `outputSchema` when the workflow should expose typed structured agent output
|