@dotrino/vaultd 0.153.1 → 0.154.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/lib/src/index.js CHANGED
@@ -217,7 +217,10 @@ export async function startDeviceVault (identity, { proxyUrl, client: injectedCl
217
217
  deviceId: x.sub ? await deviceIdOf(x.sub) : null, sub: x.sub || null,
218
218
  label: x.label || '', scope: x.scope, seq: x.seq, nonce: x.nonce
219
219
  })))
220
- send(from, { type: MSG.DEVICES_RESULT, devices, revoked: (revoked || []).map((r) => r.nonce || r) })
220
+ // La cadena de selladores va con la lista (como en el daemon): es lo que un aparato de
221
+ // Node necesita para firmar a nombre de la cuenta de forma que un extraño lo compruebe.
222
+ const sealerChain = await identity.sealerChain?.().catch(() => null) || null
223
+ send(from, { type: MSG.DEVICES_RESULT, devices, revoked: (revoked || []).map((r) => r.nonce || r), sealerChain })
221
224
  // ¿el que consulta es una máquina revocada que reapareció? → re-emite el REVOKED firmado.
222
225
  // Se busca en `revokedCerts`: desde que `issued` solo trae lo vigente, los retirados
223
226
  // ya no están ahí y este aviso dejaba de dispararse (se caía en silencio).
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@dotrino/vaultd",
3
- "version": "0.153.1",
3
+ "version": "0.154.0",
4
4
  "type": "module",
5
5
  "description": "Certificador personal de Dotrino: daemon headless que custodia la clave maestra y delega capacidades a tus dispositivos por el proxy. Tu CA propia.",
6
6
  "bin": {
@@ -25,7 +25,7 @@
25
25
  "@dotrino/identity": "^0.111.0",
26
26
  "@dotrino/opaque": "0.1.0",
27
27
  "@dotrino/passmanager": "0.17.0",
28
- "@dotrino/proxy-client": "^0.31.1",
28
+ "@dotrino/proxy-client": "^0.32.0",
29
29
  "@dotrino/roadmap": "0.3.19",
30
30
  "@dotrino/store": "0.11.0",
31
31
  "@dotrino/update": "0.5.1",
package/src/vault.js CHANGED
@@ -1288,6 +1288,12 @@ export async function startVault ({ dir = dataDir(), proxyUrl, log = console.log
1288
1288
  // sigue pidiendo `lee`. Antes no preguntaba nada, así que un aparato al que le quitaste
1289
1289
  // el permiso seguía viéndolo todo hasta que su papel caducara.
1290
1290
  const record = (await identity.profileActa?.().catch(() => null))?.acta || null
1291
+ // LA CADENA DE SELLADORES VIAJA CON LA LISTA, también para quien solo puede ver
1292
+ // revocaciones. Es lo que un aparato de Node necesita para FIRMAR a nombre de la cuenta
1293
+ // de forma que un extraño lo compruebe (`verifySignedFor` exige la cadena desde el
1294
+ // génesis), y hasta ahora ningún agente headless podía: solo el navegador la tenía. Es
1295
+ // corta a propósito (génesis, cambios de sellador, actual), así que no pasa por `fitChain`.
1296
+ const sealerChainOf = async () => { try { return (await identity.sealerChain?.()) || null } catch (e) { log('[vault] could not build the sealer chain:', e.message); return null } }
1291
1297
  const puedeVerTodo = !!record && Acta.memberCanScope(record, chk.device, SCOPE.READ)
1292
1298
  const { issued, revoked } = await identity.listDelegations()
1293
1299
  if (!puedeVerTodo) {
@@ -1296,7 +1302,7 @@ export async function startVault ({ dir = dataDir(), proxyUrl, log = console.log
1296
1302
  return reply(from, { type: MSG.ERROR, error: 'unauthorized: this vault has no record to decide with' })
1297
1303
  }
1298
1304
  audit('devices', { device: await deviceIdOf(chk.device).catch(() => null), solo: 'revocaciones' })
1299
- return reply(from, { type: MSG.DEVICES_RESULT, devices: [], revoked, blocked: blocked.pubs(), acta: record })
1305
+ return reply(from, { type: MSG.DEVICES_RESULT, devices: [], revoked, blocked: blocked.pubs(), acta: record, sealerChain: await sealerChainOf() })
1300
1306
  }
1301
1307
  // El acta viaja con la lista: así cada dispositivo se entera de los cambios de
1302
1308
  // política (quién manda, quién puede qué) sin un canal aparte.
@@ -1329,7 +1335,7 @@ export async function startVault ({ dir = dataDir(), proxyUrl, log = console.log
1329
1335
  // LA SUBACTA VIAJA CON EL ACTA. Es la mitad de «se comparte entre todos los
1330
1336
  // dispositivos»: sin esto, una renuncia sin sellar solo la respeta esta máquina.
1331
1337
  // Cada entrada va firmada por su sujeto, así que quien la recibe la verifica sola.
1332
- reply(from, fitChain({ type: MSG.DEVICES_RESULT, devices, revoked, blocked: blocked.pubs(), acta: record, chain, vault: MI_VERSION, subacta: subacta.entries() }))
1338
+ reply(from, fitChain({ type: MSG.DEVICES_RESULT, devices, revoked, blocked: blocked.pubs(), acta: record, chain, sealerChain: await sealerChainOf(), vault: MI_VERSION, subacta: subacta.entries() }))
1333
1339
  }
1334
1340
 
1335
1341
  /**