mirror of
https://github.com/versia-pub/docs.git
synced 2025-12-06 22:38:19 +01:00
feat: ✨ Add Interaction Controls Extension
This commit is contained in:
parent
9ad9436845
commit
1d375491d1
|
|
@ -21,6 +21,7 @@ This page lists changes since Working Draft 3. {{ className: 'lead' }}
|
||||||
- Switched from ISO 8601 to [RFC 3339](https://datatracker.ietf.org/doc/html/rfc3339) for timestamps.
|
- Switched from ISO 8601 to [RFC 3339](https://datatracker.ietf.org/doc/html/rfc3339) for timestamps.
|
||||||
- In most cases, the two are interchangeable, but RFC 3339 is more strict. Most implementations should not need to change anything.
|
- In most cases, the two are interchangeable, but RFC 3339 is more strict. Most implementations should not need to change anything.
|
||||||
- Add optional `$schema` field to [Entities](/entities).
|
- Add optional `$schema` field to [Entities](/entities).
|
||||||
|
- Added [Interaction Controls Extensions](/extensions/interaction-controls)
|
||||||
|
|
||||||
## Since WD 3
|
## Since WD 3
|
||||||
|
|
||||||
|
|
|
||||||
108
app/extensions/interaction-controls/page.mdx
Normal file
108
app/extensions/interaction-controls/page.mdx
Normal file
|
|
@ -0,0 +1,108 @@
|
||||||
|
export const metadata = {
|
||||||
|
title: "Interaction Controls Extension",
|
||||||
|
description: "Allows users to control who can interact with their Notes"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Interaction Controls
|
||||||
|
|
||||||
|
Often, it is desirable to post a Note, but control who is allowed to interact with it (e.g. send replies, like, dislike, etc.). This has traditionally not been possible in most federated networks: the Interaction Controls extension adds this possibility.
|
||||||
|
|
||||||
|
## Usage
|
||||||
|
|
||||||
|
The entity defined in this document must be inserted in the `pub.versia:interaction_controls` key of a [Note](/entities/note)'s extensions field.
|
||||||
|
|
||||||
|
```jsonc {{ title: "Example Usage" }}
|
||||||
|
{
|
||||||
|
"id": "456df8ed-daf1-4062-abab-491071c7b8dd",
|
||||||
|
"type": "Note",
|
||||||
|
"uri": "https://versia.social/notes/456df8ed-daf1-4062-abab-491071c7b8dd",
|
||||||
|
"created_at": "2024-04-09T01:38:51.743Z",
|
||||||
|
"content": {
|
||||||
|
"text/plain": {
|
||||||
|
"content": "Hello, world :happy_face:!"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"extensions": { // [!code focus:9]
|
||||||
|
"pub.versia:interaction_controls": {
|
||||||
|
"reply": {
|
||||||
|
"allowed": ["followers"],
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
## Entity Definition
|
||||||
|
|
||||||
|
<Row>
|
||||||
|
<Col>
|
||||||
|
<Properties>
|
||||||
|
<Property name="interaction_type">
|
||||||
|
Describes permissions for a specific interaction.
|
||||||
|
|
||||||
|
```typescript
|
||||||
|
type InteractionGroup = |
|
||||||
|
"everyone" |
|
||||||
|
"followers" |
|
||||||
|
"followed" |
|
||||||
|
"group" |
|
||||||
|
"mutuals";
|
||||||
|
|
||||||
|
type InteractionPermissions = {
|
||||||
|
allowed?: InteractionGroup[];
|
||||||
|
disallowed?: InteractionGroup[];
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Permissions can either be whitelist (`allowed` property) or blacklist (`disallowed` property). Both options are mutually exclusive.
|
||||||
|
|
||||||
|
In order of priority:
|
||||||
|
- `everyone`: Includes every single User in the federation.
|
||||||
|
- `followers`: Includes every follower of the author.
|
||||||
|
- `following`: Includes every User that the author follows.
|
||||||
|
- `mutuals`: Includes every mutual of the author (that is, every User that is both a follower and followed by the author).
|
||||||
|
- `group`: Includes every User in the [Group](/entities/group) that this Note was posted to, if any. If Note is not posted to a [Group](/entities/group), this value has no effect.
|
||||||
|
|
||||||
|
Permission groups are evaluated from highest to lowest priority: if two groups conflict each other, the group with the highest priority must be used.
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
</Col>
|
||||||
|
|
||||||
|
<Col sticky>
|
||||||
|
```jsonc {{ title: "Example"}}
|
||||||
|
{
|
||||||
|
"reply": {
|
||||||
|
"allowed": [
|
||||||
|
"group"
|
||||||
|
],
|
||||||
|
},
|
||||||
|
"pub.versia:likes#Like": {
|
||||||
|
"disallowed": [
|
||||||
|
"everyone"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
</Col>
|
||||||
|
</Row>
|
||||||
|
|
||||||
|
## Usage
|
||||||
|
|
||||||
|
### Interaction Types
|
||||||
|
|
||||||
|
The following interaction types are defined as part of the core Versia spec:
|
||||||
|
|
||||||
|
- `reply`: Sending a Note with `replies_to` including this Note.
|
||||||
|
- `quote`: Sending a Note with `quotes` including this Note.
|
||||||
|
|
||||||
|
Extensions **may** choose to register their own interaction types (such as `pub.versia:likes#Like` for the [Like Extension](/extensions/likes)). The naming scheme for interaction types is identical to [Extensions](/extensions)'s `type` property, but with a hashtag (`#`) in place of a forward slash (`/`).
|
||||||
|
|
||||||
|
### Handling Permission Errors
|
||||||
|
|
||||||
|
Implementations that find a user attempting to create an interaction they are not allowed to **MUST** return a `403 Forbidden` HTTP status code when processing the Note during federation. The Note **must** also be discarded.
|
||||||
|
|
||||||
|
It is important for implementations to backfill any related [Collections](/structures/collection) (e.g. user followers) in order to not incorrectly reject Notes based off of outdated data.
|
||||||
|
|
||||||
|
<Note>
|
||||||
|
To avoid server load from constant Collection refreshing, implementations **could** only refetch associated Collections when forbidden interactions are detected, then recalculate permissions again.
|
||||||
|
</Note>
|
||||||
|
|
@ -105,3 +105,14 @@ The Likes extension adds the following collections to the [User](/entities/user)
|
||||||
"pub.versia:likes/Dislikes": "https://example.com/users/6e0204a2-746c-4972-8602-c4f37fc63bbe/dislikes"
|
"pub.versia:likes/Dislikes": "https://example.com/users/6e0204a2-746c-4972-8602-c4f37fc63bbe/dislikes"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
## Interaction Types
|
||||||
|
|
||||||
|
<Note>
|
||||||
|
This section only applies to implementors of the [Interaction Controls Extension](/extensions/interaction-controls).
|
||||||
|
</Note>
|
||||||
|
|
||||||
|
This extension registers the following interaction types:
|
||||||
|
- `pub.versia:likes#Like`, for liking a Note
|
||||||
|
- `pub.versia:likes#Dislike`, for disliking a Note
|
||||||
|
|
@ -295,6 +295,10 @@ export const navigation: NavGroup[] = [
|
||||||
title: "Instance Messaging",
|
title: "Instance Messaging",
|
||||||
href: "/extensions/instance-messaging",
|
href: "/extensions/instance-messaging",
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
title: "Interaction Controls",
|
||||||
|
href: "/extensions/interaction-controls",
|
||||||
|
},
|
||||||
{ title: "Likes", href: "/extensions/likes" },
|
{ title: "Likes", href: "/extensions/likes" },
|
||||||
{ title: "Migration", href: "/extensions/migration" },
|
{ title: "Migration", href: "/extensions/migration" },
|
||||||
{ title: "Polls", href: "/extensions/polls" },
|
{ title: "Polls", href: "/extensions/polls" },
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue