Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Create xip-35-message-sender-signature.md #35

Open
wants to merge 1 commit into
base: main
Choose a base branch
from
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
60 changes: 60 additions & 0 deletions XIPs/xip-35-message-sender-signature.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
---
xip: 35
title: Message sender identifier in topic
description: A system for detecting who sent a message in a topic from the Notification Server
author: Noé Malzieu
status: Draft
type: Standards Track
category: XRC
created: 2023-12-06
---


## Abstract

This XRC proposes to add a signature to public envelopes for messages, that a notification server could use to detect if one of the subscribed users has sent the message and not send him the notification (i.e. avoid receiving notifications for your own messages).

## Motivation

Right now, a message sent in a topic needs to have its payload decoded to understand who sent the message.
When a notification server sees a message in a topic and decides to sent it to one of its subscribers, it has no way to know if the message is from the subscriber or not.
This means a mobile XMTP client will subscribe to a topic then receive notifications for its own messages in the topic.
This would be fine if the XMTP client could just drop the notification after having decoded the payload.
On Apple devices, to be able to decode the payload before showing the notification, we must use a [Notification Service Extension](https://developer.apple.com/documentation/usernotifications/unnotificationserviceextension) - and the only way to drop a notification from a Notification Service Extension is to obtain a specific entitlement from Apple: [com.apple.developer.usernotifications.filtering](https://developer.apple.com/documentation/bundleresources/entitlements/com_apple_developer_usernotifications_filtering)
Obtaining this entitlement from Apple has proven very hard - they might consider XMTP clients too web3, and they just don't provide this entitlement to apps that provide financial services.
Specifically, Coinbase Wallet never managed to obtain this entitlement, and Converse had it for a few months before losing it.

## Specification

The SDKs would generate a private/public key pair for each topic.
The private/public key pair should always be the same for a given user and a given topic - not dependent on installations / SDK language.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My suggestion would be that each user would have a signing key that would be synced between their devices for v1/v2 and be per-installation and not synced for group chats/v3. We would generate a per-topic key by doing HKDF(root_key, salt=$topic).

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not sure I get the difference between an "installation" and a "device"?
Goal being that I generate the same per-topic key on Coinbase Wallet & Converse

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not sure I get the difference between an "installation" and a "device"?

"Installation" is a little more specific than "device", because in the XMTP case there can be multiple different apps (Coinbase Wallet, Converse) installed on the same device. We sometimes forget and use the word "device" interchangeably, because a lot of the literature uses that term.

Goal being that I generate the same per-topic key on Coinbase Wallet & Converse

@neekolas's suggestion would work for this - the signing key is synced to all installations, and all installations perform the same HKDF to get the same per-topic key.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We would generate a per-topic key by doing HKDF(root_key, salt=$topic).

I'm not sure I understand this proposal for v3. The per-topic key needs to be the same among all installations, so what is "root_key" referring to here?


Before publishing an envelope on a topic, the SDK would use the topic private key to sign the message payload and attach it to the envelope.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's important to note that the public key of the user's signing key would be private between the user's devices and the notification server. Third parties would not be able to validate that the signatures originate from the actual sender and were not forged.


The envelope of a message would be updated to

message Envelope {
string content_topic = 1;
uint64 timestamp_ns = 2;
bytes message = 3;

optional string signature = 4; // New field added
}

When the client subscribes to a topic on its notification server, it would also provide the topic public key to the notification server.

When the notification server sees a message in a specific topic, it would do the following

1. Check if it has clients that have subscribed to this topic
2. For each client that has subscribed to the topic, try to verify the signature using the public key the client has provided when subscribing to the topic
3. If the signature is verified, it means that the message was indeed sent by this person (not necessarily from this client) and the notification server can decide wether to send the notification or not (could be a parameter configured by the developper)

## Backwards Compatibility

Notification server should allow subscribing to topics without sending a public key. This client would then receive all notifications.

Notification server should also parse envelopes that don't have any signature. These messages would be sent to every client that subscribed to the topic, wether they provided a public key for this topic or not.

## Copyright

Copyright and related rights waived via [CC0](https://creativecommons.org/publicdomain/zero/1.0/).