Skip to content

Commit 6336689

Browse files
committed
Reintroduce provide records via PUT to HTTP delegated routing
Previous work reduced the scope of IPIP-337 to read operations only. The changes here re-introduce the write operations originally written by @guseggert back into IPIP-337. The specification documents the ability to provide Bitswap records over `PUT` requests with advisory TTL. An implementation of the specification is already present in go-libipfs. See: - #370
1 parent 4c1c5d7 commit 6336689

File tree

1 file changed

+103
-3
lines changed

1 file changed

+103
-3
lines changed

routing/DELEGATED_CONTENT_ROUTING_HTTP.md

+103-3
Original file line numberDiff line numberDiff line change
@@ -66,13 +66,13 @@ Specifications for some transfer protocols are provided in the "Transfer Protoco
6666

6767
### `GET /routing/v1/providers/{CID}`
6868

69-
#### Response codes
69+
#### `GET` Response codes
7070

7171
- `200` (OK): the response body contains 0 or more records
7272
- `404` (Not Found): must be returned if no matching records are found
7373
- `422` (Unprocessable Entity): request does not conform to schema or semantic constraints
7474

75-
#### Response Body
75+
#### `GET` Response Body
7676

7777
```json
7878
{
@@ -90,6 +90,48 @@ Response limit: 100 providers
9090

9191
Each object in the `Providers` list is a *read provider record*.
9292

93+
### `PUT /routing/v1/providers`
94+
95+
#### `PUT` Response codes
96+
97+
- `200` (OK): the server processed the full list of provider records (possibly unsuccessfully, depending on the semantics of the particular records)
98+
- `400` (Bad Request): the server deems the request to be invalid and cannot process it
99+
- `422` (Unprocessable Entity): request does not conform to schema or semantic constraints
100+
- `501` (Not Implemented): the server does not support providing records
101+
102+
#### `PUT` Request Body
103+
104+
```json
105+
{
106+
"Providers": [
107+
{
108+
"Protocol": "<protocol_name>",
109+
"Schema": "bitswap",
110+
...
111+
}
112+
]
113+
}
114+
```
115+
116+
Each object in the `Providers` list is a *write provider record*.
117+
118+
#### `PUT` Response Body
119+
120+
```json
121+
{
122+
"ProvideResults": [
123+
{ ... }
124+
]
125+
}
126+
```
127+
128+
- `ProvideResults` is a list of results in the same order as the `Providers` in the request, and the schema of each object is determined by the `Protocol` of the corresponding write object (called "Write Provider Records Response" in the Known Transfer Protocols section)
129+
- This may contain output information such as TTLs, errors, etc.
130+
- It is undefined whether the server will allow partial results
131+
- The work for processing each provider record should be idempotent so that it can be retried without excessive cost in the case of full or partial failure of the request
132+
- Default limit of 100 keys per request
133+
- Implements pagination according to the Pagination section
134+
93135
## Pagination
94136

95137
This API does not support pagination, but optional pagination can be added in a backwards-compatible spec update.
@@ -118,7 +160,7 @@ limits, allowing every site to query the API for results:
118160

119161
```plaintext
120162
Access-Control-Allow-Origin: *
121-
Access-Control-Allow-Methods: GET, OPTIONS
163+
Access-Control-Allow-Methods: GET, PUT, OPTIONS
122164
```
123165

124166
## Known Transfer Protocols
@@ -148,6 +190,60 @@ Specification: [ipfs/specs/BITSWAP.md](https://github.com/ipfs/specs/blob/main/B
148190

149191
The server should respect a passed `transport` query parameter by filtering against the `Addrs` list.
150192

193+
#### Bitswap Write Provider Records
194+
195+
```json
196+
{
197+
"Protocol": "transport-bitswap",
198+
"Schema": "bitswap",
199+
"Signature": "<signature>",
200+
"Payload": "<payload>"
201+
}
202+
```
203+
204+
- `Signature`: a multibase-encoded signature of the sha256 hash of the `Payload` field, signed using the private key of the Peer ID specified in the `Payload` JSON. Signing details for specific key types should follow [libp2p/peerid specs](https://github.com/libp2p/specs/blob/master/peer-ids/peer-ids.md#key-types), unless stated otherwise.
205+
206+
- Servers may ignore this field if they do not require signature verification.
207+
- `Payload`: a string containing a serialized JSON object which conforms with the following schema:
208+
209+
```json
210+
{
211+
"Keys": ["cid1", "cid2"],
212+
"Timestamp": 0,
213+
"AdvisoryTTL": 0,
214+
"ID": "12D3K...",
215+
"Addrs": ["/ip4/..."]
216+
}
217+
```
218+
219+
- `Keys` is a list of the CIDs being provided
220+
- `Timestamp` is the current time
221+
- `AdvisoryTTL` is the time by which the caller expects the server to keep the record available
222+
- If this value is unknown, the caller may use a value of 0
223+
- `ID` is the peer ID that was used to sign the record
224+
- `Addrs` is a list of string-encoded multiaddrs
225+
226+
A [400 Bad Request](https://httpwg.org/specs/rfc9110.html#status.400) response code should be returned if the signature check fails.
227+
228+
Note that this only supports Peer IDs expressed as identity multihashes. Peer IDs with older key types that exceed 42 bytes are not verifiable since they only contain a hash of the key, not the key itself.
229+
Normally, if the Peer ID contains only a hash of the key, then the key is obtained out-of-band (e.g. by fetching the block via IPFS).
230+
If support for these Peer IDs is needed in the future, this spec can be updated to allow the client to provide the key and key type out-of-band by adding optional `PublicKey` and `PublicKeyType` fields, and if the Peer ID is a CID, then the server can verify the public key's authenticity against the CID, and then proceed with the rest of the verification scheme.
231+
232+
The `Payload` field is a string, not a proper JSON object, to prevent its contents from being accidentally parsed and re-encoded by intermediaries, which may change the order of JSON fields and thus cause the record to fail validation.
233+
234+
#### Write Provider Records Response
235+
236+
```json
237+
{
238+
"AdvisoryTTL": 0
239+
}
240+
```
241+
242+
- `AdvisoryTTL` is the time at which the server expects itself to drop the record
243+
- If less than the `AdvisoryTTL` in the request, then the client should re-issue the request by that point
244+
- If greater than the `AdvisoryTTL` in the request, then the server expects the client to be responsible for the content for up to that amount of time (TODO: this is ambiguous)
245+
- If 0, the server makes no claims about the lifetime of the record
246+
151247
### Filecoin Graphsync
152248

153249
Multicodec name: `transport-graphsync-filecoinv1`
@@ -173,3 +269,7 @@ Specification: [ipfs/go-graphsync/blob/main/docs/architecture.md](https://github
173269
- `PieceCID`: the CID of the [piece](https://spec.filecoin.io/systems/filecoin_files/piece/#section-systems.filecoin_files.piece) within which the data is stored
174270
- `VerifiedDeal`: whether the deal corresponding to the data is verified
175271
- `FastRetrieval`: whether the provider claims there is an unsealed copy of the data available for fast retrieval
272+
273+
#### Filecoin Graphsync Write Provider Records
274+
275+
There is currently no specified schema.

0 commit comments

Comments
 (0)