@stigmer/server 3.23.0 → 3.23.1-dev.20260923075205
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/dist/authorization/authorizer.d.ts +4 -8
- package/dist/authorization/authorizer.d.ts.map +1 -1
- package/dist/authorization/authorizer.js +5 -9
- package/dist/authorization/authorizer.js.map +1 -1
- package/dist/authorization/derived-tuples.d.ts.map +1 -1
- package/dist/authorization/derived-tuples.js +10 -25
- package/dist/authorization/derived-tuples.js.map +1 -1
- package/dist/authorization/evaluator.d.ts +7 -8
- package/dist/authorization/evaluator.d.ts.map +1 -1
- package/dist/authorization/evaluator.js +4 -20
- package/dist/authorization/evaluator.js.map +1 -1
- package/dist/authorization/list-read-scope.d.ts.map +1 -1
- package/dist/authorization/list-read-scope.js +5 -9
- package/dist/authorization/list-read-scope.js.map +1 -1
- package/dist/authorization/model/agent.d.ts.map +1 -1
- package/dist/authorization/model/agent.js +4 -5
- package/dist/authorization/model/agent.js.map +1 -1
- package/dist/authorization/model/agent_instance.d.ts.map +1 -1
- package/dist/authorization/model/agent_instance.js +2 -2
- package/dist/authorization/model/agent_instance.js.map +1 -1
- package/dist/authorization/model/mcp_server.d.ts.map +1 -1
- package/dist/authorization/model/mcp_server.js +2 -2
- package/dist/authorization/model/mcp_server.js.map +1 -1
- package/dist/authorization/model/plugin.d.ts.map +1 -1
- package/dist/authorization/model/plugin.js +3 -4
- package/dist/authorization/model/plugin.js.map +1 -1
- package/dist/authorization/model/rewrite.d.ts +8 -10
- package/dist/authorization/model/rewrite.d.ts.map +1 -1
- package/dist/authorization/model/rewrite.js +0 -3
- package/dist/authorization/model/rewrite.js.map +1 -1
- package/dist/authorization/model/skill.d.ts.map +1 -1
- package/dist/authorization/model/skill.js +2 -2
- package/dist/authorization/model/skill.js.map +1 -1
- package/dist/authorization/model/workflow.d.ts.map +1 -1
- package/dist/authorization/model/workflow.js +2 -2
- package/dist/authorization/model/workflow.js.map +1 -1
- package/dist/authorization/model/workflow_instance.d.ts.map +1 -1
- package/dist/authorization/model/workflow_instance.js +2 -2
- package/dist/authorization/model/workflow_instance.js.map +1 -1
- package/dist/authorization/organization-directory.d.ts.map +1 -1
- package/dist/authorization/organization-directory.js +2 -3
- package/dist/authorization/organization-directory.js.map +1 -1
- package/dist/authorization/store-test-kit.d.ts +0 -6
- package/dist/authorization/store-test-kit.d.ts.map +1 -1
- package/dist/authorization/store-test-kit.js +16 -62
- package/dist/authorization/store-test-kit.js.map +1 -1
- package/dist/authorization/tuples.d.ts +13 -32
- package/dist/authorization/tuples.d.ts.map +1 -1
- package/dist/authorization/tuples.js +3 -11
- package/dist/authorization/tuples.js.map +1 -1
- package/dist/domain/agent/controller.d.ts.map +1 -1
- package/dist/domain/agent/controller.js +4 -4
- package/dist/domain/agent/controller.js.map +1 -1
- package/dist/domain/agentchannel/controller.d.ts.map +1 -1
- package/dist/domain/agentchannel/controller.js +3 -1
- package/dist/domain/agentchannel/controller.js.map +1 -1
- package/dist/domain/agentexecution/controller.d.ts.map +1 -1
- package/dist/domain/agentexecution/controller.js +3 -1
- package/dist/domain/agentexecution/controller.js.map +1 -1
- package/dist/domain/agentinstance/controller.d.ts.map +1 -1
- package/dist/domain/agentinstance/controller.js +3 -4
- package/dist/domain/agentinstance/controller.js.map +1 -1
- package/dist/domain/agentshare/constants.d.ts +6 -11
- package/dist/domain/agentshare/constants.d.ts.map +1 -1
- package/dist/domain/agentshare/constants.js +8 -16
- package/dist/domain/agentshare/constants.js.map +1 -1
- package/dist/domain/agentshare/controller.d.ts.map +1 -1
- package/dist/domain/agentshare/controller.js +3 -1
- package/dist/domain/agentshare/controller.js.map +1 -1
- package/dist/domain/agentshare/steps.d.ts +18 -25
- package/dist/domain/agentshare/steps.d.ts.map +1 -1
- package/dist/domain/agentshare/steps.js +41 -142
- package/dist/domain/agentshare/steps.js.map +1 -1
- package/dist/domain/environment/controller.d.ts.map +1 -1
- package/dist/domain/environment/controller.js +2 -3
- package/dist/domain/environment/controller.js.map +1 -1
- package/dist/domain/executioncontext/controller.d.ts.map +1 -1
- package/dist/domain/executioncontext/controller.js +2 -1
- package/dist/domain/executioncontext/controller.js.map +1 -1
- package/dist/domain/mcpserver/controller.d.ts.map +1 -1
- package/dist/domain/mcpserver/controller.js +3 -4
- package/dist/domain/mcpserver/controller.js.map +1 -1
- package/dist/domain/plugin/controller.d.ts.map +1 -1
- package/dist/domain/plugin/controller.js +1 -3
- package/dist/domain/plugin/controller.js.map +1 -1
- package/dist/domain/plugin/push.d.ts +7 -5
- package/dist/domain/plugin/push.d.ts.map +1 -1
- package/dist/domain/plugin/push.js +8 -14
- package/dist/domain/plugin/push.js.map +1 -1
- package/dist/domain/schedule/controller.d.ts.map +1 -1
- package/dist/domain/schedule/controller.js +3 -1
- package/dist/domain/schedule/controller.js.map +1 -1
- package/dist/domain/session/controller.d.ts.map +1 -1
- package/dist/domain/session/controller.js +3 -2
- package/dist/domain/session/controller.js.map +1 -1
- package/dist/domain/skill/controller.d.ts.map +1 -1
- package/dist/domain/skill/controller.js +0 -2
- package/dist/domain/skill/controller.js.map +1 -1
- package/dist/domain/workflow/agent-call-references.d.ts +54 -0
- package/dist/domain/workflow/agent-call-references.d.ts.map +1 -0
- package/dist/domain/workflow/agent-call-references.js +97 -0
- package/dist/domain/workflow/agent-call-references.js.map +1 -0
- package/dist/domain/workflow/controller.d.ts.map +1 -1
- package/dist/domain/workflow/controller.js +14 -6
- package/dist/domain/workflow/controller.js.map +1 -1
- package/dist/domain/workflow/registry/data/task-kind-registry.json +1 -1
- package/dist/domain/workflow/validation/task-config-constraints.d.ts +10 -1
- package/dist/domain/workflow/validation/task-config-constraints.d.ts.map +1 -1
- package/dist/domain/workflow/validation/task-config-constraints.js +3 -2
- package/dist/domain/workflow/validation/task-config-constraints.js.map +1 -1
- package/dist/domain/workflowexecution/controller.d.ts.map +1 -1
- package/dist/domain/workflowexecution/controller.js +4 -2
- package/dist/domain/workflowexecution/controller.js.map +1 -1
- package/dist/domain/workflowinstance/controller.d.ts.map +1 -1
- package/dist/domain/workflowinstance/controller.js +3 -4
- package/dist/domain/workflowinstance/controller.js.map +1 -1
- package/dist/extensions/authorization-queries.d.ts +6 -5
- package/dist/extensions/authorization-queries.d.ts.map +1 -1
- package/dist/extensions/list-read-scope.d.ts +1 -1
- package/dist/extensions/resource-authorization.d.ts +3 -2
- package/dist/extensions/resource-authorization.d.ts.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js.map +1 -1
- package/dist/pipeline/apiresource-meta.d.ts +12 -3
- package/dist/pipeline/apiresource-meta.d.ts.map +1 -1
- package/dist/pipeline/apiresource-meta.js +21 -10
- package/dist/pipeline/apiresource-meta.js.map +1 -1
- package/dist/pipeline/steps/authorization-tuples.d.ts +9 -3
- package/dist/pipeline/steps/authorization-tuples.d.ts.map +1 -1
- package/dist/pipeline/steps/authorization-tuples.js +9 -11
- package/dist/pipeline/steps/authorization-tuples.js.map +1 -1
- package/dist/pipeline/steps/references.d.ts +178 -20
- package/dist/pipeline/steps/references.d.ts.map +1 -1
- package/dist/pipeline/steps/references.js +344 -43
- package/dist/pipeline/steps/references.js.map +1 -1
- package/dist/query/search/controller.js +0 -1
- package/dist/query/search/controller.js.map +1 -1
- package/dist/query/search/criteria.d.ts +1 -5
- package/dist/query/search/criteria.d.ts.map +1 -1
- package/dist/query/search/criteria.js +3 -13
- package/dist/query/search/criteria.js.map +1 -1
- package/dist/query/search/handler.d.ts +5 -4
- package/dist/query/search/handler.d.ts.map +1 -1
- package/dist/query/search/handler.js +7 -6
- package/dist/query/search/handler.js.map +1 -1
- package/dist/query/search/query-store.d.ts.map +1 -1
- package/dist/query/search/query-store.js +0 -2
- package/dist/query/search/query-store.js.map +1 -1
- package/dist/store/interface.d.ts +3 -6
- package/dist/store/interface.d.ts.map +1 -1
- package/dist/store/interface.js.map +1 -1
- package/dist/store/postgres/migrations.d.ts +3 -1
- package/dist/store/postgres/migrations.d.ts.map +1 -1
- package/dist/store/postgres/migrations.js +35 -1
- package/dist/store/postgres/migrations.js.map +1 -1
- package/dist/store/postgres/store.d.ts.map +1 -1
- package/dist/store/postgres/store.js +4 -9
- package/dist/store/postgres/store.js.map +1 -1
- package/dist/store/public-visibility-retired.d.ts +67 -0
- package/dist/store/public-visibility-retired.d.ts.map +1 -0
- package/dist/store/public-visibility-retired.js +55 -0
- package/dist/store/public-visibility-retired.js.map +1 -0
- package/dist/store/sqlite/migrations.d.ts +3 -1
- package/dist/store/sqlite/migrations.d.ts.map +1 -1
- package/dist/store/sqlite/migrations.js +36 -1
- package/dist/store/sqlite/migrations.js.map +1 -1
- package/dist/store/sqlite/store.d.ts.map +1 -1
- package/dist/store/sqlite/store.js +4 -8
- package/dist/store/sqlite/store.js.map +1 -1
- package/package.json +6 -6
- package/src/authorization/README.md +24 -26
- package/src/authorization/__tests__/authorizer.test.ts +10 -9
- package/src/authorization/__tests__/derived-tuples.test.ts +4 -11
- package/src/authorization/__tests__/evaluator.test.ts +14 -73
- package/src/authorization/__tests__/facts.test.ts +2 -2
- package/src/authorization/__tests__/fixtures/fga/agent-instance-creation.fga.yaml +19 -27
- package/src/authorization/__tests__/fixtures/fga/blueprint-private-visibility.fga.yaml +6 -98
- package/src/authorization/__tests__/fixtures/fga/default-instance-inheritance.fga.yaml +4 -61
- package/src/authorization/__tests__/fixtures/fga/mcp-server-authoring.fga.yaml +1 -15
- package/src/authorization/__tests__/fixtures/fga/org-admin-owner-inheritance.fga.yaml +1 -21
- package/src/authorization/__tests__/fixtures/fga/platform-visibility.fga.yaml +1 -25
- package/src/authorization/__tests__/fixtures/fga/workflow-execution-sharing.fga.yaml +1 -3
- package/src/authorization/__tests__/list-read-scope.test.ts +18 -17
- package/src/authorization/__tests__/store-tests.test.ts +2 -6
- package/src/authorization/__tests__/tuples.test.ts +12 -11
- package/src/authorization/authorizer.ts +4 -9
- package/src/authorization/derived-tuples.ts +14 -31
- package/src/authorization/evaluator.ts +8 -44
- package/src/authorization/list-read-scope.ts +5 -11
- package/src/authorization/model/agent.ts +2 -5
- package/src/authorization/model/agent_instance.ts +0 -2
- package/src/authorization/model/mcp_server.ts +0 -2
- package/src/authorization/model/plugin.ts +1 -4
- package/src/authorization/model/rewrite.ts +8 -13
- package/src/authorization/model/skill.ts +0 -2
- package/src/authorization/model/workflow.ts +0 -2
- package/src/authorization/model/workflow_instance.ts +0 -2
- package/src/authorization/organization-directory.ts +1 -3
- package/src/authorization/store-test-kit.ts +16 -75
- package/src/authorization/tuples.ts +16 -39
- package/src/domain/agent/__tests__/agent.test.ts +11 -4
- package/src/domain/agent/controller.ts +7 -7
- package/src/domain/agentchannel/__tests__/agentchannel.test.ts +223 -48
- package/src/domain/agentchannel/controller.ts +6 -1
- package/src/domain/agentexecution/controller.ts +6 -1
- package/src/domain/agentinstance/controller.ts +6 -12
- package/src/domain/agentshare/__tests__/agentshare.test.ts +196 -172
- package/src/domain/agentshare/__tests__/create-authorization.test.ts +16 -31
- package/src/domain/agentshare/constants.ts +14 -26
- package/src/domain/agentshare/controller.ts +6 -1
- package/src/domain/agentshare/steps.ts +41 -194
- package/src/domain/environment/controller.ts +5 -8
- package/src/domain/executioncontext/controller.ts +5 -1
- package/src/domain/mcpserver/__tests__/mcpserver.test.ts +115 -28
- package/src/domain/mcpserver/__tests__/oauth-handshake.test.ts +53 -18
- package/src/domain/mcpserver/controller.ts +6 -12
- package/src/domain/plugin/controller.ts +1 -8
- package/src/domain/plugin/push.ts +8 -16
- package/src/domain/schedule/controller.ts +6 -1
- package/src/domain/session/controller.ts +12 -4
- package/src/domain/skill/controller.ts +0 -7
- package/src/domain/workflow/__tests__/agent-call-references.test.ts +222 -0
- package/src/domain/workflow/agent-call-references.ts +157 -0
- package/src/domain/workflow/controller.ts +28 -10
- package/src/domain/workflow/registry/data/task-kind-registry.json +1 -1
- package/src/domain/workflow/validation/task-config-constraints.ts +7 -3
- package/src/domain/workflowexecution/controller.ts +7 -2
- package/src/domain/workflowinstance/controller.ts +6 -12
- package/src/extensions/__tests__/built-in-authorization-composed.test.ts +32 -19
- package/src/extensions/__tests__/extension-composition.test.ts +4 -4
- package/src/extensions/__tests__/list-read-scope-composed.test.ts +9 -6
- package/src/extensions/authorization-queries.ts +6 -5
- package/src/extensions/list-read-scope.ts +1 -1
- package/src/extensions/resource-authorization.ts +3 -5
- package/src/index.ts +0 -1
- package/src/pipeline/__tests__/supports-visibility.test.ts +112 -0
- package/src/pipeline/apiresource-meta.ts +21 -10
- package/src/pipeline/steps/__tests__/authorization-tuples.test.ts +18 -31
- package/src/pipeline/steps/__tests__/references.test.ts +703 -0
- package/src/pipeline/steps/authorization-tuples.ts +9 -11
- package/src/pipeline/steps/references.ts +578 -70
- package/src/query/search/__tests__/criteria.test.ts +0 -4
- package/src/query/search/__tests__/query-store.test.ts +11 -40
- package/src/query/search/controller.ts +0 -1
- package/src/query/search/criteria.ts +0 -14
- package/src/query/search/handler.ts +6 -7
- package/src/query/search/query-store.ts +0 -2
- package/src/store/__tests__/public-visibility-retired.test.ts +127 -0
- package/src/store/__tests__/store-contract.ts +6 -51
- package/src/store/interface.ts +3 -6
- package/src/store/postgres/__tests__/migrations.test.ts +187 -6
- package/src/store/postgres/__tests__/store-contract.test.ts +0 -2
- package/src/store/postgres/migrations.ts +48 -1
- package/src/store/postgres/store.ts +4 -11
- package/src/store/public-visibility-retired.ts +119 -0
- package/src/store/sqlite/__tests__/migrations.test.ts +191 -5
- package/src/store/sqlite/migrations.ts +45 -1
- package/src/store/sqlite/store.ts +4 -10
- package/dist/pipeline/steps/visibility-gates.d.ts +0 -27
- package/dist/pipeline/steps/visibility-gates.d.ts.map +0 -1
- package/dist/pipeline/steps/visibility-gates.js +0 -139
- package/dist/pipeline/steps/visibility-gates.js.map +0 -1
- package/src/authorization/__tests__/fixtures/fga/cross-org-share-creation.fga.yaml +0 -98
- package/src/authorization/__tests__/fixtures/fga/public-visibility-setter.fga.yaml +0 -52
- package/src/pipeline/steps/__tests__/visibility-gates.test.ts +0 -187
- package/src/pipeline/steps/visibility-gates.ts +0 -174
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Pins the create lane's two
|
|
3
|
-
*
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
7
|
-
*
|
|
2
|
+
* Pins the create lane's two questions (steps.ts, resolveShareCreateTargets):
|
|
3
|
+
* can_edit on the referenced agent, then can_create_agent_share on the
|
|
4
|
+
* share's organization, in that order, each with its byte-pinned copy. A
|
|
5
|
+
* share's agent lives in the share's organization (the resolve step refuses
|
|
6
|
+
* anything else before this runs), so the two bars are one organization's:
|
|
7
|
+
* sharing puts the agent in front of a wider audience (an editor's act) and
|
|
8
|
+
* spends the organization's credits on the open internet (an admin's). A
|
|
9
|
+
* missing referenced agent throws.
|
|
8
10
|
*/
|
|
9
11
|
import { describe, expect, it } from "vitest";
|
|
10
12
|
import { create } from "@bufbuild/protobuf";
|
|
@@ -24,15 +26,15 @@ import {
|
|
|
24
26
|
} from "../steps.js";
|
|
25
27
|
|
|
26
28
|
const agent = create(AgentSchema, {
|
|
27
|
-
metadata: { id: "
|
|
29
|
+
metadata: { id: "agt_01helper", name: "helper", org: "publisher-org" },
|
|
28
30
|
});
|
|
29
31
|
|
|
30
|
-
function ctxFor(shareOrg: string,
|
|
32
|
+
function ctxFor(shareOrg: string, stash = true) {
|
|
31
33
|
const ctx = new RequestContext(
|
|
32
34
|
AgentShareSchema,
|
|
33
35
|
create(AgentShareSchema, {
|
|
34
36
|
metadata: { name: "helper", org: shareOrg },
|
|
35
|
-
spec: { agentRef: { org:
|
|
37
|
+
spec: { agentRef: { org: shareOrg, slug: "helper" } },
|
|
36
38
|
}),
|
|
37
39
|
testCallerIdentity(),
|
|
38
40
|
ApiResourceKind.agent_share,
|
|
@@ -44,33 +46,18 @@ function ctxFor(shareOrg: string, agentOrg: string, stash = true) {
|
|
|
44
46
|
}
|
|
45
47
|
|
|
46
48
|
describe("resolveShareCreateTargets", () => {
|
|
47
|
-
it("
|
|
48
|
-
expect(
|
|
49
|
-
resolveShareCreateTargets(ctxFor("publisher-org", "publisher-org")),
|
|
50
|
-
).toEqual([
|
|
49
|
+
it("asks can_edit on the referenced agent, then can_create_agent_share on the share's organization", () => {
|
|
50
|
+
expect(resolveShareCreateTargets(ctxFor("publisher-org"))).toEqual([
|
|
51
51
|
{
|
|
52
52
|
permission: IamPermission.can_edit,
|
|
53
53
|
resourceKind: ApiResourceKind.agent,
|
|
54
|
-
resourceId: "
|
|
55
|
-
deniedMessage: SHARE_AGENT_DENIED_MESSAGE,
|
|
56
|
-
},
|
|
57
|
-
]);
|
|
58
|
-
});
|
|
59
|
-
|
|
60
|
-
it("a cross-org share asks can_execute on the agent, then can_create_agent_share on the sharing organization", () => {
|
|
61
|
-
expect(
|
|
62
|
-
resolveShareCreateTargets(ctxFor("consumer-org", "publisher-org")),
|
|
63
|
-
).toEqual([
|
|
64
|
-
{
|
|
65
|
-
permission: IamPermission.can_execute,
|
|
66
|
-
resourceKind: ApiResourceKind.agent,
|
|
67
|
-
resourceId: "agt_01public",
|
|
54
|
+
resourceId: "agt_01helper",
|
|
68
55
|
deniedMessage: SHARE_AGENT_DENIED_MESSAGE,
|
|
69
56
|
},
|
|
70
57
|
{
|
|
71
58
|
permission: IamPermission.can_create_agent_share,
|
|
72
59
|
resourceKind: ApiResourceKind.organization,
|
|
73
|
-
resourceId: "
|
|
60
|
+
resourceId: "publisher-org",
|
|
74
61
|
deniedMessage: SHARE_ORGANIZATION_DENIED_MESSAGE,
|
|
75
62
|
},
|
|
76
63
|
]);
|
|
@@ -78,9 +65,7 @@ describe("resolveShareCreateTargets", () => {
|
|
|
78
65
|
|
|
79
66
|
it("a missing referenced agent is a broken chain invariant and throws", () => {
|
|
80
67
|
expect(() =>
|
|
81
|
-
resolveShareCreateTargets(
|
|
82
|
-
ctxFor("publisher-org", "publisher-org", false),
|
|
83
|
-
),
|
|
68
|
+
resolveShareCreateTargets(ctxFor("publisher-org", false)),
|
|
84
69
|
).toThrow("referenced agent not found in context");
|
|
85
70
|
});
|
|
86
71
|
});
|
|
@@ -17,10 +17,12 @@ export const SHARE_LINK_TOKEN_BYTES = 20;
|
|
|
17
17
|
* resolveShareDefaultsStep, byte-pinned. The share's org appears in the
|
|
18
18
|
* hosted chat URL and is the billing org, so it can never be inferred.
|
|
19
19
|
*/
|
|
20
|
-
export const ORG_REQUIRED_MESSAGE =
|
|
20
|
+
export const ORG_REQUIRED_MESSAGE =
|
|
21
|
+
"metadata.org is required for an agent share";
|
|
21
22
|
|
|
22
23
|
/** InvalidArgument copy when spec.agent_ref.slug is absent — Go, pinned. */
|
|
23
|
-
export const AGENT_REF_SLUG_REQUIRED_MESSAGE =
|
|
24
|
+
export const AGENT_REF_SLUG_REQUIRED_MESSAGE =
|
|
25
|
+
"spec.agent_ref.slug is required";
|
|
24
26
|
|
|
25
27
|
/**
|
|
26
28
|
* InvalidArgument copy for BOTH profile lanes when org is absent — Go
|
|
@@ -28,34 +30,20 @@ export const AGENT_REF_SLUG_REQUIRED_MESSAGE = "spec.agent_ref.slug is required"
|
|
|
28
30
|
* Anti-enumeration: an empty org would mean "match slug across all orgs"
|
|
29
31
|
* on a public endpoint.
|
|
30
32
|
*/
|
|
31
|
-
export const ORG_REQUIRED_FOR_LOOKUP_MESSAGE =
|
|
33
|
+
export const ORG_REQUIRED_FOR_LOOKUP_MESSAGE =
|
|
34
|
+
"org is required for shared agent lookup";
|
|
32
35
|
|
|
33
36
|
/**
|
|
34
|
-
* FailedPrecondition copy
|
|
35
|
-
*
|
|
36
|
-
*
|
|
37
|
+
* FailedPrecondition copy when spec.agent_ref names another organization's
|
|
38
|
+
* agent — the schedule's and the channel's same-organization sentence in
|
|
39
|
+
* the share's own words. A share offers an agent its own organization
|
|
40
|
+
* owns; to share another organization's agent, install the plugin that
|
|
41
|
+
* carries it and share the installed copy.
|
|
37
42
|
*/
|
|
38
|
-
export function
|
|
43
|
+
export function sameOrgInvariantMessage(refOrg: string): string {
|
|
39
44
|
return (
|
|
40
|
-
"
|
|
41
|
-
`
|
|
42
|
-
);
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
/**
|
|
46
|
-
* FailedPrecondition copy naming every non-public dependency blocking a
|
|
47
|
-
* cross-org share (decision 013 D5) — Go validateCrossOrgShare,
|
|
48
|
-
* byte-pinned. Blockers are deduped, formatted "<kind> <org>/<slug>", and
|
|
49
|
-
* sorted, so the refusal is deterministic.
|
|
50
|
-
*/
|
|
51
|
-
export function crossOrgBlockersMessage(
|
|
52
|
-
agentOrg: string,
|
|
53
|
-
agentSlug: string,
|
|
54
|
-
blockers: readonly string[],
|
|
55
|
-
): string {
|
|
56
|
-
return (
|
|
57
|
-
`cannot share ${agentOrg}/${agentSlug} across organizations: ` +
|
|
58
|
-
`it references resources that are not public: ${blockers.join(", ")}`
|
|
45
|
+
"spec.agent_ref.org must match metadata.org — a share must live in " +
|
|
46
|
+
`the referenced agent's organization (${refOrg})`
|
|
59
47
|
);
|
|
60
48
|
}
|
|
61
49
|
|
|
@@ -93,7 +93,10 @@ import {
|
|
|
93
93
|
TARGET_RESOURCE_KEY,
|
|
94
94
|
newLoadTargetStep,
|
|
95
95
|
} from "../../pipeline/steps/load-target.js";
|
|
96
|
-
import {
|
|
96
|
+
import {
|
|
97
|
+
newNormalizeReferencesStep,
|
|
98
|
+
newValidateReferencesStep,
|
|
99
|
+
} from "../../pipeline/steps/references.js";
|
|
97
100
|
import {
|
|
98
101
|
newCleanupIamPoliciesStep,
|
|
99
102
|
newCreateAuthorizationTuplesStep,
|
|
@@ -195,6 +198,7 @@ async function createShare(
|
|
|
195
198
|
.addStep(newGuardReservedLabelsStep(deps.authorizer))
|
|
196
199
|
.addStep(newStampAgentPinStep())
|
|
197
200
|
.addStep(newNormalizeReferencesStep())
|
|
201
|
+
.addStep(newValidateReferencesStep(deps.store))
|
|
198
202
|
.addStep(newPersistStep(deps.store))
|
|
199
203
|
.addStep(
|
|
200
204
|
newCreateAuthorizationTuplesStep(
|
|
@@ -239,6 +243,7 @@ async function update(
|
|
|
239
243
|
.addStep(newBuildUpdateStateStep())
|
|
240
244
|
.addStep(newGuardReservedLabelsStep(deps.authorizer))
|
|
241
245
|
.addStep(newNormalizeReferencesStep())
|
|
246
|
+
.addStep(newValidateReferencesStep(deps.store))
|
|
242
247
|
.addStep(newPersistStep(deps.store))
|
|
243
248
|
.build()
|
|
244
249
|
.execute(reqCtx);
|
|
@@ -1,10 +1,19 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* AgentShare domain steps — ports pkg/domain/agentshare/controller/steps.go
|
|
3
|
-
* and the get_shared_profile.go helpers: share defaults
|
|
4
|
-
*
|
|
3
|
+
* and the get_shared_profile.go helpers: share defaults and the
|
|
4
|
+
* same-organization invariant on agent_ref, the agent-id rebind pin, the
|
|
5
5
|
* update immutability rules, the uniform-NotFound profile resolution
|
|
6
6
|
* helpers, and the constant-time link-token predicate.
|
|
7
7
|
*
|
|
8
|
+
* A share's agent lives in the share's own organization. The
|
|
9
|
+
* cross-organization arm this domain once carried (a share of another
|
|
10
|
+
* organization's public agent, gated on a public audience and a sweep of
|
|
11
|
+
* the agent's dependencies for public visibility) left with the public
|
|
12
|
+
* level; sharing another organization's agent is done by installing the
|
|
13
|
+
* plugin that carries it and sharing the installed copy. A stored share
|
|
14
|
+
* whose agent is in another organization — a row from before — fails
|
|
15
|
+
* closed at the profile like a dangling reference.
|
|
16
|
+
*
|
|
8
17
|
* OD-1 (deliberate exclusion): Go's boot migration
|
|
9
18
|
* (pkg/domain/agentshare/migration/bootstrap_shares.go — protowire
|
|
10
19
|
* decoding of the REMOVED Agent.spec.sharing fields into AgentShare rows)
|
|
@@ -29,11 +38,6 @@ import type { AgentShare } from "@stigmer/protos/ai/stigmer/agentic/agentshare/v
|
|
|
29
38
|
import { AgentShareStatusSchema } from "@stigmer/protos/ai/stigmer/agentic/agentshare/v1/status_pb";
|
|
30
39
|
import { SharedAgentProfileSchema } from "@stigmer/protos/ai/stigmer/agentic/agentshare/v1/io_pb";
|
|
31
40
|
import type { SharedAgentProfile } from "@stigmer/protos/ai/stigmer/agentic/agentshare/v1/io_pb";
|
|
32
|
-
import { AgentShareAudience } from "@stigmer/protos/ai/stigmer/agentic/agentshare/v1/spec_pb";
|
|
33
|
-
import { McpServerSchema } from "@stigmer/protos/ai/stigmer/agentic/mcpserver/v1/api_pb";
|
|
34
|
-
import { SkillSchema } from "@stigmer/protos/ai/stigmer/agentic/skill/v1/api_pb";
|
|
35
|
-
import { ApiResourceVisibility } from "@stigmer/protos/ai/stigmer/commons/apiresource/enum_pb";
|
|
36
|
-
import type { ApiResourceReference } from "@stigmer/protos/ai/stigmer/commons/apiresource/io_pb";
|
|
37
41
|
import { ApiResourceKind } from "@stigmer/protos/ai/stigmer/commons/apiresource/apiresourcekind/api_resource_kind_pb";
|
|
38
42
|
import { IamPermission } from "@stigmer/protos/ai/stigmer/iam/v1/enum_pb";
|
|
39
43
|
|
|
@@ -52,7 +56,6 @@ import {
|
|
|
52
56
|
} from "../../pipeline/steps/authorize.js";
|
|
53
57
|
import type { AuthorizationTarget } from "../../pipeline/steps/authorize.js";
|
|
54
58
|
import type { GetByReferenceDesc } from "../../pipeline/steps/authorize-resolved-target.js";
|
|
55
|
-
import { findResourceBySlug } from "../../pipeline/steps/helpers.js";
|
|
56
59
|
import { EXISTING_RESOURCE_KEY } from "../../pipeline/steps/load-existing.js";
|
|
57
60
|
import type { Store } from "../../store/interface.js";
|
|
58
61
|
import {
|
|
@@ -60,8 +63,7 @@ import {
|
|
|
60
63
|
ORG_REQUIRED_MESSAGE,
|
|
61
64
|
SHARE_LINK_TOKEN_BYTES,
|
|
62
65
|
agentRefImmutableMessage,
|
|
63
|
-
|
|
64
|
-
crossOrgBlockersMessage,
|
|
66
|
+
sameOrgInvariantMessage,
|
|
65
67
|
} from "./constants.js";
|
|
66
68
|
|
|
67
69
|
type AgentShareDesc = typeof AgentShareSchema;
|
|
@@ -84,21 +86,14 @@ export const SHARE_ORGANIZATION_DENIED_MESSAGE =
|
|
|
84
86
|
|
|
85
87
|
/**
|
|
86
88
|
* The create lane's authorization questions, for AuthorizeResolvedTarget
|
|
87
|
-
* after ResolveShareDefaults
|
|
88
|
-
*
|
|
89
|
-
*
|
|
90
|
-
*
|
|
91
|
-
*
|
|
92
|
-
*
|
|
93
|
-
*
|
|
94
|
-
*
|
|
95
|
-
*
|
|
96
|
-
* A cross-org share of another organization's public agent asks two
|
|
97
|
-
* questions, agent first as Java did: can_execute on the agent (whoever may
|
|
98
|
-
* run it may offer it) and then can_create_agent_share on the SHARING
|
|
99
|
-
* organization — a public share spends that organization's credits on the
|
|
100
|
-
* open internet, an admin-level act. The cross-org validity rules (public
|
|
101
|
-
* agent, no org audience, public dependencies) stay the resolve step's.
|
|
89
|
+
* after ResolveShareDefaults, agent first: can_edit on the agent (sharing
|
|
90
|
+
* puts it in front of a wider audience, an editor's act) and then
|
|
91
|
+
* can_create_agent_share on the organization (a share spends the
|
|
92
|
+
* organization's credits on the open internet, an admin-level act). The
|
|
93
|
+
* RPC is is_skip_authorization because the target is the referenced agent,
|
|
94
|
+
* resolved from a slug, not a request field. The resolve step has already
|
|
95
|
+
* made the reference absolute and refused an agent outside the share's
|
|
96
|
+
* organization, so the two bars are always the same organization's.
|
|
102
97
|
*/
|
|
103
98
|
export function resolveShareCreateTargets(
|
|
104
99
|
ctx: RequestContext<AgentShareDesc>,
|
|
@@ -107,24 +102,17 @@ export function resolveShareCreateTargets(
|
|
|
107
102
|
if (agent === undefined) {
|
|
108
103
|
throw new Error("referenced agent not found in context");
|
|
109
104
|
}
|
|
110
|
-
const share = ctx.newState;
|
|
111
|
-
const shareOrg = share.metadata?.org ?? "";
|
|
112
|
-
const crossOrg = (share.spec?.agentRef?.org ?? "") !== shareOrg;
|
|
113
|
-
const agentBar: AuthorizationTarget = {
|
|
114
|
-
permission: crossOrg ? IamPermission.can_execute : IamPermission.can_edit,
|
|
115
|
-
resourceKind: ApiResourceKind.agent,
|
|
116
|
-
resourceId: agent.metadata?.id ?? "",
|
|
117
|
-
deniedMessage: SHARE_AGENT_DENIED_MESSAGE,
|
|
118
|
-
};
|
|
119
|
-
if (!crossOrg) {
|
|
120
|
-
return [agentBar];
|
|
121
|
-
}
|
|
122
105
|
return [
|
|
123
|
-
|
|
106
|
+
{
|
|
107
|
+
permission: IamPermission.can_edit,
|
|
108
|
+
resourceKind: ApiResourceKind.agent,
|
|
109
|
+
resourceId: agent.metadata?.id ?? "",
|
|
110
|
+
deniedMessage: SHARE_AGENT_DENIED_MESSAGE,
|
|
111
|
+
},
|
|
124
112
|
{
|
|
125
113
|
permission: IamPermission.can_create_agent_share,
|
|
126
114
|
resourceKind: ApiResourceKind.organization,
|
|
127
|
-
resourceId:
|
|
115
|
+
resourceId: ctx.newState.metadata?.org ?? "",
|
|
128
116
|
deniedMessage: SHARE_ORGANIZATION_DENIED_MESSAGE,
|
|
129
117
|
},
|
|
130
118
|
];
|
|
@@ -306,10 +294,12 @@ export async function findShareByOrgAndSlug(
|
|
|
306
294
|
/**
|
|
307
295
|
* ResolveShareDefaults — Go resolveShareDefaultsStep:
|
|
308
296
|
* 1. Requires metadata.org (URL + billing identity, never inferred).
|
|
309
|
-
* 2. Normalizes spec.agent_ref.org (empty means same-org) and
|
|
310
|
-
*
|
|
311
|
-
*
|
|
312
|
-
*
|
|
297
|
+
* 2. Normalizes spec.agent_ref.org (empty means same-org) and refuses an
|
|
298
|
+
* agent_ref that names another organization (the module header) with
|
|
299
|
+
* the same-organization sentence, BEFORE any lookup, so the share
|
|
300
|
+
* lane never says whether another organization's slug exists.
|
|
301
|
+
* 3. Loads the referenced agent — a nonexistent agent is refused with
|
|
302
|
+
* the same NOT_FOUND a direct agent lookup would produce.
|
|
313
303
|
* 4. Defaults metadata.slug (and name) from the agent when the caller
|
|
314
304
|
* provided neither — the canonical share keeps the agent's hosted URL.
|
|
315
305
|
* Runs before ResolveSlug, which skips already-set slugs.
|
|
@@ -337,6 +327,9 @@ export function newResolveShareDefaultsStep(
|
|
|
337
327
|
if (agentRef!.org === "") {
|
|
338
328
|
agentRef!.org = metadata!.org;
|
|
339
329
|
}
|
|
330
|
+
if (agentRef!.org !== metadata!.org) {
|
|
331
|
+
throw failedPreconditionError(sameOrgInvariantMessage(agentRef!.org));
|
|
332
|
+
}
|
|
340
333
|
|
|
341
334
|
const agent = await findAgentByOrgAndSlug(
|
|
342
335
|
store,
|
|
@@ -347,10 +340,6 @@ export function newResolveShareDefaultsStep(
|
|
|
347
340
|
throw notFoundError("Agent", agentRef!.slug);
|
|
348
341
|
}
|
|
349
342
|
|
|
350
|
-
if (agentRef!.org !== metadata!.org) {
|
|
351
|
-
await validateCrossOrgShare(store, share, agent);
|
|
352
|
-
}
|
|
353
|
-
|
|
354
343
|
ctx.set(REFERENCED_AGENT_KEY, agent);
|
|
355
344
|
|
|
356
345
|
// Canonical-share default: no slug and no name means "share this
|
|
@@ -364,133 +353,6 @@ export function newResolveShareDefaultsStep(
|
|
|
364
353
|
};
|
|
365
354
|
}
|
|
366
355
|
|
|
367
|
-
/**
|
|
368
|
-
* The cross-org share contract (decision 013) — Go validateCrossOrgShare:
|
|
369
|
-
* - The agent must be marketplace-public; a non-public agent is refused
|
|
370
|
-
* with the same NOT_FOUND as a missing one (no existence probe for
|
|
371
|
-
* private slugs).
|
|
372
|
-
* - The audience must be public — org-audience semantics don't carry
|
|
373
|
-
* across the org boundary.
|
|
374
|
-
* - Every declared dependency must itself be public; the refusal names
|
|
375
|
-
* every blocker (sorted) so the sharing org knows exactly what to ask
|
|
376
|
-
* the agent's org to publish.
|
|
377
|
-
* Runtime re-enforcement is cloud-side; this create-time sweep is the
|
|
378
|
-
* fail-loud half, mirrored in both editions.
|
|
379
|
-
*/
|
|
380
|
-
async function validateCrossOrgShare(
|
|
381
|
-
store: Store,
|
|
382
|
-
share: AgentShare,
|
|
383
|
-
agent: Agent,
|
|
384
|
-
): Promise<void> {
|
|
385
|
-
const agentMeta = agent.metadata;
|
|
386
|
-
|
|
387
|
-
if (agentMeta?.visibility !== ApiResourceVisibility.visibility_public) {
|
|
388
|
-
throw notFoundError("Agent", agentMeta?.slug ?? "");
|
|
389
|
-
}
|
|
390
|
-
|
|
391
|
-
// protobuf-es strips the shared enum prefix: proto
|
|
392
|
-
// agent_share_audience_org generates as AgentShareAudience.org.
|
|
393
|
-
if (share.spec?.audience === AgentShareAudience.org) {
|
|
394
|
-
throw failedPreconditionError(crossOrgAudienceMessage(agentMeta.org));
|
|
395
|
-
}
|
|
396
|
-
|
|
397
|
-
const blockers = await findNonPublicDependencies(store, agent);
|
|
398
|
-
if (blockers.length > 0) {
|
|
399
|
-
throw failedPreconditionError(
|
|
400
|
-
crossOrgBlockersMessage(agentMeta.org, agentMeta.slug, blockers),
|
|
401
|
-
);
|
|
402
|
-
}
|
|
403
|
-
}
|
|
404
|
-
|
|
405
|
-
/**
|
|
406
|
-
* Sweeps the agent's declared blueprint dependencies — skill_refs
|
|
407
|
-
* (including every sub-agent's) and mcp_server_usages — and returns a
|
|
408
|
-
* deterministic "kind org/slug" entry for each that is missing or not
|
|
409
|
-
* visibility_public — Go findNonPublicDependencies. A reference with an
|
|
410
|
-
* empty org is relative to the AGENT's org (defensive parity with the
|
|
411
|
-
* cloud edition's referenceMatches; agent writes normalize refs to
|
|
412
|
-
* absolute form).
|
|
413
|
-
*/
|
|
414
|
-
async function findNonPublicDependencies(
|
|
415
|
-
store: Store,
|
|
416
|
-
agent: Agent,
|
|
417
|
-
): Promise<string[]> {
|
|
418
|
-
const spec = agent.spec;
|
|
419
|
-
const agentOrg = agent.metadata?.org ?? "";
|
|
420
|
-
|
|
421
|
-
interface DepRef {
|
|
422
|
-
kind: ApiResourceKind;
|
|
423
|
-
org: string;
|
|
424
|
-
slug: string;
|
|
425
|
-
}
|
|
426
|
-
|
|
427
|
-
const seen = new Set<string>();
|
|
428
|
-
const deps: DepRef[] = [];
|
|
429
|
-
const add = (
|
|
430
|
-
kind: ApiResourceKind,
|
|
431
|
-
ref: ApiResourceReference | undefined,
|
|
432
|
-
): void => {
|
|
433
|
-
if (ref === undefined || ref.slug === "") {
|
|
434
|
-
return;
|
|
435
|
-
}
|
|
436
|
-
const org = ref.org !== "" ? ref.org : agentOrg;
|
|
437
|
-
const key = `${kind}|${org}|${ref.slug}`;
|
|
438
|
-
if (!seen.has(key)) {
|
|
439
|
-
seen.add(key);
|
|
440
|
-
deps.push({ kind, org, slug: ref.slug });
|
|
441
|
-
}
|
|
442
|
-
};
|
|
443
|
-
|
|
444
|
-
for (const ref of spec?.skillRefs ?? []) {
|
|
445
|
-
add(ApiResourceKind.skill, ref);
|
|
446
|
-
}
|
|
447
|
-
for (const sub of spec?.subAgents ?? []) {
|
|
448
|
-
for (const ref of sub.skillRefs) {
|
|
449
|
-
add(ApiResourceKind.skill, ref);
|
|
450
|
-
}
|
|
451
|
-
}
|
|
452
|
-
for (const usage of spec?.mcpServerUsages ?? []) {
|
|
453
|
-
add(ApiResourceKind.mcp_server, usage.mcpServerRef);
|
|
454
|
-
}
|
|
455
|
-
|
|
456
|
-
const blockers: string[] = [];
|
|
457
|
-
for (const dep of deps) {
|
|
458
|
-
let visibility: ApiResourceVisibility | undefined;
|
|
459
|
-
try {
|
|
460
|
-
// Per-kind resolution, exactly Go's switch — skill and mcp_server
|
|
461
|
-
// are the only dependency kinds an agent blueprint declares.
|
|
462
|
-
const resolved =
|
|
463
|
-
dep.kind === ApiResourceKind.skill
|
|
464
|
-
? await findResourceBySlug(
|
|
465
|
-
store,
|
|
466
|
-
dep.kind,
|
|
467
|
-
SkillSchema,
|
|
468
|
-
dep.slug,
|
|
469
|
-
dep.org,
|
|
470
|
-
)
|
|
471
|
-
: await findResourceBySlug(
|
|
472
|
-
store,
|
|
473
|
-
dep.kind,
|
|
474
|
-
McpServerSchema,
|
|
475
|
-
dep.slug,
|
|
476
|
-
dep.org,
|
|
477
|
-
);
|
|
478
|
-
visibility = resolved?.metadata?.visibility;
|
|
479
|
-
} catch (error) {
|
|
480
|
-
throw internalError(
|
|
481
|
-
error,
|
|
482
|
-
`failed to resolve ${ApiResourceKind[dep.kind]} ${dep.org}/${dep.slug} while validating cross-org share`,
|
|
483
|
-
);
|
|
484
|
-
}
|
|
485
|
-
if (visibility !== ApiResourceVisibility.visibility_public) {
|
|
486
|
-
blockers.push(`${ApiResourceKind[dep.kind]} ${dep.org}/${dep.slug}`);
|
|
487
|
-
}
|
|
488
|
-
}
|
|
489
|
-
|
|
490
|
-
blockers.sort();
|
|
491
|
-
return blockers;
|
|
492
|
-
}
|
|
493
|
-
|
|
494
356
|
/**
|
|
495
357
|
* StampAgentPin — Go stampAgentPinStep: writes status.agent_id, the
|
|
496
358
|
* server-owned rebind pin (decision 013). agent_ref is org+slug and slugs
|
|
@@ -524,10 +386,8 @@ export function newStampAgentPinStep(): PipelineStep<AgentShareDesc> {
|
|
|
524
386
|
|
|
525
387
|
/**
|
|
526
388
|
* ValidateShareUpdate — Go validateShareUpdateStep: spec.agent_ref must
|
|
527
|
-
* keep referencing the same agent
|
|
528
|
-
*
|
|
529
|
-
* open a side door to an org-audience cross-org share). Runs after
|
|
530
|
-
* LoadExisting. metadata.slug/org immutability needs no step — the generic
|
|
389
|
+
* keep referencing the same agent. Runs after LoadExisting.
|
|
390
|
+
* metadata.slug/org immutability needs no step — the generic
|
|
531
391
|
* BuildUpdateState preserves both, and status (including the pin and link
|
|
532
392
|
* token) wholesale.
|
|
533
393
|
*/
|
|
@@ -564,14 +424,6 @@ export function newValidateShareUpdateStep(): PipelineStep<AgentShareDesc> {
|
|
|
564
424
|
),
|
|
565
425
|
);
|
|
566
426
|
}
|
|
567
|
-
|
|
568
|
-
const isCrossOrg =
|
|
569
|
-
(existingRef?.org ?? "") !== (existing.metadata?.org ?? "");
|
|
570
|
-
if (isCrossOrg && ctx.input.spec?.audience === AgentShareAudience.org) {
|
|
571
|
-
throw failedPreconditionError(
|
|
572
|
-
crossOrgAudienceMessage(existingRef?.org ?? ""),
|
|
573
|
-
);
|
|
574
|
-
}
|
|
575
427
|
},
|
|
576
428
|
};
|
|
577
429
|
}
|
|
@@ -583,8 +435,8 @@ export function newValidateShareUpdateStep(): PipelineStep<AgentShareDesc> {
|
|
|
583
435
|
* SHARE; display fields and default_instance_id from the AGENT. Three
|
|
584
436
|
* misses all fail closed with the uniform refusal, indistinguishable from
|
|
585
437
|
* absence: a dangling agent_ref, a stale agent-id pin (the rebind guard),
|
|
586
|
-
* and
|
|
587
|
-
*
|
|
438
|
+
* and an agent in another organization (a share written before the
|
|
439
|
+
* same-organization invariant; this release serves no such share).
|
|
588
440
|
*/
|
|
589
441
|
export async function buildSharedAgentProfile(
|
|
590
442
|
store: Store,
|
|
@@ -605,12 +457,7 @@ export async function buildSharedAgentProfile(
|
|
|
605
457
|
throw sharedNotFound(share.metadata?.slug ?? "");
|
|
606
458
|
}
|
|
607
459
|
|
|
608
|
-
|
|
609
|
-
(share.metadata?.org ?? "") !== (agent.metadata?.org ?? "");
|
|
610
|
-
if (
|
|
611
|
-
isCrossOrg &&
|
|
612
|
-
agent.metadata?.visibility !== ApiResourceVisibility.visibility_public
|
|
613
|
-
) {
|
|
460
|
+
if ((share.metadata?.org ?? "") !== (agent.metadata?.org ?? "")) {
|
|
614
461
|
throw sharedNotFound(share.metadata?.slug ?? "");
|
|
615
462
|
}
|
|
616
463
|
|
|
@@ -63,7 +63,6 @@ import {
|
|
|
63
63
|
newAuthorizeResolvedTargetStep,
|
|
64
64
|
} from "../../pipeline/steps/authorize-resolved-target.js";
|
|
65
65
|
import { newGuardReservedLabelsStep } from "../../pipeline/steps/guard-reserved-labels.js";
|
|
66
|
-
import { newAuthorizeVisibilityTransitionStep } from "../../pipeline/steps/visibility-gates.js";
|
|
67
66
|
import {
|
|
68
67
|
newBuildNewStateStep,
|
|
69
68
|
setAuditFieldsForUpdate,
|
|
@@ -97,7 +96,10 @@ import {
|
|
|
97
96
|
TARGET_RESOURCE_KEY,
|
|
98
97
|
newLoadTargetStep,
|
|
99
98
|
} from "../../pipeline/steps/load-target.js";
|
|
100
|
-
import {
|
|
99
|
+
import {
|
|
100
|
+
newNormalizeReferencesStep,
|
|
101
|
+
newValidateReferencesStep,
|
|
102
|
+
} from "../../pipeline/steps/references.js";
|
|
101
103
|
import {
|
|
102
104
|
newCleanupIamPoliciesStep,
|
|
103
105
|
newCreateAuthorizationTuplesStep,
|
|
@@ -244,6 +246,7 @@ async function update(
|
|
|
244
246
|
.addStep(newPreserveRedactedSecretsStep())
|
|
245
247
|
.addStep(newEncryptSecretValuesStep(deps.secretService, deps.logger))
|
|
246
248
|
.addStep(newNormalizeReferencesStep())
|
|
249
|
+
.addStep(newValidateReferencesStep(deps.store))
|
|
247
250
|
.addStep(newPersistStep(deps.store))
|
|
248
251
|
.addStep(
|
|
249
252
|
newDestroyDroppedEnvironmentSecretsStep(deps.secretService, deps.logger),
|
|
@@ -398,12 +401,6 @@ async function updateVisibility(
|
|
|
398
401
|
// After load, per the cross-edition error precedence: unknown id +
|
|
399
402
|
// bad level = NOT_FOUND on both editions.
|
|
400
403
|
.addStep(newValidateVisibilityUpdateStep())
|
|
401
|
-
.addStep(
|
|
402
|
-
newAuthorizeVisibilityTransitionStep(
|
|
403
|
-
UPDATE_VISIBILITY_ENVIRONMENT_KEY,
|
|
404
|
-
deps.authorizer,
|
|
405
|
-
),
|
|
406
|
-
)
|
|
407
404
|
.addStep(newValidateEnvironmentShareRestrictionStep())
|
|
408
405
|
.addStep(newSetEnvironmentVisibilityStep())
|
|
409
406
|
.addStep(newPersistEnvironmentForVisibilityUpdateStep(deps.store))
|
|
@@ -82,7 +82,10 @@ import {
|
|
|
82
82
|
TARGET_RESOURCE_KEY,
|
|
83
83
|
newLoadTargetStep,
|
|
84
84
|
} from "../../pipeline/steps/load-target.js";
|
|
85
|
-
import {
|
|
85
|
+
import {
|
|
86
|
+
newNormalizeReferencesStep,
|
|
87
|
+
newValidateReferencesStep,
|
|
88
|
+
} from "../../pipeline/steps/references.js";
|
|
86
89
|
import {
|
|
87
90
|
newCleanupIamPoliciesStep,
|
|
88
91
|
newCreateAuthorizationTuplesStep,
|
|
@@ -186,6 +189,7 @@ async function createExecutionContext(
|
|
|
186
189
|
.addStep(newBuildNewStateStep())
|
|
187
190
|
.addStep(newGuardReservedLabelsStep(deps.authorizer))
|
|
188
191
|
.addStep(newNormalizeReferencesStep())
|
|
192
|
+
.addStep(newValidateReferencesStep(deps.store))
|
|
189
193
|
.addStep(newEncryptSecretValuesStep(deps.secretService, deps.logger))
|
|
190
194
|
.addStep(newPersistStep(deps.store))
|
|
191
195
|
.addStep(
|