2025-03-25 22:26:58 +00:00

124 lines
3.4 KiB
Markdown

# HTTP Messages
A specification for sending/receiving HTTP messages (request/response) via a remote server. Header / Body etc are encrypted, either in the `content` (small messages) or via a blossom server (larger requests).
![](./http.png)
## Overview
Enables a local client to make and receive http requests (PUT, POST, GET, PATCH etc) from a remote computer. Requires:
* A trusted machine to process the messages (can be a home PC or Raspberry Pi)
* A relay (can be untrusted)
* A blossom server (can be untrusted)
## Architecture
```mermaid
architecture-beta
group user(internet)[Nostr Client]
group cloud(cloud)[Untrusted Servers]
group home(server)[Trusted Server]
service client(internet) in user
service blossom(database)[Blossom Storage] in cloud
service relay(logos:aws-ec2)[Relays] in cloud
service pc(logos:aws-elb) in home
service bbi[Big Bad Internet]
client:R -- L:blossom
client:B -- L:relay
pc:L -- R:blossom
pc:L -- R:relay
pc:B <--> T:bbi
```
## Sequence Diagram
```mermaid
sequenceDiagram
autoNumber
participant c as Nostr Client
participant r as Nostr Relay
participant b as Blossom Server
participant s as HTTP Server
Note over c: Convert <br>HTTP Request<br>into kind 21120
c-->>b: Encrypt & push payload (if large)
c->>r: Publish <br>Event
r<<-->>s: Fetch event
Note over s: Decrypt event
s<<-->>b: Fetch payload <br>(if large)
Note over s: Make HTTP REQUEST
Note over s: Get HTTP RESPONSE
s-->>b: Encrypt & push <br>payload (if large)
Note over s: Create kind<br>21120 (Response)
s->>r: Publish Event
r<<-->>c: Fetch event
Note over c: Decrypt event
b<<-->>c: Fetch payload (if large)
Note over c: Provide RESPONSE
```
## Event Structure
```jsonc
{
"kind": 21120,
"pubkey": "<pubkey>",
"content": "nip44Encrypt({'url':'blossom.one','hash':'xx','decrypt':'password123'})",
"tags": [
["E", "<request event id>"], // (RES) Request ID (mandatory)
["r", "https://relay.one"] // (REQ) Response Relay (optional)
],
// other fields...
}
```
Explanations:
* `kind:21120` - BIP39 word #1120 ([message](https://github.com/bitcoin/bips/blob/master/bip-0039/english.txt#L1120)), plus 20,000 to be treated as ephemeral (not stored by relays).
* `"content"` - encrypted (NIP-44) JSON with location of blob and decryption key **OR** the content itself (if under a threshold)
* `"E"` - ID of the request event. Enables a response to be easily identified.
* `"r"` - (optional) relay on which the response should be sent. For Requests only.
## Considerations
This approach only makes sense in cases where privacy and anonymity are important, or if censorship is a concern.
There are a number of drawbacks to the approach:
- Complexity. Many more moving parts than a direct request.
- Speed. Each request/response now requires:
- Encrypting the payload
- Loading to blossom (if large)
- Signing event
- broadcasting event
- remote server fetching event
- remote server decrypting event
- remote server fetching blossom blob (if large)
- remote server decrypting blossom blob (if used)
- making the actual request
And the same flow in reverse.
So why would you use it? Several reasons:
- enables a plethora of open source apps to be made available from inside private networks (localhost) but over nostr
- maximum server privacy (no domain needed, or port forwarding)
- Make regular API calls over Nostr