Sarah Jamie Lewis edited this page 2021-11-03 18:48:31 +00:00

Hybrid Groups

It all starts with the Root

All groups start with a single message. We refer to this message as the "root" of the group.

The root contains:

  • The Membership List of profiles who are considered members of the group.
  • The Access Control List (ACL) that determines who can post to the group (among other actions).
  • The Topology of the group.

The root is signed by the group creator. A group can only have a single creator, but the creator can designate additional administrators within the ACL.

Message Structure and Distribution

All additional messages to the group have the following structure:

struct GroupMessage {
    Parents: Vec<Signature>
    Contents: Vec<u8>
    Author: PublicKey

struct SignedGroupMessage {
        Message: GroupMessage
        Signature: []byte // Sig(GroupMessage, senders public key) 
  • Every message to the group must be signed by the author of the message.
  • Every message to the group must reference one-or-more previous messages received from the group.
  • Each author must only reference a parent message once.

Rules for Constructing the Tree

When a group member receives a message that references a parent message that they have not seen before, that member can request that message from other group members.

If a group member is in possession of more than one message from another group member that references an intersecting set of parents, then the other group member must be considered to be acting maliciously. All previous messages received from the malicious group member must marked as malicious, and must not be considered for future reference - except the set of messages that uncovered the fraud, which are distributed as Fraud Proofs to presumed-honest group members.


Messages distribution is governed by the Topology of the group. Depending on their needs and preferences, groups can be designated to be peer-to-peer only, rely on trusted forwarding bots, or rely on untrusted cwtch server infrastructure.


All group messages are encrypted prior to transport. The structure of an encrypted group message is the same as the v1 group structure, with the exception of the signed value

// EncryptedGroupMessage provides an encapsulation of the encrypted group message stored on the server
type EncryptedGroupMessage struct {
    Ciphertext []byte // Encryption of GroupMessage
    Signature  []byte // Signature from Signed Group Message

Verification remains similar to the current scheme:

  • Attempt decryption of Ciphertext with GroupKey
  • If successful:
    • Verify signature over GroupMessage against GroupMessage.Author
    • If successful:
      • Return SignedGroupMessage consisting of the Signature from EncryptedGroupMessage with the decrypted GroupMessage
    • Otherwise, return an error
  • Otherwise, return an error


If a member violates the protocol by sending multiple messages confirming the same parent more than once then that member is assumed malicious, and their confirmation chain is marked as invalid.

If a member references a parent signature but is unwilling to provide the GroupMessage that resulted in it, that member should be assumed to be malicious. Note: that a member that references a fake message will not have their messages included in the timeline until they present proof of such a message - as such referencing a fake message has minimal impact assuming that such messages are pruned from the tree-crdt occasionally.

Key Rotation

Rotation are accomplished when an authorized sender sends a KeyRotationMessage to the group, and a quorum of members confirm the receipt of the message indirectly via inclusion of the parent within the tree-crdt.

Once a member receives enough confirmations, they will rotate their key and begin encrypting new messages with the new key - while testing existing messages against the older key. As soon as all members have sent a message using the new key, the old key is purged.

Note: The above allows each member to identify the exact state of any other members timeline and keyring. This is a useful meta-protocol when managing the security of groups.


Messages contain a reference to their parent node to aid in tree reconstruction.

When a profile receives a message containing a reference to an unknown parent, they attempt to download the parent message from online contacts.

As such the conversation tree can be reassembled from parts.

There are no conflicts, parents can have multiple children, and these will be accessible via the UI

Access Control List (ACL)

The rules for which messages are accepted into the Tree-CRDT are governed by the ACL which is defined on group creation and be refined through messages published to the Tree-CRDT.

Maintaining Consistency

Requires acknowledgements to be published to the CRDT before a change goes into effect?


How messages are fetched for the CRDT is governed by the overlay protocol for the group. The overlay protocol can be:

  • Equal - all nodes are considered equally valid to fetch new messages from.
  • Unequal - certain nodes are given priority e.g. an untrusted cwtch server or an always online-bot are given priority when sharing new messages, or when downloading previous messages.


of the ACL

Changes need to be acknowledged by a quorum before going to effect.

of the Message Database

Conflicts are not possible, parents can have multiple children. Children can reference multiple parents to include an acknowledgement of both parts.

For the vast majority of applications relevant to Cwtch, exact consensus is not necessary, and most can be resolved via higher level protocols operating on a message tree itself.