openvibers/openvibe.network Commits
Agents: a grant on the host's own tenant never reaches the agents it hosts (#434)
Changes
@@@ -113,9 +113,9 @@ const DEFAULT_GRANTS = [// own tokens on their own tenants, not with app keys. Upload also covers the delete of an object.['inventory', 'media.object.upload', 'openvibe.media', ['inventory']],// Codes (C8 proof screenshots, the rich embeds of a task) keeps a person's pictures in Media as private objects on-- // its own tenant, reached with its own token (10-30). Actor is not granted Media yet: Actor hosts people's agents,-- // and a hosted agent may hold what its host holds (agent-grants.test.js), so a Media grant on Actor would let every-- // agent read Actor's tenant. Actor's artifacts wait for a host rule that keeps media.* out of what agents inherit.++ // its own tenant, reached with its own token (10-30). A grant on a host's own tenant never reaches the agents it++ // hosts: an agent's token names only its project's namespaces (agent-tokens.test.js), so it gets no `actor`.++ // Actor holds no Media grant for now all the same: its artifacts are in its own database, owner-only (Actor V2-4)....['media.object.upload', 'media.object.read'].map((cap) => ['codes', cap, 'openvibe.media', ['codes']]),['media-hub', 'media.object.upload', 'openvibe.media', ['media-hub']],['media-hub', 'media.object.read', 'openvibe.media', ['media-hub']],@@@ -197,6 +197,8 @@ const U = { owner: jwt.sign({ sub: 10, id: 10 }, keys.privateKey, { algorithm: 'assert.ok(validate('identity.service-token-claims@1', sc).valid);assert.deepStrictEqual([sc.sub, sc.cap, sc.cap_confirm, sc.ns, sc.env, sc.act], [`agent:${S}`, ['media.object.read'], ['media.object.delete'], [P, `app.${P}.*`], 'production', { sub: 'svc:actor' }]);assert.deepStrictEqual((await mint('actor', S, { scope: 'media.object.read' })).ns, [P], 'only what the read row names');++ await db.prepare("UPDATE principal_grants SET namespaces = '[\"actor\"]' WHERE client_id = 'actor'").run();++ assert.deepStrictEqual((await mint('actor', S)).ns, [], "the host's own tenant never reaches the agents it hosts");await db.prepare("UPDATE principal_grants SET namespaces = '[]' WHERE client_id = 'actor'").run();assert.deepStrictEqual((await mint('actor', S)).ns, [], 'rows that name no namespace give none');await refusedGrant('actor', A, 'invalid_grant');@@@ -1,8 +1,8 @@/*** OpenVibe.Codes keeps a person's pictures in Media as private objects (task screenshots, 10-30). Media takes no app* keys (C-71), so Codes reaches it with its own Network service token: upload and read, on its own tenant only, and-- * nothing else of Media's. Actor holds no Media grant: it hosts people's agents, and an agent may hold what its host-- * holds, so a Media grant there would open Actor's whole tenant to every agent.++ * nothing else of Media's. Actor holds no Media grant: its artifacts live in its own database, owner-only (Actor V2-4).++ * Were it granted one, the agents it hosts would still not reach its tenant (agent-tokens.test.js).** node test/media-private-grants.test.js*/
@@ -113,9 +113,9 @@ const DEFAULT_GRANTS = [
@@ -113,9 +113,9 @@ const DEFAULT_GRANTS = [
// own tokens on their own tenants, not with app keys. Upload also covers the delete of an object.
// own tokens on their own tenants, not with app keys. Upload also covers the delete of an object.
['inventory', 'media.object.upload', 'openvibe.media', ['inventory']],
['inventory', 'media.object.upload', 'openvibe.media', ['inventory']],
// Codes (C8 proof screenshots, the rich embeds of a task) keeps a person's pictures in Media as private objects on
// Codes (C8 proof screenshots, the rich embeds of a task) keeps a person's pictures in Media as private objects on
- // its own tenant, reached with its own token (10-30). Actor is not granted Media yet: Actor hosts people's agents,
- // and a hosted agent may hold what its host holds (agent-grants.test.js), so a Media grant on Actor would let every
- // agent read Actor's tenant. Actor's artifacts wait for a host rule that keeps media.* out of what agents inherit.
+ // its own tenant, reached with its own token (10-30). A grant on a host's own tenant never reaches the agents it
+ // hosts: an agent's token names only its project's namespaces (agent-tokens.test.js), so it gets no `actor`.
+ // Actor holds no Media grant for now all the same: its artifacts are in its own database, owner-only (Actor V2-4).
...['media.object.upload', 'media.object.read'].map((cap) => ['codes', cap, 'openvibe.media', ['codes']]),
...['media.object.upload', 'media.object.read'].map((cap) => ['codes', cap, 'openvibe.media', ['codes']]),
['media-hub', 'media.object.upload', 'openvibe.media', ['media-hub']],
['media-hub', 'media.object.upload', 'openvibe.media', ['media-hub']],
['media-hub', 'media.object.read', 'openvibe.media', ['media-hub']],
['media-hub', 'media.object.read', 'openvibe.media', ['media-hub']],
@@ -197,6 +197,8 @@ const U = { owner: jwt.sign({ sub: 10, id: 10 }, keys.privateKey, { algorithm: '
@@ -197,6 +197,8 @@ const U = { owner: jwt.sign({ sub: 10, id: 10 }, keys.privateKey, { algorithm: '
assert.ok(validate('identity.service-token-claims@1', sc).valid);
assert.ok(validate('identity.service-token-claims@1', sc).valid);
assert.deepStrictEqual([sc.sub, sc.cap, sc.cap_confirm, sc.ns, sc.env, sc.act], [`agent:${S}`, ['media.object.read'], ['media.object.delete'], [P, `app.${P}.*`], 'production', { sub: 'svc:actor' }]);
assert.deepStrictEqual([sc.sub, sc.cap, sc.cap_confirm, sc.ns, sc.env, sc.act], [`agent:${S}`, ['media.object.read'], ['media.object.delete'], [P, `app.${P}.*`], 'production', { sub: 'svc:actor' }]);
assert.deepStrictEqual((await mint('actor', S, { scope: 'media.object.read' })).ns, [P], 'only what the read row names');
assert.deepStrictEqual((await mint('actor', S, { scope: 'media.object.read' })).ns, [P], 'only what the read row names');
+ await db.prepare("UPDATE principal_grants SET namespaces = '[\"actor\"]' WHERE client_id = 'actor'").run();
+ assert.deepStrictEqual((await mint('actor', S)).ns, [], "the host's own tenant never reaches the agents it hosts");
await db.prepare("UPDATE principal_grants SET namespaces = '[]' WHERE client_id = 'actor'").run();
await db.prepare("UPDATE principal_grants SET namespaces = '[]' WHERE client_id = 'actor'").run();
assert.deepStrictEqual((await mint('actor', S)).ns, [], 'rows that name no namespace give none');
assert.deepStrictEqual((await mint('actor', S)).ns, [], 'rows that name no namespace give none');
await refusedGrant('actor', A, 'invalid_grant');
await refusedGrant('actor', A, 'invalid_grant');
@@ -1,8 +1,8 @@
@@ -1,8 +1,8 @@
/**
/**
* OpenVibe.Codes keeps a person's pictures in Media as private objects (task screenshots, 10-30). Media takes no app
* OpenVibe.Codes keeps a person's pictures in Media as private objects (task screenshots, 10-30). Media takes no app
* keys (C-71), so Codes reaches it with its own Network service token: upload and read, on its own tenant only, and
* keys (C-71), so Codes reaches it with its own Network service token: upload and read, on its own tenant only, and
- * nothing else of Media's. Actor holds no Media grant: it hosts people's agents, and an agent may hold what its host
- * holds, so a Media grant there would open Actor's whole tenant to every agent.
+ * nothing else of Media's. Actor holds no Media grant: its artifacts live in its own database, owner-only (Actor V2-4).
+ * Were it granted one, the agents it hosts would still not reach its tenant (agent-tokens.test.js).
*
*
* node test/media-private-grants.test.js
* node test/media-private-grants.test.js
*/
*/