Stratégies client de suivi des transactions

Pour le ĞMixer j’ai besoin de :

  • savoir si une transaction X existe, avec montant, émetteur, destinataire, commentaire donnés et étant écrite dans une période donnée
  • envoyer une transaction qui sera écrite uniquement si X existe (en cas de fork, elle ne devrait pas être écrite sur une branche ne contenant pas X)
  • détecter qu’une transaction envoyée n’est pas écrite, la renvoyer si elle n’a pas été écrite depuis trop longtemps et en générer une nouvelle si l’ancienne n’est plus compatible avec le fork (en étant sûr que les deux ne puissent jamais être écrites sur la même branche)

Du coup je pense enregistrer le blockstamp du dernier bloc nécessaire à ce que la tx envoyée soit valide, afin de pouvoir la renvoyer ou le générer à partir des nouvelles sources, en cas de fork ou de problème réseau.

Une session de mixage est l’émission de plusieurs txs d’un unique compte vers plusieurs comptes, avec un commentaire spécifique par tx (le destinataire vérifie que le commentaire est bien le hash attendu). Mais si on envoie plein de txs d’un coup, elles risquent de ne pas passer en même temps, et ça fait encore plus travailler Duniter.

Le suivi serait plus simple avec une seule tx multi-destinataires. Il faut donc stocker les données ailleurs que dans les commentaires. Par exemple dans IPFS (le commentaire est le lien vers une liste de hashes), mais ça me rendrait dépendant d’un système de plus.

On pourrait aussi mettre en commentaire le produit de tous les hashes : il suffit de vérifier que le commentaire est bien multiple du hash attendu. (et qu’un hash ne puisse être multiple d’un autre, en restreignant leur valeur à un intervalle) Si les hashes font 32 octets et qu’on encode le produit en base 85, on peut mixer jusqu’à exactement 17 txs par session. (limite de 255 caractères)

Vos avis ? et est-ce que les conditions des txs pourraient m’être utiles ?

Celui qui veut savoir ne connais pas le document transaction n’est-ce pas ? (Sinon quoi il suffirait de se baser sur le hash de la tx).

Le plus simple est de rechercher dans l’historique des transactions du destinataire dans l’intervalle donné : https://git.duniter.org/nodes/typescript/duniter/-/blob/dev/doc/HTTP_API.md#txhistorypubkeytimesfromto

Ensuite il faut itérer sur toutes les transactions dans « received » et voir si on en trouve une qui contient l’issuer attendu et le commentaire attendu.

L’idéal est de te servir d’une source en output de la transaction X. Comme ça tu es certain que la nouvelle transaction ne peut être écrite que si X est écrite.

Si tu ne la trouve pas dans « received » elle n’est pas écrite.

Pour éviter les problèmes de fork il te suffit de blocstamper tes transactions a plus de 100 blocs de retard

Oui, il ne le connaît pas.

J’arrive déjà à obtenir cette information, j’ai oublié de le préciser.

Ah oui, je m’étais dit que ça annulerait l’effet du mixage, en rendant visible une chaîne de sources, mais non, puisqu’on ne peut pas savoir quelle source correspond à quelle entrée. Je vais faire ça alors.

Et à propos de mon produit de hashes, y aurait-il une technique cryptographique plus efficace pour générer un nombre N à partir d’une liste de nombres donnés, et dont on peut vérifier que seuls les nombres de la liste sont dérivables de N ?

Exactement, d’où l’intérêt de mixer tout dans un seul document transaction multi-destinataires :slight_smile:

Je ne suis pas sûr de comprendre ce que signifie « sont dérivables de N ».

Cependant, j’ai l’impression que les arbres de merkle peuvent répondre a ton besoin.

Tu as une liste de hashs Hi qui sont les feuilles de l’arbre, tu inscris dans la transaction un seul hash Hr (la racine de l’arbre) qui agrège tous les Hi. Tu peux alors prouver a n’importe-qui si un hash donné H’ est une feuille de l’arbre ou non

Le hash de chaque transaction est dérivé de seeds provenant du client et des deux nœuds impliqués dans la transaction, et avant la transa, or seul le nœud qui mixe décide des transactions à mixer lors d’une session, donc on ne peut pas dériver les hashes des transactions d’une unique seed.

Si le commentaire est le hash de la liste des hashes, alors il faut encore publier la liste des hashes (qui est imprévisible). Tout doit être vérifiable a posteriori par n’importe qui sans avoir à interagir directement avec le nœud.

Je parle d’une fonction de hashage H hashant un ensemble E telle qu’on puisse déduire de H(E) si X est contenu dans E. Le produit arithmétique permet ça (on peut vérifier si il est multiple de X, donc si il contient la transaction de hash X).

Oui et bien c’est ce que permettent les arbres de merkle. Il te faut juste publier l’arbre quelque part.
La blockchain n’est pas faite pour stocker toutes les données mais pour définir un consensus et stocker des preuves, je suis déjà pour la suppression des commentaires de transactions alors les données de service gmixer forcément je ne suis pas pour.

Le client qui veut vérifier doit déjà récupérer les données en blockchain, il doit donc taper une API quelque part, cette API, il y a donc forcément interaction. Cette API peut très bien agréger des données en blockchain + des données annexes prouvées par des hashs en blockchain.

En résumé donc, tu stockes le hash d’un merkle root dans ton document transaction et avec ça tu peux déjà prouver une quantité littéralement illimitée de données que tu peux stocker n’importe où et récupérer depuis n’importe où sans avoir a te soucier de leur authenticité, car le merkle root en blockchain te permet de tout vérifier.

La blockchain n’a pas a gérer le coût de stockage des services tiers qui se basent sur elle, elle ne devrait stockée que des preuves, c’est pour cela que je suis pour la suppression des commentaires de tranasction (tu peut alors stocker le hash d’un merkle root dans la condition XHX d’un output dédié).

Du coup pour ne pas avoir à gérer le stockage et l’accès décentralisé aux données je vais utiliser IPFS : l’adresse étant le hash des données, ça sera équivalent à l’arbre de Merkle.

Ce ne sera pas équivalent, l’avantage d’un arbre de merkle c’est que tu peut prouver la présence d’un élément dans l’arbre sans donner tout l’arbre, tu a donc moins de données qui transitent sur le réseau.

Si par exemple ton ensemble contient N feuilles tu n’a que log2(N) hashs a fournir pour prouver la présence d’une feuille. Quand le volume des données deviens important ça commence a valoir le coup :slight_smile:

1 J'aime