mirror of
https://github.com/matrix-org/matrix-spec
synced 2026-04-20 18:04:10 +02:00
Merge branch 'master' into daniel/threepidinvites-2
This commit is contained in:
commit
c66a933640
13
event-schemas/examples/v1/m.receipt
Normal file
13
event-schemas/examples/v1/m.receipt
Normal file
|
|
@ -0,0 +1,13 @@
|
||||||
|
{
|
||||||
|
"type": "m.receipt",
|
||||||
|
"room_id": "!KpjVgQyZpzBwvMBsnT:matrix.org",
|
||||||
|
"content": {
|
||||||
|
"$1435641916114394fHBLK:matrix.org": {
|
||||||
|
"read": {
|
||||||
|
"@rikj:jki.re": {
|
||||||
|
"ts": 1436451550453
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
43
event-schemas/schema/v1/m.receipt
Normal file
43
event-schemas/schema/v1/m.receipt
Normal file
|
|
@ -0,0 +1,43 @@
|
||||||
|
{
|
||||||
|
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||||
|
"type": "object",
|
||||||
|
"title": "Receipt Event",
|
||||||
|
"description": "Informs the client of new receipts.",
|
||||||
|
"properties": {
|
||||||
|
"content": {
|
||||||
|
"type": "object",
|
||||||
|
"description": "The event ids which the receipts relate to.",
|
||||||
|
"patternProperties": {
|
||||||
|
"^\\$": {
|
||||||
|
"type": "object",
|
||||||
|
"description": "The types of the receipts.",
|
||||||
|
"additionalProperties": {
|
||||||
|
"type": "object",
|
||||||
|
"description": "User ids of the receipts",
|
||||||
|
"patternProperties": {
|
||||||
|
"^@": {
|
||||||
|
"type": "object",
|
||||||
|
"properties": {
|
||||||
|
"ts": {
|
||||||
|
"type": "number",
|
||||||
|
"description": "The timestamp the receipt was sent at"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"additionalProperties": false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"additionalProperties": false
|
||||||
|
},
|
||||||
|
"type": {
|
||||||
|
"type": "string",
|
||||||
|
"enum": ["m.receipt"]
|
||||||
|
},
|
||||||
|
"room_id": {
|
||||||
|
"type": "string"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"required": ["room_id", "type", "content"]
|
||||||
|
}
|
||||||
6
scripts/continuserv/README
Normal file
6
scripts/continuserv/README
Normal file
|
|
@ -0,0 +1,6 @@
|
||||||
|
continuserv proactively re-generates the spec on filesystem changes, and serves it over HTTP.
|
||||||
|
|
||||||
|
To run it, you must install the `go` tool. You will also need to install fsnotify by running:
|
||||||
|
`go get gopkg.in/fsnotify.v1`
|
||||||
|
You can then run continuserv by running:
|
||||||
|
`go run main.go`
|
||||||
|
|
@ -68,6 +68,7 @@ func watchFS(ch chan struct{}, w *fsnotify.Watcher) {
|
||||||
case e := <-w.Events:
|
case e := <-w.Events:
|
||||||
if filter(e) {
|
if filter(e) {
|
||||||
wg.Add(1)
|
wg.Add(1)
|
||||||
|
fmt.Printf("Noticed change to %s, re-generating spec\n", e.Name)
|
||||||
ch <- struct{}{}
|
ch <- struct{}{}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -79,7 +80,9 @@ func makeWalker(w *fsnotify.Watcher) filepath.WalkFunc {
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatalf("Error walking: %v", err)
|
log.Fatalf("Error walking: %v", err)
|
||||||
}
|
}
|
||||||
w.Add(path)
|
if err := w.Add(path); err != nil {
|
||||||
|
log.Fatalf("Failed to add watch: %v", err)
|
||||||
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
81
specification/46_receipts.rst
Normal file
81
specification/46_receipts.rst
Normal file
|
|
@ -0,0 +1,81 @@
|
||||||
|
Receipts
|
||||||
|
========
|
||||||
|
|
||||||
|
Receipts are used to publish which events in a room the user or their devices
|
||||||
|
have interacted with. For example, which events the user has read.
|
||||||
|
|
||||||
|
For efficiency this is done as "up to" markers, i.e. marking a particular event
|
||||||
|
as, say, ``read`` indicates the user has read all events *up to* that event.
|
||||||
|
|
||||||
|
Client-Server API
|
||||||
|
-----------------
|
||||||
|
|
||||||
|
Clients will receive receipts in the following format::
|
||||||
|
|
||||||
|
{
|
||||||
|
"type": "m.receipt",
|
||||||
|
"room_id": <room_id>,
|
||||||
|
"content": {
|
||||||
|
<event_id>: {
|
||||||
|
<receipt_type>: {
|
||||||
|
<user_id>: { "ts": <ts>, ... },
|
||||||
|
...
|
||||||
|
}
|
||||||
|
},
|
||||||
|
...
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
For example::
|
||||||
|
|
||||||
|
{
|
||||||
|
"type": "m.receipt",
|
||||||
|
"room_id": "!KpjVgQyZpzBwvMBsnT:matrix.org",
|
||||||
|
"content": {
|
||||||
|
"$1435641916114394fHBLK:matrix.org": {
|
||||||
|
"read": {
|
||||||
|
"@erikj:jki.re": { "ts": 1436451550453 },
|
||||||
|
...
|
||||||
|
}
|
||||||
|
},
|
||||||
|
...
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
For efficiency, receipts are batched into one event per room. In the initialSync
|
||||||
|
and v2 sync APIs the receipts are listed in a seperate top level ``receipts``
|
||||||
|
key.
|
||||||
|
|
||||||
|
Each ``user_id``, ``receipt_type`` pair must be associated with only a single
|
||||||
|
``event_id``.
|
||||||
|
|
||||||
|
New receipts that come down the event streams are deltas. Deltas update
|
||||||
|
existing mappings, clobbering based on ``user_id``, ``receipt_type`` pairs.
|
||||||
|
|
||||||
|
|
||||||
|
A client can update the markers for its user by issuing a request::
|
||||||
|
|
||||||
|
POST /_matrix/client/v2_alpha/rooms/<room_id>/receipt/read/<event_id>
|
||||||
|
|
||||||
|
Where the contents of the ``POST`` will be included in the content sent to
|
||||||
|
other users. The server will automatically set the ``ts`` field.
|
||||||
|
|
||||||
|
|
||||||
|
Server-Server API
|
||||||
|
-----------------
|
||||||
|
|
||||||
|
Receipts are sent across federation as EDUs with type ``m.receipt``. The
|
||||||
|
format of the EDUs are::
|
||||||
|
|
||||||
|
{
|
||||||
|
<room_id>: {
|
||||||
|
<receipt_type>: {
|
||||||
|
<user_id>: { <content> }
|
||||||
|
},
|
||||||
|
...
|
||||||
|
},
|
||||||
|
...
|
||||||
|
}
|
||||||
|
|
||||||
|
These are always sent as deltas to previously sent reciepts.
|
||||||
|
|
||||||
|
|
@ -30,7 +30,7 @@ def get_json_schema_object_fields(obj, enforce_title=False):
|
||||||
}
|
}
|
||||||
tables = [fields]
|
tables = [fields]
|
||||||
|
|
||||||
props = obj.get("properties")
|
props = obj.get("properties", obj.get("patternProperties"))
|
||||||
parents = obj.get("allOf")
|
parents = obj.get("allOf")
|
||||||
if not props and not parents:
|
if not props and not parents:
|
||||||
raise Exception(
|
raise Exception(
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue