@web42/w42 0.1.4 → 0.1.9
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/LICENSE.md +116 -0
- package/README.md +75 -47
- package/dist/commands/send.js +107 -33
- package/dist/commands/serve.js +54 -117
- package/dist/index.js +0 -0
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/package.json +12 -13
- package/dist/generated/embedded-skills.d.ts +0 -9
- package/dist/generated/embedded-skills.js +0 -40
- package/skills/web42-publish-prep/SKILL.md +0 -181
- package/skills/web42-publish-prep/_meta.json +0 -17
- package/skills/web42-publish-prep/assets/readme-template.md +0 -61
- package/skills/web42-publish-prep/references/file-hygiene.md +0 -109
- package/skills/web42-publish-prep/references/manifest-fields.md +0 -142
- package/skills/web42-publish-prep/references/marketplace-config.md +0 -99
- package/skills/web42-publish-prep/references/resources-guide.md +0 -136
- package/skills/web42-publish-prep/references/web42-folder.md +0 -120
package/LICENSE.md
ADDED
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
# EULA (End User License Agreement)
|
|
2
|
+
|
|
3
|
+
## Personal License
|
|
4
|
+
|
|
5
|
+
NewCult.co grants you an on-going, non-exclusive license to use this template.
|
|
6
|
+
|
|
7
|
+
The license grants permission to **one individual** (the Licensee) to access and use this template.
|
|
8
|
+
|
|
9
|
+
### You **can**:
|
|
10
|
+
|
|
11
|
+
- Use this template to create unlimited End Products.
|
|
12
|
+
- Modify this template to create derivative components and templates. Those components and templates are subject to this license.
|
|
13
|
+
- Use this template to create unlimited End Products for unlimited clients.
|
|
14
|
+
- Use this template to create End Products where the End Product is sold to End Users.
|
|
15
|
+
- Use this template to create End Products that are open source and freely available to End Users.
|
|
16
|
+
|
|
17
|
+
### You **cannot**:
|
|
18
|
+
|
|
19
|
+
- Use this template to create End Products that are designed to allow an End User to build their own End Products using this template or derivatives of this template.
|
|
20
|
+
- Re-distribute this template or derivatives of this template separately from an End Product, neither in code nor as design assets.
|
|
21
|
+
- Share your access to this template with any other individuals.
|
|
22
|
+
- Use this template to produce anything that may be deemed by NewCult.co, in their sole and absolute discretion, to be competitive or in conflict with the business of NewCult.co.
|
|
23
|
+
|
|
24
|
+
### Example Usage
|
|
25
|
+
|
|
26
|
+
**Allowed** by the license:
|
|
27
|
+
|
|
28
|
+
- Creating a personal website by yourself.
|
|
29
|
+
- Creating a website or web application for a client that will be owned by that client.
|
|
30
|
+
- Creating a commercial SaaS application (like an invoicing app) where end users have to pay a fee to use the application.
|
|
31
|
+
- Creating a commercial self-hosted web application that is sold to end users for a one-time fee.
|
|
32
|
+
- Creating a web application that is free and open source, where the primary purpose is not to simply re-distribute the template and the source code is publicly available.
|
|
33
|
+
|
|
34
|
+
**Not allowed** by the license:
|
|
35
|
+
|
|
36
|
+
- Creating a repository of your favorite NewCult.co components or templates (or derivatives based on NewCult.co components or templates) and publishing it publicly.
|
|
37
|
+
- Creating a React or Vue version of NewCult.co and making it available either for sale or for free.
|
|
38
|
+
- Creating a Figma or Sketch UI kit based on the NewCult.co component designs.
|
|
39
|
+
- Creating a "website builder" project where end users can build their own websites using components or templates included with or derived from NewCult.co.
|
|
40
|
+
- Creating a theme, template, or project starter kit using the components or templates and making it available either for sale or for free.
|
|
41
|
+
- Creating an admin panel tool that is made available either for sale or for free.
|
|
42
|
+
|
|
43
|
+
In simple terms, use NewCult.co for anything you like as long as it doesn't compete with NewCult.co.
|
|
44
|
+
|
|
45
|
+
### Personal License Definitions
|
|
46
|
+
|
|
47
|
+
- **Licensee**: The individual who has purchased a Personal License.
|
|
48
|
+
- **Components and Templates**: The source code and design assets made available to the Licensee after purchasing a NewCult.co license.
|
|
49
|
+
- **End Product**: Any artifact produced that incorporates the Components or Templates or derivatives of the Components or Templates.
|
|
50
|
+
- **End User**: A user of an End Product.
|
|
51
|
+
- **Client**: An individual or entity receiving custom professional services directly from the Licensee, produced specifically for that individual or entity. Customers of software-as-a-service products are not considered clients for the purpose of this document.
|
|
52
|
+
|
|
53
|
+
## Team License
|
|
54
|
+
|
|
55
|
+
NewCult.co grants you an on-going, non-exclusive license to use this template.
|
|
56
|
+
|
|
57
|
+
The license grants permission for **up to 25 Employees and Contractors of the Licensee** to access and use this template.
|
|
58
|
+
|
|
59
|
+
### You **can**:
|
|
60
|
+
|
|
61
|
+
- Use this template to create unlimited End Products.
|
|
62
|
+
- Modify this template to create derivative components and templates. Those components and templates are subject to this license.
|
|
63
|
+
- Use this template to create unlimited End Products for unlimited clients.
|
|
64
|
+
- Use this template to create End Products where the End Product is sold to End Users.
|
|
65
|
+
- Use this template to create End Products that are open source and freely available to End Users.
|
|
66
|
+
|
|
67
|
+
### You **cannot**:
|
|
68
|
+
|
|
69
|
+
- Use the Components or Templates to create End Products that are designed to allow an End User to build their own End Products using the Components or Templates or derivatives of the Components or Templates.
|
|
70
|
+
- Re-distribute the Components or Templates or derivatives of the Components or Templates separately from an End Product.
|
|
71
|
+
- Use the Components or Templates to create End Products that are the property of any individual or entity other than the Licensee or clients of the Licensee.
|
|
72
|
+
- Use the Components or Templates to produce anything that may be deemed by NewCult.co, in their sole and absolute discretion, to be competitive or in conflict with the business of NewCult.co.
|
|
73
|
+
|
|
74
|
+
### Example Usage
|
|
75
|
+
|
|
76
|
+
**Allowed** by the license:
|
|
77
|
+
|
|
78
|
+
- Creating a website for your company.
|
|
79
|
+
- Creating a website or web application for a client that will be owned by that client.
|
|
80
|
+
- Creating a commercial SaaS application (like an invoicing app) where end users have to pay a fee to use the application.
|
|
81
|
+
- Creating a commercial self-hosted web application that is sold to end users for a one-time fee.
|
|
82
|
+
- Creating a web application that is free and open source, where the primary purpose is not to simply re-distribute the components or templates and the source code is publicly available.
|
|
83
|
+
|
|
84
|
+
**Not allowed** by the license:
|
|
85
|
+
|
|
86
|
+
- Creating a repository of your favorite NewCult.co components or templates (or derivatives based on NewCult.co components or templates) and publishing it publicly.
|
|
87
|
+
- Creating a React or Vue version of NewCult.co and making it available either for sale or for free.
|
|
88
|
+
- Creating a "website builder" project where end users can build their own websites using components or templates included with or derived from NewCult.co.
|
|
89
|
+
- Creating a theme or template using the components or templates and making it available either for sale or for free.
|
|
90
|
+
- Creating any End Product that is not the sole property of either your company or a client of your company. For example, your employees/contractors can't use your company NewCult.co license to build their own websites or side projects.
|
|
91
|
+
|
|
92
|
+
### Team License Definitions
|
|
93
|
+
|
|
94
|
+
- **Licensee**: The business entity who has purchased a Team License.
|
|
95
|
+
- **Components and Templates**: The source code and design assets made available to the Licensee after purchasing a NewCult.co license.
|
|
96
|
+
- **End Product**: Any artifact produced that incorporates the Components or Templates or derivatives of the Components or Templates.
|
|
97
|
+
- **End User**: A user of an End Product.
|
|
98
|
+
- **Employee**: A full-time or part-time employee of the Licensee.
|
|
99
|
+
- **Contractor**: An individual or business entity contracted to perform services for the Licensee.
|
|
100
|
+
- **Client**: An individual or entity receiving custom professional services directly from the Licensee, produced specifically for that individual or entity. Customers of software-as-a-service products are not considered clients for the purpose of this document.
|
|
101
|
+
|
|
102
|
+
## Enforcement
|
|
103
|
+
|
|
104
|
+
If you are found to be in violation of the license, access to your NewCult.co account will be terminated, and a refund may be issued at our discretion. When license violation is blatant and malicious (such as intentionally redistributing the Components or Templates through private warez channels), no refund will be issued.
|
|
105
|
+
|
|
106
|
+
The copyright of this template is owned by NewCult.co. You are granted only the permissions described in this license; all other rights are reserved. NewCult.co reserves the right to pursue legal remedies for any unauthorized use of the Components or Templates outside the scope of this license.
|
|
107
|
+
|
|
108
|
+
## Liability
|
|
109
|
+
|
|
110
|
+
NewCult.co’s liability to you for any costs, damages, or other losses arising from your use of the Components or Templates, including third-party claims against you, is limited to a refund of your license fee. NewCult.co is not liable for any consequential damages related to your use of the Components or Templates.
|
|
111
|
+
|
|
112
|
+
This Agreement is governed by the laws of the State of North Carolina, USA. Legal proceedings related to this Agreement may only be brought in the courts of North Carolina. You agree to service of process at the e-mail address on your original order.
|
|
113
|
+
|
|
114
|
+
## Questions?
|
|
115
|
+
|
|
116
|
+
Unsure which license you need, or have questions about your use case? Contact us on Twitter at [x.com/nolansym](https://x.com/nolansym).
|
package/README.md
CHANGED
|
@@ -1,73 +1,101 @@
|
|
|
1
1
|
# @web42/cli
|
|
2
2
|
|
|
3
|
-
CLI for the Web42 Agent
|
|
3
|
+
CLI for the Web42 Agent Network — authenticate, publish, discover, and interact with A2A agents.
|
|
4
4
|
|
|
5
5
|
## Installation
|
|
6
6
|
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
```
|
|
7
|
+
```bash
|
|
10
8
|
npm install -g @web42/cli
|
|
11
9
|
```
|
|
12
10
|
|
|
13
11
|
## Authentication
|
|
14
12
|
|
|
15
|
-
|
|
13
|
+
```bash
|
|
14
|
+
web42 auth login # Sign in via GitHub OAuth
|
|
15
|
+
web42 auth logout # Sign out
|
|
16
|
+
web42 auth whoami # Show current user
|
|
17
|
+
```
|
|
18
|
+
|
|
19
|
+
## Commands
|
|
16
20
|
|
|
21
|
+
### `web42 search <query>`
|
|
22
|
+
|
|
23
|
+
Search the network for agents.
|
|
24
|
+
|
|
25
|
+
```bash
|
|
26
|
+
web42 search "data analysis"
|
|
27
|
+
web42 search "image processing" --limit 20
|
|
17
28
|
```
|
|
18
|
-
|
|
29
|
+
|
|
30
|
+
| Option | Description |
|
|
31
|
+
|---|---|
|
|
32
|
+
| `-l, --limit <number>` | Max results to show (default: 10) |
|
|
33
|
+
|
|
34
|
+
---
|
|
35
|
+
|
|
36
|
+
### `web42 send <agent> <message>`
|
|
37
|
+
|
|
38
|
+
Send a message to an A2A agent. `<agent>` can be a slug (`@user/agent`) or a direct URL (`http://localhost:3001`).
|
|
39
|
+
|
|
40
|
+
```bash
|
|
41
|
+
web42 send @alice/summarizer "Summarize this document"
|
|
42
|
+
web42 send http://localhost:3001 "Hello"
|
|
19
43
|
```
|
|
20
44
|
|
|
21
|
-
|
|
45
|
+
| Option | Description |
|
|
46
|
+
|---|---|
|
|
47
|
+
| `--new` | Start a new conversation (clears saved context) |
|
|
48
|
+
| `--context <id>` | Use a specific context ID |
|
|
49
|
+
| `--task-id <id>` | Reply to a specific task (e.g. one in `input-required` state) |
|
|
22
50
|
|
|
23
|
-
|
|
24
|
-
|-----------|--------------|
|
|
25
|
-
| openclaw | Fully Supported |
|
|
26
|
-
| claude | Fully Supported |
|
|
51
|
+
---
|
|
27
52
|
|
|
28
|
-
|
|
53
|
+
### `web42 serve`
|
|
29
54
|
|
|
30
|
-
|
|
55
|
+
Start a local A2A server for your agent, bridging to an OpenClaw gateway.
|
|
31
56
|
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
| `web42 pull` | Pull the latest agent state from the marketplace |
|
|
37
|
-
| `web42 list` | List installed agents |
|
|
38
|
-
| `web42 update <agent>` | Update an installed agent to the latest version |
|
|
39
|
-
| `web42 uninstall <agent>` | Uninstall an agent |
|
|
40
|
-
| `web42 search <query>` | Search the marketplace for agents |
|
|
41
|
-
| `web42 remix <agent>` | Remix an agent package to your account |
|
|
42
|
-
| `web42 sync` | Check sync status between local workspace and the marketplace |
|
|
57
|
+
```bash
|
|
58
|
+
web42 serve
|
|
59
|
+
web42 serve --port 3001 --url https://my-agent.ngrok.io --verbose
|
|
60
|
+
```
|
|
43
61
|
|
|
44
|
-
|
|
62
|
+
| Option | Description |
|
|
63
|
+
|---|---|
|
|
64
|
+
| `--port <port>` | Port to listen on (default: 4000) |
|
|
65
|
+
| `--url <url>` | Public URL for registration and AgentCard (e.g. from ngrok) |
|
|
66
|
+
| `--openclaw-port <port>` | OpenClaw gateway port (default: 18789) |
|
|
67
|
+
| `--openclaw-token <token>` | OpenClaw gateway auth token (or `OPENCLAW_GATEWAY_TOKEN`) |
|
|
68
|
+
| `--openclaw-agent <id>` | OpenClaw agent ID to target (default: `main`) |
|
|
69
|
+
| `--client-id <id>` | Developer app client ID (or `W42_CLIENT_ID`) |
|
|
70
|
+
| `--client-secret <secret>` | Developer app client secret (or `W42_CLIENT_SECRET`) |
|
|
71
|
+
| `--visibility <vis>` | Marketplace visibility: `public` or `private` |
|
|
72
|
+
| `--verbose` | Enable verbose request/response logging |
|
|
45
73
|
|
|
46
|
-
|
|
47
|
-
```
|
|
48
|
-
web42 init
|
|
49
|
-
```
|
|
74
|
+
---
|
|
50
75
|
|
|
51
|
-
|
|
52
|
-
```
|
|
53
|
-
web42 pack --agent <name>
|
|
54
|
-
```
|
|
76
|
+
### `web42 register <url>`
|
|
55
77
|
|
|
56
|
-
|
|
57
|
-
```
|
|
58
|
-
web42 push --agent <name>
|
|
59
|
-
```
|
|
78
|
+
Register an agent with the Web42 Network. The URL must serve `/.well-known/agent-card.json`.
|
|
60
79
|
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
80
|
+
```bash
|
|
81
|
+
web42 register https://my-agent.example.com
|
|
82
|
+
web42 register https://my-agent.example.com --visibility private --tags "nlp,summarization"
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
| Option | Description |
|
|
86
|
+
|---|---|
|
|
87
|
+
| `--price <cents>` | Price in cents (default: 0 = free) |
|
|
88
|
+
| `--license <license>` | License (e.g. `MIT`, `Apache-2.0`) |
|
|
89
|
+
| `--visibility <vis>` | `public` or `private` (default: `public`) |
|
|
90
|
+
| `--tags <tags>` | Comma-separated tags |
|
|
91
|
+
| `--categories <cats>` | Comma-separated categories |
|
|
65
92
|
|
|
66
|
-
|
|
67
|
-
```
|
|
68
|
-
web42 claude install -g @user/agent
|
|
69
|
-
```
|
|
93
|
+
---
|
|
70
94
|
|
|
71
|
-
##
|
|
95
|
+
## Environment variables
|
|
72
96
|
|
|
73
|
-
|
|
97
|
+
```bash
|
|
98
|
+
W42_CLIENT_ID=your-client-id
|
|
99
|
+
W42_CLIENT_SECRET=your-client-secret
|
|
100
|
+
OPENCLAW_GATEWAY_TOKEN=your-openclaw-token
|
|
101
|
+
```
|
package/dist/commands/send.js
CHANGED
|
@@ -1,18 +1,41 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { ClientFactory, ClientFactoryOptions, JsonRpcTransportFactory, } from "@a2a-js/sdk/client";
|
|
2
2
|
import chalk from "chalk";
|
|
3
|
+
import { Command } from "commander";
|
|
3
4
|
import ora from "ora";
|
|
4
5
|
import { v4 as uuidv4 } from "uuid";
|
|
5
|
-
import { requireAuth, setConfigValue, getConfigValue } from "../utils/config.js";
|
|
6
6
|
import { apiPost } from "../utils/api.js";
|
|
7
|
+
import { getConfigValue, requireAuth, setConfigValue } from "../utils/config.js";
|
|
7
8
|
function isUrl(s) {
|
|
8
9
|
return s.startsWith("http://") || s.startsWith("https://");
|
|
9
10
|
}
|
|
11
|
+
function printPart(part) {
|
|
12
|
+
if (part.kind === "text") {
|
|
13
|
+
if (part.text)
|
|
14
|
+
process.stdout.write(part.text);
|
|
15
|
+
}
|
|
16
|
+
else if (part.kind === "file") {
|
|
17
|
+
const f = part.file;
|
|
18
|
+
const label = [f.name, f.mimeType].filter(Boolean).join(" ");
|
|
19
|
+
process.stdout.write(`\n[file${label ? `: ${label}` : ""}]\n`);
|
|
20
|
+
if ("uri" in f) {
|
|
21
|
+
process.stdout.write(f.uri + "\n");
|
|
22
|
+
}
|
|
23
|
+
else {
|
|
24
|
+
process.stdout.write(`<${f.bytes.length} base64 chars>\n`);
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
else if (part.kind === "data") {
|
|
28
|
+
process.stdout.write("\n" + JSON.stringify(part.data, null, 2) + "\n");
|
|
29
|
+
}
|
|
30
|
+
}
|
|
10
31
|
function getCachedToken(slug) {
|
|
11
32
|
const raw = getConfigValue(`agentTokens.${slug}`);
|
|
12
33
|
if (!raw)
|
|
13
34
|
return null;
|
|
14
35
|
try {
|
|
15
|
-
const cached = typeof raw === "string"
|
|
36
|
+
const cached = typeof raw === "string"
|
|
37
|
+
? JSON.parse(raw)
|
|
38
|
+
: raw;
|
|
16
39
|
if (new Date(cached.expiresAt) <= new Date())
|
|
17
40
|
return null;
|
|
18
41
|
return cached;
|
|
@@ -27,6 +50,7 @@ export const sendCommand = new Command("send")
|
|
|
27
50
|
.argument("<message>", "Message to send")
|
|
28
51
|
.option("--new", "Start a new conversation (clears saved context)")
|
|
29
52
|
.option("--context <id>", "Use a specific context ID")
|
|
53
|
+
.option("--task-id <id>", "Reply to a specific task (e.g. one in input-required state)")
|
|
30
54
|
.action(async (rawAgent, userMessage, opts) => {
|
|
31
55
|
// Normalize slug: @user/name → @user~name (DB format)
|
|
32
56
|
const agent = rawAgent.includes("/") && !isUrl(rawAgent)
|
|
@@ -37,10 +61,30 @@ export const sendCommand = new Command("send")
|
|
|
37
61
|
let bearerToken;
|
|
38
62
|
let agentKey;
|
|
39
63
|
if (isUrl(agent)) {
|
|
40
|
-
// Direct URL mode — local development, no handshake needed
|
|
41
64
|
agentUrl = agent;
|
|
42
|
-
bearerToken = config.token;
|
|
43
65
|
agentKey = new URL(agent).host.replace(/[.:]/g, "-");
|
|
66
|
+
const cached = getCachedToken(agentKey);
|
|
67
|
+
if (cached) {
|
|
68
|
+
bearerToken = cached.token;
|
|
69
|
+
}
|
|
70
|
+
else {
|
|
71
|
+
const spinner = ora("Getting auth token...").start();
|
|
72
|
+
try {
|
|
73
|
+
const res = await apiPost("/api/auth/token", {});
|
|
74
|
+
bearerToken = res.token;
|
|
75
|
+
setConfigValue(`agentTokens.${agentKey}`, JSON.stringify({
|
|
76
|
+
token: res.token,
|
|
77
|
+
agentUrl,
|
|
78
|
+
expiresAt: res.expiresAt,
|
|
79
|
+
}));
|
|
80
|
+
spinner.stop();
|
|
81
|
+
}
|
|
82
|
+
catch (err) {
|
|
83
|
+
spinner.fail("Failed to get auth token");
|
|
84
|
+
console.error(chalk.red(String(err)));
|
|
85
|
+
process.exit(1);
|
|
86
|
+
}
|
|
87
|
+
}
|
|
44
88
|
}
|
|
45
89
|
else {
|
|
46
90
|
// Slug mode — handshake with Web42 Network platform
|
|
@@ -85,20 +129,6 @@ export const sendCommand = new Command("send")
|
|
|
85
129
|
contextId = getConfigValue(contextKey) ?? uuidv4();
|
|
86
130
|
}
|
|
87
131
|
setConfigValue(contextKey, contextId);
|
|
88
|
-
// Dynamically import @a2a-js/sdk client
|
|
89
|
-
let ClientFactory;
|
|
90
|
-
let JsonRpcTransportFactory;
|
|
91
|
-
let ClientFactoryOptions;
|
|
92
|
-
try {
|
|
93
|
-
const clientModule = await import("@a2a-js/sdk/client");
|
|
94
|
-
ClientFactory = clientModule.ClientFactory;
|
|
95
|
-
JsonRpcTransportFactory = clientModule.JsonRpcTransportFactory;
|
|
96
|
-
ClientFactoryOptions = clientModule.ClientFactoryOptions;
|
|
97
|
-
}
|
|
98
|
-
catch {
|
|
99
|
-
console.error(chalk.red("Failed to load @a2a-js/sdk. Run: pnpm add @a2a-js/sdk"));
|
|
100
|
-
process.exit(1);
|
|
101
|
-
}
|
|
102
132
|
const bearerInterceptor = {
|
|
103
133
|
before: async (args) => {
|
|
104
134
|
if (!args.options)
|
|
@@ -119,8 +149,7 @@ export const sendCommand = new Command("send")
|
|
|
119
149
|
interceptors: [bearerInterceptor],
|
|
120
150
|
},
|
|
121
151
|
}));
|
|
122
|
-
|
|
123
|
-
client = await factory.createFromUrl(a2aBaseUrl);
|
|
152
|
+
client = await factory.createFromUrl(agentUrl);
|
|
124
153
|
connectSpinner.stop();
|
|
125
154
|
}
|
|
126
155
|
catch {
|
|
@@ -136,22 +165,67 @@ export const sendCommand = new Command("send")
|
|
|
136
165
|
parts: [{ kind: "text", text: userMessage }],
|
|
137
166
|
kind: "message",
|
|
138
167
|
contextId,
|
|
168
|
+
...(opts.taskId ? { taskId: opts.taskId } : {}),
|
|
139
169
|
},
|
|
140
170
|
});
|
|
141
171
|
for await (const event of stream) {
|
|
142
|
-
if (event.kind === "
|
|
143
|
-
const
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
172
|
+
if (event.kind === "message" && event.role === "agent") {
|
|
173
|
+
for (const part of event.parts)
|
|
174
|
+
printPart(part);
|
|
175
|
+
}
|
|
176
|
+
else if (event.kind === "artifact-update") {
|
|
177
|
+
// When append is true we're receiving streaming chunks — write inline.
|
|
178
|
+
// When it's a new artifact (append falsy), separate from prior output.
|
|
179
|
+
if (!event.append)
|
|
180
|
+
process.stdout.write("\n");
|
|
181
|
+
for (const part of event.artifact.parts ?? [])
|
|
182
|
+
printPart(part);
|
|
150
183
|
}
|
|
151
|
-
if (event.kind === "status-update") {
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
184
|
+
else if (event.kind === "status-update") {
|
|
185
|
+
if (event.status?.message) {
|
|
186
|
+
for (const part of event.status.message.parts ?? [])
|
|
187
|
+
printPart(part);
|
|
188
|
+
}
|
|
189
|
+
const state = event.status?.state;
|
|
190
|
+
if (state === "input-required") {
|
|
191
|
+
process.stdout.write("\n");
|
|
192
|
+
console.log(chalk.yellow(`[task ${event.taskId} is awaiting input — reply with --task-id ${event.taskId}]`));
|
|
193
|
+
}
|
|
194
|
+
else if (state === "auth-required") {
|
|
195
|
+
console.error(chalk.red("\nAgent requires authentication."));
|
|
196
|
+
process.exit(1);
|
|
197
|
+
}
|
|
198
|
+
else if (state === "failed" ||
|
|
199
|
+
state === "canceled" ||
|
|
200
|
+
state === "rejected") {
|
|
201
|
+
console.error(chalk.red(`\nAgent ${state}.`));
|
|
202
|
+
process.exit(1);
|
|
203
|
+
}
|
|
204
|
+
}
|
|
205
|
+
else if (event.kind === "task") {
|
|
206
|
+
// Non-streaming fallback: server returned the full task object.
|
|
207
|
+
// Print accumulated artifacts and handle terminal state.
|
|
208
|
+
const task = event;
|
|
209
|
+
for (const artifact of task.artifacts ?? []) {
|
|
210
|
+
process.stdout.write("\n");
|
|
211
|
+
for (const part of artifact.parts ?? [])
|
|
212
|
+
printPart(part);
|
|
213
|
+
}
|
|
214
|
+
if (task.status?.message) {
|
|
215
|
+
for (const part of task.status.message.parts ?? [])
|
|
216
|
+
printPart(part);
|
|
217
|
+
}
|
|
218
|
+
const taskState = task.status?.state;
|
|
219
|
+
if (taskState === "input-required") {
|
|
220
|
+
process.stdout.write("\n");
|
|
221
|
+
console.log(chalk.yellow(`[task ${task.id} is awaiting input — reply with --task-id ${task.id}]`));
|
|
222
|
+
}
|
|
223
|
+
else if (taskState === "auth-required") {
|
|
224
|
+
console.error(chalk.red("\nAgent requires authentication."));
|
|
225
|
+
process.exit(1);
|
|
226
|
+
}
|
|
227
|
+
else if (taskState === "failed" || taskState === "canceled" || taskState === "rejected") {
|
|
228
|
+
console.error(chalk.red(`\nAgent ${taskState}.`));
|
|
155
229
|
process.exit(1);
|
|
156
230
|
}
|
|
157
231
|
}
|