Skip to content

Commit

Permalink
Merge branch 'main' of github.com:xmtp/XIPs into rev-xip-0
Browse files Browse the repository at this point in the history
  • Loading branch information
jhaaaa committed Mar 15, 2024
2 parents 736781f + c2d45fb commit f9f8f81
Show file tree
Hide file tree
Showing 4 changed files with 203 additions and 33 deletions.
16 changes: 8 additions & 8 deletions XIPs/xip-0-purpose-process.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ The XIP author and editor should ensure an XIP provides a concise technical spec

## The purpose of XIPs

XIPs address the need for a standardized, transparent process for proposing, discussing, and integrating new features for XMTP.
XIPs address the need for a standardized, transparent process for proposing, discussing, and integrating new features for XMTP.

XIPs offer a structured proposal system that ensures comprehensive community participation and informed decision-making.

Expand Down Expand Up @@ -53,13 +53,13 @@ A **Standards** XIP describes any changes that affect most or all XMTP implement

### Process XIP

A **Process** XIP describes a new process or changes to an existing process surrounding XMTP. These XIPs may propose an implementation but do not modify the XMTP codebase.
A **Process** XIP describes a new process or changes to an existing process surrounding XMTP. These XIPs may propose an implementation but do not modify the XMTP codebase.

They often require community consensus and are more than mere recommendations. However, unlike **Informational** XIPs, the community cannot ignore them.

### Informational XIP

An **Informational** XIP provides general guidelines or information to the XMTP community without proposing a new feature.
An **Informational** XIP provides general guidelines or information to the XMTP community without proposing a new feature.

These XIPs do not necessarily reflect an XMTP community consensus or recommendation, allowing users and implementors to disregard or heed their advice.

Expand All @@ -80,7 +80,7 @@ Additional validation may involve reviewing reference implementations or assessi
1. Share your idea with the XMTP community, including developers, reviewers, and editors. Beyond posting to the XMTP Community Forums, consider sharing your idea across your networks on other platforms.

1. Request feedback that will enable you to validate, measure overall interest in, and assess the originality of your idea, potentially saving you time and effort.

After you feel your idea has received enough feedback, create an XIP draft for it as described in the next section. A good standard for "enough feedback" is at least one comment from an XMTP community member and one from an XMTP Core Developer (currently the XMTP Labs team).

## Start the XIP process
Expand All @@ -99,7 +99,7 @@ An XIP must fulfill certain minimum criteria:

### Draft status

This is the first formally tracked stage of an XIP.
This is the first formally tracked stage of an XIP.

1. The XIP author uses the [XIP template](../xip-template.md) to create the XIP draft, adhering to the guidelines in this document.

Expand All @@ -119,7 +119,7 @@ This is the first formally tracked stage of an XIP.

1. The XIP editor merges the corresponding pull request and sends a message to the XIP author with next steps.

The XIP author uses the forum topic to gather feedback from the community and at least one XMTP Core Developer. The XIP author is responsible for building consensus and documenting dissenting opinions.
The XIP author uses the forum topic to gather feedback from the community and at least one XMTP Core Developer. The XIP author is responsible for building consensus and documenting dissenting opinions.

The XIP author may work with XIP editors to open pull requests against their merged XIP draft to update it to address feedback in preparation for the review phase.

Expand All @@ -139,7 +139,7 @@ The XIP author may work with XIP editors to open pull requests against their mer

### Final status

If the XIP is an **Informational** or **Process** XIP, it automatically goes into **Final** status after the 14-day **Last call** period.
If the XIP is an **Informational** or **Process** XIP, it automatically goes into **Final** status after the 14-day **Last call** period.

An XIP in **Final** status exists in this status permanently and can be updated only to correct errata and add non-normative clarifications.

Expand Down Expand Up @@ -183,7 +183,7 @@ An XIP author should not provide this value. An XIP editor will assign the XIP n

### title

A short descriptive title, limited to 44 characters. It should not include the XIP number.
A short descriptive title, limited to 44 characters. It should not include the XIP number.

### description

Expand Down
74 changes: 74 additions & 0 deletions XIPs/xip-42-universal-allow-block-preferences.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
---
xip: 42
title: Universal 'allow' and 'block' preferences
description:
author: Saul Carlin (@saulmc), Nick Molnar (@neekolas), Naomi Plasterer (@nplasterer), Ry Racherbaumer (@rygine)
discussions-to: <https://community.xmtp.org/t/xip-42-universal-allow-and-block-preferences/544>
status: Draft
type: Standards
category: XRC
created: 2024-02-14
---

## Abstract

This XIP establishes 'allow' and 'block' permission preferences, enabling users to explicitly specify which contacts should be able to reach them and which should be blocked across all inbox apps. By respecting these preferences, XMTP inbox apps not only shield users from spam but also give them greater control over their contacts.

*Special thanks to @polmaire for [initiating the discussion](https://github.com/xmtp/XIPs/pull/28/files) that inspired this XIP.*

## Motivation

The ability to 'allow' or 'block' contacts is fundamental for safeguarding users' inboxes in messaging. 'Allow' promotes a conversation from a 'request' or 'invitations' UI component to a 'primary inbox' component, while 'Block' gives users the vital ability to remove spam and other unwanted content from their inbox.

Because XMTP hasn't yet standardized a method for communicating these actions across the network, changing preferences in one app does not affect other inboxes. This results in inbox apps failing to remove unwanted conversations and properly displaying desired communications.

## Specification

In code we use `consent` to abbreviate "contact permission preferences", and `denied` as the inverse of `allowed`.

- **New Message Topic**: `userpreferences-${identifier}` for encrypted `ConsentList` objects (`type: 'allowed' | 'denied', addresses: [string]`).
- **ConsentState Type**: Introduce `ConsentState = 'allowed' | 'denied' | 'unknown'`.
- **Conversation Field**: Add `consentState` to indicate the consent state of a conversation.
- **APIs**: Introduce APIs for retrieving and managing permission preference lists and states.

## Rationale

This approach will enable apps to accurately reflect users' contact permission preferences by default, thereby shielding them from spam and granting them more ownership and control over their communications.

## Backward Compatibility

Apps must adhere to the logic described below to keep the contact permission preferences on the network synchronized with local app's user preferences, and vice versa.

Update a contact permission preference in the `ConsentList` on the network in the following scenarios only:

- A user explicitly denies a contact. For example, the user blocks, unsubscribes from, or otherwise disables messages for the contact. The app should update the corresponding preference in the network to `denied`.
- A user explicitly allows a contact. For example, the user allows, subscribes to, or otherwise enables messages for the contact. The app should update the corresponding preference in the network to `allowed`.
- An existing conversation has an `unknown` contact permission preference, but a legacy permission in the local database exists. The app should update the corresponding preference in the network to match the legacy local preference.
- An existing conversation has an `unknown` contact permission preference, but has an existing response from the user. The app should update the corresponding preference in the network to `allowed`.

## Test Cases

Test cases will validate the functionality of sending messages using the new message topic and the handling and interpretation of all three permission preferences.

## Reference Implementation

The [reference implementation](https://github.com/xmtp-labs/xmtp-inbox-web/pull/422) in the [XMTP reference client](https://xmtp.chat) demonstrates the integration of contact permission preferences, along with usable code snippets and UI components for allowing and blocking contacts.

## Security Considerations

The `identifier` in the topic is derived from the private key using HKDF and SHA256 to ensure that it cannot be linked back to the user.

### Message Envelope Encryption

1. Generates a new key via HKDF from the user's identity key.
2. Encrypts the message via AES-256-GCM using the derived encryption key and the user's public key as associated data. Then converts it to a `PrivatePreferencesPayload` protobuf containing the ciphertext, nonce, and salt.

### Message Envelope Decryption

1. Decodes the `PrivatePreferencesPayload`.
2. Derives the encryption key via HKDF from the user's identity key.
3. Decrypts the contents via AES-256-GCM using the public key as associated data.

## Copyright

Copyright and related rights waived via [CC0](https://creativecommons.org/publicdomain/zero/1.0/).
91 changes: 91 additions & 0 deletions XIPs/xip-43-permission-pref-proofs.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
---
title: Permission preference proofs
description: Enables recipients to sign to specify inbox permission preferences
author: @rygine @neekolas @saulmc
discussions-to: https://community.xmtp.org/t/xip-43-permission-preference-proofs/552
status: Draft
type: Standards
category: Interface
created: 2024-02-22
---

## Abstract

This XIP proposes to add an _optional_ signed payload to conversations that client apps can consider as proof that a recipient has granted a sender permission to reach their main inbox.

## Motivation

Today, a recipient must use a full XMTP client to set a universal permission preference such as allowing a sender. This presents challenges to senders due to the XMTP client's bundle size and integration requirements. For integrations such as simple subscribe buttons, these hurdles can be blockers.

To solve these issues, senders can simply ask users to produce a signature attesting to the permission preference update. Inbox apps can consider this signature as proof that the recipient has explicitly opted in to receive the sender's messages. This eliminates the bundle size problem, as very little code is required to initiate signing a message with a user's wallet. It also greatly simplifies integration by providing a single function to obtain the user’s signature and return an encoded payload to be used by SDKs to verify the granted permission.

## Specification

There are 3 components to the proposed workflow:

1. Obtain a permission signature from the user
_Requires actions by the **sender** and **receiver**_
2. Create a new conversation with the encoded payload
_Requires actions by the **sender**_
3. Verify the permission payload to allow the sender
_Requires actions by the **client SDK**_

### Obtain a permission signature from the user

A permission signature must be obtained from a user's wallet, which is then encoded into a payload that can be used by client SDKs to verify and validate opt-in before allowing the sender.

The decoded payload that must be collected by senders will be defined in a protobuf as follows:

```protobuf
message PermissionPayload {
// the user's signature in hex format
string signature = 1;
// approximate time when the user signed
uint64 timestamp = 2;
// version of the payload
uint32 payload_version = 3;
}
```

The message that will be signed by the user's wallet will contain the sender's address and a timestamp. It must include a human-readable explanation, such as follows.

```text
XMTP : Grant inbox permission to sender
Current Time: <ISO 8601 date and time in UTC>
From Address: <ethereum address>
For more info: https://xmtp.org/signatures/
```

A light-weight JavaScript bundle will provide a function that will initiate the signing process and return an encoded payload that senders must store on their end. This function is intended to be used as a callback to a click event, such as clicking on a Subscribe button.

### Create a new conversation with the encoded payload

Once senders have the encoded payload, they can include it when starting a new conversation with a user.

An example of what this might look like:

```ts
const conversation = await client.conversations.newConversation(peerAddress, context, permissionPayload);
```

Users who have created a permission signature may not have an identity on the XMTP network. Senders should check for an identity with `Client.canMessage` prior to starting a new conversation. If a user does not yet have an XMTP identity, the sender can routinely check for a network identity and start a conversation when it's found.

### Verify the permission payload

In order to finalize the permission preference, SDKs must look for the permission payload in new conversations. Using this payload, SDKs can verify that the current user's wallet signed the permission message and validate that the addresses and timestamp match the expected values.

Once the permission payload is verified and validated, the SDKs will then update network permission preferences automatically.

## Backward Compatibility

The encoded permission payload is an _optional_ parameter when starting a new conversation. Existing conversations will not be affected, and client apps using outdated SDKs will continue to work without updates.

## Security Considerations

There are no known negative security implications introduced as a result of collecting a signature from a user and including it as part of a conversation. The contents of the message being signed will be shown to the user beforehand, and the resulting signature is only useful to SDKs connected to the wallet that signed the message.

## Copyright

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

0 comments on commit f9f8f81

Please sign in to comment.