aboutsummaryrefslogtreecommitdiffstats
path: root/packages/meshbay-hub/src/meshbay_hub/static/transport.js
diff options
context:
space:
mode:
authorChristophe Besson <cbesson@gmail.com>2026-09-30 21:04:39 +0200
committerChristophe Besson <cbesson@gmail.com>2026-09-30 21:04:39 +0200
commit0378e8e0912a1a7e6cea4424e69d524e7afecbf8 (patch)
tree4ae94e32d6638b4c2cc1ae4f74cbe5d00c940636 /packages/meshbay-hub/src/meshbay_hub/static/transport.js
parent0ed56d3a1b4f71cf622d3e27edc87a15ef33c185 (diff)
downloadmeshbay-0378e8e0912a1a7e6cea4424e69d524e7afecbf8.tar.gz
fix: an identity signs a named kind, and a device approval answers a request
The desktop main process builds every transcript itself from fields (transcripts.js) and signs no raw bytes; the page's identity has the same contract (crypto.js transcriptFor). The keyring seals no bundle while browser access is off. On the node, device_add must redeem a pending request filed by the same keys, and device_revoke is signed under its own prefix (meshbay:device_revoke:v1), so a retirement signature admits nothing. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Diffstat (limited to 'packages/meshbay-hub/src/meshbay_hub/static/transport.js')
-rw-r--r--packages/meshbay-hub/src/meshbay_hub/static/transport.js24
1 files changed, 14 insertions, 10 deletions
diff --git a/packages/meshbay-hub/src/meshbay_hub/static/transport.js b/packages/meshbay-hub/src/meshbay_hub/static/transport.js
index 17a8e5d..9b86921 100644
--- a/packages/meshbay-hub/src/meshbay_hub/static/transport.js
+++ b/packages/meshbay-hub/src/meshbay_hub/static/transport.js
@@ -52,10 +52,13 @@ async function _pkEdFromSk(skPkcs8B64) {
*/
async function _identityFromKeys(skEdB64, skXB64) {
const skXRaw = Uint8Array.from(atob(skXB64), c => c.charCodeAt(0));
+ const own = { pkEdB64: await _pkEdFromSk(skEdB64), pkXB64: await _pkFromSk(skXB64) };
return {
- pkEdB64: await _pkEdFromSk(skEdB64),
- pkXB64: await _pkFromSk(skXB64),
- sign: (bytes) => window.MeshBayKeys.signBytes(skEdB64, bytes),
+ ...own,
+ // By kind and fields, never over bytes a caller chose (crypto.js,
+ // transcriptFor) — the same contract the desktop's main process keeps.
+ signAs: (kind, fields) => window.MeshBayKeys.signBytes(
+ skEdB64, window.MeshBayCrypto.transcriptFor(kind, fields, own)),
async shared(peerPkRaw) {
const sk = await crypto.subtle.importKey(
'pkcs8', skXRaw, { name: 'X25519' }, false, ['deriveBits']);
@@ -77,7 +80,8 @@ function _nativeIdentityHandle(keys, userId, nodePk, pub) {
pkXB64: pub.pkXB64,
sealedWith: pub.sealedWith || null,
native: true,
- sign: (bytes) => keys.sign(userId, nodePk, b64(bytes)),
+ // The main process builds the bytes from the kind and the fields.
+ signAs: (kind, fields) => keys.sign(userId, nodePk, kind, fields),
async shared(peerPkRaw) {
const out = await keys.shared(userId, nodePk, b64(peerPkRaw));
return Uint8Array.from(atob(out), c => c.charCodeAt(0)).buffer;
@@ -672,10 +676,10 @@ class MeshBayTransport {
set onNeedToken(fn) { this._onNeedToken = fn; }
get identity() { return this._identity; }
- /** Signs with this node's identity, or null when there is none yet. */
+ /** Signs an admin operation with this node's identity, or null when there is none yet. */
get signFn() {
const id = this._identity;
- return id ? (transcript) => id.sign(transcript) : null;
+ return id ? (fields) => id.signAs('admin', fields) : null;
}
/** Set on a first join: the identity created for this node, still to be left with it. */
@@ -1343,10 +1347,10 @@ class MeshBayTransport {
// substitution this mechanism exists to close.
const pkEdB64 = this._identity.pkEdB64;
const ts = Math.floor(Date.now() / 1000);
- const transcript = C.deviceHelloTranscript(
- this.nodePk, this._groupId || '', this._userId, pkEdB64,
- this._nonceNode, ts);
- const sig = await this._identity.sign(transcript);
+ const sig = await this._identity.signAs('device_hello', {
+ nodePk: this.nodePk, groupId: this._groupId || '', userId: this._userId,
+ nonceNode: C.b64encode(this._nonceNode), ts,
+ });
const resp = await this._sendAndWait({
type: 'device_hello', v: '2.0', pk_ed25519: pkEdB64, ts, sig,