@fileverse/api 0.0.20 → 0.0.21
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/dist/cli/index.js.map +1 -1
- package/dist/cloudflare.js +40 -57
- package/dist/cloudflare.js.map +1 -1
- package/dist/commands/index.js +1 -6
- package/dist/commands/index.js.map +1 -1
- package/dist/index.js +22 -45
- package/dist/index.js.map +1 -1
- package/dist/worker.js +21 -39
- package/dist/worker.js.map +1 -1
- package/package.json +1 -1
- package/public/llm.txt +478 -204
package/public/llm.txt
CHANGED
|
@@ -1,347 +1,621 @@
|
|
|
1
1
|
# Fileverse API - AI Agent Guide
|
|
2
2
|
|
|
3
|
-
> Fileverse API
|
|
3
|
+
> Fileverse API is a document management system by Fileverse that stores and syncs documents (ddocs) between a local database and blockchain.
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
**Skill Name**: fileverse-api
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
## How to use this document
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
Fetch this via GET {SERVER_URL}/llm.txt. Use it to discover the server URL, decide API vs CLI mode, then follow the relevant section below.
|
|
10
10
|
|
|
11
|
-
|
|
11
|
+
## Integration checklist
|
|
12
12
|
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
13
|
+
1. Get server URL (from the URL you used to fetch this doc, minus /llm.txt) and apiKey (see API Key Configuration).
|
|
14
|
+
2. Try GET {SERVER_URL}/ping. If you get 200 and {"reply":"pong"}, use API mode; otherwise use CLI mode.
|
|
15
|
+
3. In API mode: every request must include apiKey as a query parameter; the path is complete before any query string.
|
|
16
|
+
4. For create/update: extract ddocId from response.data.ddocId (not from the top level of the response).
|
|
17
|
+
5. After create or update, poll GET /api/ddocs/{ddocId}?apiKey=... until syncStatus is "synced" or "failed", then show the link if synced.
|
|
18
|
+
|
|
19
|
+
## Server URL
|
|
20
|
+
|
|
21
|
+
If you fetched this document from a URL (e.g., http://localhost:8001/llm.txt):
|
|
22
|
+
- Your server URL is that URL without the /llm.txt suffix
|
|
23
|
+
- Example: http://localhost:8001/llm.txt → Server URL is http://localhost:8001
|
|
24
|
+
|
|
25
|
+
If this document was provided another way, ask the user for their server URL.
|
|
26
|
+
|
|
27
|
+
## API Key Configuration
|
|
28
|
+
|
|
29
|
+
Before starting, check for stored credentials:
|
|
30
|
+
|
|
31
|
+
1. Look for config file at: ~/.fileverseapirc
|
|
32
|
+
2. If found with valid apiKey, use it automatically
|
|
33
|
+
3. If not found or missing apiKey:
|
|
34
|
+
- Ask user for their Fileverse API key
|
|
35
|
+
- Offer to save it: "Would you like me to save this API key for future sessions?"
|
|
36
|
+
- If yes, create/update ~/.fileverseapirc with JSON: {"apiKey": "...", "serverUrl": "..."}
|
|
37
|
+
|
|
38
|
+
## Connection Strategy
|
|
39
|
+
|
|
40
|
+
After getting the server URL:
|
|
41
|
+
|
|
42
|
+
1. **Try API first**: Attempt GET {SERVER_URL}/ping
|
|
43
|
+
2. **If successful** (response: {"reply":"pong"}) → Use API Mode
|
|
44
|
+
3. **If connection fails** (timeout, refused, unreachable) → Switch to CLI Mode
|
|
45
|
+
|
|
46
|
+
In API mode, every request must include apiKey as a query parameter; the path is complete before any query string.
|
|
47
|
+
|
|
48
|
+
When switching to CLI mode, inform the user:
|
|
49
|
+
"I can't reach your server directly (localhost isn't accessible from here). I'll help you using CLI commands instead - just run them and share the output with me."
|
|
50
|
+
|
|
51
|
+
---
|
|
52
|
+
|
|
53
|
+
# Quick reference
|
|
54
|
+
|
|
55
|
+
## All API endpoints
|
|
56
|
+
|
|
57
|
+
| Method | Path | Auth | Key params/body |
|
|
58
|
+
|--------|------|------|-----------------|
|
|
59
|
+
| GET | /ping | No | - |
|
|
60
|
+
| GET | /api/ddocs | apiKey | limit, skip |
|
|
61
|
+
| GET | /api/ddocs/{ddocId} | apiKey | - |
|
|
62
|
+
| POST | /api/ddocs | apiKey | JSON: {title, content} or form-data: file |
|
|
63
|
+
| PUT | /api/ddocs/{ddocId} | apiKey | JSON: {title?, content?} or form-data: file |
|
|
64
|
+
| DELETE | /api/ddocs/{ddocId} | apiKey | - |
|
|
65
|
+
| GET | /api/folders | apiKey | limit, skip |
|
|
66
|
+
| POST | /api/folders | apiKey | body: see Create Folder |
|
|
67
|
+
| GET | /api/folders/{folderRef}/{folderId} | apiKey | - |
|
|
68
|
+
| GET | /api/search | apiKey | q (required), limit, skip |
|
|
69
|
+
| GET | /api/events/failed | apiKey | - |
|
|
70
|
+
| POST | /api/events/retry-failed | apiKey | - |
|
|
71
|
+
| POST | /api/events/{id}/retry | apiKey | - |
|
|
72
|
+
|
|
73
|
+
## All ddctl commands
|
|
74
|
+
|
|
75
|
+
| Command | Purpose | Key options |
|
|
76
|
+
|---------|---------|-------------|
|
|
77
|
+
| ddctl list | List ddocs | -l/--limit, -s/--skip |
|
|
78
|
+
| ddctl get <ddocId> | Get document metadata | - |
|
|
79
|
+
| ddctl view <ddocId> | View content preview | -n/--lines (default 10) |
|
|
80
|
+
| ddctl create <filepath> | Create from file | title = filename; file cannot be empty |
|
|
81
|
+
| ddctl update <ddocId> | Update ddoc | -f/--file <path> or opens editor |
|
|
82
|
+
| ddctl download <ddocId> | Download to file | -o/--output <filename> |
|
|
83
|
+
| ddctl delete <ddocIds...> | Delete one or more | space-separated ids |
|
|
84
|
+
| ddctl events list-failed | List failed worker events | - |
|
|
85
|
+
| ddctl events retry <eventId> | Retry one failed event | - |
|
|
86
|
+
| ddctl events retry-all | Retry all failed events | - |
|
|
87
|
+
|
|
88
|
+
---
|
|
89
|
+
|
|
90
|
+
# MCP Integration (Recommended for AI Agents)
|
|
91
|
+
|
|
92
|
+
The Fileverse API MCP server is the easiest way for AI agents to interact with Fileverse API. It wraps all API calls into native MCP tools with built-in sync polling.
|
|
16
93
|
|
|
17
|
-
|
|
94
|
+
## Setup
|
|
95
|
+
|
|
96
|
+
Install Fileverse API globally, then configure your MCP client:
|
|
97
|
+
|
|
98
|
+
### Claude Code / Cursor
|
|
99
|
+
|
|
100
|
+
Add to your MCP config (e.g., `.claude/mcp.json` or Cursor MCP settings):
|
|
18
101
|
|
|
19
102
|
```json
|
|
20
103
|
{
|
|
21
104
|
"mcpServers": {
|
|
22
105
|
"fileverse-api": {
|
|
23
|
-
"command": "
|
|
24
|
-
"
|
|
106
|
+
"command": "fileverse-api-mcp",
|
|
107
|
+
"env": {
|
|
108
|
+
"FILEVERSE_API_KEY": "your-api-key",
|
|
109
|
+
"FILEVERSE_SERVER_URL": "http://localhost:8001"
|
|
110
|
+
}
|
|
25
111
|
}
|
|
26
112
|
}
|
|
27
113
|
}
|
|
28
114
|
```
|
|
29
115
|
|
|
30
|
-
|
|
116
|
+
The MCP server can also read credentials from `~/.fileverseapirc` if env vars are not set.
|
|
31
117
|
|
|
32
|
-
|
|
118
|
+
## Available MCP Tools
|
|
33
119
|
|
|
34
|
-
|
|
120
|
+
| Tool | Description |
|
|
121
|
+
|------|-------------|
|
|
122
|
+
| fileverse_list_documents | List documents with pagination |
|
|
123
|
+
| fileverse_get_document | Get a single document by ddocId |
|
|
124
|
+
| fileverse_create_document | Create document and wait for sync (returns link) |
|
|
125
|
+
| fileverse_update_document | Update document and wait for sync (returns link) |
|
|
126
|
+
| fileverse_delete_document | Delete a document |
|
|
127
|
+
| fileverse_search_documents | Search documents by text query |
|
|
128
|
+
| fileverse_get_sync_status | Check sync status and link of a document |
|
|
129
|
+
| fileverse_retry_failed_events | Retry all failed blockchain sync events |
|
|
130
|
+
|
|
131
|
+
Create and update tools automatically poll until blockchain sync completes, so the agent does not need to implement polling logic.
|
|
132
|
+
|
|
133
|
+
---
|
|
134
|
+
|
|
135
|
+
# Response Schemas
|
|
136
|
+
|
|
137
|
+
## Document
|
|
138
|
+
|
|
139
|
+
Fields returned by GET /api/ddocs/{ddocId} and in list/search results:
|
|
140
|
+
|
|
141
|
+
```
|
|
35
142
|
{
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
143
|
+
ddocId: string, // Unique document identifier
|
|
144
|
+
title: string, // Document title
|
|
145
|
+
content: string, // Document content (text/markdown)
|
|
146
|
+
syncStatus: "pending" | "synced" | "failed",
|
|
147
|
+
link: string | null, // Public URL (only when syncStatus is "synced")
|
|
148
|
+
localVersion: number, // Increments on each local edit
|
|
149
|
+
onchainVersion: number, // Version published to blockchain
|
|
150
|
+
isDeleted: number, // 0 = active, 1 = deleted
|
|
151
|
+
onChainFileId: number | null,
|
|
152
|
+
portalAddress: string,
|
|
153
|
+
createdAt: string, // ISO timestamp
|
|
154
|
+
updatedAt: string // ISO timestamp
|
|
42
155
|
}
|
|
43
156
|
```
|
|
44
157
|
|
|
45
|
-
|
|
158
|
+
## Document List
|
|
46
159
|
|
|
47
|
-
|
|
160
|
+
Returned by GET /api/ddocs:
|
|
48
161
|
|
|
49
|
-
```
|
|
162
|
+
```
|
|
50
163
|
{
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
"args": ["-y", "@anthropic-ai/mcp-proxy@latest", "--endpoint", "YOUR_SERVER_URL/mcp", "--header", "x-api-key: YOUR_API_KEY"]
|
|
55
|
-
}
|
|
56
|
-
}
|
|
164
|
+
ddocs: Document[],
|
|
165
|
+
total: number,
|
|
166
|
+
hasNext: boolean
|
|
57
167
|
}
|
|
58
168
|
```
|
|
59
169
|
|
|
60
|
-
|
|
170
|
+
## Search Result
|
|
61
171
|
|
|
62
|
-
|
|
172
|
+
Returned by GET /api/search:
|
|
63
173
|
|
|
64
|
-
|
|
65
|
-
|
|
174
|
+
```
|
|
175
|
+
{
|
|
176
|
+
nodes: Document[], // Note: "nodes" not "ddocs"
|
|
177
|
+
total: number,
|
|
178
|
+
hasNext: boolean
|
|
179
|
+
}
|
|
180
|
+
```
|
|
66
181
|
|
|
67
|
-
|
|
182
|
+
## Create/Update Response
|
|
68
183
|
|
|
69
|
-
|
|
184
|
+
Returned by POST /api/ddocs and PUT /api/ddocs/{ddocId}:
|
|
70
185
|
|
|
71
|
-
|
|
186
|
+
```
|
|
187
|
+
{
|
|
188
|
+
message: string,
|
|
189
|
+
data: Document // Extract ddocId from data.ddocId
|
|
190
|
+
}
|
|
191
|
+
```
|
|
72
192
|
|
|
73
|
-
|
|
74
|
-
- **YOUR_API_KEY**: The user's Fileverse API key. Check `~/.fileverseapirc` for stored credentials, or ask the user to provide it.
|
|
193
|
+
## Event
|
|
75
194
|
|
|
76
|
-
|
|
195
|
+
Returned by GET /api/events/failed:
|
|
77
196
|
|
|
78
|
-
|
|
197
|
+
```
|
|
198
|
+
{
|
|
199
|
+
_id: string,
|
|
200
|
+
type: "create" | "update" | "delete",
|
|
201
|
+
timestamp: number,
|
|
202
|
+
fileId: string,
|
|
203
|
+
portalAddress: string,
|
|
204
|
+
status: "pending" | "processing" | "processed" | "failed",
|
|
205
|
+
retryCount: number,
|
|
206
|
+
lastError: string | null,
|
|
207
|
+
userOpHash: string | null
|
|
208
|
+
}
|
|
209
|
+
```
|
|
79
210
|
|
|
80
|
-
|
|
81
|
-
|------|-------------|
|
|
82
|
-
| `fileverse_list_documents` | List documents with pagination |
|
|
83
|
-
| `fileverse_get_document` | Get a single document by ddocId |
|
|
84
|
-
| `fileverse_create_document` | Create document and wait for blockchain sync (returns link) |
|
|
85
|
-
| `fileverse_update_document` | Update document and wait for blockchain sync (returns link) |
|
|
86
|
-
| `fileverse_delete_document` | Delete a document |
|
|
87
|
-
| `fileverse_search_documents` | Search documents by text query |
|
|
88
|
-
| `fileverse_get_sync_status` | Check sync status and blockchain link of a document |
|
|
89
|
-
| `fileverse_retry_failed_events` | Retry all failed blockchain sync events |
|
|
211
|
+
---
|
|
90
212
|
|
|
91
|
-
|
|
213
|
+
# CLI MODE (Fallback when server unreachable)
|
|
92
214
|
|
|
93
|
-
|
|
215
|
+
Use this when you cannot reach the user's server (localhost, firewall, etc.).
|
|
216
|
+
You generate commands, user runs them and shares output with you.
|
|
94
217
|
|
|
95
|
-
##
|
|
218
|
+
## Installation and invocation
|
|
96
219
|
|
|
97
|
-
|
|
220
|
+
To set up Fileverse API and run the server:
|
|
221
|
+
|
|
222
|
+
```bash
|
|
223
|
+
npm install -g @fileverse/api
|
|
224
|
+
npx @fileverse/api --apiKey <key> --rpcUrl <url>
|
|
225
|
+
```
|
|
98
226
|
|
|
99
|
-
|
|
227
|
+
The package exposes the ddctl binary. After npm install -g @fileverse/api, run ddctl <command>. Without global install: npx -p @fileverse/api ddctl <command>.
|
|
100
228
|
|
|
101
|
-
|
|
229
|
+
## CLI Commands Reference
|
|
102
230
|
|
|
103
|
-
###
|
|
231
|
+
### List Documents
|
|
232
|
+
```bash
|
|
233
|
+
ddctl list
|
|
234
|
+
ddctl list -l 10 -s 20
|
|
235
|
+
ddctl list --limit 10 --skip 20
|
|
236
|
+
```
|
|
104
237
|
|
|
105
|
-
|
|
238
|
+
### Get Document Details
|
|
239
|
+
```bash
|
|
240
|
+
ddctl get <ddocId>
|
|
241
|
+
```
|
|
242
|
+
Shows metadata including the link (if synced to blockchain).
|
|
243
|
+
|
|
244
|
+
### View Document Content
|
|
245
|
+
```bash
|
|
246
|
+
ddctl view <ddocId>
|
|
247
|
+
ddctl view <ddocId> -n 20
|
|
248
|
+
ddctl view <ddocId> --lines 20
|
|
249
|
+
```
|
|
250
|
+
Default preview is 10 lines.
|
|
251
|
+
|
|
252
|
+
### Create Document
|
|
253
|
+
```bash
|
|
254
|
+
ddctl create <filepath>
|
|
255
|
+
```
|
|
256
|
+
Creates document from file. Title is derived from filename. File content cannot be empty.
|
|
257
|
+
|
|
258
|
+
### Update Document
|
|
259
|
+
```bash
|
|
260
|
+
ddctl update <ddocId> -f <filepath>
|
|
261
|
+
ddctl update <ddocId> --file <filepath>
|
|
262
|
+
ddctl update <ddocId>
|
|
263
|
+
```
|
|
264
|
+
Without --file opens in editor (uses EDITOR env or vi).
|
|
106
265
|
|
|
266
|
+
### Download Document
|
|
267
|
+
```bash
|
|
268
|
+
ddctl download <ddocId>
|
|
269
|
+
ddctl download <ddocId> -o myfile.md
|
|
270
|
+
ddctl download <ddocId> --output myfile.md
|
|
107
271
|
```
|
|
108
|
-
|
|
272
|
+
Output supports markdown.
|
|
273
|
+
|
|
274
|
+
### Delete Document
|
|
275
|
+
```bash
|
|
276
|
+
ddctl delete <ddocId>
|
|
277
|
+
ddctl delete <id1> <id2> <id3>
|
|
109
278
|
```
|
|
279
|
+
One or more space-separated ddoc IDs.
|
|
110
280
|
|
|
111
|
-
|
|
281
|
+
### Worker events
|
|
282
|
+
```bash
|
|
283
|
+
ddctl events list-failed
|
|
284
|
+
ddctl events retry <eventId>
|
|
285
|
+
ddctl events retry-all
|
|
286
|
+
```
|
|
287
|
+
If sync is stuck, run ddctl events list-failed then ddctl events retry <id> or ddctl events retry-all.
|
|
112
288
|
|
|
113
|
-
|
|
289
|
+
## CLI Workflow Examples
|
|
114
290
|
|
|
291
|
+
### Create and Check Sync Status
|
|
292
|
+
```bash
|
|
293
|
+
ddctl create mydocument.md
|
|
294
|
+
ddctl get <ddocId>
|
|
115
295
|
```
|
|
116
|
-
|
|
296
|
+
Repeat get until syncStatus is "synced"; then the link field shows the public URL.
|
|
297
|
+
|
|
298
|
+
### Search and Update
|
|
299
|
+
```bash
|
|
300
|
+
ddctl list
|
|
301
|
+
ddctl view <ddocId>
|
|
302
|
+
ddctl update <ddocId> --file updated.md
|
|
303
|
+
ddctl get <ddocId>
|
|
117
304
|
```
|
|
118
305
|
|
|
119
|
-
|
|
306
|
+
---
|
|
120
307
|
|
|
121
|
-
|
|
308
|
+
# API MODE (Primary - when server is reachable)
|
|
122
309
|
|
|
123
|
-
|
|
124
|
-
|--------|------|-------------|
|
|
125
|
-
| GET | /ping | Health check (no auth) |
|
|
126
|
-
| GET | /api/ddocs?apiKey=...&limit=10&skip=0 | List documents |
|
|
127
|
-
| GET | /api/ddocs/{ddocId}?apiKey=... | Get one document |
|
|
128
|
-
| POST | /api/ddocs?apiKey=... | Create document (JSON body: `{title, content}`) |
|
|
129
|
-
| PUT | /api/ddocs/{ddocId}?apiKey=... | Update document (JSON body: `{title?, content?}`) |
|
|
130
|
-
| DELETE | /api/ddocs/{ddocId}?apiKey=... | Delete document |
|
|
131
|
-
| GET | /api/search?apiKey=...&q={query} | Search documents |
|
|
132
|
-
| GET | /api/events/failed?apiKey=... | List failed sync events |
|
|
133
|
-
| POST | /api/events/retry-failed?apiKey=... | Retry all failed events |
|
|
134
|
-
| POST | /api/events/{id}/retry?apiKey=... | Retry one failed event |
|
|
310
|
+
Use this when GET /ping succeeds. You make HTTP requests directly to the server.
|
|
135
311
|
|
|
136
|
-
|
|
312
|
+
## Authentication & URL Construction
|
|
137
313
|
|
|
138
|
-
|
|
314
|
+
CRITICAL: The apiKey is a query parameter that goes at the END of the URL, after the complete path.
|
|
139
315
|
|
|
140
|
-
|
|
141
|
-
2. Extract `ddocId` from `response.data.ddocId` (not from the top level)
|
|
142
|
-
3. Poll `GET /api/ddocs/{ddocId}?apiKey=...` every 5 seconds
|
|
143
|
-
4. When `syncStatus` is `"synced"`: show the `link` field to the user
|
|
144
|
-
5. When `syncStatus` is `"failed"`: inform the user and suggest retrying
|
|
316
|
+
URL Structure: {SERVER_URL}{PATH}?apiKey={API_KEY}&{OTHER_PARAMS}
|
|
145
317
|
|
|
146
|
-
|
|
318
|
+
Step-by-step URL construction:
|
|
319
|
+
1. Start with the server URL: http://localhost:8001
|
|
320
|
+
2. Add the complete path: /api/ddocs/abc123
|
|
321
|
+
3. Add ? and the apiKey: ?apiKey=your-key
|
|
322
|
+
4. Add any other params with &: &limit=10
|
|
147
323
|
|
|
148
|
-
|
|
324
|
+
CORRECT examples:
|
|
325
|
+
- GET http://localhost:8001/api/ddocs?apiKey=xxx
|
|
326
|
+
- GET http://localhost:8001/api/ddocs/abc123?apiKey=xxx
|
|
327
|
+
- PUT http://localhost:8001/api/ddocs/abc123?apiKey=xxx
|
|
328
|
+
- GET http://localhost:8001/api/ddocs?apiKey=xxx&limit=10&skip=0
|
|
149
329
|
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
```
|
|
330
|
+
WRONG (do NOT do this):
|
|
331
|
+
- GET http://localhost:8001/api/ddocs?apiKey=xxx/abc123 ← WRONG: path after query param
|
|
332
|
+
- GET http://localhost:8001/api?apiKey=xxx/ddocs/abc123 ← WRONG: path after query param
|
|
154
333
|
|
|
155
|
-
|
|
334
|
+
The query string (?apiKey=...) must ALWAYS come after the full path is complete.
|
|
156
335
|
|
|
157
|
-
##
|
|
336
|
+
## Common mistakes
|
|
158
337
|
|
|
159
|
-
|
|
338
|
+
- Putting path segments after ?apiKey=... (wrong).
|
|
339
|
+
- Forgetting that create/update return data.ddocId, not top-level ddocId; always use response.data.ddocId.
|
|
340
|
+
- Not polling after create/update until syncStatus is "synced" or "failed".
|
|
160
341
|
|
|
161
|
-
|
|
342
|
+
## Important: Sync Status Polling
|
|
162
343
|
|
|
163
|
-
|
|
164
|
-
npm install -g @fileverse/api
|
|
165
|
-
```
|
|
344
|
+
When you create or update a document, it syncs to blockchain asynchronously:
|
|
166
345
|
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|---------|---------|
|
|
171
|
-
| `ddctl list` | List documents (`-l`/`--limit`, `-s`/`--skip`) |
|
|
172
|
-
| `ddctl get <ddocId>` | Get document metadata |
|
|
173
|
-
| `ddctl view <ddocId>` | Preview content (`-n`/`--lines`, default 10) |
|
|
174
|
-
| `ddctl create <filepath>` | Create from file (title = filename) |
|
|
175
|
-
| `ddctl update <ddocId> -f <filepath>` | Update from file |
|
|
176
|
-
| `ddctl download <ddocId>` | Download document (`-o`/`--output`) |
|
|
177
|
-
| `ddctl delete <ddocId> [...]` | Delete one or more documents |
|
|
178
|
-
| `ddctl events list-failed` | List failed sync events |
|
|
179
|
-
| `ddctl events retry <eventId>` | Retry one failed event |
|
|
180
|
-
| `ddctl events retry-all` | Retry all failed events |
|
|
346
|
+
- **pending**: Saved locally, blockchain sync in progress
|
|
347
|
+
- **synced**: Published to blockchain (link field available)
|
|
348
|
+
- **failed**: Sync failed
|
|
181
349
|
|
|
182
|
-
|
|
350
|
+
After CREATE or UPDATE, poll until syncStatus is "synced" or "failed":
|
|
183
351
|
|
|
184
|
-
|
|
352
|
+
1. POST /api/ddocs or PUT /api/ddocs/{id}
|
|
353
|
+
2. Extract ddocId from response.data.ddocId (not from the top level)
|
|
354
|
+
3. Poll: GET /api/ddocs/{ddocId}?apiKey={API_KEY}
|
|
355
|
+
4. If "pending", wait 5 seconds and poll again
|
|
356
|
+
5. If "synced": extract the "link" field and show as clickable: [View Document](link)
|
|
357
|
+
6. If "failed", inform user of sync failure
|
|
185
358
|
|
|
186
|
-
|
|
359
|
+
Typical sync time: 5-30 seconds.
|
|
187
360
|
|
|
188
|
-
|
|
361
|
+
## API Reference
|
|
362
|
+
|
|
363
|
+
Base: {SERVER_URL}
|
|
364
|
+
|
|
365
|
+
### Health Check (No Auth)
|
|
366
|
+
GET /ping
|
|
367
|
+
Response: {"reply":"pong"}
|
|
368
|
+
|
|
369
|
+
### List Documents
|
|
370
|
+
GET /api/ddocs?apiKey={API_KEY}&limit=10&skip=0
|
|
371
|
+
|
|
372
|
+
Response:
|
|
189
373
|
{
|
|
190
|
-
"
|
|
191
|
-
"
|
|
192
|
-
"
|
|
193
|
-
"syncStatus": "pending | synced | failed",
|
|
194
|
-
"link": "string | null",
|
|
195
|
-
"localVersion": 0,
|
|
196
|
-
"onchainVersion": 0,
|
|
197
|
-
"isDeleted": 0,
|
|
198
|
-
"onChainFileId": null,
|
|
199
|
-
"portalAddress": "string",
|
|
200
|
-
"createdAt": "ISO timestamp",
|
|
201
|
-
"updatedAt": "ISO timestamp"
|
|
374
|
+
"ddocs": [...],
|
|
375
|
+
"total": 100,
|
|
376
|
+
"hasNext": true
|
|
202
377
|
}
|
|
203
|
-
```
|
|
204
378
|
|
|
205
|
-
|
|
379
|
+
### Get Document
|
|
380
|
+
GET /api/ddocs/{ddocId}?apiKey={API_KEY}
|
|
206
381
|
|
|
207
|
-
|
|
208
|
-
{
|
|
209
|
-
|
|
382
|
+
Response:
|
|
383
|
+
{
|
|
384
|
+
"ddocId": "...",
|
|
385
|
+
"title": "...",
|
|
386
|
+
"content": "...",
|
|
387
|
+
"syncStatus": "pending|synced|failed",
|
|
388
|
+
"link": "https://...",
|
|
389
|
+
...
|
|
390
|
+
}
|
|
391
|
+
(link available when synced)
|
|
210
392
|
|
|
211
|
-
|
|
393
|
+
### Create Document (JSON - recommended for AI agents)
|
|
394
|
+
POST /api/ddocs?apiKey={API_KEY}
|
|
395
|
+
Content-Type: application/json
|
|
212
396
|
|
|
213
|
-
|
|
214
|
-
{ "nodes": [...], "total": 100, "hasNext": true }
|
|
215
|
-
```
|
|
397
|
+
{ "title": "Document Title", "content": "Document content here..." }
|
|
216
398
|
|
|
217
|
-
|
|
399
|
+
Response: 201 with { "message": "...", "data": { "ddocId": "...", "title": "...", "syncStatus": "...", ... } }
|
|
400
|
+
Extract ddocId from response.data.ddocId. Then poll GET /api/ddocs/{ddocId} until syncStatus is "synced", then show the link.
|
|
218
401
|
|
|
219
|
-
|
|
402
|
+
### Create Document (Multipart - for file uploads)
|
|
403
|
+
POST /api/ddocs?apiKey={API_KEY}
|
|
404
|
+
Content-Type: multipart/form-data
|
|
220
405
|
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
406
|
+
Send a single form field "file" with the document file. Title is derived from the filename. Max file size 10MB.
|
|
407
|
+
|
|
408
|
+
Response: same as JSON create above.
|
|
409
|
+
|
|
410
|
+
### Update Document (JSON - recommended for AI agents)
|
|
411
|
+
PUT /api/ddocs/{ddocId}?apiKey={API_KEY}
|
|
412
|
+
Content-Type: application/json
|
|
413
|
+
|
|
414
|
+
{ "title": "New Title", "content": "Updated content..." }
|
|
415
|
+
|
|
416
|
+
Both fields are optional; send only what you want to change.
|
|
417
|
+
|
|
418
|
+
Response: 200 with { "message": "...", "data": { ... } }
|
|
419
|
+
Poll until synced, then show the link.
|
|
420
|
+
|
|
421
|
+
### Update Document (Multipart - for file uploads)
|
|
422
|
+
PUT /api/ddocs/{ddocId}?apiKey={API_KEY}
|
|
423
|
+
Content-Type: multipart/form-data
|
|
224
424
|
|
|
225
|
-
|
|
425
|
+
Send a single form field "file" with the updated document file. Title is derived from the filename. Max file size 10MB.
|
|
426
|
+
|
|
427
|
+
Response: same as JSON update above.
|
|
428
|
+
|
|
429
|
+
### Delete Document
|
|
430
|
+
DELETE /api/ddocs/{ddocId}?apiKey={API_KEY}
|
|
431
|
+
|
|
432
|
+
### List Folders
|
|
433
|
+
GET /api/folders?apiKey={API_KEY}&limit=10&skip=0
|
|
434
|
+
|
|
435
|
+
Response:
|
|
436
|
+
{
|
|
437
|
+
"folders": [...],
|
|
438
|
+
"total": 100,
|
|
439
|
+
"hasNext": true
|
|
440
|
+
}
|
|
441
|
+
|
|
442
|
+
### Create Folder
|
|
443
|
+
POST /api/folders?apiKey={API_KEY}
|
|
444
|
+
Content-Type: application/json
|
|
445
|
+
|
|
446
|
+
Required body fields: onchainFileId, folderId, folderRef, folderName, portalAddress, metadataIPFSHash, lastTransactionBlockNumber, lastTransactionBlockTimestamp.
|
|
447
|
+
Typically used for sync/on-chain integration, not ad-hoc folder creation by agents.
|
|
448
|
+
|
|
449
|
+
### Get Folder
|
|
450
|
+
GET /api/folders/{folderRef}/{folderId}?apiKey={API_KEY}
|
|
451
|
+
Both folderRef and folderId are required.
|
|
452
|
+
|
|
453
|
+
### Search Documents
|
|
454
|
+
GET /api/search?apiKey={API_KEY}&q={query}&limit=10&skip=0
|
|
455
|
+
Query parameter "q" is required.
|
|
456
|
+
|
|
457
|
+
Response:
|
|
458
|
+
{
|
|
459
|
+
"nodes": [...],
|
|
460
|
+
"total": 100,
|
|
461
|
+
"hasNext": true
|
|
462
|
+
}
|
|
463
|
+
(Search returns "nodes", not "ddocs".)
|
|
464
|
+
|
|
465
|
+
### List Failed Events
|
|
466
|
+
GET /api/events/failed?apiKey={API_KEY}
|
|
467
|
+
|
|
468
|
+
Response: array of events (e.g. _id, fileId, portalAddress, type, timestamp, lastError).
|
|
469
|
+
|
|
470
|
+
### Retry All Failed Events
|
|
471
|
+
POST /api/events/retry-failed?apiKey={API_KEY}
|
|
472
|
+
|
|
473
|
+
Response: { "retried": number }
|
|
474
|
+
|
|
475
|
+
### Retry One Failed Event
|
|
476
|
+
POST /api/events/{id}/retry?apiKey={API_KEY}
|
|
477
|
+
|
|
478
|
+
Response: { "ok": true } or 404 if event not found or not in failed state.
|
|
479
|
+
|
|
480
|
+
## OpenAPI Specification
|
|
481
|
+
|
|
482
|
+
A machine-readable OpenAPI 3.1 spec is available at GET {SERVER_URL}/openapi.json. Use it for auto-generating tool definitions or importing into Swagger UI / Postman.
|
|
226
483
|
|
|
227
484
|
---
|
|
228
485
|
|
|
229
|
-
#
|
|
486
|
+
# Agent Workflow Recipes
|
|
230
487
|
|
|
231
|
-
|
|
232
|
-
- **syncStatus**: `pending` (saving to blockchain) -> `synced` (published, `link` available) or `failed`
|
|
233
|
-
- **link**: Public URL to view the document on-chain (only present when synced)
|
|
234
|
-
- **localVersion**: Increments on each local edit
|
|
235
|
-
- **onchainVersion**: Version published to blockchain
|
|
488
|
+
## Recipe 1: Publish a local file to blockchain
|
|
236
489
|
|
|
237
|
-
|
|
490
|
+
1. Read the file content from the local filesystem
|
|
491
|
+
2. POST /api/ddocs?apiKey={API_KEY} with JSON body: {"title": "<filename>", "content": "<file content>"}
|
|
492
|
+
3. Extract ddocId from response.data.ddocId
|
|
493
|
+
4. Poll GET /api/ddocs/{ddocId}?apiKey={API_KEY} every 5 seconds
|
|
494
|
+
5. When syncStatus is "synced", show: "Published! [View Document](link)"
|
|
495
|
+
6. If syncStatus is "failed", show: "Saved locally but blockchain sync failed. Run retry."
|
|
238
496
|
|
|
239
|
-
|
|
240
|
-
|--------|---------|
|
|
241
|
-
| 400 | Validation error (missing/invalid params) |
|
|
242
|
-
| 401 | Invalid or missing API key |
|
|
243
|
-
| 404 | Resource not found |
|
|
244
|
-
| 429 | Rate limited (respect Retry-After header) |
|
|
245
|
-
| 500 | Server error (retry or inform user) |
|
|
497
|
+
## Recipe 2: Find and update a document by title
|
|
246
498
|
|
|
247
|
-
|
|
499
|
+
1. GET /api/search?apiKey={API_KEY}&q={title} to search for the document
|
|
500
|
+
2. From the results (response.nodes), find the matching document and extract its ddocId
|
|
501
|
+
3. PUT /api/ddocs/{ddocId}?apiKey={API_KEY} with JSON body: {"content": "<new content>"}
|
|
502
|
+
4. Poll GET /api/ddocs/{ddocId}?apiKey={API_KEY} until synced
|
|
503
|
+
5. Show the updated link
|
|
248
504
|
|
|
249
|
-
|
|
505
|
+
## Recipe 3: Check health and diagnose sync issues
|
|
506
|
+
|
|
507
|
+
1. GET /ping - verify server is running (expect {"reply":"pong"})
|
|
508
|
+
2. GET /api/ddocs?apiKey={API_KEY}&limit=5 - verify API key works and list recent docs
|
|
509
|
+
3. GET /api/events/failed?apiKey={API_KEY} - check for failed sync events
|
|
510
|
+
4. If failed events exist, POST /api/events/retry-failed?apiKey={API_KEY} to retry them
|
|
511
|
+
5. Report: server status, number of documents, number of failed events (and if retried)
|
|
250
512
|
|
|
251
513
|
---
|
|
252
514
|
|
|
253
|
-
#
|
|
515
|
+
# Claude Code Integration
|
|
516
|
+
|
|
517
|
+
## Custom Slash Commands
|
|
254
518
|
|
|
255
|
-
|
|
519
|
+
You can create custom slash commands for Claude Code that integrate with Fileverse API. Create a `.claude/commands/` directory in your project and add markdown prompt files.
|
|
256
520
|
|
|
257
|
-
|
|
521
|
+
### fileverse-publish.md
|
|
258
522
|
|
|
259
|
-
|
|
523
|
+
Create `.claude/commands/fileverse-publish.md`:
|
|
260
524
|
|
|
261
525
|
```markdown
|
|
262
|
-
Publish a file to Fileverse blockchain storage.
|
|
526
|
+
Publish a file to Fileverse API blockchain storage.
|
|
263
527
|
|
|
264
528
|
Steps:
|
|
265
|
-
1. Read
|
|
266
|
-
2.
|
|
267
|
-
3.
|
|
268
|
-
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
529
|
+
1. Read credentials from ~/.fileverseapirc (JSON with apiKey and serverUrl fields)
|
|
530
|
+
2. Read the file at: $ARGUMENTS
|
|
531
|
+
3. POST to {serverUrl}/api/ddocs?apiKey={apiKey} with JSON body:
|
|
532
|
+
Content-Type: application/json
|
|
533
|
+
{"title": "<filename without extension>", "content": "<file contents>"}
|
|
534
|
+
4. Extract ddocId from response.data.ddocId
|
|
535
|
+
5. Poll GET {serverUrl}/api/ddocs/{ddocId}?apiKey={apiKey} every 5 seconds until syncStatus is "synced" or "failed"
|
|
536
|
+
6. If synced: show "Published! Link: {link}"
|
|
537
|
+
7. If failed: show "Saved locally but blockchain sync failed"
|
|
274
538
|
```
|
|
275
539
|
|
|
276
540
|
Usage: `/fileverse-publish path/to/document.md`
|
|
277
541
|
|
|
278
|
-
|
|
542
|
+
### fileverse-list.md
|
|
543
|
+
|
|
544
|
+
Create `.claude/commands/fileverse-list.md`:
|
|
279
545
|
|
|
280
546
|
```markdown
|
|
281
|
-
List all documents
|
|
547
|
+
List all documents in Fileverse API.
|
|
282
548
|
|
|
283
549
|
Steps:
|
|
284
|
-
1.
|
|
285
|
-
2.
|
|
286
|
-
- Read credentials from ~/.fileverseapirc
|
|
287
|
-
- GET {serverUrl}/api/ddocs?apiKey={apiKey}&limit=50
|
|
550
|
+
1. Read credentials from ~/.fileverseapirc (JSON with apiKey and serverUrl fields)
|
|
551
|
+
2. GET {serverUrl}/api/ddocs?apiKey={apiKey}&limit=50
|
|
288
552
|
3. Display results as a table with columns: ddocId, title, syncStatus, link, updatedAt
|
|
289
553
|
4. Show total count and whether more documents exist (hasNext)
|
|
290
554
|
```
|
|
291
555
|
|
|
292
556
|
Usage: `/fileverse-list`
|
|
293
557
|
|
|
294
|
-
|
|
558
|
+
### fileverse-search.md
|
|
559
|
+
|
|
560
|
+
Create `.claude/commands/fileverse-search.md`:
|
|
295
561
|
|
|
296
562
|
```markdown
|
|
297
|
-
Search for documents in Fileverse.
|
|
563
|
+
Search for documents in Fileverse API.
|
|
298
564
|
|
|
299
565
|
Steps:
|
|
300
|
-
1.
|
|
301
|
-
2.
|
|
302
|
-
- Read credentials from ~/.fileverseapirc
|
|
303
|
-
- GET {serverUrl}/api/search?apiKey={apiKey}&q=$ARGUMENTS
|
|
566
|
+
1. Read credentials from ~/.fileverseapirc (JSON with apiKey and serverUrl fields)
|
|
567
|
+
2. GET {serverUrl}/api/search?apiKey={apiKey}&q=$ARGUMENTS
|
|
304
568
|
3. Display matching documents with: ddocId, title, syncStatus, link
|
|
305
569
|
4. Show total matches found
|
|
306
570
|
```
|
|
307
571
|
|
|
308
572
|
Usage: `/fileverse-search meeting notes`
|
|
309
573
|
|
|
310
|
-
|
|
574
|
+
### fileverse-status.md
|
|
575
|
+
|
|
576
|
+
Create `.claude/commands/fileverse-status.md`:
|
|
311
577
|
|
|
312
578
|
```markdown
|
|
313
|
-
Check the sync status of a Fileverse document.
|
|
579
|
+
Check the sync status of a Fileverse API document.
|
|
314
580
|
|
|
315
581
|
Steps:
|
|
316
|
-
1.
|
|
317
|
-
2.
|
|
318
|
-
- Read credentials from ~/.fileverseapirc
|
|
319
|
-
- GET {serverUrl}/api/ddocs/$ARGUMENTS?apiKey={apiKey}
|
|
582
|
+
1. Read credentials from ~/.fileverseapirc (JSON with apiKey and serverUrl fields)
|
|
583
|
+
2. GET {serverUrl}/api/ddocs/$ARGUMENTS?apiKey={apiKey}
|
|
320
584
|
3. Display:
|
|
321
585
|
- Title
|
|
322
586
|
- Sync Status (pending/synced/failed)
|
|
323
587
|
- Link (if synced)
|
|
324
588
|
- Local Version vs On-chain Version
|
|
325
589
|
- Last Updated
|
|
326
|
-
4. If status is "failed",
|
|
590
|
+
4. If status is "failed", suggest running: POST {serverUrl}/api/events/retry-failed?apiKey={apiKey}
|
|
327
591
|
```
|
|
328
592
|
|
|
329
593
|
Usage: `/fileverse-status <ddocId>`
|
|
330
594
|
|
|
331
|
-
|
|
595
|
+
---
|
|
332
596
|
|
|
333
|
-
|
|
334
|
-
Delete a document from Fileverse.
|
|
597
|
+
# Key Concepts
|
|
335
598
|
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
599
|
+
- **DDoc**: A document with unique ddocId
|
|
600
|
+
- **syncStatus**: pending → synced (success) or failed
|
|
601
|
+
- **link**: Public URL to view document (only available when synced)
|
|
602
|
+
- **localVersion**: Increments on each edit
|
|
603
|
+
- **onchainVersion**: Version on blockchain
|
|
604
|
+
|
|
605
|
+
# Error Handling
|
|
606
|
+
|
|
607
|
+
**400 Bad Request**: Validation errors (missing/invalid body or params). Response body: { "error": "..." } or { "message": "..." }.
|
|
608
|
+
**401 Unauthorized**: Invalid or missing API key
|
|
609
|
+
**404 Not Found**: Resource doesn't exist
|
|
610
|
+
**429 Too Many Requests**: If returned (e.g. from upstream), respect Retry-After header if present.
|
|
611
|
+
**500 Server Error**: Internal error, retry or inform user
|
|
612
|
+
|
|
613
|
+
---
|
|
614
|
+
|
|
615
|
+
# Future Improvements (Planned)
|
|
346
616
|
|
|
347
|
-
|
|
617
|
+
- **SSE for Sync Status**: Real-time sync status push via GET /api/ddocs/:ddocId/stream to eliminate polling
|
|
618
|
+
- **Batch Operations**: POST /api/ddocs/bulk for creating/updating/deleting multiple documents at once
|
|
619
|
+
- **Partial Responses**: ?fields=ddocId,syncStatus,link for requesting only specific fields
|
|
620
|
+
- **TypeScript SDK**: Typed client library with built-in sync polling at @fileverse/api/client
|
|
621
|
+
- **Webhook Callbacks**: Register a URL to be notified when sync completes instead of polling
|