diff options
| -rw-r--r-- | 01.md | 10 | ||||
| -rw-r--r-- | 05.md | 13 | ||||
| -rw-r--r-- | 07.md | 4 | ||||
| -rw-r--r-- | 09.md | 30 | ||||
| -rw-r--r-- | 13.md | 10 | ||||
| -rw-r--r-- | 15.md | 16 | ||||
| -rw-r--r-- | 17.md | 2 | ||||
| -rw-r--r-- | 19.md | 5 | ||||
| -rw-r--r-- | 21.md | 2 | ||||
| -rw-r--r-- | 23.md | 2 | ||||
| -rw-r--r-- | 24.md | 6 | ||||
| -rw-r--r-- | 25.md | 20 | ||||
| -rw-r--r-- | 27.md | 2 | ||||
| -rw-r--r-- | 29.md | 19 | ||||
| -rw-r--r-- | 32.md | 21 | ||||
| -rw-r--r-- | 33.md | 2 | ||||
| -rw-r--r-- | 34.md | 32 | ||||
| -rw-r--r-- | 38.md | 2 | ||||
| -rw-r--r-- | 39.md | 4 | ||||
| -rw-r--r-- | 45.md | 8 | ||||
| -rw-r--r-- | 46.md | 8 | ||||
| -rw-r--r-- | 47.md | 2 | ||||
| -rw-r--r-- | 51.md | 4 | ||||
| -rw-r--r-- | 52.md | 23 | ||||
| -rw-r--r-- | 53.md | 2 | ||||
| -rw-r--r-- | 54.md | 12 | ||||
| -rw-r--r-- | 57.md | 2 | ||||
| -rw-r--r-- | 58.md | 2 | ||||
| -rw-r--r-- | 64.md | 146 | ||||
| -rw-r--r-- | 65.md | 2 | ||||
| -rw-r--r-- | 70.md | 45 | ||||
| -rw-r--r-- | 71.md | 2 | ||||
| -rw-r--r-- | 72.md | 45 | ||||
| -rw-r--r-- | 73.md | 48 | ||||
| -rw-r--r-- | 75.md | 4 | ||||
| -rw-r--r-- | 78.md | 2 | ||||
| -rw-r--r-- | 96.md | 2 | ||||
| -rw-r--r-- | 99.md | 10 | ||||
| -rw-r--r-- | BREAKING.md | 6 | ||||
| -rw-r--r-- | README.md | 235 |
40 files changed, 582 insertions, 230 deletions
| @@ -78,8 +78,8 @@ This NIP defines 3 standard tags that can be used across all event kinds with th | |||
| 78 | - The `e` tag, used to refer to an event: `["e", <32-bytes lowercase hex of the id of another event>, <recommended relay URL, optional>]` | 78 | - The `e` tag, used to refer to an event: `["e", <32-bytes lowercase hex of the id of another event>, <recommended relay URL, optional>]` |
| 79 | - The `p` tag, used to refer to another user: `["p", <32-bytes lowercase hex of a pubkey>, <recommended relay URL, optional>]` | 79 | - The `p` tag, used to refer to another user: `["p", <32-bytes lowercase hex of a pubkey>, <recommended relay URL, optional>]` |
| 80 | - The `a` tag, used to refer to a (maybe parameterized) replaceable event | 80 | - The `a` tag, used to refer to a (maybe parameterized) replaceable event |
| 81 | - for a parameterized replaceable event: `["a", <kind integer>:<32-bytes lowercase hex of a pubkey>:<d tag value>, <recommended relay URL, optional>]` | 81 | - for an addressable event: `["a", <kind integer>:<32-bytes lowercase hex of a pubkey>:<d tag value>, <recommended relay URL, optional>]` |
| 82 | - for a non-parameterized replaceable event: `["a", <kind integer>:<32-bytes lowercase hex of a pubkey>:, <recommended relay URL, optional>]` | 82 | - for a normal replaceable event: `["a", <kind integer>:<32-bytes lowercase hex of a pubkey>:, <recommended relay URL, optional>]` |
| 83 | 83 | ||
| 84 | As a convention, all single-letter (only english alphabet letters: a-z, A-Z) key tags are expected to be indexed by relays, such that it is possible, for example, to query or subscribe to events that reference the event `"5c83da77af1dec6d7289834998ad7aafbd9e2191396d75ec3cc27f5a77226f36"` by using the `{"#e": ["5c83da77af1dec6d7289834998ad7aafbd9e2191396d75ec3cc27f5a77226f36"]}` filter. | 84 | As a convention, all single-letter (only english alphabet letters: a-z, A-Z) key tags are expected to be indexed by relays, such that it is possible, for example, to query or subscribe to events that reference the event `"5c83da77af1dec6d7289834998ad7aafbd9e2191396d75ec3cc27f5a77226f36"` by using the `{"#e": ["5c83da77af1dec6d7289834998ad7aafbd9e2191396d75ec3cc27f5a77226f36"]}` filter. |
| 85 | 85 | ||
| @@ -125,8 +125,8 @@ Clients can send 3 types of messages, which must be JSON arrays, according to th | |||
| 125 | "authors": <a list of lowercase pubkeys, the pubkey of an event must be one of these>, | 125 | "authors": <a list of lowercase pubkeys, the pubkey of an event must be one of these>, |
| 126 | "kinds": <a list of a kind numbers>, | 126 | "kinds": <a list of a kind numbers>, |
| 127 | "#<single-letter (a-zA-Z)>": <a list of tag values, for #e — a list of event ids, for #p — a list of pubkeys, etc.>, | 127 | "#<single-letter (a-zA-Z)>": <a list of tag values, for #e — a list of event ids, for #p — a list of pubkeys, etc.>, |
| 128 | "since": <an integer unix timestamp in seconds, events must be newer than this to pass>, | 128 | "since": <an integer unix timestamp in seconds. Events must have a created_at >= to this to pass>, |
| 129 | "until": <an integer unix timestamp in seconds, events must be older than this to pass>, | 129 | "until": <an integer unix timestamp in seconds. Events must have a created_at <= to this to pass>, |
| 130 | "limit": <maximum number of events relays SHOULD return in the initial query> | 130 | "limit": <maximum number of events relays SHOULD return in the initial query> |
| 131 | } | 131 | } |
| 132 | ``` | 132 | ``` |
| @@ -143,7 +143,7 @@ All conditions of a filter that are specified must match for an event for it to | |||
| 143 | 143 | ||
| 144 | A `REQ` message may contain multiple filters. In this case, events that match any of the filters are to be returned, i.e., multiple filters are to be interpreted as `||` conditions. | 144 | A `REQ` message may contain multiple filters. In this case, events that match any of the filters are to be returned, i.e., multiple filters are to be interpreted as `||` conditions. |
| 145 | 145 | ||
| 146 | The `limit` property of a filter is only valid for the initial query and MUST be ignored afterwards. When `limit: n` is present it is assumed that the events returned in the initial query will be the last `n` events ordered by the `created_at`. It is safe to return less events than `limit` specifies, but it is expected that relays do not return (much) more events than requested so clients don't get unnecessarily overwhelmed by data. | 146 | The `limit` property of a filter is only valid for the initial query and MUST be ignored afterwards. When `limit: n` is present it is assumed that the events returned in the initial query will be the last `n` events ordered by the `created_at`. Newer events should appear first, and in the case of ties the event with the lowest id (first in lexical order) should be first. It is safe to return less events than `limit` specifies, but it is expected that relays do not return (much) more events than requested so clients don't get unnecessarily overwhelmed by data. |
| 147 | 147 | ||
| 148 | ### From relay to client: sending events and notices | 148 | ### From relay to client: sending events and notices |
| 149 | 149 | ||
| @@ -58,6 +58,15 @@ A client may implement support for finding users' public keys from _internet ide | |||
| 58 | 58 | ||
| 59 | ## Notes | 59 | ## Notes |
| 60 | 60 | ||
| 61 | ### Identification, not verification | ||
| 62 | |||
| 63 | The NIP-05 is not intended to _verify_ a user, but only to _identify_ them, for the purpose of facilitating the exchange of a contact or their search. | ||
| 64 | Exceptions are people who own (e.g., a company) or are connected (e.g., a project) to a well-known domain, who can exploit NIP-05 as an attestation of their relationship with it, and thus to the organization behind it, thereby gaining an element of trust. | ||
| 65 | |||
| 66 | ### User discovery implementation suggestion | ||
| 67 | |||
| 68 | A client can use this to allow users to search other profiles. If a client has a search box or something like that, a user may be able to type "bob@example.com" there and the client would recognize that and do the proper queries to obtain a pubkey and suggest that to the user. | ||
| 69 | |||
| 61 | ### Clients must always follow public keys, not NIP-05 addresses | 70 | ### Clients must always follow public keys, not NIP-05 addresses |
| 62 | 71 | ||
| 63 | For example, if after finding that `bob@bob.com` has the public key `abc...def`, the user clicks a button to follow that profile, the client must keep a primary reference to `abc...def`, not `bob@bob.com`. If, for any reason, the address `https://bob.com/.well-known/nostr.json?name=bob` starts returning the public key `1d2...e3f` at any time in the future, the client must not replace `abc...def` in his list of followed profiles for the user (but it should stop displaying "bob@bob.com" for that user, as that will have become an invalid `"nip05"` property). | 72 | For example, if after finding that `bob@bob.com` has the public key `abc...def`, the user clicks a button to follow that profile, the client must keep a primary reference to `abc...def`, not `bob@bob.com`. If, for any reason, the address `https://bob.com/.well-known/nostr.json?name=bob` starts returning the public key `1d2...e3f` at any time in the future, the client must not replace `abc...def` in his list of followed profiles for the user (but it should stop displaying "bob@bob.com" for that user, as that will have become an invalid `"nip05"` property). |
| @@ -66,10 +75,6 @@ For example, if after finding that `bob@bob.com` has the public key `abc...def`, | |||
| 66 | 75 | ||
| 67 | Keys must be returned in hex format. Keys in NIP-19 `npub` format are only meant to be used for display in client UIs, not in this NIP. | 76 | Keys must be returned in hex format. Keys in NIP-19 `npub` format are only meant to be used for display in client UIs, not in this NIP. |
| 68 | 77 | ||
| 69 | ### User Discovery implementation suggestion | ||
| 70 | |||
| 71 | A client can also use this to allow users to search other profiles. If a client has a search box or something like that, a user may be able to type "bob@example.com" there and the client would recognize that and do the proper queries to obtain a pubkey and suggest that to the user. | ||
| 72 | |||
| 73 | ### Showing just the domain as an identifier | 78 | ### Showing just the domain as an identifier |
| 74 | 79 | ||
| 75 | Clients may treat the identifier `_@domain` as the "root" identifier, and choose to display it as just the `<domain>`. For example, if Bob owns `bob.com`, he may not want an identifier like `bob@bob.com` as that is redundant. Instead, Bob can use the identifier `_@bob.com` and expect Nostr clients to show and treat that as just `bob.com` for all purposes. | 80 | Clients may treat the identifier `_@domain` as the "root" identifier, and choose to display it as just the `<domain>`. For example, if Bob owns `bob.com`, he may not want an identifier like `bob@bob.com` as that is redundant. Instead, Bob can use the identifier `_@bob.com` and expect Nostr clients to show and treat that as just `bob.com` for all purposes. |
| @@ -24,6 +24,10 @@ async window.nostr.nip44.encrypt(pubkey, plaintext): string // returns ciphertex | |||
| 24 | async window.nostr.nip44.decrypt(pubkey, ciphertext): string // takes ciphertext as specified in nip-44 | 24 | async window.nostr.nip44.decrypt(pubkey, ciphertext): string // takes ciphertext as specified in nip-44 |
| 25 | ``` | 25 | ``` |
| 26 | 26 | ||
| 27 | ### Recommendation to Extension Authors | ||
| 28 | To make sure that the `window.nostr` is available to nostr clients on page load, the authors who create Chromium and Firefox extensions should load their scripts by specifying `"run_at": "document_end"` in the extension's manifest. | ||
| 29 | |||
| 30 | |||
| 27 | ### Implementation | 31 | ### Implementation |
| 28 | 32 | ||
| 29 | See https://github.com/aljazceru/awesome-nostr#nip-07-browser-extensions. | 33 | See https://github.com/aljazceru/awesome-nostr#nip-07-browser-extensions. |
| @@ -1,16 +1,14 @@ | |||
| 1 | NIP-09 | 1 | NIP-09 |
| 2 | ====== | 2 | ====== |
| 3 | 3 | ||
| 4 | Event Deletion | 4 | Event Deletion Request |
| 5 | -------------- | 5 | -------------- |
| 6 | 6 | ||
| 7 | `draft` `optional` | 7 | `draft` `optional` |
| 8 | 8 | ||
| 9 | A special event with kind `5`, meaning "deletion" is defined as having a list of one or more `e` tags, each referencing an event the author is requesting to be deleted. | 9 | A special event with kind `5`, meaning "deletion request" is defined as having a list of one or more `e` or `a` tags, each referencing an event the author is requesting to be deleted. Deletion requests SHOULD include a `k` tag for the kind of each event being requested for deletion. |
| 10 | 10 | ||
| 11 | Each tag entry must contain an "e" event id and/or `a` tags intended for deletion. | 11 | The event's `content` field MAY contain a text note describing the reason for the deletion request. |
| 12 | |||
| 13 | The event's `content` field MAY contain a text note describing the reason for the deletion. | ||
| 14 | 12 | ||
| 15 | For example: | 13 | For example: |
| 16 | 14 | ||
| @@ -21,31 +19,35 @@ For example: | |||
| 21 | "tags": [ | 19 | "tags": [ |
| 22 | ["e", "dcd59..464a2"], | 20 | ["e", "dcd59..464a2"], |
| 23 | ["e", "968c5..ad7a4"], | 21 | ["e", "968c5..ad7a4"], |
| 24 | ["a", "<kind>:<pubkey>:<d-identifier>"] | 22 | ["a", "<kind>:<pubkey>:<d-identifier>"], |
| 23 | ["k", "1"], | ||
| 24 | ["k", "30023"] | ||
| 25 | ], | 25 | ], |
| 26 | "content": "these posts were published by accident", | 26 | "content": "these posts were published by accident", |
| 27 | ...other fields | 27 | ...other fields |
| 28 | } | 28 | } |
| 29 | ``` | 29 | ``` |
| 30 | 30 | ||
| 31 | Relays SHOULD delete or stop publishing any referenced events that have an identical `pubkey` as the deletion request. Clients SHOULD hide or otherwise indicate a deletion status for referenced events. | 31 | Relays SHOULD delete or stop publishing any referenced events that have an identical `pubkey` as the deletion request. Clients SHOULD hide or otherwise indicate a deletion request status for referenced events. |
| 32 | 32 | ||
| 33 | Relays SHOULD continue to publish/share the deletion events indefinitely, as clients may already have the event that's intended to be deleted. Additionally, clients SHOULD broadcast deletion events to other relays which don't have it. | 33 | Relays SHOULD continue to publish/share the deletion request events indefinitely, as clients may already have the event that's intended to be deleted. Additionally, clients SHOULD broadcast deletion request events to other relays which don't have it. |
| 34 | 34 | ||
| 35 | When an `a` tag is used, relays SHOULD delete all versions of the replaceable event up to the `created_at` timestamp of the deletion event. | 35 | When an `a` tag is used, relays SHOULD delete all versions of the replaceable event up to the `created_at` timestamp of the deletion request event. |
| 36 | 36 | ||
| 37 | ## Client Usage | 37 | ## Client Usage |
| 38 | 38 | ||
| 39 | Clients MAY choose to fully hide any events that are referenced by valid deletion events. This includes text notes, direct messages, or other yet-to-be defined event kinds. Alternatively, they MAY show the event along with an icon or other indication that the author has "disowned" the event. The `content` field MAY also be used to replace the deleted events' own content, although a user interface should clearly indicate that this is a deletion reason, not the original content. | 39 | Clients MAY choose to fully hide any events that are referenced by valid deletion request events. This includes text notes, direct messages, or other yet-to-be defined event kinds. Alternatively, they MAY show the event along with an icon or other indication that the author has "disowned" the event. The `content` field MAY also be used to replace the deleted events' own content, although a user interface should clearly indicate that this is a deletion request reason, not the original content. |
| 40 | 40 | ||
| 41 | A client MUST validate that each event `pubkey` referenced in the `e` tag of the deletion request is identical to the deletion request `pubkey`, before hiding or deleting any event. Relays can not, in general, perform this validation and should not be treated as authoritative. | 41 | A client MUST validate that each event `pubkey` referenced in the `e` tag of the deletion request is identical to the deletion request `pubkey`, before hiding or deleting any event. Relays can not, in general, perform this validation and should not be treated as authoritative. |
| 42 | 42 | ||
| 43 | Clients display the deletion event itself in any way they choose, e.g., not at all, or with a prominent notice. | 43 | Clients display the deletion request event itself in any way they choose, e.g., not at all, or with a prominent notice. |
| 44 | |||
| 45 | Clients MAY choose to inform the user that their request for deletion does not guarantee deletion because it is impossible to delete events from all relays and clients. | ||
| 44 | 46 | ||
| 45 | ## Relay Usage | 47 | ## Relay Usage |
| 46 | 48 | ||
| 47 | Relays MAY validate that a deletion event only references events that have the same `pubkey` as the deletion itself, however this is not required since relays may not have knowledge of all referenced events. | 49 | Relays MAY validate that a deletion request event only references events that have the same `pubkey` as the deletion request itself, however this is not required since relays may not have knowledge of all referenced events. |
| 48 | 50 | ||
| 49 | ## Deleting a Deletion | 51 | ## Deletion Request of a Deletion Request |
| 50 | 52 | ||
| 51 | Publishing a deletion event against a deletion has no effect. Clients and relays are not obliged to support "undelete" functionality. | 53 | Publishing a deletion request event against a deletion request has no effect. Clients and relays are not obliged to support "unrequest deletion" functionality. |
| @@ -103,16 +103,6 @@ function countLeadingZeroes(hex) { | |||
| 103 | } | 103 | } |
| 104 | ``` | 104 | ``` |
| 105 | 105 | ||
| 106 | Querying relays for PoW notes | ||
| 107 | ----------------------------- | ||
| 108 | |||
| 109 | If relays allow searching on prefixes, you can use this as a way to filter notes of a certain difficulty: | ||
| 110 | |||
| 111 | ``` | ||
| 112 | $ echo '["REQ", "subid", {"ids": ["000000000"]}]' | websocat wss://some-relay.com | jq -c '.[2]' | ||
| 113 | {"id":"000000000121637feeb68a06c8fa7abd25774bdedfa9b6ef648386fb3b70c387", ...} | ||
| 114 | ``` | ||
| 115 | |||
| 116 | Delegated Proof of Work | 106 | Delegated Proof of Work |
| 117 | ----------------------- | 107 | ----------------------- |
| 118 | 108 | ||
| @@ -6,7 +6,7 @@ Nostr Marketplace | |||
| 6 | 6 | ||
| 7 | `draft` `optional` | 7 | `draft` `optional` |
| 8 | 8 | ||
| 9 | Based on https://github.com/lnbits/Diagon-Alley. | 9 | Based on [Diagon-Alley](https://github.com/lnbits/Diagon-Alley). |
| 10 | 10 | ||
| 11 | Implemented in [NostrMarket](https://github.com/lnbits/nostrmarket) and [Plebeian Market](https://github.com/PlebeianTech/plebeian-market). | 11 | Implemented in [NostrMarket](https://github.com/lnbits/nostrmarket) and [Plebeian Market](https://github.com/PlebeianTech/plebeian-market). |
| 12 | 12 | ||
| @@ -139,7 +139,7 @@ Fields that are not self-explanatory: | |||
| 139 | 139 | ||
| 140 | ## Checkout events | 140 | ## Checkout events |
| 141 | 141 | ||
| 142 | All checkout events are sent as JSON strings using ([NIP-04](https://github.com/nostr-protocol/nips/blob/master/04.md)). | 142 | All checkout events are sent as JSON strings using [NIP-04](04.md). |
| 143 | 143 | ||
| 144 | The `merchant` and the `customer` can exchange JSON messages that represent different actions. Each `JSON` message `MUST` have a `type` field indicating the what the JSON represents. Possible types: | 144 | The `merchant` and the `customer` can exchange JSON messages that represent different actions. Each `JSON` message `MUST` have a `type` field indicating the what the JSON represents. Possible types: |
| 145 | 145 | ||
| @@ -150,7 +150,7 @@ The `merchant` and the `customer` can exchange JSON messages that represent diff | |||
| 150 | | 2 | Merchant | Order Status Update | | 150 | | 2 | Merchant | Order Status Update | |
| 151 | 151 | ||
| 152 | ### Step 1: `customer` order (event) | 152 | ### Step 1: `customer` order (event) |
| 153 | The below JSON goes in content of [NIP-04](https://github.com/nostr-protocol/nips/blob/master/04.md). | 153 | The below JSON goes in content of [NIP-04](04.md). |
| 154 | 154 | ||
| 155 | ```json | 155 | ```json |
| 156 | { | 156 | { |
| @@ -182,7 +182,7 @@ _Open_: is `contact.nostr` required? | |||
| 182 | 182 | ||
| 183 | Sent back from the merchant for payment. Any payment option is valid that the merchant can check. | 183 | Sent back from the merchant for payment. Any payment option is valid that the merchant can check. |
| 184 | 184 | ||
| 185 | The below JSON goes in `content` of [NIP-04](https://github.com/nostr-protocol/nips/blob/master/04.md). | 185 | The below JSON goes in `content` of [NIP-04](04.md). |
| 186 | 186 | ||
| 187 | `payment_options`/`type` include: | 187 | `payment_options`/`type` include: |
| 188 | 188 | ||
| @@ -217,7 +217,7 @@ The below JSON goes in `content` of [NIP-04](https://github.com/nostr-protocol/n | |||
| 217 | 217 | ||
| 218 | Once payment has been received and processed. | 218 | Once payment has been received and processed. |
| 219 | 219 | ||
| 220 | The below JSON goes in `content` of [NIP-04](https://github.com/nostr-protocol/nips/blob/master/04.md). | 220 | The below JSON goes in `content` of [NIP-04](04.md). |
| 221 | 221 | ||
| 222 | ```json | 222 | ```json |
| 223 | { | 223 | { |
| @@ -231,7 +231,7 @@ The below JSON goes in `content` of [NIP-04](https://github.com/nostr-protocol/n | |||
| 231 | 231 | ||
| 232 | ## Customize Marketplace | 232 | ## Customize Marketplace |
| 233 | 233 | ||
| 234 | Create a customized user experience using the `naddr` from [NIP-19](https://github.com/nostr-protocol/nips/blob/master/19.md#shareable-identifiers-with-extra-metadata). The use of `naddr` enables easy sharing of marketplace events while incorporating a rich set of metadata. This metadata can include relays, merchant profiles, and more. Subsequently, it allows merchants to be grouped into a market, empowering the market creator to configure the marketplace's user interface and user experience, and share that marketplace. This customization can encompass elements such as market name, description, logo, banner, themes, and even color schemes, offering a tailored and unique marketplace experience. | 234 | Create a customized user experience using the `naddr` from [NIP-19](19.md#shareable-identifiers-with-extra-metadata). The use of `naddr` enables easy sharing of marketplace events while incorporating a rich set of metadata. This metadata can include relays, merchant profiles, and more. Subsequently, it allows merchants to be grouped into a market, empowering the market creator to configure the marketplace's user interface and user experience, and share that marketplace. This customization can encompass elements such as market name, description, logo, banner, themes, and even color schemes, offering a tailored and unique marketplace experience. |
| 235 | 235 | ||
| 236 | ### Event `30019`: Create or update marketplace UI/UX | 236 | ### Event `30019`: Create or update marketplace UI/UX |
| 237 | 237 | ||
| @@ -300,7 +300,7 @@ This event leverages naddr to enable comprehensive customization and sharing of | |||
| 300 | Bids are simply events of kind `1021` with a `content` field specifying the amount, in the currency of the auction. Bids must reference an auction. | 300 | Bids are simply events of kind `1021` with a `content` field specifying the amount, in the currency of the auction. Bids must reference an auction. |
| 301 | 301 | ||
| 302 | > [!NOTE] | 302 | > [!NOTE] |
| 303 | > Auctions can be edited as many times as desired (they are "parameterized replaceable events") by the author - even after the start_date, but they cannot be edited after they have received the first bid! This is enforced by the fact that bids reference the event ID of the auction (rather than the product UUID), which changes with every new version of the auctioned product. So a bid is always attached to one "version". Editing the auction after a bid would result in the new product losing the bid! | 303 | > Auctions can be edited as many times as desired (they are "addressable events") by the author - even after the start_date, but they cannot be edited after they have received the first bid! This is enforced by the fact that bids reference the event ID of the auction (rather than the product UUID), which changes with every new version of the auctioned product. So a bid is always attached to one "version". Editing the auction after a bid would result in the new product losing the bid! |
| 304 | 304 | ||
| 305 | ### Event `1022`: Bid confirmation | 305 | ### Event `1022`: Bid confirmation |
| 306 | 306 | ||
| @@ -331,7 +331,7 @@ Another thing that can happen is - if bids happen very close to the end date of | |||
| 331 | 331 | ||
| 332 | ## Customer support events | 332 | ## Customer support events |
| 333 | 333 | ||
| 334 | Customer support is handled over whatever communication method was specified. If communicating via nostr, NIP-04 is used https://github.com/nostr-protocol/nips/blob/master/04.md. | 334 | Customer support is handled over whatever communication method was specified. If communicating via nostr, [NIP-04](04.md) is used. |
| 335 | 335 | ||
| 336 | ## Additional | 336 | ## Additional |
| 337 | 337 | ||
| @@ -102,7 +102,7 @@ Clients SHOULD publish kind `14` events to the `10050`-listed relays. If that is | |||
| 102 | 102 | ||
| 103 | ## Relays | 103 | ## Relays |
| 104 | 104 | ||
| 105 | It's advisable that relays do not serve `kind:14` to clients other than the ones tagged in them. | 105 | It's advisable that relays do not serve `kind:1059` to clients other than the ones tagged in them. |
| 106 | 106 | ||
| 107 | It's advisable that users choose relays that conform to these practices. | 107 | It's advisable that users choose relays that conform to these practices. |
| 108 | 108 | ||
| @@ -34,8 +34,8 @@ These are the possible bech32 prefixes with `TLV`: | |||
| 34 | 34 | ||
| 35 | - `nprofile`: a nostr profile | 35 | - `nprofile`: a nostr profile |
| 36 | - `nevent`: a nostr event | 36 | - `nevent`: a nostr event |
| 37 | - `nrelay`: a nostr relay | ||
| 38 | - `naddr`: a nostr _replaceable event_ coordinate | 37 | - `naddr`: a nostr _replaceable event_ coordinate |
| 38 | - `nrelay`: a nostr relay (deprecated) | ||
| 39 | 39 | ||
| 40 | These possible standardized `TLV` types are indicated here: | 40 | These possible standardized `TLV` types are indicated here: |
| 41 | 41 | ||
| @@ -43,8 +43,7 @@ These possible standardized `TLV` types are indicated here: | |||
| 43 | - depends on the bech32 prefix: | 43 | - depends on the bech32 prefix: |
| 44 | - for `nprofile` it will be the 32 bytes of the profile public key | 44 | - for `nprofile` it will be the 32 bytes of the profile public key |
| 45 | - for `nevent` it will be the 32 bytes of the event id | 45 | - for `nevent` it will be the 32 bytes of the event id |
| 46 | - for `nrelay`, this is the relay URL | 46 | - for `naddr`, it is the identifier (the `"d"` tag) of the event being referenced. For normal replaceable events use an empty string. |
| 47 | - for `naddr`, it is the identifier (the `"d"` tag) of the event being referenced. For non-parameterized replaceable events, use an empty string. | ||
| 48 | - `1`: `relay` | 47 | - `1`: `relay` |
| 49 | - for `nprofile`, `nevent` and `naddr`, _optionally_, a relay in which the entity (profile or event) is more likely to be found, encoded as ascii | 48 | - for `nprofile`, `nevent` and `naddr`, _optionally_, a relay in which the entity (profile or event) is more likely to be found, encoded as ascii |
| 50 | - this may be included multiple times | 49 | - this may be included multiple times |
| @@ -10,7 +10,7 @@ This NIP standardizes the usage of a common URI scheme for maximum interoperabil | |||
| 10 | 10 | ||
| 11 | The scheme is `nostr:`. | 11 | The scheme is `nostr:`. |
| 12 | 12 | ||
| 13 | The identifiers that come after are expected to be the same as those defined in [NIP-19](https://github.com/nostr-protocol/nips/blob/master/19.md) (except `nsec`). | 13 | The identifiers that come after are expected to be the same as those defined in [NIP-19](19.md) (except `nsec`). |
| 14 | 14 | ||
| 15 | ## Examples | 15 | ## Examples |
| 16 | 16 | ||
| @@ -6,7 +6,7 @@ Long-form Content | |||
| 6 | 6 | ||
| 7 | `draft` `optional` | 7 | `draft` `optional` |
| 8 | 8 | ||
| 9 | This NIP defines `kind:30023` (a _parameterized replaceable event_) for long-form text content, generally referred to as "articles" or "blog posts". `kind:30024` has the same structure as `kind:30023` and is used to save long form drafts. | 9 | This NIP defines `kind:30023` (an _addressable event_) for long-form text content, generally referred to as "articles" or "blog posts". `kind:30024` has the same structure as `kind:30023` and is used to save long form drafts. |
| 10 | 10 | ||
| 11 | "Social" clients that deal primarily with `kind:1` notes should not be expected to implement this NIP. | 11 | "Social" clients that deal primarily with `kind:1` notes should not be expected to implement this NIP. |
| 12 | 12 | ||
| @@ -39,5 +39,7 @@ tags | |||
| 39 | 39 | ||
| 40 | These tags may be present in multiple event kinds. Whenever a different meaning is not specified by some more specific NIP, they have the following meanings: | 40 | These tags may be present in multiple event kinds. Whenever a different meaning is not specified by some more specific NIP, they have the following meanings: |
| 41 | 41 | ||
| 42 | - `r`: a web URL the event is referring to in some way | 42 | - `r`: a web URL the event is referring to in some way. |
| 43 | - `title`: name of [NIP-51](51.md) sets, [NIP-52](52.md) calendar event, [NIP-53](53.md) live event or [NIP-99](99.md) listing | 43 | - `i`: an external id the event is referring to in some way - see [NIP-73](73.md). |
| 44 | - `title`: name of [NIP-51](51.md) sets, [NIP-52](52.md) calendar event, [NIP-53](53.md) live event or [NIP-99](99.md) listing. | ||
| 45 | - `t`: a hashtag. The value MUST be a lowercase string. | ||
| @@ -52,6 +52,26 @@ func make_like_event(pubkey: String, privkey: String, liked: NostrEvent) -> Nost | |||
| 52 | } | 52 | } |
| 53 | ``` | 53 | ``` |
| 54 | 54 | ||
| 55 | Reactions to a website | ||
| 56 | --------------------- | ||
| 57 | |||
| 58 | If the target of the reaction is a website, the reaction MUST be a `kind 17` event and MUST include an `r` tag with the website's URL. | ||
| 59 | |||
| 60 | ```json | ||
| 61 | { | ||
| 62 | "kind": 17, | ||
| 63 | "content": "⭐", | ||
| 64 | "tags": [ | ||
| 65 | ["r", "https://example.com/"] | ||
| 66 | ], | ||
| 67 | ...other fields | ||
| 68 | } | ||
| 69 | ``` | ||
| 70 | |||
| 71 | URLs SHOULD be [normalized](https://datatracker.ietf.org/doc/html/rfc3986#section-6), so that reactions to the same website are not omitted from queries. | ||
| 72 | A fragment MAY be attached to the URL, to react to a section of the page. | ||
| 73 | It should be noted that a URL with a fragment is not considered to be the same URL as the original. | ||
| 74 | |||
| 55 | Custom Emoji Reaction | 75 | Custom Emoji Reaction |
| 56 | --------------------- | 76 | --------------------- |
| 57 | 77 | ||
| @@ -20,7 +20,7 @@ A reader client that receives an event with such `nostr:...` mentions in its `.c | |||
| 20 | 20 | ||
| 21 | Suppose Bob is writing a note in a client that has search-and-autocomplete functionality for users that is triggered when they write the character `@`. | 21 | Suppose Bob is writing a note in a client that has search-and-autocomplete functionality for users that is triggered when they write the character `@`. |
| 22 | 22 | ||
| 23 | As Bob types `"hello @mat"` the client will prompt him to autocomplete with [mattn's profile](https://gateway.nostr.com/p/2c7cc62a697ea3a7826521f3fd34f0cb273693cbe5e9310f35449f43622a5cdc), showing a picture and name. | 23 | As Bob types `"hello @mat"` the client will prompt him to autocomplete with [mattn's profile](https://njump.me/npub1937vv2nf06360qn9y8el6d8sevnndy7tuh5nzre4gj05xc32tnwqauhaj6), showing a picture and name. |
| 24 | 24 | ||
| 25 | Bob presses "enter" and now he sees his typed note as `"hello @mattn"`, `@mattn` is highlighted, indicating that it is a mention. Internally, however, the event looks like this: | 25 | Bob presses "enter" and now he sees his typed note as `"hello @mattn"`, `@mattn` is highlighted, indicating that it is a mention. Internally, however, the event looks like this: |
| 26 | 26 | ||
| @@ -16,7 +16,7 @@ Normally a group will originally belong to one specific relay, but the community | |||
| 16 | 16 | ||
| 17 | ## Relay-generated events | 17 | ## Relay-generated events |
| 18 | 18 | ||
| 19 | Relays are supposed to generate the events that describe group metadata and group admins. These are parameterized replaceable events signed by the relay keypair directly, with the group _id_ as the `d` tag. | 19 | Relays are supposed to generate the events that describe group metadata and group admins. These are _addressable_ events signed by the relay keypair directly, with the group _id_ as the `d` tag. |
| 20 | 20 | ||
| 21 | ## Group identifier | 21 | ## Group identifier |
| 22 | 22 | ||
| @@ -93,6 +93,20 @@ Any user can send one of these events to the relay in order to be automatically | |||
| 93 | } | 93 | } |
| 94 | ``` | 94 | ``` |
| 95 | 95 | ||
| 96 | - *leave request* (`kind:9022`) | ||
| 97 | |||
| 98 | Any user can send one of these events to the relay in order to be automatically removed from the group. The relay will automatically issue a `kind:9001` in response removing this user. | ||
| 99 | |||
| 100 | ```js | ||
| 101 | { | ||
| 102 | "kind": 9022, | ||
| 103 | "content": "optional reason", | ||
| 104 | "tags": [ | ||
| 105 | ["h", "<group-id>"] | ||
| 106 | ] | ||
| 107 | } | ||
| 108 | ``` | ||
| 109 | |||
| 96 | - *moderation events* (`kinds:9000-9020`) (optional) | 110 | - *moderation events* (`kinds:9000-9020`) (optional) |
| 97 | 111 | ||
| 98 | Clients can send these events to a relay in order to accomplish a moderation action. Relays must check if the pubkey sending the event is capable of performing the given action. The relay may discard the event after taking action or keep it as a moderation log. | 112 | Clients can send these events to a relay in order to accomplish a moderation action. Relays must check if the pubkey sending the event is capable of performing the given action. The relay may discard the event after taking action or keep it as a moderation log. |
| @@ -119,6 +133,8 @@ Each moderation action uses a different kind and requires different arguments, w | |||
| 119 | | 9004 | `remove-permission` | `p` (pubkey), `permission` (name) | | 133 | | 9004 | `remove-permission` | `p` (pubkey), `permission` (name) | |
| 120 | | 9005 | `delete-event` | `e` (id hex) | | 134 | | 9005 | `delete-event` | `e` (id hex) | |
| 121 | | 9006 | `edit-group-status` | `public` or `private`, `open` or `closed` | | 135 | | 9006 | `edit-group-status` | `public` or `private`, `open` or `closed` | |
| 136 | | 9007 | `create-group` | | | ||
| 137 | | 9008 | `delete-group` | | | ||
| 122 | 138 | ||
| 123 | - *group metadata* (`kind:39000`) (optional) | 139 | - *group metadata* (`kind:39000`) (optional) |
| 124 | 140 | ||
| @@ -159,6 +175,7 @@ The list of capabilities, as defined by this NIP, for now, is the following: | |||
| 159 | - `add-permission` | 175 | - `add-permission` |
| 160 | - `remove-permission` | 176 | - `remove-permission` |
| 161 | - `edit-group-status` | 177 | - `edit-group-status` |
| 178 | - `delete-group` | ||
| 162 | 179 | ||
| 163 | ```js | 180 | ```js |
| 164 | { | 181 | { |
| @@ -6,10 +6,9 @@ Labeling | |||
| 6 | 6 | ||
| 7 | `draft` `optional` | 7 | `draft` `optional` |
| 8 | 8 | ||
| 9 | A label is a `kind 1985` event that is used to label other entities. This supports a number of use cases, | 9 | This NIP defines two new indexable tags to label events and a new event kind (`kind:1985`) to attach those labels to existing events. This supports several use cases, including distributed moderation, collection management, license assignment, and content classification. |
| 10 | including distributed moderation, collection management, license assignment, and content classification. | ||
| 11 | 10 | ||
| 12 | This NIP introduces two new tags: | 11 | New Tags: |
| 13 | 12 | ||
| 14 | - `L` denotes a label namespace | 13 | - `L` denotes a label namespace |
| 15 | - `l` denotes a label | 14 | - `l` denotes a label |
| @@ -129,10 +128,24 @@ is labeling their note as being related to Milan, Italy using ISO 3166-2. | |||
| 129 | } | 128 | } |
| 130 | ``` | 129 | ``` |
| 131 | 130 | ||
| 131 | Author is labeling their note language as English using ISO-639-1. | ||
| 132 | |||
| 133 | ```json | ||
| 134 | { | ||
| 135 | "kind": 1, | ||
| 136 | "tags": [ | ||
| 137 | ["L", "ISO-639-1"], | ||
| 138 | ["l", "en", "ISO-639-1"] | ||
| 139 | ], | ||
| 140 | "content": "English text", | ||
| 141 | ... | ||
| 142 | } | ||
| 143 | ``` | ||
| 144 | |||
| 132 | Other Notes | 145 | Other Notes |
| 133 | ----------- | 146 | ----------- |
| 134 | 147 | ||
| 135 | When using this NIP to bulk-label many targets at once, events may be deleted and a replacement | 148 | When using this NIP to bulk-label many targets at once, events may be requested for deletion using [NIP-09](09.md) and a replacement |
| 136 | may be published. We have opted not to use parameterizable/replaceable events for this due to the | 149 | may be published. We have opted not to use parameterizable/replaceable events for this due to the |
| 137 | complexity in coming up with a standard `d` tag. In order to avoid ambiguity when querying, | 150 | complexity in coming up with a standard `d` tag. In order to avoid ambiguity when querying, |
| 138 | publishers SHOULD limit labeling events to a single namespace. | 151 | publishers SHOULD limit labeling events to a single namespace. |
| @@ -6,4 +6,4 @@ Parameterized Replaceable Events | |||
| 6 | 6 | ||
| 7 | `final` `mandatory` | 7 | `final` `mandatory` |
| 8 | 8 | ||
| 9 | Moved to [NIP-01](01.md). | 9 | Renamed to "Addressable events" and moved to [NIP-01](01.md). |
| @@ -35,6 +35,36 @@ The `r` tag annotated with the `"euc"` marker should be the commit ID of the ear | |||
| 35 | 35 | ||
| 36 | Except `d`, all tags are optional. | 36 | Except `d`, all tags are optional. |
| 37 | 37 | ||
| 38 | ## Repository state announcements | ||
| 39 | |||
| 40 | An optional source of truth for the state of branches and tags in a repository. | ||
| 41 | |||
| 42 | ```jsonc | ||
| 43 | { | ||
| 44 | "kind": 30618, | ||
| 45 | "content": "", | ||
| 46 | "tags": [ | ||
| 47 | ["d", "<repo-id>"], // matches the identifier in the coresponding repository announcement | ||
| 48 | ["refs/<heads|tags>/<branch-or-tag-name>","<commit-id>"] | ||
| 49 | ["HEAD", "ref: refs/heads/<branch-name>"] | ||
| 50 | ] | ||
| 51 | } | ||
| 52 | ``` | ||
| 53 | |||
| 54 | The `refs` tag may appear multiple times, or none. | ||
| 55 | |||
| 56 | If no `refs` tags are present, the author is no longer tracking repository state using this event. This approach enables the author to restart tracking state at a later time unlike [NIP-09](09.md) deletion requests. | ||
| 57 | |||
| 58 | The `refs` tag can be optionally extended to enable clients to identify how many commits ahead a ref is: | ||
| 59 | |||
| 60 | ```jsonc | ||
| 61 | { | ||
| 62 | "tags": [ | ||
| 63 | ["refs/<heads|tags>/<branch-or-tag-name>", "<commit-id>", "<shorthand-parent-commit-id>", "<shorthand-grandparent>", ...], | ||
| 64 | ] | ||
| 65 | } | ||
| 66 | ``` | ||
| 67 | |||
| 38 | ## Patches | 68 | ## Patches |
| 39 | 69 | ||
| 40 | Patches can be sent by anyone to any repository. Patches to a specific repository SHOULD be sent to the relays specified in that repository's announcement event's `"relays"` tag. Patch events SHOULD include an `a` tag pointing to that repository's announcement address. | 70 | Patches can be sent by anyone to any repository. Patches to a specific repository SHOULD be sent to the relays specified in that repository's announcement event's `"relays"` tag. Patch events SHOULD include an `a` tag pointing to that repository's announcement address. |
| @@ -53,7 +83,7 @@ The first patch revision in a patch revision SHOULD include a NIP-10 `e` `reply` | |||
| 53 | ["p", "<repository-owner>"], | 83 | ["p", "<repository-owner>"], |
| 54 | ["p", "<other-user>"], // optionally send the patch to another user to bring it to their attention | 84 | ["p", "<other-user>"], // optionally send the patch to another user to bring it to their attention |
| 55 | 85 | ||
| 56 | ["t", "root"], // ommited for additional patches in a series | 86 | ["t", "root"], // omitted for additional patches in a series |
| 57 | // for the first patch in a revision | 87 | // for the first patch in a revision |
| 58 | ["t", "root-revision"], | 88 | ["t", "root-revision"], |
| 59 | 89 | ||
| @@ -13,7 +13,7 @@ This NIP enables a way for users to share live statuses such as what music they | |||
| 13 | 13 | ||
| 14 | ## Live Statuses | 14 | ## Live Statuses |
| 15 | 15 | ||
| 16 | A special event with `kind:30315` "User Status" is defined as an *optionally expiring* _parameterized replaceable event_, where the `d` tag represents the status type: | 16 | A special event with `kind:30315` "User Status" is defined as an *optionally expiring* _addressable event_, where the `d` tag represents the status type: |
| 17 | 17 | ||
| 18 | For example: | 18 | For example: |
| 19 | 19 | ||
| @@ -12,9 +12,11 @@ Nostr protocol users may have other online identities such as usernames, profile | |||
| 12 | 12 | ||
| 13 | ## `i` tag on a metadata event | 13 | ## `i` tag on a metadata event |
| 14 | 14 | ||
| 15 | A new optional `i` tag is introduced for `kind 0` metadata event contents in addition to name, about, picture fields as included in [NIP-01](https://github.com/nostr-protocol/nips/blob/master/01.md): | 15 | A new optional `i` tag is introduced for `kind 0` metadata event defined in [NIP-01](01.md): |
| 16 | ```json | 16 | ```json |
| 17 | { | 17 | { |
| 18 | "id": <id>, | ||
| 19 | "pubkey": <pubkey>, | ||
| 18 | "tags": [ | 20 | "tags": [ |
| 19 | ["i", "github:semisol", "9721ce4ee4fceb91c9711ca2a6c9a5ab"], | 21 | ["i", "github:semisol", "9721ce4ee4fceb91c9711ca2a6c9a5ab"], |
| 20 | ["i", "twitter:semisol_public", "1619358434134196225"], | 22 | ["i", "twitter:semisol_public", "1619358434134196225"], |
| @@ -16,14 +16,14 @@ Some queries a client may want to execute against connected relays are prohibiti | |||
| 16 | 16 | ||
| 17 | This NIP defines the verb `COUNT`, which accepts a subscription id and filters as specified in [NIP 01](01.md) for the verb `REQ`. Multiple filters are OR'd together and aggregated into a single count result. | 17 | This NIP defines the verb `COUNT`, which accepts a subscription id and filters as specified in [NIP 01](01.md) for the verb `REQ`. Multiple filters are OR'd together and aggregated into a single count result. |
| 18 | 18 | ||
| 19 | ```json | 19 | ``` |
| 20 | ["COUNT", <subscription_id>, <filters JSON>...] | 20 | ["COUNT", <subscription_id>, <filters JSON>...] |
| 21 | ``` | 21 | ``` |
| 22 | 22 | ||
| 23 | Counts are returned using a `COUNT` response in the form `{"count": <integer>}`. Relays may use probabilistic counts to reduce compute requirements. | 23 | Counts are returned using a `COUNT` response in the form `{"count": <integer>}`. Relays may use probabilistic counts to reduce compute requirements. |
| 24 | In case a relay uses probabilistic counts, it MAY indicate it in the response with `approximate` key i.e. `{"count": <integer>, "approximate": <true|false>}`. | 24 | In case a relay uses probabilistic counts, it MAY indicate it in the response with `approximate` key i.e. `{"count": <integer>, "approximate": <true|false>}`. |
| 25 | 25 | ||
| 26 | ```json | 26 | ``` |
| 27 | ["COUNT", <subscription_id>, {"count": <integer>}] | 27 | ["COUNT", <subscription_id>, {"count": <integer>}] |
| 28 | ``` | 28 | ``` |
| 29 | 29 | ||
| @@ -33,14 +33,14 @@ Whenever the relay decides to refuse to fulfill the `COUNT` request, it MUST ret | |||
| 33 | 33 | ||
| 34 | ### Followers count | 34 | ### Followers count |
| 35 | 35 | ||
| 36 | ```json | 36 | ``` |
| 37 | ["COUNT", <subscription_id>, {"kinds": [3], "#p": [<pubkey>]}] | 37 | ["COUNT", <subscription_id>, {"kinds": [3], "#p": [<pubkey>]}] |
| 38 | ["COUNT", <subscription_id>, {"count": 238}] | 38 | ["COUNT", <subscription_id>, {"count": 238}] |
| 39 | ``` | 39 | ``` |
| 40 | 40 | ||
| 41 | ### Count posts and reactions | 41 | ### Count posts and reactions |
| 42 | 42 | ||
| 43 | ```json | 43 | ``` |
| 44 | ["COUNT", <subscription_id>, {"kinds": [1, 7], "authors": [<pubkey>]}] | 44 | ["COUNT", <subscription_id>, {"kinds": [1, 7], "authors": [<pubkey>]}] |
| 45 | ["COUNT", <subscription_id>, {"count": 5}] | 45 | ["COUNT", <subscription_id>, {"count": 5}] |
| 46 | ``` | 46 | ``` |
| @@ -28,7 +28,7 @@ The remote signer would provide a connection token in the form: | |||
| 28 | bunker://<remote-user-pubkey>?relay=<wss://relay-to-connect-on>&relay=<wss://another-relay-to-connect-on>&secret=<optional-secret-value> | 28 | bunker://<remote-user-pubkey>?relay=<wss://relay-to-connect-on>&relay=<wss://another-relay-to-connect-on>&secret=<optional-secret-value> |
| 29 | ``` | 29 | ``` |
| 30 | 30 | ||
| 31 | This token is pasted into the client by the user and the client then uses the details to connect to the remote signer via the specified relay(s). | 31 | This token is pasted into the client by the user and the client then uses the details to connect to the remote signer via the specified relay(s). Optional secret can be used for single successfully established connection only, remote signer SHOULD ignore new attempts to establish connection with old optional secret. |
| 32 | 32 | ||
| 33 | ### Direct connection initiated by the client | 33 | ### Direct connection initiated by the client |
| 34 | 34 | ||
| @@ -101,7 +101,7 @@ nostrconnect://<local-keypair-pubkey>?relay=<wss://relay-to-connect-on>&metadata | |||
| 101 | } | 101 | } |
| 102 | ``` | 102 | ``` |
| 103 | 103 | ||
| 104 | The `content` field is a JSON-RPC-like message that is [NIP-04](https://github.com/nostr-protocol/nips/blob/master/04.md) encrypted and has the following structure: | 104 | The `content` field is a JSON-RPC-like message that is [NIP-04](04.md) encrypted and has the following structure: |
| 105 | 105 | ||
| 106 | ```json | 106 | ```json |
| 107 | { | 107 | { |
| @@ -148,7 +148,7 @@ The `connect` method may be provided with `optional_requested_permissions` for u | |||
| 148 | } | 148 | } |
| 149 | ``` | 149 | ``` |
| 150 | 150 | ||
| 151 | The `content` field is a JSON-RPC-like message that is [NIP-04](https://github.com/nostr-protocol/nips/blob/master/04.md) encrypted and has the following structure: | 151 | The `content` field is a JSON-RPC-like message that is [NIP-04](04.md) encrypted and has the following structure: |
| 152 | 152 | ||
| 153 | ```json | 153 | ```json |
| 154 | { | 154 | { |
| @@ -224,4 +224,4 @@ Coming soon... | |||
| 224 | 224 | ||
| 225 | ## References | 225 | ## References |
| 226 | 226 | ||
| 227 | - [NIP-04 - Encryption](https://github.com/nostr-protocol/nips/blob/master/04.md) | 227 | - [NIP-04 - Encryption](04.md) |
| @@ -38,7 +38,7 @@ a plaintext string with the supported commands, space-separated, eg. `pay_invoic | |||
| 38 | Both the request and response events SHOULD contain one `p` tag, containing the public key of the **wallet service** if this is a request, and the public key of the **user** if this is a response. The response event SHOULD contain an `e` tag with the id of the request event it is responding to. | 38 | Both the request and response events SHOULD contain one `p` tag, containing the public key of the **wallet service** if this is a request, and the public key of the **user** if this is a response. The response event SHOULD contain an `e` tag with the id of the request event it is responding to. |
| 39 | Optionally, a request can have an `expiration` tag that has a unix timestamp in seconds. If the request is received after this timestamp, it should be ignored. | 39 | Optionally, a request can have an `expiration` tag that has a unix timestamp in seconds. If the request is received after this timestamp, it should be ignored. |
| 40 | 40 | ||
| 41 | The content of requests and responses is encrypted with [NIP04](https://github.com/nostr-protocol/nips/blob/master/04.md), and is a JSON-RPCish object with a semi-fixed structure: | 41 | The content of requests and responses is encrypted with [NIP04](04.md), and is a JSON-RPCish object with a semi-fixed structure: |
| 42 | 42 | ||
| 43 | Request: | 43 | Request: |
| 44 | ```jsonc | 44 | ```jsonc |
| @@ -16,7 +16,7 @@ When new items are added to an existing list, clients SHOULD append them to the | |||
| 16 | 16 | ||
| 17 | ## Standard lists | 17 | ## Standard lists |
| 18 | 18 | ||
| 19 | Standard lists use non-parameterized replaceable events, meaning users may only have a single list of each kind. They have special meaning and clients may rely on them to augment a user's profile or browsing experience. | 19 | Standard lists use normal replaceable events, meaning users may only have a single list of each kind. They have special meaning and clients may rely on them to augment a user's profile or browsing experience. |
| 20 | 20 | ||
| 21 | For example, _mute list_ can contain the public keys of spammers and bad actors users don't want to see in their feeds or receive annoying notifications from. | 21 | For example, _mute list_ can contain the public keys of spammers and bad actors users don't want to see in their feeds or receive annoying notifications from. |
| 22 | 22 | ||
| @@ -32,6 +32,7 @@ For example, _mute list_ can contain the public keys of spammers and bad actors | |||
| 32 | | Simple groups | 10009 | [NIP-29](29.md) groups the user is in | `"group"` ([NIP-29](29.md) group ids + mandatory relay URL) | | 32 | | Simple groups | 10009 | [NIP-29](29.md) groups the user is in | `"group"` ([NIP-29](29.md) group ids + mandatory relay URL) | |
| 33 | | Interests | 10015 | topics a user may be interested in and pointers | `"t"` (hashtags) and `"a"` (kind:30015 interest set) | | 33 | | Interests | 10015 | topics a user may be interested in and pointers | `"t"` (hashtags) and `"a"` (kind:30015 interest set) | |
| 34 | | Emojis | 10030 | user preferred emojis and pointers to emoji sets | `"emoji"` (see [NIP-30](30.md)) and `"a"` (kind:30030 emoji set) | | 34 | | Emojis | 10030 | user preferred emojis and pointers to emoji sets | `"emoji"` (see [NIP-30](30.md)) and `"a"` (kind:30030 emoji set) | |
| 35 | | DM relays | 10050 | Where to receive [NIP-17](17.md) direct messages | `"relay"` (see [NIP-17](17.md)) | | ||
| 35 | | Good wiki authors | 10101 | [NIP-54](54.md) user recommended wiki authors | `"p"` (pubkeys) | | 36 | | Good wiki authors | 10101 | [NIP-54](54.md) user recommended wiki authors | `"p"` (pubkeys) | |
| 36 | | Good wiki relays | 10102 | [NIP-54](54.md) relays deemed to only host useful articles | `"relay"` (relay URLs) | | 37 | | Good wiki relays | 10102 | [NIP-54](54.md) relays deemed to only host useful articles | `"relay"` (relay URLs) | |
| 37 | 38 | ||
| @@ -50,6 +51,7 @@ Aside from their main identifier, the `"d"` tag, sets can optionally have a `"ti | |||
| 50 | | Bookmark sets | 30003 | user-defined bookmarks categories , for when bookmarks must be in labeled separate groups | `"e"` (kind:1 notes), `"a"` (kind:30023 articles), `"t"` (hashtags), `"r"` (URLs) | | 51 | | Bookmark sets | 30003 | user-defined bookmarks categories , for when bookmarks must be in labeled separate groups | `"e"` (kind:1 notes), `"a"` (kind:30023 articles), `"t"` (hashtags), `"r"` (URLs) | |
| 51 | | Curation sets | 30004 | groups of articles picked by users as interesting and/or belonging to the same category | `"a"` (kind:30023 articles), `"e"` (kind:1 notes) | | 52 | | Curation sets | 30004 | groups of articles picked by users as interesting and/or belonging to the same category | `"a"` (kind:30023 articles), `"e"` (kind:1 notes) | |
| 52 | | Curation sets | 30005 | groups of videos picked by users as interesting and/or belonging to the same category | `"a"` (kind:34235 videos) | | 53 | | Curation sets | 30005 | groups of videos picked by users as interesting and/or belonging to the same category | `"a"` (kind:34235 videos) | |
| 54 | | Kind mute sets | 30007 | mute pubkeys by kinds<br>`"d"` tag MUST be the kind string | `"p"` (pubkeys) | | ||
| 53 | | Interest sets | 30015 | interest topics represented by a bunch of "hashtags" | `"t"` (hashtags) | | 55 | | Interest sets | 30015 | interest topics represented by a bunch of "hashtags" | `"t"` (hashtags) | |
| 54 | | Emoji sets | 30030 | categorized emoji groups | `"emoji"` (see [NIP-30](30.md)) | | 56 | | Emoji sets | 30030 | categorized emoji groups | `"emoji"` (see [NIP-30](30.md)) | |
| 55 | | Release artifact sets | 30063 | groups of files of a software release | `"e"` (kind:1063 [file metadata](94.md) events), `"i"` (application identifier, typically reverse domain notation), `"version"` | | 57 | | Release artifact sets | 30063 | groups of files of a software release | `"e"` (kind:1063 [file metadata](94.md) events), `"i"` (application identifier, typically reverse domain notation), `"version"` | |
| @@ -6,7 +6,7 @@ Calendar Events | |||
| 6 | 6 | ||
| 7 | `draft` `optional` | 7 | `draft` `optional` |
| 8 | 8 | ||
| 9 | This specification defines calendar events representing an occurrence at a specific moment or between moments. These calendar events are _parameterized replaceable_ and deletable per [NIP-09](09.md). | 9 | This specification defines calendar events representing an occurrence at a specific moment or between moments. These calendar events are _addressable_ and deletable per [NIP-09](09.md). |
| 10 | 10 | ||
| 11 | Unlike the term `calendar event` specific to this NIP, the term `event` is used broadly in all the NIPs to describe any Nostr event. The distinction is being made here to discern between the two terms. | 11 | Unlike the term `calendar event` specific to this NIP, the term `event` is used broadly in all the NIPs to describe any Nostr event. The distinction is being made here to discern between the two terms. |
| 12 | 12 | ||
| @@ -90,9 +90,12 @@ The list of tags are as follows: | |||
| 90 | * `end` (optional) exclusive end Unix timestamp in seconds. If omitted, the calendar event ends instantaneously. | 90 | * `end` (optional) exclusive end Unix timestamp in seconds. If omitted, the calendar event ends instantaneously. |
| 91 | * `start_tzid` (optional) time zone of the start timestamp, as defined by the IANA Time Zone Database. e.g., `America/Costa_Rica` | 91 | * `start_tzid` (optional) time zone of the start timestamp, as defined by the IANA Time Zone Database. e.g., `America/Costa_Rica` |
| 92 | * `end_tzid` (optional) time zone of the end timestamp, as defined by the IANA Time Zone Database. e.g., `America/Costa_Rica`. If omitted and `start_tzid` is provided, the time zone of the end timestamp is the same as the start timestamp. | 92 | * `end_tzid` (optional) time zone of the end timestamp, as defined by the IANA Time Zone Database. e.g., `America/Costa_Rica`. If omitted and `start_tzid` is provided, the time zone of the end timestamp is the same as the start timestamp. |
| 93 | * `summary` (optional) brief description of the calendar event | ||
| 94 | * `image` (optional) url of an image to use for the event | ||
| 93 | * `location` (optional, repeated) location of the calendar event. e.g. address, GPS coordinates, meeting room name, link to video call | 95 | * `location` (optional, repeated) location of the calendar event. e.g. address, GPS coordinates, meeting room name, link to video call |
| 94 | * `g` (optional) [geohash](https://en.wikipedia.org/wiki/Geohash) to associate calendar event with a searchable physical location | 96 | * `g` (optional) [geohash](https://en.wikipedia.org/wiki/Geohash) to associate calendar event with a searchable physical location |
| 95 | * `p` (optional, repeated) 32-bytes hex pubkey of a participant, optional recommended relay URL, and participant's role in the meeting | 97 | * `p` (optional, repeated) 32-bytes hex pubkey of a participant, optional recommended relay URL, and participant's role in the meeting |
| 98 | * `l` (optional, repeated) label to categorize calendar event. e.g. `audiospace` to denote a scheduled event from a live audio space implementation such as cornychat.com | ||
| 96 | * `t` (optional, repeated) hashtag to categorize calendar event | 99 | * `t` (optional, repeated) hashtag to categorize calendar event |
| 97 | * `r` (optional, repeated) references / links to web pages, documents, video calls, recorded videos, etc. | 100 | * `r` (optional, repeated) references / links to web pages, documents, video calls, recorded videos, etc. |
| 98 | 101 | ||
| @@ -110,6 +113,8 @@ The following tags are deprecated: | |||
| 110 | ["d", "<UUID>"], | 113 | ["d", "<UUID>"], |
| 111 | 114 | ||
| 112 | ["title", "<title of calendar event>"], | 115 | ["title", "<title of calendar event>"], |
| 116 | ["summary", "<brief description of the calendar event>"], | ||
| 117 | ["image", "<string with image URI>"], | ||
| 113 | 118 | ||
| 114 | // Timestamps | 119 | // Timestamps |
| 115 | ["start", "<Unix timestamp in seconds>"], | 120 | ["start", "<Unix timestamp in seconds>"], |
| @@ -126,6 +131,10 @@ The following tags are deprecated: | |||
| 126 | ["p", "<32-bytes hex of a pubkey>", "<optional recommended relay URL>", "<role>"], | 131 | ["p", "<32-bytes hex of a pubkey>", "<optional recommended relay URL>", "<role>"], |
| 127 | ["p", "<32-bytes hex of a pubkey>", "<optional recommended relay URL>", "<role>"], | 132 | ["p", "<32-bytes hex of a pubkey>", "<optional recommended relay URL>", "<role>"], |
| 128 | 133 | ||
| 134 | // Labels (example using com.cornychat namespace denoting the event as an audiospace) | ||
| 135 | ["L", "com.cornychat"], | ||
| 136 | ["l", "audiospace", "com.cornychat"], | ||
| 137 | |||
| 129 | // Hashtags | 138 | // Hashtags |
| 130 | ["t", "<tag>"], | 139 | ["t", "<tag>"], |
| 131 | ["t", "<tag>"], | 140 | ["t", "<tag>"], |
| @@ -178,6 +187,10 @@ This NIP is intentionally not defining who is authorized to attend a calendar ev | |||
| 178 | 187 | ||
| 179 | This NIP is also intentionally not defining what happens if a calendar event changes after an RSVP is submitted. | 188 | This NIP is also intentionally not defining what happens if a calendar event changes after an RSVP is submitted. |
| 180 | 189 | ||
| 190 | The RSVP MUST have an `a` tag of the event coordinates to the calendar event, and optionally an `e` tag of the id of the specific calendar event revision. If an `e` tag is present, clients SHOULD interpret it as an indication that the RSVP is a response to that revision of the calendar event, and MAY interpret it to not necessarily apply to other revisions of the calendar event. | ||
| 191 | |||
| 192 | The RSVP MAY tag the author of the calendar event it is in response to using a `p` tag so that clients can easily query all RSVPs that pertain to the author. | ||
| 193 | |||
| 181 | ### Format | 194 | ### Format |
| 182 | 195 | ||
| 183 | The format uses a parameterized replaceable event kind `31925`. | 196 | The format uses a parameterized replaceable event kind `31925`. |
| @@ -185,10 +198,12 @@ The format uses a parameterized replaceable event kind `31925`. | |||
| 185 | The `.content` of these events is optional and should be a free-form note that adds more context to this calendar event response. | 198 | The `.content` of these events is optional and should be a free-form note that adds more context to this calendar event response. |
| 186 | 199 | ||
| 187 | The list of tags are as follows: | 200 | The list of tags are as follows: |
| 188 | * `a` (required) reference tag to kind `31922` or `31923` calendar event being responded to. | 201 | * `a` (required) coordinates to a kind `31922` or `31923` calendar event being responded to. |
| 202 | * `e` (optional) event id of a kind `31922` or `31923` calendar event being responded to. | ||
| 189 | * `d` (required) universally unique identifier. Generated by the client creating the calendar event RSVP. | 203 | * `d` (required) universally unique identifier. Generated by the client creating the calendar event RSVP. |
| 190 | * `status` (required) `accepted`, `declined`, or `tentative`. Determines attendance status to the referenced calendar event. | 204 | * `status` (required) `accepted`, `declined`, or `tentative`. Determines attendance status to the referenced calendar event. |
| 191 | * `fb` (optional) `free` or `busy`. Determines if the user would be free or busy for the duration of the calendar event. This tag must be omitted or ignored if the `status` label is set to `declined`. | 205 | * `fb` (optional) `free` or `busy`. Determines if the user would be free or busy for the duration of the calendar event. This tag must be omitted or ignored if the `status` label is set to `declined`. |
| 206 | * `p` (optional) pubkey of the author of the calendar event being responded to. | ||
| 192 | 207 | ||
| 193 | ```json | 208 | ```json |
| 194 | { | 209 | { |
| @@ -198,10 +213,12 @@ The list of tags are as follows: | |||
| 198 | "kind": 31925, | 213 | "kind": 31925, |
| 199 | "content": "<note>", | 214 | "content": "<note>", |
| 200 | "tags": [ | 215 | "tags": [ |
| 201 | ["a", "<31922 or 31923>:<calendar event author pubkey>:<d-identifier of calendar event>", "<optional relay url>"], | 216 | ["e", "<kind 31922 or 31923 event id", "<optional recommended relay URL>"] |
| 217 | ["a", "<31922 or 31923>:<calendar event author pubkey>:<d-identifier of calendar event>", "<optional recommended relay URL>"], | ||
| 202 | ["d", "<UUID>"], | 218 | ["d", "<UUID>"], |
| 203 | ["status", "<accepted/declined/tentative>"], | 219 | ["status", "<accepted/declined/tentative>"], |
| 204 | ["fb", "<free/busy>"], | 220 | ["fb", "<free/busy>"], |
| 221 | ["p", "<hex pubkey of kind 31922 or 31923 event>", "<optional recommended relay URL>"] | ||
| 205 | ] | 222 | ] |
| 206 | } | 223 | } |
| 207 | ``` | 224 | ``` |
| @@ -12,7 +12,7 @@ Service providers want to offer live activities to the Nostr network in such a w | |||
| 12 | 12 | ||
| 13 | ### Live Event | 13 | ### Live Event |
| 14 | 14 | ||
| 15 | A special event with `kind:30311` "Live Event" is defined as a _parameterized replaceable event_ of public `p` tags. Each `p` tag SHOULD have a **displayable** marker name for the current role (e.g. `Host`, `Speaker`, `Participant`) of the user in the event and the relay information MAY be empty. This event will be constantly updated as participants join and leave the activity. | 15 | A special event with `kind:30311` "Live Event" is defined as an _addressable event_ of public `p` tags. Each `p` tag SHOULD have a **displayable** marker name for the current role (e.g. `Host`, `Speaker`, `Participant`) of the user in the event and the relay information MAY be empty. This event will be constantly updated as participants join and leave the activity. |
| 16 | 16 | ||
| 17 | For example: | 17 | For example: |
| 18 | 18 | ||
| @@ -6,7 +6,7 @@ Wiki | |||
| 6 | 6 | ||
| 7 | `draft` `optional` | 7 | `draft` `optional` |
| 8 | 8 | ||
| 9 | This NIP defines `kind:30818` (a _parameterized replaceable event_) for long-form text content similar to [NIP-23](23.md), but with one important difference: articles are meant to be descriptions, or encyclopedia entries, of particular subjects, and it's expected that multiple people will write articles about the exact same subjects, with either small variations or completely independent content. | 9 | This NIP defines `kind:30818` (an _addressable event_) for long-form text content similar to [NIP-23](23.md), but with one important difference: articles are meant to be descriptions, or encyclopedia entries, of particular subjects, and it's expected that multiple people will write articles about the exact same subjects, with either small variations or completely independent content. |
| 10 | 10 | ||
| 11 | Articles are identified by lowercase, normalized ascii `d` tags. | 11 | Articles are identified by lowercase, normalized ascii `d` tags. |
| 12 | 12 | ||
| @@ -28,13 +28,13 @@ Articles are identified by lowercase, normalized ascii `d` tags. | |||
| 28 | 28 | ||
| 29 | ### Content rules | 29 | ### Content rules |
| 30 | 30 | ||
| 31 | The content should be Markdown, following the same rules as of [NIP-23](23.md), although it takes some extra (optional) metadata tags: | 31 | The content should be Asciidoc, following the same rules as of [NIP-23](23.md), although it takes some extra (optional) metadata tags: |
| 32 | 32 | ||
| 33 | - `title`: for when the display title should be different from the `d` tag. | 33 | - `title`: for when the display title should be different from the `d` tag. |
| 34 | - `summary`: for display in lists. | 34 | - `summary`: for display in lists. |
| 35 | - `a` and `e`: for referencing the original event a wiki article was forked from. | 35 | - `a` and `e`: for referencing the original event a wiki article was forked from. |
| 36 | 36 | ||
| 37 | One extra functionality is added: **wikilinks**. Unlike normal Markdown links `[]()` that link to webpages, wikilinks `[[]]` link to other articles in the wiki. In this case, the wiki is the entirety of Nostr. Clicking on a wikilink should cause the client to ask relays for events with `d` tags equal to the target of that wikilink. | 37 | One extra functionality is added: **wikilinks**. Unlike normal Asciidoc links `[]()` that link to webpages, wikilinks `[[]]` link to other articles in the wiki. In this case, the wiki is the entirety of Nostr. Clicking on a wikilink should cause the client to ask relays for events with `d` tags equal to the target of that wikilink. |
| 38 | 38 | ||
| 39 | Wikilinks can take these two forms: | 39 | Wikilinks can take these two forms: |
| 40 | 40 | ||
| @@ -86,12 +86,12 @@ This is a stronger signal of trust than a `+` reaction. | |||
| 86 | 86 | ||
| 87 | This marker is useful when a user edits someone else's entry; if the original author includes the editor's changes and the editor doesn't want to keep/maintain an independent version, the `link` tag could effectively be a considered a "deletion" of the editor's version and putting that pubkey's WoT weight behind the original author's version. | 87 | This marker is useful when a user edits someone else's entry; if the original author includes the editor's changes and the editor doesn't want to keep/maintain an independent version, the `link` tag could effectively be a considered a "deletion" of the editor's version and putting that pubkey's WoT weight behind the original author's version. |
| 88 | 88 | ||
| 89 | Why Markdown? | 89 | Why Asciidoc? |
| 90 | ------------- | 90 | ------------- |
| 91 | 91 | ||
| 92 | If the idea is to make a wiki then the most obvious text format to use is probably the mediawiki/wikitext format used by Wikipedia since it's widely deployed in all mediawiki installations and used for decades with great success. However, it turns out that format is very bloated and convoluted, has way too many features and probably because of that it doesn't have many alternative implementations out there, and the ones that exist are not complete and don't look very trustworthy. Also it is very much a centralized format that can probably be changed at the whims of the Wikipedia owners. | 92 | Wikitext is [garbage](nostr:nevent1qqsqt0gcggry60n72uglhuhypdlmr2dm6swjj69jex5v530gcpazlzsprpmhxue69uhhyetvv9ujumn0wdmksetjv5hxxmmdqy28wumn8ghj7un9d3shjtnyv9kh2uewd9hsygpm7rrrljungc6q0tuh5hj7ue863q73qlheu4vywtzwhx42a7j9n5ueneex) and Markdown is not powerful enough (besides being too freeform and unspecified and prone to generate incompatibilities in the future). |
| 93 | 93 | ||
| 94 | On the other hand, Markdown has proven to work well for small scale wikis and one of the biggest wikis in the planet (which is not very often thought of as a wiki), [StackOverflow](https://stackoverflow.com) and its child sites, and also one of the biggest "personal wiki" software, [Obsidian](https://obsidian.md/). Markdown can probably deliver 95% of the functionality of wikitext. When augmented with tables, diagram generators and MathJax (which are common extensions that exist in the wild and can be included in this NIP) that rate probably goes to 99%, and its simplicity is a huge benefit that can't be overlooked. Wikitext format can also be transpíled into Markdown using Pandoc. Given all that, I think it's a reasonable suspicion that mediawiki is not inherently better than Markdown, the success of Wikipedia probably cannot be predicated on the syntax language choice. | 94 | Asciidoc has a strict spec, multiple implementations in many languages, and support for features that are very much necessary in a wiki article, like _sidebars_, _tables_ (with rich markup inside cells), many levels of _headings_, _footnotes_, _superscript_ and _subscript_ markup and _description lists_. It is also arguably easier to read in its plaintext format than Markdown (and certainly much better than Wikitext). |
| 95 | 95 | ||
| 96 | # Appendix 1: Merge requests | 96 | # Appendix 1: Merge requests |
| 97 | Users can request other users to get their entries merged into someone else's entry by creating a `kind:818` event. | 97 | Users can request other users to get their entries merged into someone else's entry by creating a `kind:818` event. |
| @@ -36,7 +36,7 @@ A `zap request` is an event of kind `9734` that is _not_ published to relays, bu | |||
| 36 | In addition, the event MAY include the following tags: | 36 | In addition, the event MAY include the following tags: |
| 37 | 37 | ||
| 38 | - `e` is an optional hex-encoded event id. Clients MUST include this if zapping an event rather than a person. | 38 | - `e` is an optional hex-encoded event id. Clients MUST include this if zapping an event rather than a person. |
| 39 | - `a` is an optional event coordinate that allows tipping parameterized replaceable events such as NIP-23 long-form notes. | 39 | - `a` is an optional event coordinate that allows tipping addressable events such as NIP-23 long-form notes. |
| 40 | 40 | ||
| 41 | Example: | 41 | Example: |
| 42 | 42 | ||
| @@ -9,7 +9,7 @@ Badges | |||
| 9 | Three special events are used to define, award and display badges in | 9 | Three special events are used to define, award and display badges in |
| 10 | user profiles: | 10 | user profiles: |
| 11 | 11 | ||
| 12 | 1. A "Badge Definition" event is defined as a parameterized replaceable event with kind `30009` having a `d` tag with a value that uniquely identifies the badge (e.g. `bravery`) published by the badge issuer. Badge definitions can be updated. | 12 | 1. A "Badge Definition" event is defined as an addressable event with kind `30009` having a `d` tag with a value that uniquely identifies the badge (e.g. `bravery`) published by the badge issuer. Badge definitions can be updated. |
| 13 | 13 | ||
| 14 | 2. A "Badge Award" event is a kind `8` event with a single `a` tag referencing a "Badge Definition" event and one or more `p` tags, one for each pubkey the badge issuer wishes to award. Awarded badges are immutable and non-transferrable. | 14 | 2. A "Badge Award" event is a kind `8` event with a single `a` tag referencing a "Badge Definition" event and one or more `p` tags, one for each pubkey the badge issuer wishes to award. Awarded badges are immutable and non-transferrable. |
| 15 | 15 | ||
| @@ -0,0 +1,146 @@ | |||
| 1 | NIP-64 | ||
| 2 | ====== | ||
| 3 | |||
| 4 | Chess (Portable Game Notation) | ||
| 5 | ----- | ||
| 6 | |||
| 7 | `draft` `optional` | ||
| 8 | |||
| 9 | This NIP defines `kind:64` notes representing chess games in [PGN][pgn_specification] format, which can be read by humans and is also supported by most chess software. | ||
| 10 | |||
| 11 | ## Note | ||
| 12 | |||
| 13 | ### Content | ||
| 14 | |||
| 15 | The `.content` of these notes is a string representing a [PGN-database][pgn_formal_syntax]. | ||
| 16 | |||
| 17 | ### Notes | ||
| 18 | |||
| 19 | ```json | ||
| 20 | { | ||
| 21 | "kind": 64, | ||
| 22 | "content": "1. e4 *", | ||
| 23 | ... | ||
| 24 | } | ||
| 25 | ``` | ||
| 26 | |||
| 27 | ```json | ||
| 28 | { | ||
| 29 | "kind": 64, | ||
| 30 | "tags": [ | ||
| 31 | ["alt", "Fischer vs. Spassky in Belgrade on 1992-11-04 (F/S Return Match, Round 29)"], | ||
| 32 | ... | ||
| 33 | ], | ||
| 34 | "content": "[Event \"F/S Return Match\"]\n[Site \"Belgrade, Serbia JUG\"]\n[Date \"1992.11.04\"]\n[Round \"29\"]\n[White \"Fischer, Robert J.\"]\n[Black \"Spassky, Boris V.\"]\n[Result \"1/2-1/2\"]\n\n1. e4 e5 2. Nf3 Nc6 3. Bb5 {This opening is called the Ruy Lopez.} 3... a6\n4. Ba4 Nf6 5. O-O Be7 6. Re1 b5 7. Bb3 d6 8. c3 O-O 9. h3 Nb8 10. d4 Nbd7\n11. c4 c6 12. cxb5 axb5 13. Nc3 Bb7 14. Bg5 b4 15. Nb1 h6 16. Bh4 c5 17. dxe5\nNxe4 18. Bxe7 Qxe7 19. exd6 Qf6 20. Nbd2 Nxd6 21. Nc4 Nxc4 22. Bxc4 Nb6\n23. Ne5 Rae8 24. Bxf7+ Rxf7 25. Nxf7 Rxe1+ 26. Qxe1 Kxf7 27. Qe3 Qg5 28. Qxg5\nhxg5 29. b3 Ke6 30. a3 Kd6 31. axb4 cxb4 32. Ra5 Nd5 33. f3 Bc8 34. Kf2 Bf5\n35. Ra7 g6 36. Ra6+ Kc5 37. Ke1 Nf4 38. g3 Nxh3 39. Kd2 Kb5 40. Rd6 Kc5 41. Ra6\nNf2 42. g4 Bd3 43. Re6 1/2-1/2" | ||
| 35 | ... | ||
| 36 | } | ||
| 37 | ``` | ||
| 38 | |||
| 39 | ## Client Behavior | ||
| 40 | |||
| 41 | Clients SHOULD display the content represented as chessboard. | ||
| 42 | |||
| 43 | Clients SHOULD publish PGN notes in ["export format"][pgn_export_format] ("strict mode", i.e. created by machines) but expect incoming notes to be in ["import format"][pgn_import_format] ("lax mode", i.e. created by humans). | ||
| 44 | |||
| 45 | Clients SHOULD check whether the formatting is valid and all moves comply with chess rules. | ||
| 46 | |||
| 47 | Clients MAY include additional tags (e.g. like [`"alt"`](https://github.com/nostr-protocol/nips/blob/master/31.md)) in order to represent the note to users of non-supporting clients. | ||
| 48 | |||
| 49 | ## Relay Behavior | ||
| 50 | |||
| 51 | Relays MAY validate PGN contents and reject invalid notes. | ||
| 52 | |||
| 53 | |||
| 54 | ## Examples | ||
| 55 | |||
| 56 | ```pgn | ||
| 57 | // A game where nothing is known. Game still in progress, game abandoned, or result otherwise unknown. | ||
| 58 | // Maybe players died before a move has been made. | ||
| 59 | * | ||
| 60 | ``` | ||
| 61 | |||
| 62 | ```pgn | ||
| 63 | 1. e4 * | ||
| 64 | ``` | ||
| 65 | |||
| 66 | ```pgn | ||
| 67 | [White "Fischer, Robert J."] | ||
| 68 | [Black "Spassky, Boris V."] | ||
| 69 | |||
| 70 | 1. e4 e5 2. Nf3 Nc6 3. Bb5 {This opening is called the Ruy Lopez.} * | ||
| 71 | ``` | ||
| 72 | |||
| 73 | ```pgn | ||
| 74 | [Event "F/S Return Match"] | ||
| 75 | [Site "Belgrade, Serbia JUG"] | ||
| 76 | [Date "1992.11.04"] | ||
| 77 | [Round "29"] | ||
| 78 | [White "Fischer, Robert J."] | ||
| 79 | [Black "Spassky, Boris V."] | ||
| 80 | [Result "1/2-1/2"] | ||
| 81 | |||
| 82 | 1. e4 e5 2. Nf3 Nc6 3. Bb5 {This opening is called the Ruy Lopez.} 3... a6 | ||
| 83 | 4. Ba4 Nf6 5. O-O Be7 6. Re1 b5 7. Bb3 d6 8. c3 O-O 9. h3 Nb8 10. d4 Nbd7 | ||
| 84 | 11. c4 c6 12. cxb5 axb5 13. Nc3 Bb7 14. Bg5 b4 15. Nb1 h6 16. Bh4 c5 17. dxe5 | ||
| 85 | Nxe4 18. Bxe7 Qxe7 19. exd6 Qf6 20. Nbd2 Nxd6 21. Nc4 Nxc4 22. Bxc4 Nb6 | ||
| 86 | 23. Ne5 Rae8 24. Bxf7+ Rxf7 25. Nxf7 Rxe1+ 26. Qxe1 Kxf7 27. Qe3 Qg5 28. Qxg5 | ||
| 87 | hxg5 29. b3 Ke6 30. a3 Kd6 31. axb4 cxb4 32. Ra5 Nd5 33. f3 Bc8 34. Kf2 Bf5 | ||
| 88 | 35. Ra7 g6 36. Ra6+ Kc5 37. Ke1 Nf4 38. g3 Nxh3 39. Kd2 Kb5 40. Rd6 Kc5 41. Ra6 | ||
| 89 | Nf2 42. g4 Bd3 43. Re6 1/2-1/2 | ||
| 90 | ``` | ||
| 91 | |||
| 92 | ```pgn | ||
| 93 | [Event "Hourly HyperBullet Arena"] | ||
| 94 | [Site "https://lichess.org/wxx4GldJ"] | ||
| 95 | [Date "2017.04.01"] | ||
| 96 | [White "T_LUKE"] | ||
| 97 | [Black "decidement"] | ||
| 98 | [Result "1-0"] | ||
| 99 | [UTCDate "2017.04.01"] | ||
| 100 | [UTCTime "11:56:14"] | ||
| 101 | [WhiteElo "2047"] | ||
| 102 | [BlackElo "1984"] | ||
| 103 | [WhiteRatingDiff "+10"] | ||
| 104 | [BlackRatingDiff "-7"] | ||
| 105 | [Variant "Standard"] | ||
| 106 | [TimeControl "30+0"] | ||
| 107 | [ECO "B00"] | ||
| 108 | [Termination "Abandoned"] | ||
| 109 | |||
| 110 | 1. e4 1-0 | ||
| 111 | |||
| 112 | |||
| 113 | [Event "Hourly HyperBullet Arena"] | ||
| 114 | [Site "https://lichess.org/rospUdSk"] | ||
| 115 | [Date "2017.04.01"] | ||
| 116 | [White "Bastel"] | ||
| 117 | [Black "oslochess"] | ||
| 118 | [Result "1-0"] | ||
| 119 | [UTCDate "2017.04.01"] | ||
| 120 | [UTCTime "11:55:56"] | ||
| 121 | [WhiteElo "2212"] | ||
| 122 | [BlackElo "2000"] | ||
| 123 | [WhiteRatingDiff "+6"] | ||
| 124 | [BlackRatingDiff "-4"] | ||
| 125 | [Variant "Standard"] | ||
| 126 | [TimeControl "30+0"] | ||
| 127 | [ECO "A01"] | ||
| 128 | [Termination "Normal"] | ||
| 129 | |||
| 130 | 1. b3 d5 2. Bb2 c6 3. Nc3 Bf5 4. d4 Nf6 5. e3 Nbd7 6. f4 Bg6 7. Nf3 Bh5 8. Bd3 e6 9. O-O Be7 10. Qe1 O-O 11. Ne5 Bg6 12. Nxg6 hxg6 13. e4 dxe4 14. Nxe4 Nxe4 15. Bxe4 Nf6 16. c4 Bd6 17. Bc2 Qc7 18. f5 Be7 19. fxe6 fxe6 20. Qxe6+ Kh8 21. Qh3+ Kg8 22. Bxg6 Qd7 23. Qe3 Bd6 24. Bf5 Qe7 25. Be6+ Kh8 26. Qh3+ Nh7 27. Bf5 Rf6 28. Qxh7# 1-0 | ||
| 131 | ``` | ||
| 132 | |||
| 133 | ## Resources | ||
| 134 | - [PGN Specification][pgn_specification]: PGN (Portable Game Notation) specification | ||
| 135 | - [PGN Specification Supplement](https://github.com/mliebelt/pgn-spec-commented/blob/main/pgn-spec-supplement.md): Addition for adding graphical elements, clock values, eval, ... | ||
| 136 | - [PGN Formal Syntax][pgn_formal_syntax] | ||
| 137 | - [PGN Seven Tag Roster][pgn_seven_tag_roster] | ||
| 138 | - [PGN Import Format][pgn_import_format] | ||
| 139 | - [PGN Export Format][pgn_export_format] | ||
| 140 | - [lichess / pgn-viewer (GitHub)](https://github.com/lichess-org/pgn-viewer): PGN viewer widget, designed to be embedded in content pages | ||
| 141 | |||
| 142 | [pgn_specification]: https://github.com/mliebelt/pgn-spec-commented/blob/main/pgn-specification.md | ||
| 143 | [pgn_formal_syntax]: https://github.com/mliebelt/pgn-spec-commented/blob/main/pgn-specification.md#18-formal-syntax | ||
| 144 | [pgn_seven_tag_roster]: https://github.com/mliebelt/pgn-spec-commented/blob/main/pgn-specification.md#811-seven-tag-roster | ||
| 145 | [pgn_import_format]: https://github.com/mliebelt/pgn-spec-commented/blob/main/pgn-specification.md#31-import-format-allows-for-manually-prepared-data | ||
| 146 | [pgn_export_format]: https://github.com/mliebelt/pgn-spec-commented/blob/main/pgn-specification.md#32-export-format-used-for-program-generated-output | ||
| @@ -37,7 +37,7 @@ When seeking events **about** a user, where the user was tagged, Clients SHOULD | |||
| 37 | When broadcasting an event, Clients SHOULD: | 37 | When broadcasting an event, Clients SHOULD: |
| 38 | 38 | ||
| 39 | - Broadcast the event to the WRITE relays of the author | 39 | - Broadcast the event to the WRITE relays of the author |
| 40 | - Broadcast the event all READ relays of each tagged user | 40 | - Broadcast the event to all READ relays of each tagged user |
| 41 | 41 | ||
| 42 | ## Motivation | 42 | ## Motivation |
| 43 | 43 | ||
| @@ -0,0 +1,45 @@ | |||
| 1 | NIP-70 | ||
| 2 | ====== | ||
| 3 | |||
| 4 | Protected Events | ||
| 5 | ---------------- | ||
| 6 | |||
| 7 | `draft` `optional` | ||
| 8 | |||
| 9 | When the `"-"` tag is present, that means the event is "protected". | ||
| 10 | |||
| 11 | A protected event is an event that can only be published to relays by its author. This is achieved by relays ensuring that the author is [authenticated](42.md) before publishing their own events or by just rejecting events with `["-"]` outright. | ||
| 12 | |||
| 13 | The default behavior of a relay MUST be to reject any event that contains `["-"]`. | ||
| 14 | |||
| 15 | Relays that want to accept such events MUST first require that the client perform the [NIP-42](42.md) `AUTH` flow and then check if the authenticated client has the same pubkey as the event being published and only accept the event in that case. | ||
| 16 | |||
| 17 | ## The tag | ||
| 18 | |||
| 19 | The tag is a simple tag with a single item: `["-"]`. It may be added to any event. | ||
| 20 | |||
| 21 | ## Example flow | ||
| 22 | |||
| 23 | - User `79be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798` connects to relay `wss://example.com`: | ||
| 24 | |||
| 25 | ```jsonc | ||
| 26 | /* client: */ | ||
| 27 | ["EVENT",{"id":"cb8feca582979d91fe90455867b34dbf4d65e4b86e86b3c68c368ca9f9eef6f2","pubkey":"79be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798","created_at":1707409439,"kind":1,"tags":[["-"]],"content":"hello members of the secret group","sig":"fa163f5cfb75d77d9b6269011872ee22b34fb48d23251e9879bb1e4ccbdd8aaaf4b6dc5f5084a65ef42c52fbcde8f3178bac3ba207de827ec513a6aa39fa684c"}] | ||
| 28 | /* relay: */ | ||
| 29 | ["AUTH", "<challenge>"] | ||
| 30 | ["OK", "cb8feca582979d91fe90455867b34dbf4d65e4b86e86b3c68c368ca9f9eef6f2", false, "auth-required: this event may only be published by its author"] | ||
| 31 | /* client: */ | ||
| 32 | ["AUTH", {}] | ||
| 33 | ["EVENT",{"id":"cb8feca582979d91fe90455867b34dbf4d65e4b86e86b3c68c368ca9f9eef6f2","pubkey":"79be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798","created_at":1707409439,"kind":1,"tags":[["-"]],"content":"hello members of the secret group","sig":"fa163f5cfb75d77d9b6269011872ee22b34fb48d23251e9879bb1e4ccbdd8aaaf4b6dc5f5084a65ef42c52fbcde8f3178bac3ba207de827ec513a6aa39fa684c"}] | ||
| 34 | ["OK", "cb8feca582979d91fe90455867b34dbf4d65e4b86e86b3c68c368ca9f9eef6f2", true, ""] | ||
| 35 | ``` | ||
| 36 | |||
| 37 | ## Why | ||
| 38 | |||
| 39 | There are multiple circumstances in which it would be beneficial to prevent the unlimited spreading of an event through all relays imaginable and restrict some to only a certain demographic or to a semi-closed community relay. Even when the information is public it may make sense to keep it compartimentalized across different relays. | ||
| 40 | |||
| 41 | It's also possible to create closed access feeds with this when the publisher has some relationship with the relay and trusts the relay to not release their published events to anyone. | ||
| 42 | |||
| 43 | Even though it's ultimately impossible to restrict the spread of information on the internet (for example, one of the members of the closed group may want to take an event intended to be restricted and republish it to other relays), most relays would be happy to not facilitate the acts of these so-called "pirates", in respect to the original decision of the author and therefore gladly reject these republish acts if given the means to. | ||
| 44 | |||
| 45 | This NIP gives these authors and relays the means to clearly signal when a given event is not intended to be republished by third parties. | ||
| @@ -6,7 +6,7 @@ Video Events | |||
| 6 | 6 | ||
| 7 | `draft` `optional` | 7 | `draft` `optional` |
| 8 | 8 | ||
| 9 | This specification defines video events representing a dedicated post of externally hosted content. These video events are _parameterized replaceable_ and deletable per [NIP-09](09.md). | 9 | This specification defines video events representing a dedicated post of externally hosted content. These video events are _addressable_ and delete-requestable per [NIP-09](09.md). |
| 10 | 10 | ||
| 11 | Unlike a `kind 1` event with a video attached, Video Events are meant to contain all additional metadata concerning the subject media and to be surfaced in video-specific clients rather than general micro-blogging clients. The thought is for events of this kind to be referenced in a Netflix, YouTube, or TikTok like nostr client where the video itself is at the center of the experience. | 11 | Unlike a `kind 1` event with a video attached, Video Events are meant to contain all additional metadata concerning the subject media and to be surfaced in video-specific clients rather than general micro-blogging clients. The thought is for events of this kind to be referenced in a Netflix, YouTube, or TikTok like nostr client where the video itself is at the center of the experience. |
| 12 | 12 | ||
| @@ -6,11 +6,11 @@ Moderated Communities (Reddit Style) | |||
| 6 | 6 | ||
| 7 | `draft` `optional` | 7 | `draft` `optional` |
| 8 | 8 | ||
| 9 | The goal of this NIP is to create moderator-approved public communities around a topic. It defines the replaceable event `kind:34550` to define the community and the current list of moderators/administrators. Users that want to post into the community, simply tag any Nostr event with the community's `a` tag. Moderators issue an approval event `kind:4550` that links the community with the new post. | 9 | The goal of this NIP is to enable public communities. It defines the replaceable event `kind:34550` to define the community and the current list of moderators/administrators. Users that want to post into the community, simply tag any Nostr event with the community's `a` tag. Moderators may issue an approval event `kind:4550`. |
| 10 | 10 | ||
| 11 | # Community Definition | 11 | # Community Definition |
| 12 | 12 | ||
| 13 | `kind:34550` SHOULD include any field that helps define the community and the set of moderators. `relay` tags MAY be used to describe the preferred relay to download requests and approvals. | 13 | `Kind:34550` SHOULD include any field that helps define the community and the set of moderators. `relay` tags MAY be used to describe the preferred relay to download requests and approvals. A community definition event's `d` tag MAY double as its name, but if a `name` tag is provided, it SHOULD be displayed instead of the `d` tag. |
| 14 | 14 | ||
| 15 | ```jsonc | 15 | ```jsonc |
| 16 | { | 16 | { |
| @@ -18,6 +18,7 @@ The goal of this NIP is to create moderator-approved public communities around a | |||
| 18 | "kind": 34550, | 18 | "kind": 34550, |
| 19 | "tags": [ | 19 | "tags": [ |
| 20 | ["d", "<community-d-identifier>"], | 20 | ["d", "<community-d-identifier>"], |
| 21 | ["name", "<Community name>"], | ||
| 21 | ["description", "<Community description>"], | 22 | ["description", "<Community description>"], |
| 22 | ["image", "<Community image url>", "<Width>x<Height>"], | 23 | ["image", "<Community image url>", "<Width>x<Height>"], |
| 23 | 24 | ||
| @@ -38,9 +39,9 @@ The goal of this NIP is to create moderator-approved public communities around a | |||
| 38 | } | 39 | } |
| 39 | ``` | 40 | ``` |
| 40 | 41 | ||
| 41 | # New Post Request | 42 | # Posting to a community |
| 42 | 43 | ||
| 43 | Any Nostr event can be submitted to a community by anyone for approval. Clients MUST add the community's `a` tag to the new post event in order to be presented for the moderator's approval. | 44 | Any Nostr event can be posted to a community. Clients MUST add one or more community `a` tags, each with a recommended relay. |
| 44 | 45 | ||
| 45 | ```jsonc | 46 | ```jsonc |
| 46 | { | 47 | { |
| @@ -53,11 +54,15 @@ Any Nostr event can be submitted to a community by anyone for approval. Clients | |||
| 53 | } | 54 | } |
| 54 | ``` | 55 | ``` |
| 55 | 56 | ||
| 56 | Community management clients MAY filter all mentions to a given `kind:34550` event and request moderators to approve each submission. Moderators MAY delete his/her approval of a post at any time using event deletions (See [NIP-09](09.md)). | 57 | # Moderation |
| 57 | 58 | ||
| 58 | # Post Approval by moderators | 59 | Anyone may issue an approval event to express their opinion that a post is appropriate for a community. Clients MAY choose which approval events to honor, but SHOULD at least use ones published by the group's defined moderators. |
| 59 | 60 | ||
| 60 | The post-approval event MUST include `a` tags of the communities the moderator is posting into (one or more), the `e` tag of the post and `p` tag of the author of the post (for approval notifications). The event SHOULD also include the stringified `post request` event inside the `.content` ([NIP-18-style](18.md)) and a `k` tag with the original post's event kind to allow filtering of approved posts by kind. | 61 | An approval event MUST include one or more community `a` tags, an `e` or `a` tag pointing to the post, and the `p` tag of the author of the post (for approval notifications). `a` tag prefixes can be used to disambiguate between community and replaceable event pointers (community `a` tags always begin with `34550`). |
| 62 | |||
| 63 | The event SHOULD also include the JSON-stringified `post request` event inside the `.content`, and a `k` tag with the original post's event kind to allow filtering of approved posts by kind. | ||
| 64 | |||
| 65 | Moderators MAY request deletion of their approval of a post at any time using [NIP-09 event deletion requests](09.md). | ||
| 61 | 66 | ||
| 62 | ```jsonc | 67 | ```jsonc |
| 63 | { | 68 | { |
| @@ -76,26 +81,16 @@ The post-approval event MUST include `a` tags of the communities the moderator i | |||
| 76 | 81 | ||
| 77 | It's recommended that multiple moderators approve posts to avoid deleting them from the community when a moderator is removed from the owner's list. In case the full list of moderators must be rotated, the new moderator set must sign new approvals for posts in the past or the community will restart. The owner can also periodically copy and re-sign of each moderator's approval events to make sure posts don't disappear with moderators. | 82 | It's recommended that multiple moderators approve posts to avoid deleting them from the community when a moderator is removed from the owner's list. In case the full list of moderators must be rotated, the new moderator set must sign new approvals for posts in the past or the community will restart. The owner can also periodically copy and re-sign of each moderator's approval events to make sure posts don't disappear with moderators. |
| 78 | 83 | ||
| 79 | Post Approvals of replaceable events can be created in three ways: (i) by tagging the replaceable event as an `e` tag if moderators want to approve each individual change to the replaceable event; (ii) by tagging the replaceable event as an `a` tag if the moderator authorizes the replaceable event author to make changes without additional approvals and (iii) by tagging the replaceable event with both its `e` and `a` tag which empowers clients to display the original and updated versions of the event, with appropriate remarks in the UI. Since relays are instructed to delete old versions of a replaceable event, the `.content` of an `e`-approval MUST have the specific version of the event or Clients might not be able to find that version of the content anywhere. | 84 | Approvals of replaceable events can be created in three ways: |
| 80 | 85 | ||
| 81 | Clients SHOULD evaluate any non-`34550:*` `a` tag as posts to be included in all `34550:*` `a` tags. | 86 | 1. By tagging the replaceable event as an `e` tag if moderators want to approve each individual change to the replaceable event |
| 87 | 2. By tagging the replaceable event as an `a` tag if the moderator authorizes the replaceable event author to make changes without additional approvals and | ||
| 88 | 3. By tagging the replaceable event with both its `e` and `a` tag which empowers clients to display the original and updated versions of the event, with appropriate remarks in the UI. | ||
| 82 | 89 | ||
| 83 | # Displaying | 90 | Since relays are instructed to delete old versions of a replaceable event, the `content` of an approval using an `e` tag MUST have the specific version of the event or clients might not be able to find that version of the content anywhere. |
| 84 | 91 | ||
| 85 | Community clients SHOULD display posts that have been approved by at least 1 moderator or by the community owner. | 92 | Clients SHOULD evaluate any non-`34550:*` `a` tag as posts to be approved for all `34550:*` `a` tags. |
| 86 | 93 | ||
| 87 | The following filter displays the approved posts. | 94 | # Cross-posting |
| 88 | |||
| 89 | ```json | ||
| 90 | [ | ||
| 91 | "REQ", | ||
| 92 | "_", | ||
| 93 | { | ||
| 94 | "authors": ["<owner-pubkey>", "<moderator1-pubkey>", "<moderator2-pubkey>", "<moderator3-pubkey>", ...], | ||
| 95 | "kinds": [4550], | ||
| 96 | "#a": ["34550:<Community event author pubkey>:<d-identifier of the community>"], | ||
| 97 | } | ||
| 98 | ] | ||
| 99 | ``` | ||
| 100 | 95 | ||
| 101 | Clients MAY hide approvals by blocked moderators at the user's request. | 96 | Clients MAY support cross-posting between communities by posting a NIP 18 `kind 6` or `kind 16` repost to one or more communities using `a` tags as described above. The `content` of the repost MUST be the original event, not the approval event. |
| @@ -0,0 +1,48 @@ | |||
| 1 | NIP-73 | ||
| 2 | ====== | ||
| 3 | |||
| 4 | External Content IDs | ||
| 5 | ------------------------- | ||
| 6 | |||
| 7 | `draft` `optional` | ||
| 8 | |||
| 9 | There are certain established global content identifiers that would be useful to reference in nostr events so that clients can query all events assosiated with these ids. | ||
| 10 | |||
| 11 | - Book [ISBNs](https://en.wikipedia.org/wiki/ISBN) | ||
| 12 | - Podcast [GUIDs](https://podcastnamespace.org/tag/guid) | ||
| 13 | - Movie [ISANs](https://en.wikipedia.org/wiki/International_Standard_Audiovisual_Number) | ||
| 14 | |||
| 15 | Since the `i` tag is already used for similar references in kind-0 metadata events it makes sense to use it for these content ids as well. | ||
| 16 | |||
| 17 | |||
| 18 | ## Supported IDs | ||
| 19 | |||
| 20 | ### Books: | ||
| 21 | |||
| 22 | - Book ISBN: `["i", "isbn:9780765382030"]` - https://isbnsearch.org/isbn/9780765382030 | ||
| 23 | |||
| 24 | Book ISBNs MUST be referenced _**without hyphens**_ as many book search APIs return the ISBNs without hyphens. Removing hypens from ISBNs is trivial, whereas adding the hyphens back in is non-trivial requiring a library. | ||
| 25 | |||
| 26 | ### Podcasts: | ||
| 27 | |||
| 28 | - Podcast RSS Feed GUID: `["i", "podcast:guid:c90e609a-df1e-596a-bd5e-57bcc8aad6cc"]` - https://podcastindex.org/podcast/c90e609a-df1e-596a-bd5e-57bcc8aad6cc | ||
| 29 | - Podcast RSS Item GUID: `["i", "podcast:item:guid:d98d189b-dc7b-45b1-8720-d4b98690f31f"]` | ||
| 30 | - Podcast RSS Publisher GUID: `["i", "podcast:publisher:guid:18bcbf10-6701-4ffb-b255-bc057390d738"]` | ||
| 31 | |||
| 32 | ### Movies: | ||
| 33 | |||
| 34 | - Movie ISAN: `["i", "isan:0000-0000-401A-0000-7"]` - https://web.isan.org/public/en/isan/0000-0000-401A-0000-7 | ||
| 35 | |||
| 36 | Movie ISANs SHOULD be referenced _**without the version part**_ as the versions / edits of movies are not relevant. More info on ISAN parts here - https://support.isan.org/hc/en-us/articles/360002783131-Records-relations-and-hierarchies-in-the-ISAN-Registry | ||
| 37 | |||
| 38 | --- | ||
| 39 | |||
| 40 | ### Optional URL Hints | ||
| 41 | |||
| 42 | Each `i` tag MAY have a url hint as the second argument to redirect people to a website if the client isn't opinionated about how to interpret the id: | ||
| 43 | |||
| 44 | `["i", "podcast:item:guid:d98d189b-dc7b-45b1-8720-d4b98690f31f", https://fountain.fm/episode/z1y9TMQRuqXl2awyrQxg]` | ||
| 45 | |||
| 46 | `["i", "isan:0000-0000-401A-0000-7", https://www.imdb.com/title/tt0120737]` | ||
| 47 | |||
| 48 | |||
| @@ -53,11 +53,11 @@ The following tags are OPTIONAL. | |||
| 53 | } | 53 | } |
| 54 | ``` | 54 | ``` |
| 55 | 55 | ||
| 56 | The goal MAY include an `r` or `a` tag linking to a URL or parameterized replaceable event. | 56 | The goal MAY include an `r` or `a` tag linking to a URL or addressable event. |
| 57 | 57 | ||
| 58 | The goal MAY include multiple beneficiary pubkeys by specifying [`zap` tags](57.md#appendix-g-zap-tag-on-other-events). | 58 | The goal MAY include multiple beneficiary pubkeys by specifying [`zap` tags](57.md#appendix-g-zap-tag-on-other-events). |
| 59 | 59 | ||
| 60 | Parameterized replaceable events can link to a goal by using a `goal` tag specifying the event id and an optional relay hint. | 60 | Addressable events can link to a goal by using a `goal` tag specifying the event id and an optional relay hint. |
| 61 | 61 | ||
| 62 | ```json | 62 | ```json |
| 63 | { | 63 | { |
| @@ -12,7 +12,7 @@ Even though interoperability is great, some apps do not want or do not need inte | |||
| 12 | 12 | ||
| 13 | ## Nostr event | 13 | ## Nostr event |
| 14 | 14 | ||
| 15 | This NIP specifies the use of event kind `30078` (parameterized replaceable event) with a `d` tag containing some reference to the app name and context -- or any other arbitrary string. `content` and other `tags` can be anything or in any format. | 15 | This NIP specifies the use of event kind `30078` (an _addressable_ event) with a `d` tag containing some reference to the app name and context -- or any other arbitrary string. `content` and other `tags` can be anything or in any format. |
| 16 | 16 | ||
| 17 | ## Some use cases | 17 | ## Some use cases |
| 18 | 18 | ||
| @@ -301,7 +301,7 @@ Example Response: | |||
| 301 | // ...other metadata | 301 | // ...other metadata |
| 302 | ] | 302 | ] |
| 303 | "content": "haha funny meme", // caption | 303 | "content": "haha funny meme", // caption |
| 304 | "created_at": 1715691130 // upload timestmap | 304 | "created_at": 1715691130 // upload timestamp |
| 305 | }, | 305 | }, |
| 306 | ... | 306 | ... |
| 307 | ] | 307 | ] |
| @@ -6,11 +6,11 @@ Classified Listings | |||
| 6 | 6 | ||
| 7 | `draft` `optional` | 7 | `draft` `optional` |
| 8 | 8 | ||
| 9 | This NIP defines `kind:30402`: a parameterized replaceable event to describe classified listings that list any arbitrary product, service, or other thing for sale or offer and includes enough structured metadata to make them useful. | 9 | This NIP defines `kind:30402`: an addressable event to describe classified listings that list any arbitrary product, service, or other thing for sale or offer and includes enough structured metadata to make them useful. |
| 10 | 10 | ||
| 11 | The category of classifieds includes a very broad range of physical goods, services, work opportunities, rentals, free giveaways, personals, etc. and is distinct from the more strictly structured marketplaces defined in [NIP-15](https://github.com/nostr-protocol/nips/blob/master/15.md) that often sell many units of specific products through very specific channels. | 11 | The category of classifieds includes a very broad range of physical goods, services, work opportunities, rentals, free giveaways, personals, etc. and is distinct from the more strictly structured marketplaces defined in [NIP-15](15.md) that often sell many units of specific products through very specific channels. |
| 12 | 12 | ||
| 13 | The structure of these events is very similar to [NIP-23](https://github.com/nostr-protocol/nips/blob/master/23.md) long-form content events. | 13 | The structure of these events is very similar to [NIP-23](23.md) long-form content events. |
| 14 | 14 | ||
| 15 | ### Draft / Inactive Listings | 15 | ### Draft / Inactive Listings |
| 16 | 16 | ||
| @@ -26,8 +26,8 @@ The `.pubkey` field of these events are treated as the party creating the listin | |||
| 26 | 26 | ||
| 27 | ### Metadata | 27 | ### Metadata |
| 28 | 28 | ||
| 29 | - For "tags"/"hashtags" (i.e. categories or keywords of relevance for the listing) the `"t"` event tag should be used, as per [NIP-12](https://github.com/nostr-protocol/nips/blob/master/12.md). | 29 | - For "tags"/"hashtags" (i.e. categories or keywords of relevance for the listing) the `"t"` event tag should be used, as per [NIP-12](12.md). |
| 30 | - For images, whether included in the markdown content or not, clients SHOULD use `image` tags as described in [NIP-58](https://github.com/nostr-protocol/nips/blob/master/58.md). This allows clients to display images in carousel format more easily. | 30 | - For images, whether included in the markdown content or not, clients SHOULD use `image` tags as described in [NIP-58](58.md). This allows clients to display images in carousel format more easily. |
| 31 | 31 | ||
| 32 | The following tags, used for structured metadata, are standardized and SHOULD be included. Other tags may be added as necessary. | 32 | The following tags, used for structured metadata, are standardized and SHOULD be included. Other tags may be added as necessary. |
| 33 | 33 | ||
diff --git a/BREAKING.md b/BREAKING.md index c8255cd..83b104b 100644 --- a/BREAKING.md +++ b/BREAKING.md | |||
| @@ -5,6 +5,11 @@ reverse chronological order. | |||
| 5 | 5 | ||
| 6 | | Date | Commit | NIP | Change | | 6 | | Date | Commit | NIP | Change | |
| 7 | | ----------- | --------- | -------- | ------ | | 7 | | ----------- | --------- | -------- | ------ | |
| 8 | | 2024-08-18 | [3aff37bd](https://github.com/nostr-protocol/nips/commit/3aff37bd) | [NIP-54](54.md) | content should be Asciidoc | | ||
| 9 | | 2024-07-31 | [3ea2f1a4](https://github.com/nostr-protocol/nips/commit/3ea2f1a4) | [NIP-45](45.md) | [444ad28d](https://github.com/nostr-protocol/nips/commit/444ad28d) was reverted | | ||
| 10 | | 2024-07-30 | [444ad28d](https://github.com/nostr-protocol/nips/commit/444ad28d) | [NIP-45](45.md) | NIP-45 was deprecated | | ||
| 11 | | 2024-07-26 | [ecee40df](https://github.com/nostr-protocol/nips/commit/ecee40df) | [NIP-19](19.md) | `nrelay` was deprecated | | ||
| 12 | | 2024-07-23 | [0227a2cd](https://github.com/nostr-protocol/nips/commit/0227a2cd) | [NIP-01](01.md) | events should be sorted by id after created_at | | ||
| 8 | | 2024-06-06 | [58e94b20](https://github.com/nostr-protocol/nips/commit/58e94b20) | [NIP-25](25.md) | [8073c848](https://github.com/nostr-protocol/nips/commit/8073c848) was reverted | | 13 | | 2024-06-06 | [58e94b20](https://github.com/nostr-protocol/nips/commit/58e94b20) | [NIP-25](25.md) | [8073c848](https://github.com/nostr-protocol/nips/commit/8073c848) was reverted | |
| 9 | | 2024-06-06 | [a6dfc7b5](https://github.com/nostr-protocol/nips/commit/a6dfc7b5) | [NIP-55](55.md) | NIP number was changed | | 14 | | 2024-06-06 | [a6dfc7b5](https://github.com/nostr-protocol/nips/commit/a6dfc7b5) | [NIP-55](55.md) | NIP number was changed | |
| 10 | | 2024-05-25 | [5d1d1c17](https://github.com/nostr-protocol/nips/commit/5d1d1c17) | [NIP-71](71.md) | 'aes-256-gcm' tag was removed | | 15 | | 2024-05-25 | [5d1d1c17](https://github.com/nostr-protocol/nips/commit/5d1d1c17) | [NIP-71](71.md) | 'aes-256-gcm' tag was removed | |
| @@ -43,6 +48,7 @@ reverse chronological order. | |||
| 43 | | 2023-06-18 | [83cbd3e1](https://github.com/nostr-protocol/nips/commit/83cbd3e1) | [NIP-11](11.md) | 'image' was renamed to 'icon' | | 48 | | 2023-06-18 | [83cbd3e1](https://github.com/nostr-protocol/nips/commit/83cbd3e1) | [NIP-11](11.md) | 'image' was renamed to 'icon' | |
| 44 | | 2023-04-13 | [bf0a0da6](https://github.com/nostr-protocol/nips/commit/bf0a0da6) | [NIP-15](15.md) | different NIP was re-added as NIP-15 | | 49 | | 2023-04-13 | [bf0a0da6](https://github.com/nostr-protocol/nips/commit/bf0a0da6) | [NIP-15](15.md) | different NIP was re-added as NIP-15 | |
| 45 | | 2023-04-09 | [fb5b7c73](https://github.com/nostr-protocol/nips/commit/fb5b7c73) | [NIP-15](15.md) | NIP-15 was merged into NIP-01 | | 50 | | 2023-04-09 | [fb5b7c73](https://github.com/nostr-protocol/nips/commit/fb5b7c73) | [NIP-15](15.md) | NIP-15 was merged into NIP-01 | |
| 51 | | 2023-03-29 | [599e1313](https://github.com/nostr-protocol/nips/commit/599e1313) | [NIP-18](18.md) | NIP-18 was bring back | | ||
| 46 | | 2023-03-15 | [e1004d3d](https://github.com/nostr-protocol/nips/commit/e1004d3d) | [NIP-19](19.md) | `1: relay` was changed to optionally | | 52 | | 2023-03-15 | [e1004d3d](https://github.com/nostr-protocol/nips/commit/e1004d3d) | [NIP-19](19.md) | `1: relay` was changed to optionally | |
| 47 | 53 | ||
| 48 | Breaking changes prior to 2023-03-01 are not yet documented. | 54 | Breaking changes prior to 2023-03-01 are not yet documented. |
| @@ -30,7 +30,7 @@ They exist to document what may be implemented by [Nostr](https://github.com/nos | |||
| 30 | - [NIP-06: Basic key derivation from mnemonic seed phrase](06.md) | 30 | - [NIP-06: Basic key derivation from mnemonic seed phrase](06.md) |
| 31 | - [NIP-07: `window.nostr` capability for web browsers](07.md) | 31 | - [NIP-07: `window.nostr` capability for web browsers](07.md) |
| 32 | - [NIP-08: Handling Mentions](08.md) --- **unrecommended**: deprecated in favor of [NIP-27](27.md) | 32 | - [NIP-08: Handling Mentions](08.md) --- **unrecommended**: deprecated in favor of [NIP-27](27.md) |
| 33 | - [NIP-09: Event Deletion](09.md) | 33 | - [NIP-09: Event Deletion Request](09.md) |
| 34 | - [NIP-10: Conventions for clients' use of `e` and `p` tags in text events](10.md) | 34 | - [NIP-10: Conventions for clients' use of `e` and `p` tags in text events](10.md) |
| 35 | - [NIP-11: Relay Information Document](11.md) | 35 | - [NIP-11: Relay Information Document](11.md) |
| 36 | - [NIP-13: Proof of Work](13.md) | 36 | - [NIP-13: Proof of Work](13.md) |
| @@ -73,9 +73,12 @@ They exist to document what may be implemented by [Nostr](https://github.com/nos | |||
| 73 | - [NIP-57: Lightning Zaps](57.md) | 73 | - [NIP-57: Lightning Zaps](57.md) |
| 74 | - [NIP-58: Badges](58.md) | 74 | - [NIP-58: Badges](58.md) |
| 75 | - [NIP-59: Gift Wrap](59.md) | 75 | - [NIP-59: Gift Wrap](59.md) |
| 76 | - [NIP-64: Chess (PGN)](64.md) | ||
| 76 | - [NIP-65: Relay List Metadata](65.md) | 77 | - [NIP-65: Relay List Metadata](65.md) |
| 78 | - [NIP-70: Protected Events](70.md) | ||
| 77 | - [NIP-71: Video Events](71.md) | 79 | - [NIP-71: Video Events](71.md) |
| 78 | - [NIP-72: Moderated Communities](72.md) | 80 | - [NIP-72: Moderated Communities](72.md) |
| 81 | - [NIP-73: External Content IDs](73.md) | ||
| 79 | - [NIP-75: Zap Goals](75.md) | 82 | - [NIP-75: Zap Goals](75.md) |
| 80 | - [NIP-78: Application-specific data](78.md) | 83 | - [NIP-78: Application-specific data](78.md) |
| 81 | - [NIP-84: Highlights](84.md) | 84 | - [NIP-84: Highlights](84.md) |
| @@ -88,112 +91,116 @@ They exist to document what may be implemented by [Nostr](https://github.com/nos | |||
| 88 | - [NIP-99: Classified Listings](99.md) | 91 | - [NIP-99: Classified Listings](99.md) |
| 89 | 92 | ||
| 90 | ## Event Kinds | 93 | ## Event Kinds |
| 91 | | kind | description | NIP | | 94 | |
| 92 | | ------------- | -------------------------- | ------------------------ | | 95 | | kind | description | NIP | |
| 93 | | `0` | User Metadata | [01](01.md) | | 96 | | ------------- | ------------------------------- | -------------------------------------- | |
| 94 | | `1` | Short Text Note | [01](01.md) | | 97 | | `0` | User Metadata | [01](01.md) | |
| 95 | | `2` | Recommend Relay | 01 (deprecated) | | 98 | | `1` | Short Text Note | [01](01.md) | |
| 96 | | `3` | Follows | [02](02.md) | | 99 | | `2` | Recommend Relay | 01 (deprecated) | |
| 97 | | `4` | Encrypted Direct Messages | [04](04.md) | | 100 | | `3` | Follows | [02](02.md) | |
| 98 | | `5` | Event Deletion | [09](09.md) | | 101 | | `4` | Encrypted Direct Messages | [04](04.md) | |
| 99 | | `6` | Repost | [18](18.md) | | 102 | | `5` | Event Deletion Request | [09](09.md) | |
| 100 | | `7` | Reaction | [25](25.md) | | 103 | | `6` | Repost | [18](18.md) | |
| 101 | | `8` | Badge Award | [58](58.md) | | 104 | | `7` | Reaction | [25](25.md) | |
| 102 | | `9` | Group Chat Message | [29](29.md) | | 105 | | `8` | Badge Award | [58](58.md) | |
| 103 | | `10` | Group Chat Threaded Reply | [29](29.md) | | 106 | | `9` | Group Chat Message | [29](29.md) | |
| 104 | | `11` | Group Thread | [29](29.md) | | 107 | | `10` | Group Chat Threaded Reply | [29](29.md) | |
| 105 | | `12` | Group Thread Reply | [29](29.md) | | 108 | | `11` | Group Thread | [29](29.md) | |
| 106 | | `13` | Seal | [59](59.md) | | 109 | | `12` | Group Thread Reply | [29](29.md) | |
| 107 | | `14` | Direct Message | [17](17.md) | | 110 | | `13` | Seal | [59](59.md) | |
| 108 | | `16` | Generic Repost | [18](18.md) | | 111 | | `14` | Direct Message | [17](17.md) | |
| 109 | | `40` | Channel Creation | [28](28.md) | | 112 | | `16` | Generic Repost | [18](18.md) | |
| 110 | | `41` | Channel Metadata | [28](28.md) | | 113 | | `17` | Reaction to a website | [25](25.md) | |
| 111 | | `42` | Channel Message | [28](28.md) | | 114 | | `40` | Channel Creation | [28](28.md) | |
| 112 | | `43` | Channel Hide Message | [28](28.md) | | 115 | | `41` | Channel Metadata | [28](28.md) | |
| 113 | | `44` | Channel Mute User | [28](28.md) | | 116 | | `42` | Channel Message | [28](28.md) | |
| 114 | | `818` | Merge Requests | [54](54.md) | | 117 | | `43` | Channel Hide Message | [28](28.md) | |
| 115 | | `1021` | Bid | [15](15.md) | | 118 | | `44` | Channel Mute User | [28](28.md) | |
| 116 | | `1022` | Bid confirmation | [15](15.md) | | 119 | | `64` | Chess (PGN) | [64](64.md) | |
| 117 | | `1040` | OpenTimestamps | [03](03.md) | | 120 | | `818` | Merge Requests | [54](54.md) | |
| 118 | | `1059` | Gift Wrap | [59](59.md) | | 121 | | `1021` | Bid | [15](15.md) | |
| 119 | | `1063` | File Metadata | [94](94.md) | | 122 | | `1022` | Bid confirmation | [15](15.md) | |
| 120 | | `1311` | Live Chat Message | [53](53.md) | | 123 | | `1040` | OpenTimestamps | [03](03.md) | |
| 121 | | `1617` | Patches | [34](34.md) | | 124 | | `1059` | Gift Wrap | [59](59.md) | |
| 122 | | `1621` | Issues | [34](34.md) | | 125 | | `1063` | File Metadata | [94](94.md) | |
| 123 | | `1622` | Replies | [34](34.md) | | 126 | | `1311` | Live Chat Message | [53](53.md) | |
| 124 | | `1630`-`1633` | Status | [34](34.md) | | 127 | | `1617` | Patches | [34](34.md) | |
| 125 | | `1971` | Problem Tracker | [nostrocket][nostrocket] | | 128 | | `1621` | Issues | [34](34.md) | |
| 126 | | `1984` | Reporting | [56](56.md) | | 129 | | `1622` | Replies | [34](34.md) | |
| 127 | | `1985` | Label | [32](32.md) | | 130 | | `1630`-`1633` | Status | [34](34.md) | |
| 128 | | `2003` | Torrent | [35](35.md) | | 131 | | `1971` | Problem Tracker | [nostrocket][nostrocket] | |
| 129 | | `2004` | Torrent Comment | [35](35.md) | | 132 | | `1984` | Reporting | [56](56.md) | |
| 130 | | `2022` | Coinjoin Pool | [joinstr][joinstr] | | 133 | | `1985` | Label | [32](32.md) | |
| 131 | | `4550` | Community Post Approval | [72](72.md) | | 134 | | `2003` | Torrent | [35](35.md) | |
| 132 | | `5000`-`5999` | Job Request | [90](90.md) | | 135 | | `2004` | Torrent Comment | [35](35.md) | |
| 133 | | `6000`-`6999` | Job Result | [90](90.md) | | 136 | | `2022` | Coinjoin Pool | [joinstr][joinstr] | |
| 134 | | `7000` | Job Feedback | [90](90.md) | | 137 | | `4550` | Community Post Approval | [72](72.md) | |
| 135 | | `9000`-`9030` | Group Control Events | [29](29.md) | | 138 | | `5000`-`5999` | Job Request | [90](90.md) | |
| 136 | | `9041` | Zap Goal | [75](75.md) | | 139 | | `6000`-`6999` | Job Result | [90](90.md) | |
| 137 | | `9734` | Zap Request | [57](57.md) | | 140 | | `7000` | Job Feedback | [90](90.md) | |
| 138 | | `9735` | Zap | [57](57.md) | | 141 | | `9000`-`9030` | Group Control Events | [29](29.md) | |
| 139 | | `9802` | Highlights | [84](84.md) | | 142 | | `9041` | Zap Goal | [75](75.md) | |
| 140 | | `10000` | Mute list | [51](51.md) | | 143 | | `9734` | Zap Request | [57](57.md) | |
| 141 | | `10001` | Pin list | [51](51.md) | | 144 | | `9735` | Zap | [57](57.md) | |
| 142 | | `10002` | Relay List Metadata | [65](65.md) | | 145 | | `9802` | Highlights | [84](84.md) | |
| 143 | | `10003` | Bookmark list | [51](51.md) | | 146 | | `10000` | Mute list | [51](51.md) | |
| 144 | | `10004` | Communities list | [51](51.md) | | 147 | | `10001` | Pin list | [51](51.md) | |
| 145 | | `10005` | Public chats list | [51](51.md) | | 148 | | `10002` | Relay List Metadata | [65](65.md) | |
| 146 | | `10006` | Blocked relays list | [51](51.md) | | 149 | | `10003` | Bookmark list | [51](51.md) | |
| 147 | | `10007` | Search relays list | [51](51.md) | | 150 | | `10004` | Communities list | [51](51.md) | |
| 148 | | `10009` | User groups | [51](51.md), [29](29.md) | | 151 | | `10005` | Public chats list | [51](51.md) | |
| 149 | | `10015` | Interests list | [51](51.md) | | 152 | | `10006` | Blocked relays list | [51](51.md) | |
| 150 | | `10030` | User emoji list | [51](51.md) | | 153 | | `10007` | Search relays list | [51](51.md) | |
| 151 | | `10050` | Relay list to receive DMs | [17](17.md) | | 154 | | `10009` | User groups | [51](51.md), [29](29.md) | |
| 152 | | `10096` | File storage server list | [96](96.md) | | 155 | | `10015` | Interests list | [51](51.md) | |
| 153 | | `13194` | Wallet Info | [47](47.md) | | 156 | | `10030` | User emoji list | [51](51.md) | |
| 154 | | `21000` | Lightning Pub RPC | [Lightning.Pub][lnpub] | | 157 | | `10050` | Relay list to receive DMs | [51](51.md), [17](17.md) | |
| 155 | | `22242` | Client Authentication | [42](42.md) | | 158 | | `10096` | File storage server list | [96](96.md) | |
| 156 | | `23194` | Wallet Request | [47](47.md) | | 159 | | `13194` | Wallet Info | [47](47.md) | |
| 157 | | `23195` | Wallet Response | [47](47.md) | | 160 | | `21000` | Lightning Pub RPC | [Lightning.Pub][lnpub] | |
| 158 | | `24133` | Nostr Connect | [46](46.md) | | 161 | | `22242` | Client Authentication | [42](42.md) | |
| 159 | | `27235` | HTTP Auth | [98](98.md) | | 162 | | `23194` | Wallet Request | [47](47.md) | |
| 160 | | `30000` | Follow sets | [51](51.md) | | 163 | | `23195` | Wallet Response | [47](47.md) | |
| 161 | | `30001` | Generic lists | [51](51.md) | | 164 | | `24133` | Nostr Connect | [46](46.md) | |
| 162 | | `30002` | Relay sets | [51](51.md) | | 165 | | `27235` | HTTP Auth | [98](98.md) | |
| 163 | | `30003` | Bookmark sets | [51](51.md) | | 166 | | `30000` | Follow sets | [51](51.md) | |
| 164 | | `30004` | Curation sets | [51](51.md) | | 167 | | `30001` | Generic lists | [51](51.md) | |
| 165 | | `30005` | Video sets | [51](51.md) | | 168 | | `30002` | Relay sets | [51](51.md) | |
| 166 | | `30008` | Profile Badges | [58](58.md) | | 169 | | `30003` | Bookmark sets | [51](51.md) | |
| 167 | | `30009` | Badge Definition | [58](58.md) | | 170 | | `30004` | Curation sets | [51](51.md) | |
| 168 | | `30015` | Interest sets | [51](51.md) | | 171 | | `30005` | Video sets | [51](51.md) | |
| 169 | | `30017` | Create or update a stall | [15](15.md) | | 172 | | `30008` | Profile Badges | [58](58.md) | |
| 170 | | `30018` | Create or update a product | [15](15.md) | | 173 | | `30009` | Badge Definition | [58](58.md) | |
| 171 | | `30019` | Marketplace UI/UX | [15](15.md) | | 174 | | `30015` | Interest sets | [51](51.md) | |
| 172 | | `30020` | Product sold as an auction | [15](15.md) | | 175 | | `30017` | Create or update a stall | [15](15.md) | |
| 173 | | `30023` | Long-form Content | [23](23.md) | | 176 | | `30018` | Create or update a product | [15](15.md) | |
| 174 | | `30024` | Draft Long-form Content | [23](23.md) | | 177 | | `30019` | Marketplace UI/UX | [15](15.md) | |
| 175 | | `30030` | Emoji sets | [51](51.md) | | 178 | | `30020` | Product sold as an auction | [15](15.md) | |
| 176 | | `30063` | Release artifact sets | [51](51.md) | | 179 | | `30023` | Long-form Content | [23](23.md) | |
| 177 | | `30078` | Application-specific Data | [78](78.md) | | 180 | | `30024` | Draft Long-form Content | [23](23.md) | |
| 178 | | `30311` | Live Event | [53](53.md) | | 181 | | `30030` | Emoji sets | [51](51.md) | |
| 179 | | `30315` | User Statuses | [38](38.md) | | 182 | | `30063` | Release artifact sets | [51](51.md) | |
| 180 | | `30402` | Classified Listing | [99](99.md) | | 183 | | `30078` | Application-specific Data | [78](78.md) | |
| 181 | | `30403` | Draft Classified Listing | [99](99.md) | | 184 | | `30311` | Live Event | [53](53.md) | |
| 182 | | `30617` | Repository announcements | [34](34.md) | | 185 | | `30315` | User Statuses | [38](38.md) | |
| 183 | | `30818` | Wiki article | [54](54.md) | | 186 | | `30402` | Classified Listing | [99](99.md) | |
| 184 | | `30819` | Redirects | [54](54.md) | | 187 | | `30403` | Draft Classified Listing | [99](99.md) | |
| 185 | | `31890` | Feed | [NUD: Custom Feeds](https://wikifreedia.xyz/cip-01/97c70a44366a6535c1) | | 188 | | `30617` | Repository announcements | [34](34.md) | |
| 186 | | `31922` | Date-Based Calendar Event | [52](52.md) | | 189 | | `30618` | Repository state announcements | [34](34.md) | |
| 187 | | `31923` | Time-Based Calendar Event | [52](52.md) | | 190 | | `30818` | Wiki article | [54](54.md) | |
| 188 | | `31924` | Calendar | [52](52.md) | | 191 | | `30819` | Redirects | [54](54.md) | |
| 189 | | `31925` | Calendar Event RSVP | [52](52.md) | | 192 | | `31890` | Feed | [NUD: Custom Feeds][NUD: Custom Feeds] | |
| 190 | | `31989` | Handler recommendation | [89](89.md) | | 193 | | `31922` | Date-Based Calendar Event | [52](52.md) | |
| 191 | | `31990` | Handler information | [89](89.md) | | 194 | | `31923` | Time-Based Calendar Event | [52](52.md) | |
| 192 | | `34235` | Video Event | [71](71.md) | | 195 | | `31924` | Calendar | [52](52.md) | |
| 193 | | `34236` | Short-form Portrait Video Event | [71](71.md) | | 196 | | `31925` | Calendar Event RSVP | [52](52.md) | |
| 194 | | `34237` | Video View Event | [71](71.md) | | 197 | | `31989` | Handler recommendation | [89](89.md) | |
| 195 | | `34550` | Community Definition | [72](72.md) | | 198 | | `31990` | Handler information | [89](89.md) | |
| 196 | | `39000-9` | Group metadata events | [29](29.md) | | 199 | | `34235` | Video Event | [71](71.md) | |
| 200 | | `34236` | Short-form Portrait Video Event | [71](71.md) | | ||
| 201 | | `34237` | Video View Event | [71](71.md) | | ||
| 202 | | `34550` | Community Definition | [72](72.md) | | ||
| 203 | | `39000-9` | Group metadata events | [29](29.md) | | ||
| 197 | 204 | ||
| 198 | [NUD: Custom Feeds]: https://wikifreedia.xyz/cip-01/97c70a44366a6535c1 | 205 | [NUD: Custom Feeds]: https://wikifreedia.xyz/cip-01/97c70a44366a6535c1 |
| 199 | [nostrocket]: https://github.com/nostrocket/NIPS/blob/main/Problems.md | 206 | [nostrocket]: https://github.com/nostrocket/NIPS/blob/main/Problems.md |
| @@ -232,16 +239,18 @@ They exist to document what may be implemented by [Nostr](https://github.com/nos | |||
| 232 | | `p` | pubkey (hex) | relay URL, petname | [01](01.md), [02](02.md) | | 239 | | `p` | pubkey (hex) | relay URL, petname | [01](01.md), [02](02.md) | |
| 233 | | `a` | coordinates to an event | relay URL | [01](01.md) | | 240 | | `a` | coordinates to an event | relay URL | [01](01.md) | |
| 234 | | `d` | identifier | -- | [01](01.md) | | 241 | | `d` | identifier | -- | [01](01.md) | |
| 242 | | `-` | -- | -- | [70](70.md) | | ||
| 235 | | `g` | geohash | -- | [52](52.md) | | 243 | | `g` | geohash | -- | [52](52.md) | |
| 236 | | `i` | identity | proof | [39](39.md) | | 244 | | `h` | group id | -- | [29](29.md) | |
| 245 | | `i` | external identity | proof, url hint | [39](39.md), [73](73.md) | | ||
| 237 | | `k` | kind number (string) | -- | [18](18.md), [25](25.md), [72](72.md) | | 246 | | `k` | kind number (string) | -- | [18](18.md), [25](25.md), [72](72.md) | |
| 238 | | `l` | label, label namespace | -- | [32](32.md) | | 247 | | `l` | label, label namespace | -- | [32](32.md) | |
| 239 | | `L` | label namespace | -- | [32](32.md) | | 248 | | `L` | label namespace | -- | [32](32.md) | |
| 240 | | `m` | MIME type | -- | [94](94.md) | | 249 | | `m` | MIME type | -- | [94](94.md) | |
| 241 | | `q` | event id (hex) | relay URL | [18](18.md) | | 250 | | `q` | event id (hex) | relay URL | [18](18.md) | |
| 242 | | `r` | a reference (URL, etc) | petname | [24](24.md) | | 251 | | `r` | a reference (URL, etc) | -- | [24](24.md), [25](25.md) | |
| 243 | | `r` | relay url | marker | [65](65.md) | | 252 | | `r` | relay url | marker | [65](65.md) | |
| 244 | | `t` | hashtag | -- | | | 253 | | `t` | hashtag | -- | [24](24.md) | |
| 245 | | `alt` | summary | -- | [31](31.md) | | 254 | | `alt` | summary | -- | [31](31.md) | |
| 246 | | `amount` | millisatoshis, stringified | -- | [57](57.md) | | 255 | | `amount` | millisatoshis, stringified | -- | [57](57.md) | |
| 247 | | `bolt11` | `bolt11` invoice | -- | [57](57.md) | | 256 | | `bolt11` | `bolt11` invoice | -- | [57](57.md) | |
| @@ -255,11 +264,11 @@ They exist to document what may be implemented by [Nostr](https://github.com/nos | |||
| 255 | | `encrypted` | -- | -- | [90](90.md) | | 264 | | `encrypted` | -- | -- | [90](90.md) | |
| 256 | | `expiration` | unix timestamp (string) | -- | [40](40.md) | | 265 | | `expiration` | unix timestamp (string) | -- | [40](40.md) | |
| 257 | | `goal` | event id (hex) | relay URL | [75](75.md) | | 266 | | `goal` | event id (hex) | relay URL | [75](75.md) | |
| 258 | | `image` | image URL | dimensions in pixels | [23](23.md), [58](58.md) | | 267 | | `image` | image URL | dimensions in pixels | [23](23.md), [52](52.md), [58](58.md) | |
| 259 | | `imeta` | inline metadata | -- | [92](92.md) | | 268 | | `imeta` | inline metadata | -- | [92](92.md) | |
| 260 | | `lnurl` | `bech32` encoded `lnurl` | -- | [57](57.md) | | 269 | | `lnurl` | `bech32` encoded `lnurl` | -- | [57](57.md) | |
| 261 | | `location` | location string | -- | [52](52.md), [99](99.md) | | 270 | | `location` | location string | -- | [52](52.md), [99](99.md) | |
| 262 | | `name` | name | -- | [34](34.md), [58](58.md) | | 271 | | `name` | name | -- | [34](34.md), [58](58.md), [72](72.md) | |
| 263 | | `nonce` | random | difficulty | [13](13.md) | | 272 | | `nonce` | random | difficulty | [13](13.md) | |
| 264 | | `preimage` | hash of `bolt11` invoice | -- | [57](57.md) | | 273 | | `preimage` | hash of `bolt11` invoice | -- | [57](57.md) | |
| 265 | | `price` | price | currency, frequency | [99](99.md) | | 274 | | `price` | price | currency, frequency | [99](99.md) | |
| @@ -269,7 +278,7 @@ They exist to document what may be implemented by [Nostr](https://github.com/nos | |||
| 269 | | `relays` | relay list | -- | [57](57.md) | | 278 | | `relays` | relay list | -- | [57](57.md) | |
| 270 | | `server` | file storage server url | -- | [96](96.md) | | 279 | | `server` | file storage server url | -- | [96](96.md) | |
| 271 | | `subject` | subject | -- | [14](14.md), [17](17.md) | | 280 | | `subject` | subject | -- | [14](14.md), [17](17.md) | |
| 272 | | `summary` | article summary | -- | [23](23.md) | | 281 | | `summary` | summary | -- | [23](23.md), [52](52.md) | |
| 273 | | `thumb` | badge thumbnail | dimensions in pixels | [58](58.md) | | 282 | | `thumb` | badge thumbnail | dimensions in pixels | [58](58.md) | |
| 274 | | `title` | article title | -- | [23](23.md) | | 283 | | `title` | article title | -- | [23](23.md) | |
| 275 | | `web` | webpage URL | -- | [34](34.md) | | 284 | | `web` | webpage URL | -- | [34](34.md) | |