nostr-protocol / nips

Nostr Implementation Possibilities
2.31k stars 563 forks source link

NIP-XX Creating an Ephemeral Identity Token #766

Open geeknik opened 1 year ago

geeknik commented 1 year ago

Abstract

This proposal proposes a method for creating an ephemeral identity token without revealing the Nostr public key (npub) while avoiding leakage of metadata or personally identifiable information (PII). It uses a secure cryptographic algorithm, with an emphasis on leveraging post-quantum encryption methodologies to ensure long-term security.

Background

The Nostr protocol allows users to create and manage public identities. However, certain situations require privacy that extends beyond the protection of pseudonymity offered by public identities. The challenge lies in creating a temporary, anonymous identity token without revealing the user's npub, other identifying information, or PII

Proposal

We suggest a method that employs elliptic-curve cryptography (ECC), specifically, the sidh algorithm, a post-quantum cryptographic (PQC) algorithm.

Step 1 - Ephemeral Key Generation

A user generates a pair of ephemeral sidh keys (pk_e, sk_e). The pke will be the temporary npub equivalent for the user, while ske is their private key.

from sidh.common import attrdict
from sidh.procedural import StrategySequence, strategy_data
from sidh.internals.isogeny_walk import IsoStrategy
from sidh.internals.sidh import sidh_initializer, sidh_private_key, sidh_public_key, sidh_shared_secret

params, bf, isog, f = sidh_initializer(None, 64)

Alice = attrdict()
Bob = attrdict()

Alice.update(
    {
        "params": params,
        "member": attrdict({"l": params.ALICE, "m": params.ALICE_MAX}),
        "mask": attrdict({"strategy": 0xFF, "torsion": 0x03}),
        "ranges": [(-1, 1)],
    }
)

Alice.sk = sidh_private_key(params, Alice)
Alice.pk = sidh_public_key(params, Alice, Alice.sk)

pk_e = Alice.pk
sk_e = Alice.sk

Step 2 - Challenge Generation

A challenge C is created using a secure hash function such as SHA3-256. The input to the hash function should preclude the possibility of metadata or PII leakages. It could be a user-provided random number or the current timestamp.

import hashlib
import time

C = hashlib.sha3_256(str(time.time()).encode()).digest()[:16]

Step 3 - Response Generation

Before generating the HMAC response, we compute a symmetric key from the private key sk_e using a Key Derivation Function (KDF). SHA3-256 can be used for the KDF.

import hashlib

kdfkey = hashlib.sha3256(sk_e).digest()
R = hmac.new(kdf_key, C, hashlib.sha256).digest()[:16]

This way, potential timing attacks on the hmac.new() function won't directly affect our private key sk_e.

Conclusion: Ephemeral Identity Token

We define the ephemeral identity token IDe as the tuple (pke, C, R). The ID_e token can now be used for temporary identification purposes.

Event Handling with Anonymity

Once the ephemeral identity token (ID_e) is generated, it can be used in various scenarios where anonymous interaction is required. For example, in anonymous voting, the token can serve as a unique identifier, providing the necessary privacy.

Similarly, in private messaging, users could use their IDe instead of npub when emitting messages. Recipients, who also have the user's IDe, can then derive the sender's ephemeral private key and verify the integrity of the received messages.

Please note that these are just examples. The actual implementation would depend on the specific requirements and constraints of the specific Nostr network protocol interaction. This proposal does not change the overall Nostr event model; it simply provides an additional tool that can be used in that model where anonymity is required.

Security Considerations

The sidh algorithm used for ephemeral key generation provides a degree of security against quantum computing attacks, making the ephemeral key's private portion virtually impossible to reverse-engineer. The use of HMAC further ensures the integrity of the transaction, eliminating the possibility of tampering.

The representation of the ephemeral identity token does not include any metadata or PII. The user's real npub or other identifying information is not disclosed at any point during the process.

Future Work

Further security enhancements can be made to this proposal by employing additional PQC algorithms to augment sidh, ensuring security in the ever-evolving landscape of encryption and quantum computing.

Conclusion

This proposal provides a solid foundation for creating ephemeral identity tokens in the Nostr protocol without revealing an individual's npub or other identifying information. It strikes a balance between security, leveraging PQC methodologies, and anonymity, with the objective of making the Nostr protocol more secure and privacy-preserving.

License

This NIP is public domain.

vitorpamplona commented 1 year ago

Since this could be used for voting, what guarantees there is only one token per private key?

geeknik commented 1 year ago

Since this could be used for voting, what guarantees there is only one token per private key?

Good point.

This provides a probabilistic limitation on Sybil attacks while maintaining anonymity and without requiring additional complex cryptographic operations. We can tweak the parameters and implementation details as needed.

vitorpamplona commented 1 year ago

The voting application tracks which pke have already cast a vote. Duplicates are thusly rejected.

How do they do that without revealing the original pub key to make sure a person doesn't vote twice?

geeknik commented 11 months ago

How do they do that without revealing the original pub key to make sure a person doesn't vote twice?

Generate a pair of ephemeral sidh keys (pk_e, sk_e) as described in the original proposal.

Generate a timestamp T at the time of ephemeral key creation.

Sign the ephemeral public key (pk_e) and timestamp (T) using the user's original Nostr public key (npub).

Hash the signed data to produce a unique identifier H.

The voting application should track the hash H. If H is already recorded, the new vote is rejected.