@lazyingart/agintiflow 0.20.47 → 0.20.49
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/docs/skillmesh.md +158 -0
- package/package.json +4 -2
- package/references/skill-mesh-sharing-design.md +1123 -0
- package/scripts/smoke-skillmesh.js +128 -0
- package/src/cli.js +14 -2
- package/src/i18n.js +1 -0
- package/src/interactive-cli.js +40 -0
- package/src/skill-library.js +66 -3
- package/src/skillmesh.js +1284 -0
|
@@ -0,0 +1,1123 @@
|
|
|
1
|
+
# AgInTiFlow Skill Mesh Sharing Design
|
|
2
|
+
|
|
3
|
+
## Goal
|
|
4
|
+
|
|
5
|
+
AgInTiFlow should let different users benefit from skills, tool patterns, command policies, profiles, and troubleshooting lessons learned by other users without uploading private transcripts, source code, file paths, secrets, or artifacts.
|
|
6
|
+
|
|
7
|
+
The proposed feature name is **Skill Mesh**.
|
|
8
|
+
|
|
9
|
+
Implementation note as of v0.20.48:
|
|
10
|
+
|
|
11
|
+
- `aginti skillmesh` and `/skillmesh` exist as the first conservative MVP.
|
|
12
|
+
- The shipped implementation uses signed JSON skill packs first, not tarballs, to avoid archive traversal and executable-file risk.
|
|
13
|
+
- Relay nodes can run without model/API keys via `aginti skillmesh serve`.
|
|
14
|
+
- Relay nodes can persist after reboot with `aginti skillmesh service install`; system services require sudo, while user services need systemd lingering for boot persistence.
|
|
15
|
+
- Community imports install disabled by default and cannot override built-in skills.
|
|
16
|
+
- Sync is explicit and metadata-first; no continuous background polling is enabled yet.
|
|
17
|
+
|
|
18
|
+
User-facing command:
|
|
19
|
+
|
|
20
|
+
```text
|
|
21
|
+
/skillmesh
|
|
22
|
+
```
|
|
23
|
+
|
|
24
|
+
CLI command:
|
|
25
|
+
|
|
26
|
+
```bash
|
|
27
|
+
aginti skillmesh
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
Useful aliases can be added later:
|
|
31
|
+
|
|
32
|
+
```text
|
|
33
|
+
/skill-sync
|
|
34
|
+
/skill-share
|
|
35
|
+
aginti skillsync
|
|
36
|
+
```
|
|
37
|
+
|
|
38
|
+
Product default should be **Record + Share Reviewed Skills**. This sounds active, but the implementation must still be conservative: it records locally by default, shares only reviewed/high-value skill packs, syncs slowly during idle time, and never uploads raw logs or raw sessions.
|
|
39
|
+
|
|
40
|
+
The sync philosophy should be **slow, strict, and high-signal**. Skill Mesh is not chat, telemetry streaming, or a real-time swarm bus. It should exchange only reviewed, deduplicated, high-value capability packs during idle time.
|
|
41
|
+
|
|
42
|
+
## Core Modes
|
|
43
|
+
|
|
44
|
+
The selector for `/skillmesh` should have three modes:
|
|
45
|
+
|
|
46
|
+
1. **Disabled**
|
|
47
|
+
|
|
48
|
+
No housekeeping export, no community sync, no skill suggestions from shared feeds. Raw local session history still stays in `~/.agintiflow/sessions/` if normal sessions are enabled, but no Skill Mesh aggregation is used.
|
|
49
|
+
|
|
50
|
+
2. **Record Locally**
|
|
51
|
+
|
|
52
|
+
AgInTiFlow records sanitized local capability metadata into `~/.agintiflow/housekeeping/`. This includes model/tool names, selected skill ids, command categories, outcome hashes, and short redacted previews. It does not upload anything.
|
|
53
|
+
|
|
54
|
+
3. **Record + Share Reviewed Packs**
|
|
55
|
+
|
|
56
|
+
AgInTiFlow records locally and allows the user to review/export/share **skill packs**. Sharing must never mean uploading raw sessions automatically. It should mean publishing a small reviewed package containing reusable Markdown skills, task profile hints, safe command policy patterns, test snippets, and metadata. This should be the default mode for the product, with strict text in settings explaining what is and is not shared.
|
|
57
|
+
|
|
58
|
+
Better label in UI:
|
|
59
|
+
|
|
60
|
+
```text
|
|
61
|
+
Record + Share Reviewed Skills
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
Settings page explanatory text:
|
|
65
|
+
|
|
66
|
+
```text
|
|
67
|
+
Skill sharing improves AgInTiFlow's skill set across users. Sharing is strict: AgInTiFlow never uploads raw chats, raw session logs, project source files, .env files, keys, browser storage, or artifacts by default. Only reviewed, redacted, high-value skill packs can be shared, and shared skills are deduplicated and verified before they can enter the mesh.
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
When the user selects **Disabled**, show:
|
|
71
|
+
|
|
72
|
+
```text
|
|
73
|
+
Skill Mesh is disabled. AgInTiFlow will not record local skill-learning metadata and will not share or receive reviewed skill packs. Enabling Record + Share Reviewed Skills can improve the shared skill set, but sharing remains strict and never uploads raw sessions or secrets.
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
Avoid label:
|
|
77
|
+
|
|
78
|
+
```text
|
|
79
|
+
Auto-share logs
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
because that is the wrong privacy model.
|
|
83
|
+
|
|
84
|
+
## How Users Communicate Without Sharing Raw Sessions
|
|
85
|
+
|
|
86
|
+
Users communicate through **capability artifacts**, not through transcripts.
|
|
87
|
+
|
|
88
|
+
Shared artifact types:
|
|
89
|
+
|
|
90
|
+
- `SKILL.md` files with frontmatter and workflow guidance.
|
|
91
|
+
- Task profile patches or suggestions.
|
|
92
|
+
- Command-policy examples, such as safe git pull/merge/rebase patterns.
|
|
93
|
+
- Tool recipes, such as Android emulator screenshot capture or LaTeX compile fallback.
|
|
94
|
+
- Smoke tests that prove a skill/tool pattern works.
|
|
95
|
+
- Failure postmortems rewritten as generic lessons.
|
|
96
|
+
- Model routing hints, such as which model is reliable for which class of task.
|
|
97
|
+
|
|
98
|
+
Never share by default:
|
|
99
|
+
|
|
100
|
+
- Raw prompts.
|
|
101
|
+
- Raw model responses.
|
|
102
|
+
- Raw `events.jsonl`.
|
|
103
|
+
- Source files from the user project.
|
|
104
|
+
- Absolute paths.
|
|
105
|
+
- Shell output containing environment variables.
|
|
106
|
+
- Screenshots/images/PDFs unless the user explicitly includes them in a reviewed example.
|
|
107
|
+
- Provider keys, npm tokens, SSH data, cookies, auth headers, or `.env` content.
|
|
108
|
+
|
|
109
|
+
## Local Pipeline
|
|
110
|
+
|
|
111
|
+
The local machine should have a lightweight housekeeping pipeline:
|
|
112
|
+
|
|
113
|
+
```text
|
|
114
|
+
session events
|
|
115
|
+
-> redaction and path masking
|
|
116
|
+
-> local housekeeping ledger
|
|
117
|
+
-> candidate capability extractor
|
|
118
|
+
-> user review queue
|
|
119
|
+
-> signed skill pack
|
|
120
|
+
-> optional share/sync
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
Existing foundation:
|
|
124
|
+
|
|
125
|
+
```text
|
|
126
|
+
~/.agintiflow/housekeeping/events.jsonl
|
|
127
|
+
~/.agintiflow/housekeeping/capabilities.json
|
|
128
|
+
```
|
|
129
|
+
|
|
130
|
+
Future local folders:
|
|
131
|
+
|
|
132
|
+
```text
|
|
133
|
+
~/.agintiflow/skillmesh/
|
|
134
|
+
config.json
|
|
135
|
+
identity.json
|
|
136
|
+
inbox/
|
|
137
|
+
outbox/
|
|
138
|
+
reviewed/
|
|
139
|
+
rejected/
|
|
140
|
+
feeds/
|
|
141
|
+
trusted-keys/
|
|
142
|
+
```
|
|
143
|
+
|
|
144
|
+
Candidate skill packs should stay local until reviewed.
|
|
145
|
+
|
|
146
|
+
## Slow Sync And Value Gate
|
|
147
|
+
|
|
148
|
+
Skill Mesh should avoid heavy or frequent communication.
|
|
149
|
+
|
|
150
|
+
Default sync behavior:
|
|
151
|
+
|
|
152
|
+
- No sync while an agent run is active.
|
|
153
|
+
- No sync while shell tools, browser tools, package installs, tests, or model calls are running.
|
|
154
|
+
- Sync only during idle windows.
|
|
155
|
+
- Add jitter so many clients do not sync at the same second.
|
|
156
|
+
- Cap outbound submissions per day.
|
|
157
|
+
- Cap inbound downloads per sync.
|
|
158
|
+
- Prefer metadata sync first, pack download second.
|
|
159
|
+
- Never use Skill Mesh as a live coordination channel for active agent tasks.
|
|
160
|
+
|
|
161
|
+
Suggested defaults:
|
|
162
|
+
|
|
163
|
+
```json
|
|
164
|
+
{
|
|
165
|
+
"syncPolicy": {
|
|
166
|
+
"enabled": false,
|
|
167
|
+
"idleOnly": true,
|
|
168
|
+
"minIdleSeconds": 90,
|
|
169
|
+
"minIntervalMinutes": 360,
|
|
170
|
+
"jitterMinutes": 30,
|
|
171
|
+
"maxOutboundPacksPerDay": 3,
|
|
172
|
+
"maxInboundPacksPerSync": 20,
|
|
173
|
+
"metadataFirst": true,
|
|
174
|
+
"downloadRequiresUserReview": true
|
|
175
|
+
}
|
|
176
|
+
}
|
|
177
|
+
```
|
|
178
|
+
|
|
179
|
+
The local scheduler should be simple:
|
|
180
|
+
|
|
181
|
+
```text
|
|
182
|
+
if skillmesh.mode != "share": skip
|
|
183
|
+
if agent is running: skip
|
|
184
|
+
if last sync too recent: skip
|
|
185
|
+
if no reviewed outbox packs and no feed refresh due: skip
|
|
186
|
+
fetch feed metadata
|
|
187
|
+
dedupe against local database
|
|
188
|
+
download only selected/high-trust candidates
|
|
189
|
+
upload only reviewed outbound packs
|
|
190
|
+
```
|
|
191
|
+
|
|
192
|
+
### Value Scoring
|
|
193
|
+
|
|
194
|
+
The candidate extractor should not share every local observation. It should rank candidates and export only the most useful.
|
|
195
|
+
|
|
196
|
+
Signals that increase value:
|
|
197
|
+
|
|
198
|
+
- The same failure happened more than once and a reusable fix was found.
|
|
199
|
+
- A new skill/tool recipe was used successfully with verification.
|
|
200
|
+
- A command policy pattern prevented a dangerous or stuck command.
|
|
201
|
+
- A generated smoke test caught a real regression.
|
|
202
|
+
- A workflow applies across many projects, not only one user folder.
|
|
203
|
+
- The candidate contains acceptance criteria and verification commands.
|
|
204
|
+
- The candidate is small and self-contained.
|
|
205
|
+
|
|
206
|
+
Signals that reduce value:
|
|
207
|
+
|
|
208
|
+
- It mentions private project names, file paths, users, servers, or proprietary APIs.
|
|
209
|
+
- It depends on a very specific local machine layout.
|
|
210
|
+
- It duplicates an existing core skill.
|
|
211
|
+
- It only says generic advice.
|
|
212
|
+
- It was not verified by a test, command, screenshot, or file evidence.
|
|
213
|
+
- It requires secrets, sudo passwords, or private accounts.
|
|
214
|
+
|
|
215
|
+
Example scoring:
|
|
216
|
+
|
|
217
|
+
```json
|
|
218
|
+
{
|
|
219
|
+
"minShareScore": 80,
|
|
220
|
+
"weights": {
|
|
221
|
+
"verified": 30,
|
|
222
|
+
"reusedAcrossSessions": 20,
|
|
223
|
+
"hasSmokeTest": 20,
|
|
224
|
+
"hasClearTrigger": 10,
|
|
225
|
+
"smallAndGeneric": 10,
|
|
226
|
+
"duplicatesExistingSkill": -40,
|
|
227
|
+
"containsPrivateContext": -100
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
```
|
|
231
|
+
|
|
232
|
+
Only reviewed packs above the threshold should enter the share outbox.
|
|
233
|
+
|
|
234
|
+
## Deduplication Database
|
|
235
|
+
|
|
236
|
+
Both clients and relay servers need a database to avoid duplication and noisy sync.
|
|
237
|
+
|
|
238
|
+
Local database:
|
|
239
|
+
|
|
240
|
+
```text
|
|
241
|
+
~/.agintiflow/skillmesh/index.sqlite
|
|
242
|
+
```
|
|
243
|
+
|
|
244
|
+
Relay database:
|
|
245
|
+
|
|
246
|
+
```text
|
|
247
|
+
~/.aginti-skill-relay/index.sqlite
|
|
248
|
+
```
|
|
249
|
+
|
|
250
|
+
Core tables:
|
|
251
|
+
|
|
252
|
+
```sql
|
|
253
|
+
CREATE TABLE packs (
|
|
254
|
+
pack_hash TEXT PRIMARY KEY,
|
|
255
|
+
canonical_id TEXT NOT NULL,
|
|
256
|
+
name TEXT NOT NULL,
|
|
257
|
+
version TEXT NOT NULL,
|
|
258
|
+
author_key_id TEXT NOT NULL,
|
|
259
|
+
status TEXT NOT NULL,
|
|
260
|
+
trust_level TEXT NOT NULL,
|
|
261
|
+
value_score INTEGER NOT NULL DEFAULT 0,
|
|
262
|
+
created_at TEXT NOT NULL,
|
|
263
|
+
received_at TEXT NOT NULL,
|
|
264
|
+
last_seen_at TEXT NOT NULL,
|
|
265
|
+
metadata_json TEXT NOT NULL
|
|
266
|
+
);
|
|
267
|
+
|
|
268
|
+
CREATE TABLE pack_signatures (
|
|
269
|
+
pack_hash TEXT NOT NULL,
|
|
270
|
+
key_id TEXT NOT NULL,
|
|
271
|
+
signature TEXT NOT NULL,
|
|
272
|
+
verified INTEGER NOT NULL DEFAULT 0,
|
|
273
|
+
PRIMARY KEY (pack_hash, key_id)
|
|
274
|
+
);
|
|
275
|
+
|
|
276
|
+
CREATE TABLE installed_packs (
|
|
277
|
+
pack_hash TEXT PRIMARY KEY,
|
|
278
|
+
enabled INTEGER NOT NULL DEFAULT 0,
|
|
279
|
+
installed_at TEXT NOT NULL,
|
|
280
|
+
source_feed TEXT NOT NULL DEFAULT ''
|
|
281
|
+
);
|
|
282
|
+
|
|
283
|
+
CREATE TABLE rejected_packs (
|
|
284
|
+
pack_hash TEXT PRIMARY KEY,
|
|
285
|
+
reason TEXT NOT NULL,
|
|
286
|
+
rejected_at TEXT NOT NULL
|
|
287
|
+
);
|
|
288
|
+
```
|
|
289
|
+
|
|
290
|
+
Hash strategy:
|
|
291
|
+
|
|
292
|
+
- `pack_hash`: SHA-256 of the canonical tarball bytes.
|
|
293
|
+
- `canonical_id`: stable hash of normalized semantic content, excluding timestamps and signatures.
|
|
294
|
+
- `skill_hash`: SHA-256 of normalized `SKILL.md` body and frontmatter.
|
|
295
|
+
- `policy_hash`: SHA-256 of normalized command-policy JSON.
|
|
296
|
+
|
|
297
|
+
Deduplication should use both exact and semantic hashes:
|
|
298
|
+
|
|
299
|
+
- If `pack_hash` exists, skip.
|
|
300
|
+
- If `canonical_id` exists with the same or higher version, skip.
|
|
301
|
+
- If a skill body hash matches a core skill, mark as duplicate.
|
|
302
|
+
- If a pack is rejected locally, do not re-download it unless the hash changes.
|
|
303
|
+
|
|
304
|
+
Relay response should support metadata-only dedupe:
|
|
305
|
+
|
|
306
|
+
```json
|
|
307
|
+
{
|
|
308
|
+
"feedVersion": 1,
|
|
309
|
+
"packs": [
|
|
310
|
+
{
|
|
311
|
+
"packHash": "sha256:...",
|
|
312
|
+
"canonicalId": "skill:android-emulator-screenshot:...",
|
|
313
|
+
"name": "android-emulator-screenshot",
|
|
314
|
+
"version": "0.1.0",
|
|
315
|
+
"valueScore": 92,
|
|
316
|
+
"trustLevel": "community-reviewed",
|
|
317
|
+
"downloadUrl": "/packs/sha256-....tgz",
|
|
318
|
+
"metadataUrl": "/packs/sha256-.../metadata.json"
|
|
319
|
+
}
|
|
320
|
+
]
|
|
321
|
+
}
|
|
322
|
+
```
|
|
323
|
+
|
|
324
|
+
Clients should send only hashes when asking what is new:
|
|
325
|
+
|
|
326
|
+
```http
|
|
327
|
+
POST /sync/metadata
|
|
328
|
+
```
|
|
329
|
+
|
|
330
|
+
```json
|
|
331
|
+
{
|
|
332
|
+
"clientProtocol": 1,
|
|
333
|
+
"knownPackHashes": ["sha256:..."],
|
|
334
|
+
"knownCanonicalIds": ["skill:..."],
|
|
335
|
+
"acceptedTrustLevels": ["core", "trusted-publisher", "community-reviewed"]
|
|
336
|
+
}
|
|
337
|
+
```
|
|
338
|
+
|
|
339
|
+
This keeps routine communication small.
|
|
340
|
+
|
|
341
|
+
## Skill Pack Format
|
|
342
|
+
|
|
343
|
+
A shared skill pack should be a normal directory or tarball:
|
|
344
|
+
|
|
345
|
+
```text
|
|
346
|
+
skillpack.json
|
|
347
|
+
skills/<skill-id>/SKILL.md
|
|
348
|
+
profiles/<profile-id>.json
|
|
349
|
+
policies/<policy-id>.json
|
|
350
|
+
tests/<test-id>.js
|
|
351
|
+
examples/<example-id>/README.md
|
|
352
|
+
```
|
|
353
|
+
|
|
354
|
+
`skillpack.json` should include:
|
|
355
|
+
|
|
356
|
+
```json
|
|
357
|
+
{
|
|
358
|
+
"schema": 1,
|
|
359
|
+
"name": "android-emulator-screenshot",
|
|
360
|
+
"version": "0.1.0",
|
|
361
|
+
"author": "local-user-or-org",
|
|
362
|
+
"license": "Apache-2.0",
|
|
363
|
+
"createdAt": "2026-05-04T00:00:00.000Z",
|
|
364
|
+
"source": "reviewed-local-learning",
|
|
365
|
+
"privacy": {
|
|
366
|
+
"rawSessionsIncluded": false,
|
|
367
|
+
"secretsRedacted": true,
|
|
368
|
+
"pathsMasked": true,
|
|
369
|
+
"requiresHumanReview": true
|
|
370
|
+
},
|
|
371
|
+
"contents": {
|
|
372
|
+
"skills": ["android-emulator-screenshot"],
|
|
373
|
+
"profiles": ["android"],
|
|
374
|
+
"tests": ["android-screenshot-smoke"]
|
|
375
|
+
},
|
|
376
|
+
"signature": {
|
|
377
|
+
"algorithm": "ed25519",
|
|
378
|
+
"publicKeyId": "..."
|
|
379
|
+
}
|
|
380
|
+
}
|
|
381
|
+
```
|
|
382
|
+
|
|
383
|
+
The pack should be installable locally:
|
|
384
|
+
|
|
385
|
+
```bash
|
|
386
|
+
aginti skillmesh import ./android-emulator-screenshot.skillpack.tgz
|
|
387
|
+
```
|
|
388
|
+
|
|
389
|
+
and exportable:
|
|
390
|
+
|
|
391
|
+
```bash
|
|
392
|
+
aginti skillmesh export android-emulator-screenshot
|
|
393
|
+
```
|
|
394
|
+
|
|
395
|
+
## Trust Model
|
|
396
|
+
|
|
397
|
+
Skill Mesh should treat shared capabilities like dependencies.
|
|
398
|
+
|
|
399
|
+
Trust levels:
|
|
400
|
+
|
|
401
|
+
- **Core**: shipped by the npm package.
|
|
402
|
+
- **Trusted publisher**: signed by LazyingArt or a configured team key.
|
|
403
|
+
- **Community reviewed**: available from a feed, but not automatically active.
|
|
404
|
+
- **Local experimental**: created on this machine.
|
|
405
|
+
- **Blocked**: rejected by the user or a policy rule.
|
|
406
|
+
|
|
407
|
+
Installing a skill pack should show:
|
|
408
|
+
|
|
409
|
+
- Author.
|
|
410
|
+
- Signature status.
|
|
411
|
+
- Files included.
|
|
412
|
+
- Tools/commands it recommends.
|
|
413
|
+
- Whether it changes command policy.
|
|
414
|
+
- Whether it adds tests.
|
|
415
|
+
- Whether it has examples.
|
|
416
|
+
|
|
417
|
+
Default import behavior:
|
|
418
|
+
|
|
419
|
+
```text
|
|
420
|
+
download -> verify -> preview -> install disabled -> user enables
|
|
421
|
+
```
|
|
422
|
+
|
|
423
|
+
Do not auto-enable community skills that can cause shell, git, network, browser, or file-writing behavior.
|
|
424
|
+
|
|
425
|
+
## Server And P2P Options
|
|
426
|
+
|
|
427
|
+
There are three viable distribution modes.
|
|
428
|
+
|
|
429
|
+
### 1. No Server: npm-Only Sharing
|
|
430
|
+
|
|
431
|
+
This is the safest and simplest.
|
|
432
|
+
|
|
433
|
+
Flow:
|
|
434
|
+
|
|
435
|
+
```text
|
|
436
|
+
users learn locally -> useful lessons become PRs or releases -> npm package ships updated skills
|
|
437
|
+
```
|
|
438
|
+
|
|
439
|
+
Pros:
|
|
440
|
+
|
|
441
|
+
- Strong review.
|
|
442
|
+
- Easy install and update.
|
|
443
|
+
- No user data service.
|
|
444
|
+
- Good for stable core skills.
|
|
445
|
+
|
|
446
|
+
Cons:
|
|
447
|
+
|
|
448
|
+
- Slower feedback loop.
|
|
449
|
+
- Less community experimentation.
|
|
450
|
+
|
|
451
|
+
### 2. Skill Relay Server
|
|
452
|
+
|
|
453
|
+
Use an ECS machine as a lightweight relay/index. Suggested product name:
|
|
454
|
+
|
|
455
|
+
```text
|
|
456
|
+
AgInTi Skill Relay
|
|
457
|
+
```
|
|
458
|
+
|
|
459
|
+
The relay should store only reviewed skill packs and feed metadata.
|
|
460
|
+
|
|
461
|
+
Server responsibilities:
|
|
462
|
+
|
|
463
|
+
- Receive signed skill packs.
|
|
464
|
+
- Reject raw session uploads.
|
|
465
|
+
- Run redaction/sanity checks.
|
|
466
|
+
- Compute hashes and deduplicate.
|
|
467
|
+
- Expose feed indexes.
|
|
468
|
+
- Serve downloads.
|
|
469
|
+
- Keep reputation/signature metadata.
|
|
470
|
+
- Optionally maintain review status.
|
|
471
|
+
- Rate-limit clients and publishers.
|
|
472
|
+
- Maintain dedupe indexes by exact and semantic hash.
|
|
473
|
+
- Support metadata-only sync.
|
|
474
|
+
- Quarantine untrusted uploads before feed publication.
|
|
475
|
+
|
|
476
|
+
Server should not:
|
|
477
|
+
|
|
478
|
+
- Store raw `~/.agintiflow/sessions`.
|
|
479
|
+
- Store raw project source.
|
|
480
|
+
- Store provider keys.
|
|
481
|
+
- Execute uploaded code.
|
|
482
|
+
- Auto-push updates to clients.
|
|
483
|
+
- Accept anonymous bulk uploads without rate limits.
|
|
484
|
+
- Act as a general file-sharing server.
|
|
485
|
+
- Serve packs that failed redaction or archive policy checks.
|
|
486
|
+
|
|
487
|
+
Possible server command:
|
|
488
|
+
|
|
489
|
+
```bash
|
|
490
|
+
aginti-skill-relay serve --host 0.0.0.0 --port 7377 --data ~/.aginti-skill-relay
|
|
491
|
+
```
|
|
492
|
+
|
|
493
|
+
Client sync:
|
|
494
|
+
|
|
495
|
+
```bash
|
|
496
|
+
aginti skillmesh feed add lazyingart https://skills.flow.lazying.art/feed.json
|
|
497
|
+
aginti skillmesh sync
|
|
498
|
+
aginti skillmesh inbox
|
|
499
|
+
```
|
|
500
|
+
|
|
501
|
+
### Strict Server Contract
|
|
502
|
+
|
|
503
|
+
The relay should be defensive by default.
|
|
504
|
+
|
|
505
|
+
Inbound upload checks:
|
|
506
|
+
|
|
507
|
+
- Require authenticated publisher identity or a temporary upload token.
|
|
508
|
+
- Require signed `skillpack.json`.
|
|
509
|
+
- Require archive size under a small limit, for example 2 MB initially.
|
|
510
|
+
- Require max file count, for example 100 files.
|
|
511
|
+
- Require all paths to be relative and normalized.
|
|
512
|
+
- Reject symlinks, hardlinks, device files, absolute paths, and `..` path traversal.
|
|
513
|
+
- Reject executable binaries by default.
|
|
514
|
+
- Reject nested archives by default.
|
|
515
|
+
- Reject any archive containing raw session filenames.
|
|
516
|
+
- Scan every text file for token/secret patterns.
|
|
517
|
+
- Require `privacy.rawSessionsIncluded=false`.
|
|
518
|
+
- Require `privacy.requiresHumanReview=true` unless the publisher is trusted.
|
|
519
|
+
- Put uploads into `pending` before public feed inclusion.
|
|
520
|
+
|
|
521
|
+
Outbound feed checks:
|
|
522
|
+
|
|
523
|
+
- Serve only approved or trusted packs.
|
|
524
|
+
- Include content hashes and signature metadata.
|
|
525
|
+
- Include trust level and review status.
|
|
526
|
+
- Do not expose uploader IPs or private client metadata.
|
|
527
|
+
- Keep feed response small and cacheable.
|
|
528
|
+
- Use ETag/If-None-Match for low traffic.
|
|
529
|
+
|
|
530
|
+
Abuse controls:
|
|
531
|
+
|
|
532
|
+
- Per-IP rate limits.
|
|
533
|
+
- Per-publisher daily upload limits.
|
|
534
|
+
- Maximum pending queue size.
|
|
535
|
+
- Manual blocklist for bad keys, bad IPs, and bad pack hashes.
|
|
536
|
+
- Audit log of decisions without storing raw private content.
|
|
537
|
+
|
|
538
|
+
The relay should fail closed: if validation cannot prove a pack is safe, the pack stays private/pending.
|
|
539
|
+
|
|
540
|
+
### Strict Client Contract
|
|
541
|
+
|
|
542
|
+
Clients must also be defensive.
|
|
543
|
+
|
|
544
|
+
Before upload:
|
|
545
|
+
|
|
546
|
+
- Export only reviewed packs from `~/.agintiflow/skillmesh/reviewed/`.
|
|
547
|
+
- Run local redaction scan.
|
|
548
|
+
- Run archive policy scan.
|
|
549
|
+
- Show a human-readable manifest preview.
|
|
550
|
+
- Require explicit confirmation unless the publisher key is configured for unattended sharing.
|
|
551
|
+
- Upload only pack metadata first if possible.
|
|
552
|
+
|
|
553
|
+
Before download/install:
|
|
554
|
+
|
|
555
|
+
- Fetch metadata first.
|
|
556
|
+
- Deduplicate locally.
|
|
557
|
+
- Verify signature when present.
|
|
558
|
+
- Reject packs with unsupported schema.
|
|
559
|
+
- Reject packs requiring disabled capabilities.
|
|
560
|
+
- Install community packs disabled by default.
|
|
561
|
+
- Show diff/manifest before enabling.
|
|
562
|
+
- Never let a downloaded pack directly change provider keys, `.env`, shell policy, or auto-update settings.
|
|
563
|
+
|
|
564
|
+
Client setting:
|
|
565
|
+
|
|
566
|
+
```json
|
|
567
|
+
{
|
|
568
|
+
"downloadPolicy": {
|
|
569
|
+
"autoDownloadMetadata": true,
|
|
570
|
+
"autoDownloadPacks": false,
|
|
571
|
+
"autoEnableSkills": false,
|
|
572
|
+
"allowPolicyChanges": false,
|
|
573
|
+
"allowExecutableTests": false
|
|
574
|
+
}
|
|
575
|
+
}
|
|
576
|
+
```
|
|
577
|
+
|
|
578
|
+
### 3. P2P Mesh
|
|
579
|
+
|
|
580
|
+
True P2P can come later. It is harder because NAT traversal, identity, signatures, spam, and moderation become product concerns.
|
|
581
|
+
|
|
582
|
+
Pragmatic first step:
|
|
583
|
+
|
|
584
|
+
- Use the ECS server as a rendezvous and relay.
|
|
585
|
+
- Keep client identity keypairs local.
|
|
586
|
+
- Sign every skill pack.
|
|
587
|
+
- Let users subscribe to feeds rather than broadcast everything.
|
|
588
|
+
|
|
589
|
+
This gives most of the value of P2P without building a fragile distributed network first.
|
|
590
|
+
|
|
591
|
+
### Volunteer Shared Nodes
|
|
592
|
+
|
|
593
|
+
A volunteer shared node is a user-run relay that can exchange reviewed skill packs with the major node and with trusted peers.
|
|
594
|
+
|
|
595
|
+
Modes:
|
|
596
|
+
|
|
597
|
+
- **Client only**: syncs with feeds, does not accept inbound connections.
|
|
598
|
+
- **Volunteer node**: serves a local feed and accepts reviewed pack submissions from configured peers.
|
|
599
|
+
- **Major node**: public, stable relay operated by LazyingArt or a trusted maintainer.
|
|
600
|
+
|
|
601
|
+
Volunteer nodes should be opt-in and conservative:
|
|
602
|
+
|
|
603
|
+
```bash
|
|
604
|
+
aginti skillmesh node init
|
|
605
|
+
aginti skillmesh node check-public
|
|
606
|
+
aginti skillmesh node serve --port 7377
|
|
607
|
+
```
|
|
608
|
+
|
|
609
|
+
Node health checks:
|
|
610
|
+
|
|
611
|
+
- Public URL configured.
|
|
612
|
+
- TLS available or explicitly disabled for LAN-only.
|
|
613
|
+
- `/health` reachable from outside if public.
|
|
614
|
+
- Feed endpoint reachable.
|
|
615
|
+
- Upload endpoint protected.
|
|
616
|
+
- Data directory not inside a project repo.
|
|
617
|
+
- Rate limits enabled.
|
|
618
|
+
- Pack quarantine enabled.
|
|
619
|
+
|
|
620
|
+
If a machine is behind LAN/NAT, the user can provide an external tunnel:
|
|
621
|
+
|
|
622
|
+
```bash
|
|
623
|
+
ngrok http 7377
|
|
624
|
+
aginti skillmesh node set-url https://example.ngrok-free.app
|
|
625
|
+
aginti skillmesh node check-public
|
|
626
|
+
```
|
|
627
|
+
|
|
628
|
+
The node should not guess that it is public. It should verify from an external check endpoint or ask the major relay to call back:
|
|
629
|
+
|
|
630
|
+
```text
|
|
631
|
+
local node -> major node: please verify https://example.ngrok-free.app/health with nonce abc
|
|
632
|
+
major node -> local node: GET /health?nonce=abc
|
|
633
|
+
local node -> major node: verification succeeds
|
|
634
|
+
```
|
|
635
|
+
|
|
636
|
+
Only verified nodes should be listed as reachable peers.
|
|
637
|
+
|
|
638
|
+
### Verified Node Admission
|
|
639
|
+
|
|
640
|
+
A node can join the mesh only after a currently verified node can connect to it and complete the designed verification API.
|
|
641
|
+
|
|
642
|
+
Default admission authority:
|
|
643
|
+
|
|
644
|
+
```text
|
|
645
|
+
skills.flow.lazying.art
|
|
646
|
+
```
|
|
647
|
+
|
|
648
|
+
This means a LAN machine exposed by ngrok or a public `ip:port` is not trusted just because the user typed a URL. The major node must verify it first.
|
|
649
|
+
|
|
650
|
+
Admission flow:
|
|
651
|
+
|
|
652
|
+
```text
|
|
653
|
+
candidate node starts local relay
|
|
654
|
+
candidate node sets public URL, for example ngrok URL or https://ip:port
|
|
655
|
+
candidate node asks major node to verify
|
|
656
|
+
major node creates nonce and expected callback challenge
|
|
657
|
+
major node calls candidate /health and /node/verify endpoints
|
|
658
|
+
candidate proves it owns the local node identity key
|
|
659
|
+
major node checks protocol version, TLS/public URL, feed endpoint, upload protection, rate limits, and quarantine
|
|
660
|
+
major node adds candidate to node list as verified
|
|
661
|
+
verified node appears in feed metadata for optional peer sync
|
|
662
|
+
```
|
|
663
|
+
|
|
664
|
+
Verification API shape:
|
|
665
|
+
|
|
666
|
+
```http
|
|
667
|
+
POST /nodes/register
|
|
668
|
+
GET /health?nonce=<nonce>
|
|
669
|
+
POST /node/verify
|
|
670
|
+
GET /feed.json
|
|
671
|
+
```
|
|
672
|
+
|
|
673
|
+
Candidate registration payload:
|
|
674
|
+
|
|
675
|
+
```json
|
|
676
|
+
{
|
|
677
|
+
"nodeId": "ed25519:key-id",
|
|
678
|
+
"publicUrl": "https://example.ngrok-free.app",
|
|
679
|
+
"role": "volunteer",
|
|
680
|
+
"protocol": 1,
|
|
681
|
+
"capabilities": ["feed", "metadata-sync"],
|
|
682
|
+
"signature": "signature over publicUrl + nonce"
|
|
683
|
+
}
|
|
684
|
+
```
|
|
685
|
+
|
|
686
|
+
Major node checks:
|
|
687
|
+
|
|
688
|
+
- Public URL is reachable from the major node.
|
|
689
|
+
- Node identity signature verifies.
|
|
690
|
+
- `/health` returns the expected nonce.
|
|
691
|
+
- `/feed.json` is valid and small.
|
|
692
|
+
- Upload endpoint is either disabled or protected.
|
|
693
|
+
- Node advertises idle/slow sync policy.
|
|
694
|
+
- Node does not claim to accept raw sessions.
|
|
695
|
+
- Node version/protocol is compatible.
|
|
696
|
+
|
|
697
|
+
Node list table:
|
|
698
|
+
|
|
699
|
+
```sql
|
|
700
|
+
CREATE TABLE verified_nodes (
|
|
701
|
+
node_id TEXT PRIMARY KEY,
|
|
702
|
+
public_url TEXT NOT NULL,
|
|
703
|
+
role TEXT NOT NULL,
|
|
704
|
+
protocol INTEGER NOT NULL,
|
|
705
|
+
status TEXT NOT NULL,
|
|
706
|
+
first_verified_at TEXT NOT NULL,
|
|
707
|
+
last_verified_at TEXT NOT NULL,
|
|
708
|
+
last_seen_at TEXT NOT NULL,
|
|
709
|
+
failure_count INTEGER NOT NULL DEFAULT 0,
|
|
710
|
+
metadata_json TEXT NOT NULL
|
|
711
|
+
);
|
|
712
|
+
```
|
|
713
|
+
|
|
714
|
+
Removal policy:
|
|
715
|
+
|
|
716
|
+
- Recheck verified nodes occasionally, for example every 6-24 hours.
|
|
717
|
+
- If a node fails once, mark `degraded`.
|
|
718
|
+
- If it fails repeatedly, mark `offline`.
|
|
719
|
+
- If it stays offline beyond a threshold, remove it from the public node list.
|
|
720
|
+
- Keep the historical record locally for audit, but do not advertise unavailable nodes.
|
|
721
|
+
|
|
722
|
+
Suggested thresholds:
|
|
723
|
+
|
|
724
|
+
```json
|
|
725
|
+
{
|
|
726
|
+
"nodeVerification": {
|
|
727
|
+
"recheckIntervalHours": 12,
|
|
728
|
+
"degradedAfterFailures": 1,
|
|
729
|
+
"offlineAfterFailures": 3,
|
|
730
|
+
"removeAfterOfflineDays": 7
|
|
731
|
+
}
|
|
732
|
+
}
|
|
733
|
+
```
|
|
734
|
+
|
|
735
|
+
## ECS Deployment Role
|
|
736
|
+
|
|
737
|
+
The Alibaba Cloud ECS host can run a Skill Relay node.
|
|
738
|
+
|
|
739
|
+
Recommended architecture:
|
|
740
|
+
|
|
741
|
+
```text
|
|
742
|
+
nginx or caddy
|
|
743
|
+
-> aginti-skill-relay node process
|
|
744
|
+
-> ~/.aginti-skill-relay/index.sqlite
|
|
745
|
+
-> ~/.aginti-skill-relay/packs/
|
|
746
|
+
```
|
|
747
|
+
|
|
748
|
+
Minimum endpoints:
|
|
749
|
+
|
|
750
|
+
```text
|
|
751
|
+
GET /health
|
|
752
|
+
GET /feed.json
|
|
753
|
+
GET /packs/<hash>.tgz
|
|
754
|
+
POST /submit
|
|
755
|
+
GET /packs/<hash>/metadata.json
|
|
756
|
+
```
|
|
757
|
+
|
|
758
|
+
Major node role:
|
|
759
|
+
|
|
760
|
+
- Stable public rendezvous point.
|
|
761
|
+
- Canonical community feed.
|
|
762
|
+
- Deduplication authority for public packs.
|
|
763
|
+
- Optional verification callback service for volunteer nodes.
|
|
764
|
+
- Optional relay for metadata exchange between trusted nodes.
|
|
765
|
+
- Not a raw memory server.
|
|
766
|
+
|
|
767
|
+
Recommended domain:
|
|
768
|
+
|
|
769
|
+
```text
|
|
770
|
+
skills.flow.lazying.art
|
|
771
|
+
```
|
|
772
|
+
|
|
773
|
+
Possible deployment command on `sshem`:
|
|
774
|
+
|
|
775
|
+
```bash
|
|
776
|
+
npm install -g @lazyingart/agintiflow
|
|
777
|
+
aginti skillmesh serve \
|
|
778
|
+
--role major \
|
|
779
|
+
--host 127.0.0.1 \
|
|
780
|
+
--port 7377 \
|
|
781
|
+
--data ~/.aginti-skill-relay \
|
|
782
|
+
--public-url https://skills.flow.lazying.art
|
|
783
|
+
```
|
|
784
|
+
|
|
785
|
+
With nginx/caddy terminating TLS:
|
|
786
|
+
|
|
787
|
+
```text
|
|
788
|
+
https://skills.flow.lazying.art
|
|
789
|
+
-> 127.0.0.1:7377
|
|
790
|
+
```
|
|
791
|
+
|
|
792
|
+
Initial server config:
|
|
793
|
+
|
|
794
|
+
```json
|
|
795
|
+
{
|
|
796
|
+
"role": "major",
|
|
797
|
+
"publicUrl": "https://skills.flow.lazying.art",
|
|
798
|
+
"dataDir": "~/.aginti-skill-relay",
|
|
799
|
+
"acceptUploads": true,
|
|
800
|
+
"requireSignatures": true,
|
|
801
|
+
"requireReview": true,
|
|
802
|
+
"maxPackBytes": 2097152,
|
|
803
|
+
"maxFilesPerPack": 100,
|
|
804
|
+
"rateLimits": {
|
|
805
|
+
"submitPerIpPerHour": 10,
|
|
806
|
+
"submitPerPublisherPerDay": 20,
|
|
807
|
+
"metadataPerIpPerMinute": 60
|
|
808
|
+
}
|
|
809
|
+
}
|
|
810
|
+
```
|
|
811
|
+
|
|
812
|
+
### Major Node Bootstrap On `sshem`
|
|
813
|
+
|
|
814
|
+
The `sshem` ECS machine should be treated as the first **major node**. Other users who enable `Record + Share Reviewed Skills` can sync with it, but the node should still accept only reviewed/signed packs and should publish feeds slowly.
|
|
815
|
+
|
|
816
|
+
Host assumptions from the current ECS login:
|
|
817
|
+
|
|
818
|
+
```text
|
|
819
|
+
OS: Ubuntu 24.04 LTS
|
|
820
|
+
role: public major relay
|
|
821
|
+
service user: aginti-relay
|
|
822
|
+
data: /var/lib/aginti-skill-relay
|
|
823
|
+
logs: /var/log/aginti-skill-relay
|
|
824
|
+
public domain: skills.flow.lazying.art
|
|
825
|
+
internal port: 7377
|
|
826
|
+
```
|
|
827
|
+
|
|
828
|
+
Bootstrap outline:
|
|
829
|
+
|
|
830
|
+
```bash
|
|
831
|
+
sudo adduser --system --group --home /var/lib/aginti-skill-relay aginti-relay
|
|
832
|
+
sudo mkdir -p /var/lib/aginti-skill-relay /var/log/aginti-skill-relay
|
|
833
|
+
sudo chown -R aginti-relay:aginti-relay /var/lib/aginti-skill-relay /var/log/aginti-skill-relay
|
|
834
|
+
npm install -g @lazyingart/agintiflow
|
|
835
|
+
```
|
|
836
|
+
|
|
837
|
+
Service command:
|
|
838
|
+
|
|
839
|
+
```bash
|
|
840
|
+
sudo -u aginti-relay aginti skillmesh serve \
|
|
841
|
+
--role major \
|
|
842
|
+
--host 127.0.0.1 \
|
|
843
|
+
--port 7377 \
|
|
844
|
+
--data /var/lib/aginti-skill-relay \
|
|
845
|
+
--public-url https://skills.flow.lazying.art
|
|
846
|
+
```
|
|
847
|
+
|
|
848
|
+
Systemd shape:
|
|
849
|
+
|
|
850
|
+
```ini
|
|
851
|
+
[Unit]
|
|
852
|
+
Description=AgInTi Skill Relay
|
|
853
|
+
After=network-online.target
|
|
854
|
+
Wants=network-online.target
|
|
855
|
+
|
|
856
|
+
[Service]
|
|
857
|
+
Type=simple
|
|
858
|
+
User=aginti-relay
|
|
859
|
+
Group=aginti-relay
|
|
860
|
+
WorkingDirectory=/var/lib/aginti-skill-relay
|
|
861
|
+
Environment=NODE_ENV=production
|
|
862
|
+
ExecStart=/usr/bin/env aginti skillmesh serve --role major --host 127.0.0.1 --port 7377 --data /var/lib/aginti-skill-relay --public-url https://skills.flow.lazying.art
|
|
863
|
+
Restart=on-failure
|
|
864
|
+
RestartSec=5
|
|
865
|
+
NoNewPrivileges=true
|
|
866
|
+
PrivateTmp=true
|
|
867
|
+
ProtectSystem=strict
|
|
868
|
+
ProtectHome=true
|
|
869
|
+
ReadWritePaths=/var/lib/aginti-skill-relay /var/log/aginti-skill-relay
|
|
870
|
+
|
|
871
|
+
[Install]
|
|
872
|
+
WantedBy=multi-user.target
|
|
873
|
+
```
|
|
874
|
+
|
|
875
|
+
Nginx/Caddy should terminate TLS and proxy only the relay domain to `127.0.0.1:7377`. The relay process itself should not bind directly to `0.0.0.0` on the major node unless there is no reverse proxy.
|
|
876
|
+
|
|
877
|
+
Firewall:
|
|
878
|
+
|
|
879
|
+
```text
|
|
880
|
+
allow 22/tcp for SSH
|
|
881
|
+
allow 80/tcp for ACME HTTP challenge if needed
|
|
882
|
+
allow 443/tcp for HTTPS
|
|
883
|
+
deny public 7377/tcp
|
|
884
|
+
```
|
|
885
|
+
|
|
886
|
+
Backups:
|
|
887
|
+
|
|
888
|
+
- Back up `index.sqlite`, `packs/`, `trusted-keys/`, and `review-state/`.
|
|
889
|
+
- Do not back up temporary upload quarantine forever; expire rejected uploads.
|
|
890
|
+
- Keep audit logs but rotate them.
|
|
891
|
+
- Never back up or store submitted raw sessions because those should be rejected before persistence.
|
|
892
|
+
|
|
893
|
+
Major node publishing cadence:
|
|
894
|
+
|
|
895
|
+
```text
|
|
896
|
+
incoming upload -> quarantine -> validation -> pending review -> approved feed batch
|
|
897
|
+
feed batch interval: 30-60 minutes
|
|
898
|
+
metadata cache: ETag + max-age
|
|
899
|
+
pack files: immutable by hash
|
|
900
|
+
```
|
|
901
|
+
|
|
902
|
+
Major node failure mode:
|
|
903
|
+
|
|
904
|
+
- If validation worker fails, uploads stay pending.
|
|
905
|
+
- If database write fails, upload fails.
|
|
906
|
+
- If redaction scanner fails, upload is rejected or held pending.
|
|
907
|
+
- If feed generation fails, keep serving the last known good feed.
|
|
908
|
+
- If disk usage is high, stop accepting uploads before serving breaks.
|
|
909
|
+
|
|
910
|
+
Submission policy:
|
|
911
|
+
|
|
912
|
+
- Require signed packs.
|
|
913
|
+
- Require `privacy.rawSessionsIncluded=false`.
|
|
914
|
+
- Reject archives containing `.env`, `.git`, `.aginti-sessions`, `.sessions`, `events.jsonl`, `state.json`, `storage-state.json`, or obvious private paths.
|
|
915
|
+
- Run content scans for token patterns.
|
|
916
|
+
- Put new packs into `pending` until approved or trusted.
|
|
917
|
+
- Reject too frequent submissions.
|
|
918
|
+
- Reject duplicate exact hashes immediately.
|
|
919
|
+
- Merge duplicate semantic packs into the same canonical record.
|
|
920
|
+
|
|
921
|
+
## Sync Frequency Policy
|
|
922
|
+
|
|
923
|
+
Skill Mesh should be closer to package update checks than chat messages.
|
|
924
|
+
|
|
925
|
+
Default sync cadence:
|
|
926
|
+
|
|
927
|
+
```text
|
|
928
|
+
metadata refresh: every 6-12 hours
|
|
929
|
+
pack upload: idle-only, max 3/day by default
|
|
930
|
+
pack download: manual review or trusted feed only
|
|
931
|
+
major relay feed publish: batch every 30-60 minutes
|
|
932
|
+
volunteer node peer sync: every 12-24 hours
|
|
933
|
+
```
|
|
934
|
+
|
|
935
|
+
Reasons:
|
|
936
|
+
|
|
937
|
+
- Skills are slow-changing knowledge.
|
|
938
|
+
- Frequent sync increases privacy and abuse risk.
|
|
939
|
+
- Low-frequency sync makes server costs predictable.
|
|
940
|
+
- Idle-only sync avoids interfering with agent work.
|
|
941
|
+
- Batch publishing gives time for validation and review.
|
|
942
|
+
|
|
943
|
+
The UI should show sync state:
|
|
944
|
+
|
|
945
|
+
```text
|
|
946
|
+
Skill Mesh: Record + Share Reviewed Skills
|
|
947
|
+
last sync: 2026-05-04 13:06
|
|
948
|
+
next sync: after 18:58, idle-only
|
|
949
|
+
outbox: 1 reviewed pack pending
|
|
950
|
+
inbox: 4 new candidates, 0 enabled
|
|
951
|
+
relay: skills.flow.lazying.art healthy
|
|
952
|
+
```
|
|
953
|
+
|
|
954
|
+
## Commands
|
|
955
|
+
|
|
956
|
+
Interactive:
|
|
957
|
+
|
|
958
|
+
```text
|
|
959
|
+
/skillmesh
|
|
960
|
+
```
|
|
961
|
+
|
|
962
|
+
Selector:
|
|
963
|
+
|
|
964
|
+
```text
|
|
965
|
+
Skill Mesh
|
|
966
|
+
> Record + Share Reviewed Skills
|
|
967
|
+
Record Locally
|
|
968
|
+
Disabled
|
|
969
|
+
```
|
|
970
|
+
|
|
971
|
+
CLI:
|
|
972
|
+
|
|
973
|
+
```bash
|
|
974
|
+
aginti skillmesh status
|
|
975
|
+
aginti skillmesh off
|
|
976
|
+
aginti skillmesh record
|
|
977
|
+
aginti skillmesh share
|
|
978
|
+
aginti skillmesh review
|
|
979
|
+
aginti skillmesh export <name>
|
|
980
|
+
aginti skillmesh import <file-or-url>
|
|
981
|
+
aginti skillmesh feed add <name> <url>
|
|
982
|
+
aginti skillmesh sync
|
|
983
|
+
aginti skillmesh serve
|
|
984
|
+
aginti skillmesh node init
|
|
985
|
+
aginti skillmesh node check-public
|
|
986
|
+
aginti skillmesh node set-url <url>
|
|
987
|
+
```
|
|
988
|
+
|
|
989
|
+
Config:
|
|
990
|
+
|
|
991
|
+
```json
|
|
992
|
+
{
|
|
993
|
+
"mode": "share",
|
|
994
|
+
"feeds": [],
|
|
995
|
+
"shareRequiresReview": true,
|
|
996
|
+
"autoInstallSharedSkills": false,
|
|
997
|
+
"trustedPublishers": [],
|
|
998
|
+
"syncPolicy": {
|
|
999
|
+
"idleOnly": true,
|
|
1000
|
+
"minIntervalMinutes": 360,
|
|
1001
|
+
"maxOutboundPacksPerDay": 3
|
|
1002
|
+
}
|
|
1003
|
+
}
|
|
1004
|
+
```
|
|
1005
|
+
|
|
1006
|
+
Environment override:
|
|
1007
|
+
|
|
1008
|
+
```bash
|
|
1009
|
+
AGINTIFLOW_SKILLMESH=off
|
|
1010
|
+
AGINTIFLOW_SKILLMESH=record
|
|
1011
|
+
AGINTIFLOW_SKILLMESH=share
|
|
1012
|
+
```
|
|
1013
|
+
|
|
1014
|
+
## Safety Rules
|
|
1015
|
+
|
|
1016
|
+
Hard rules:
|
|
1017
|
+
|
|
1018
|
+
- Never upload raw session directories.
|
|
1019
|
+
- Never upload `.aginti-sessions/` or `.sessions/`.
|
|
1020
|
+
- Never upload `.env`, `.npmrc`, SSH keys, browser storage, cookies, or auth tokens.
|
|
1021
|
+
- Never enable shared skills automatically if they affect shell, git, network, filesystem writes, browser auth, or package installation.
|
|
1022
|
+
- Keep the sharing state visible through `aginti skillmesh status`.
|
|
1023
|
+
|
|
1024
|
+
Good defaults:
|
|
1025
|
+
|
|
1026
|
+
- `Record + Share Reviewed Skills` for product default, because it can improve the shared skill set while still requiring strict reviewed-pack sharing.
|
|
1027
|
+
- `Record Locally` for users who want learning logs but no network sharing.
|
|
1028
|
+
- Shared packs install disabled until enabled.
|
|
1029
|
+
- ECS relay accepts uploads only after local pack validation.
|
|
1030
|
+
- Sync is idle-only and low-frequency.
|
|
1031
|
+
- Metadata sync happens before pack transfer.
|
|
1032
|
+
- Deduplication happens before download or upload.
|
|
1033
|
+
|
|
1034
|
+
## Implementation Stages
|
|
1035
|
+
|
|
1036
|
+
### Stage 1: Local Skill Mesh
|
|
1037
|
+
|
|
1038
|
+
- Add `/skillmesh` selector with three modes.
|
|
1039
|
+
- Store config in `~/.agintiflow/skillmesh/config.json`.
|
|
1040
|
+
- Add `aginti skillmesh status`.
|
|
1041
|
+
- Keep using the existing housekeeping ledger.
|
|
1042
|
+
- Add local review queue from housekeeping candidates.
|
|
1043
|
+
|
|
1044
|
+
### Stage 2: Skill Pack Export/Import
|
|
1045
|
+
|
|
1046
|
+
- Add `aginti skillmesh export`.
|
|
1047
|
+
- Add `aginti skillmesh import`.
|
|
1048
|
+
- Support signature generation and verification.
|
|
1049
|
+
- Install imported skills disabled by default.
|
|
1050
|
+
|
|
1051
|
+
### Stage 3: Relay Server
|
|
1052
|
+
|
|
1053
|
+
- Add a separate npm binary:
|
|
1054
|
+
|
|
1055
|
+
```bash
|
|
1056
|
+
npm install -g @lazyingart/aginti-skill-relay
|
|
1057
|
+
aginti-skill-relay serve
|
|
1058
|
+
```
|
|
1059
|
+
|
|
1060
|
+
or keep it inside AgInTiFlow:
|
|
1061
|
+
|
|
1062
|
+
```bash
|
|
1063
|
+
aginti skillmesh serve
|
|
1064
|
+
```
|
|
1065
|
+
|
|
1066
|
+
Recommendation: start inside AgInTiFlow for speed, split into `@lazyingart/aginti-skill-relay` once the protocol stabilizes.
|
|
1067
|
+
|
|
1068
|
+
Stage 3 should include:
|
|
1069
|
+
|
|
1070
|
+
- SQLite dedupe database.
|
|
1071
|
+
- Pack archive validator.
|
|
1072
|
+
- Secret scanner.
|
|
1073
|
+
- Signature verifier.
|
|
1074
|
+
- Pending/reviewed/rejected states.
|
|
1075
|
+
- Metadata-only sync endpoint.
|
|
1076
|
+
- Public reachability check for volunteer nodes.
|
|
1077
|
+
- Nginx/Caddy deployment docs for ECS.
|
|
1078
|
+
|
|
1079
|
+
### Stage 4: Community Feed And Review
|
|
1080
|
+
|
|
1081
|
+
- Add feed subscription.
|
|
1082
|
+
- Add pending inbox.
|
|
1083
|
+
- Add publisher trust list.
|
|
1084
|
+
- Add simple moderation state on the relay.
|
|
1085
|
+
- Publish stable reviewed skills through npm releases.
|
|
1086
|
+
|
|
1087
|
+
### Stage 5: Volunteer Node Federation
|
|
1088
|
+
|
|
1089
|
+
- Add volunteer node mode.
|
|
1090
|
+
- Add ngrok/public URL configuration.
|
|
1091
|
+
- Add major-node callback verification.
|
|
1092
|
+
- Add peer allowlists.
|
|
1093
|
+
- Add low-frequency node-to-node metadata sync.
|
|
1094
|
+
- Keep major node as the default rendezvous and dedupe authority.
|
|
1095
|
+
- Remove nodes from the advertised node list when repeated reachability checks fail.
|
|
1096
|
+
|
|
1097
|
+
## Naming Recommendation
|
|
1098
|
+
|
|
1099
|
+
Use:
|
|
1100
|
+
|
|
1101
|
+
```text
|
|
1102
|
+
Skill Mesh
|
|
1103
|
+
/skillmesh
|
|
1104
|
+
aginti skillmesh
|
|
1105
|
+
AgInTi Skill Relay
|
|
1106
|
+
```
|
|
1107
|
+
|
|
1108
|
+
Why:
|
|
1109
|
+
|
|
1110
|
+
- `Skill Mesh` describes distributed capability sharing without promising raw P2P networking immediately.
|
|
1111
|
+
- `Skill Relay` is honest for the ECS role: it relays and indexes reviewed packs.
|
|
1112
|
+
- The names are short enough for CLI and clear enough for docs.
|
|
1113
|
+
|
|
1114
|
+
Avoid:
|
|
1115
|
+
|
|
1116
|
+
```text
|
|
1117
|
+
Skill Cloud
|
|
1118
|
+
Skill Brain
|
|
1119
|
+
Auto Learn Share
|
|
1120
|
+
Swarm Memory
|
|
1121
|
+
```
|
|
1122
|
+
|
|
1123
|
+
because they imply centralized memory, automatic uploads, or raw agent transcript sharing.
|