diff --git a/frontend/src/tools/nachrichten.jsx b/frontend/src/tools/nachrichten.jsx index 71e1575..7f76917 100644 --- a/frontend/src/tools/nachrichten.jsx +++ b/frontend/src/tools/nachrichten.jsx @@ -4,6 +4,7 @@ import { UserIcon, TrashIcon } from '../icons.jsx'; import { getOrCreateKeyPair, getPublicKeyJwk, + getFingerprint, deriveSharedKey, encryptMsg, decryptMsg, @@ -17,6 +18,7 @@ export default function Nachrichten({ toast, mobile }) { const [messages, setMessages] = useState([]); const [sharedKey, setSharedKey] = useState(null); // null | CryptoKey | 'error' const [decrypted, setDecrypted] = useState({}); + const [partnerFp, setPartnerFp] = useState(''); const [text, setText] = useState(''); const [sending, setSending] = useState(false); const bottomRef = useRef(null); @@ -45,16 +47,22 @@ export default function Nachrichten({ toast, mobile }) { return () => clearInterval(pollRef.current); }, [activeUser?.id]); - // ── Shared Key ─────────────────────────────────────────────────────────────── + // ── Shared Key + Partner-Fingerprint ───────────────────────────────────────── useEffect(() => { setSharedKey(null); setDecrypted({}); + setPartnerFp(''); if (!kp || !activeUser?.public_key) return; try { const pubJwk = JSON.parse(activeUser.public_key); deriveSharedKey(kp.privateKey, pubJwk) .then(setSharedKey) .catch(() => setSharedKey('error')); + // Fingerprint des Partner-Keys berechnen (aus dem auf dem Server gespeicherten Public Key) + crypto.subtle.importKey('jwk', pubJwk, { name:'X25519' }, true, []) + .then(k => getFingerprint({ publicKey: k })) + .then(setPartnerFp) + .catch(() => setPartnerFp('?')); } catch { setSharedKey('error'); } @@ -241,10 +249,21 @@ export default function Nachrichten({ toast, mobile }) { whiteSpace:'nowrap', overflow:'hidden', textOverflow:'ellipsis' }}> {activeUser.username} -