mirror of
https://github.com/nostr-protocol/nips.git
synced 2025-01-18 20:21:35 +00:00
fc323706fa
The NIP has been renamed to represent the goals of the NIP more accurately. The x/ extension namespace has been removed, and any features meant to be standardized as a NIP should create a preliminary PR and use the `nip/` namespace. Any extensions that are meant to be standardized externally should use their own namespace.
89 lines
3.2 KiB
Markdown
89 lines
3.2 KiB
Markdown
NIP-91
|
|
======
|
|
|
|
Extension Negotiation
|
|
---------------------
|
|
|
|
`draft` `optional`
|
|
|
|
This NIP defines a method for clients to negotiate new features with relays.
|
|
|
|
## Extension Names
|
|
|
|
Each extension has a **extension name** that can uniquely identify the extension. Currently the following formats are recommended:
|
|
- `nip/XX-<description>`: For extensions that are standardized in NIPs. Experimental extensions are recommended to have a unique description to not conflict.
|
|
- `<namespace>/<extension>`: For extensions standardized by an independent body. The namespace should uniquely identify the standardizing body for this extension with a DNS name. (example: `example.com/example-extension`)
|
|
|
|
Any extension name outside this list MUST NOT be used.
|
|
|
|
## Extension Offers
|
|
|
|
The relay may send a extension offer as a `EN-OFFER` message. The client SHOULD NOT send any messages relating to extension negotiation until it receives an `EN-OFFER`.
|
|
```jsonc
|
|
[
|
|
"EN-OFFER",
|
|
{
|
|
"example.com/example-extension": {...},
|
|
"nip-XX-example-extension": {...}
|
|
}
|
|
]
|
|
```
|
|
|
|
The first entry MUST be an object, with the keys being extension names, and the values being objects. The format of the object is left to the specification of the specific extension.
|
|
|
|
A extension offer can be sent multiple times in a connection, such as to update availability based off of their [NIP-42](./42.md) authentication status.
|
|
|
|
Clients SHOULD be able to handle extension offers being able to be withdrawn, and should treat them as if it was a `EN-SHUTDOWN` if they were in use.
|
|
|
|
Certain extensions, such as extensions to REQs, may not need negotiation. This is up to the extension specification.
|
|
|
|
## Extension Requests
|
|
|
|
A client may request a extension offered by the relay be enabled with the `EN-REQUEST` message:
|
|
```jsonc
|
|
[
|
|
"EN-REQUEST",
|
|
"example.com/example-extension",
|
|
{...}
|
|
]
|
|
```
|
|
|
|
The first entry MUST be the extension name, and the second entry MUST be a extension-dependent object for the extension enable request.
|
|
|
|
The relay SHOULD respond with a `EN-OK` or `EN-ERROR` message:
|
|
```jsonc
|
|
[
|
|
"EN-OK",
|
|
"example.com/example-extension",
|
|
{...}
|
|
]
|
|
```
|
|
```jsonc
|
|
[
|
|
"EN-ERROR",
|
|
"example.com/example-extension",
|
|
"improper extension request data"
|
|
]
|
|
```
|
|
|
|
In both messages, the first entry MUST be the extension name. The second entry depends on the type:
|
|
- `EN-OK`: Response data for the extension negotiation. After this message, the extension can be used.
|
|
- `EN-ERROR`: An error message.
|
|
|
|
An error message SHOULD start with a single-word prefix, followed by a colon (:) and space character, and a human readable message. The following types are defined:
|
|
- `error`: An internal error has occurred in the relay.
|
|
- `not-offered`: The extension was not offered. This may happen due to a `EN-REQUEST` being sent at the same time as a new `EN-OFFER`.
|
|
- `bad-data`: The client has sent improper extension negotiation data.
|
|
|
|
## Extension Cancel
|
|
|
|
The relay or client may stop the usage of the extension any time with a `EN-CANCEL` message:
|
|
```jsonc
|
|
[
|
|
"EN-CANCEL",
|
|
"example.com/example-extension"
|
|
]
|
|
```
|
|
|
|
After this message, the sending party will no longer accept and send new extension messages, and the receiver should not continue attempting to use the extension functionality.
|