From e02958416c8483585ef747e8c2a0071698904d1d Mon Sep 17 00:00:00 2001 From: Antoine Toussaint <312536060+antoinetoussaint-byte@users.noreply.github.com> Date: Tue, 13 Oct 2026 16:11:34 -0400 Subject: [PATCH 1/5] fix!: adopt Core v0.19.4 and refresh host v0.0.97 bindings --- CHANGELOG.md | 28 +++++++++++++++++++++++ README.md | 16 +++++++++---- conformance/hostgateway/AGENTS.md | 6 +++++ go.mod | 10 ++++---- go.sum | 38 ++++++++----------------------- moduleauthority/host_fake_test.go | 6 ++--- 6 files changed, 63 insertions(+), 41 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f452215..18784f7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,29 @@ ## Unreleased +### Changed + +- Raise the Core dependency floor from v0.19.1 to v0.19.4, consuming Core's + Kubernetes dependency compatibility fix for stable client-go consumers. + Existing hand-written facade methods retain their signatures. +- Regenerate from released module-saas-starter v0.0.97 with the existing plugin + pins. `SOURCE.txt` now holds both generated bindings and gateway conformance + to that release: its gateway pins gRPC v1.84.0, matching Core v0.19.4's floor. + The upstream module package version remains 0.1.0; no SDK release is cut by + regeneration. +- Align conformance with host v0.0.97's work-context mint: Accounts' + `FailedPrecondition` now returns HTTP 412 (installation pending), previously + 502. The SDK preserves it as `BrokerError` without a delegation sentinel. + The source mint's 412 still maps to `ErrDelegationMissing`. + +### Removed (breaking) + +- Generated `StartTaskWorkContextRequest`, `StartInstallationTaskRequest`, and + `StartChildSessionWorkContextRequest` lose `SessionId` and `GetSessionId`. + Accounts assigns the session and returns it in `IssuedWorkContext.SessionId`; + callers must not choose one. The deleted proto names and field numbers are + reserved upstream. No hand-written facade exposes these request types. + ### Added - **`moduleauthority.WorkContextSources`**, the three live-authority sources a @@ -36,6 +59,11 @@ `CodeFailedPrecondition` ("the issuer decided; mint again") from `CodeUnavailable` ("the lookup failed; retry"). +- Generated source-trigger declaration, delegation, reconciliation and lookup + messages and RPCs; installation retry and pending/failed status values; + solution workload mint `Upstream` and `Manifest` fields; and authorization + revision `OperationBindingId`. These bindings add no hand-written facades. + - **`moduleauthority.WorkloadTokenFile()`**, the one answer to "where is this module's projected token": the file `CODEFLY__WORKLOAD_TOKEN_FILE` names when it is set to a non-blank value, and the pod mount diff --git a/README.md b/README.md index ae265e5..d5ad2ad 100644 --- a/README.md +++ b/README.md @@ -449,8 +449,8 @@ The proto source of truth is `module-saas-starter/module/services/accounts/proto To refresh from a released tag (in a checkout of that repo): ```bash -git fetch origin tag v0.0.94 -git checkout --detach v0.0.94 +git fetch origin tag v0.0.97 +git checkout --detach v0.0.97 cd module/services/accounts/proto buf generate --template /buf.gen.yaml -o ``` @@ -465,9 +465,11 @@ The template generates the complete host-owned `saas/` schema tree. Its vendored `codefly/` import closure is compiled for Runnable annotations, with imports resolved to `github.com/codefly-dev/core/generated/go`; Core owns those Go descriptors. Emitting a second copy in this SDK would conflict at -protobuf initialization. Core v0.19.1 supplies the required Runnable package; -the SDK need not adopt the host's entire dependency generation. Verify the -compatible dependency floor with SDK and consumer builds when refreshing it. +protobuf initialization. The SDK requires Core v0.19.4, which supplies the +required Runnable package and keeps the Kubernetes dependency graph compatible +with stable client-go's structured-merge-diff/v6. The SDK need not adopt the +host's entire dependency generation. Verify the compatible dependency floor +with SDK and consumer builds when refreshing it. The generation plugin versions remain pinned. Record the release tag in `SOURCE.txt`; CI checks out that tag through `refs/tags/` and verifies that regeneration leaves no diff. Before a host @@ -660,6 +662,10 @@ reconnect it — minting again will not help. The gateway answers 412 there only for a missing delegation, so the status alone decides it. Body-based delegation distinctions are gone: source 403s all return `ErrDelegationInvalid`, whether the delegation was revoked or is otherwise unusable. +At host v0.0.97, a module work-context mint can also answer 412 when the +workload is admitted but installed nowhere. That remains a `BrokerError` +with `StatusCode == 412` and `BrokerErrorOther`, without a delegation sentinel; +the module can serve its install endpoint while waiting for installation. `BrokerError.Path` and `BrokerError.Reason` have been removed. Transport and response read failures return `*moduleauthority.BrokerTransportError` diff --git a/conformance/hostgateway/AGENTS.md b/conformance/hostgateway/AGENTS.md index 8a196c6..1ac42f9 100644 --- a/conformance/hostgateway/AGENTS.md +++ b/conformance/hostgateway/AGENTS.md @@ -76,6 +76,12 @@ duplicate, non-Bearer or empty bearer refused before accounts; the 64 KiB token bound; and the three gateway answers the fake copies (D1, D3, D4 in `moduleauthority/host_fake_test.go`). +At host v0.0.97 (`640ee503617a0130abdba79d8eeb11dc4d8be723`), a work-context +mint's `FailedPrecondition` maps to HTTP 412 (installation pending), preserved +as `BrokerError` without a delegation sentinel. This differs from the source +mint's 412 (`ErrDelegationMissing`). The host's `gateway_modules.go` and +`TestGateway_ModuleWorkContext_RelaysAccountsOutcome` define that mapping. + ## When it goes red First ask which kind of red it is. Two kinds look alike after a `SOURCE.txt` diff --git a/go.mod b/go.mod index 6ce3735..ee5d9aa 100644 --- a/go.mod +++ b/go.mod @@ -5,12 +5,12 @@ go 1.27.0 require ( buf.build/gen/go/bufbuild/protovalidate/protocolbuffers/go v1.36.12-20260825204119-511051f7f437.2 connectrpc.com/connect v1.21.0 - github.com/codefly-dev/core v0.19.1 + github.com/codefly-dev/core v0.19.4 github.com/google/uuid v1.6.0 golang.org/x/tools v0.52.0 - google.golang.org/genproto/googleapis/api v0.0.0-20260819154853-08b0e4226688 - google.golang.org/genproto/googleapis/rpc v0.0.0-20260825221802-da73d73af1c5 - google.golang.org/grpc v1.83.2 + google.golang.org/genproto/googleapis/api v0.0.0-20260928230214-8a89bd6388cc + google.golang.org/genproto/googleapis/rpc v0.0.0-20260928230214-8a89bd6388cc + google.golang.org/grpc v1.84.0 google.golang.org/protobuf v1.36.12 ) @@ -21,7 +21,7 @@ require ( github.com/antlr4-go/antlr/v4 v4.13.1 // indirect github.com/pkg/errors v0.9.1 // indirect go.yaml.in/yaml/v3 v3.0.5 // indirect - golang.org/x/exp v0.0.0-20260820142414-ca536658362e // indirect + golang.org/x/exp v0.0.0-20260908205506-85c1c2202aba // indirect golang.org/x/mod v0.42.0 // indirect golang.org/x/net v0.61.0 // indirect golang.org/x/sync v0.24.0 // indirect diff --git a/go.sum b/go.sum index 6511ba1..a2b057d 100644 --- a/go.sum +++ b/go.sum @@ -12,14 +12,8 @@ github.com/antlr4-go/antlr/v4 v4.13.1 h1:SqQKkuVZ+zWkMMNkjy5FZe5mr5WURWnlpmOuzYW github.com/antlr4-go/antlr/v4 v4.13.1/go.mod h1:GKmUxMtwp6ZgGwZSva4eWPC5mS6vUAmOABFgjdkM7Nw= github.com/brianvoe/gofakeit/v6 v6.28.0 h1:Xib46XXuQfmlLS2EXRuJpqcw8St6qSZz75OUo0tgAW4= github.com/brianvoe/gofakeit/v6 v6.28.0/go.mod h1:Xj58BMSnFqcn/fAQeSK+/PLtC5kSb7FJIq4JyGa8vEs= -github.com/cespare/xxhash/v2 v2.3.0 h1:UL815xU9SqsFlibzuggzjXhog7bL6oX9BbNZnL2UFvs= -github.com/cespare/xxhash/v2 v2.3.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= -github.com/codefly-dev/core v0.19.1 h1:DLzrbgQu5Io6cnhD2QD9dAqNfh1HVwCs+G3BHP+JQFE= -github.com/codefly-dev/core v0.19.1/go.mod h1:FKBqn6GMGIsx9b3LNY6kKCRxCEjjeswvqt2CxSZWq20= -github.com/go-logr/logr v1.4.4 h1:tG4xh9yMsRCAiodLVTxyrkzSZ9+o0L1Kg/+cPVcbP/8= -github.com/go-logr/logr v1.4.4/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= -github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag= -github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE= +github.com/codefly-dev/core v0.19.4 h1:vUvaFrWkB8B3ksQY/qlgBTVj3jMNhdEpJca8aofaals= +github.com/codefly-dev/core v0.19.4/go.mod h1:0uX/7lTBVaGV0RI2Mb3mpEr/PPdx/jZqXHym/U8FVDI= github.com/golang/protobuf v1.5.4 h1:i7eJL8qZTpSEXOPTxNKhASYpMn+8e5Q6AdndVa1dWek= github.com/golang/protobuf v1.5.4/go.mod h1:lnTiLA8Wa4RWRcIUkrtSVa5nRhsEGBg48fD6rSs7xps= github.com/google/go-cmp v0.7.0 h1:wk8382ETsv4JYUZwIsn6YpYiWiBsYLSJiTsyBybVuN8= @@ -32,22 +26,10 @@ github.com/rodaine/protogofakeit v0.1.1 h1:ZKouljuRM3A+TArppfBqnH8tGZHOwM/pjvtXe github.com/rodaine/protogofakeit v0.1.1/go.mod h1:pXn/AstBYMaSfc1/RqH3N82pBuxtWgejz1AlYpY1mI0= github.com/stretchr/testify v1.12.1 h1:EuwCh5fleGS7H32xRwO3wRGT7DxrDhLAT6FF8MpWDWE= github.com/stretchr/testify v1.12.1/go.mod h1:MDEgiDPPsNp5cuIrHPPCyornHKgEVbtFUmoNlxoYthg= -go.opentelemetry.io/auto/sdk v1.2.1 h1:jXsnJ4Lmnqd11kwkBV2LgLoFMZKizbCi5fNZ/ipaZ64= -go.opentelemetry.io/auto/sdk v1.2.1/go.mod h1:KRTj+aOaElaLi+wW1kO/DZRXwkF4C5xPbEe3ZiIhN7Y= -go.opentelemetry.io/otel v1.46.0 h1:FHt5/CDyVxi/8IM1CH7VE/rRgq3kLHa2mSTVMO8AWyc= -go.opentelemetry.io/otel v1.46.0/go.mod h1:Gj3SEScelsNC45tp4nSxRYlS+f5iez7W8XPMCt905kE= -go.opentelemetry.io/otel/metric v1.46.0 h1:yBnkXvgV7AXFILZc5K6IZe/CBFF3OS7BJ8ov6/lj0K8= -go.opentelemetry.io/otel/metric v1.46.0/go.mod h1:iPmdWqifKUdzziPkvvzIJXITl56fQx2mGM/DHLB3/2o= -go.opentelemetry.io/otel/sdk v1.46.0 h1:h5CNQQjEbuQXY/JfZtgt3i7HVFV3aHPO2OAwO2eTYPI= -go.opentelemetry.io/otel/sdk v1.46.0/go.mod h1:GAERFXFt5SYCEB+YiKUbMBeza6UaDH7GmGOZEfh2gSM= -go.opentelemetry.io/otel/sdk/metric v1.44.0 h1:3LlKgI+VjbVsjNRFZJZAJ30WjXC5VkNRks6si09iEfI= -go.opentelemetry.io/otel/sdk/metric v1.44.0/go.mod h1:5B5pMARnXxKhltooO4xUuCBorl65a4EpnTalObqOigA= -go.opentelemetry.io/otel/trace v1.46.0 h1:OULy7ccdJnZtJ0UDYFOIGaCmiWzJ8Vi2G/Rsu60qs1c= -go.opentelemetry.io/otel/trace v1.46.0/go.mod h1:J7GAXweO77XSFkB/rmAqk9D6ihszhFjLU+d9WuUxDLI= go.yaml.in/yaml/v3 v3.0.5 h1:N6y/pJk8buWs9NY5ERU2HSMfm+IuD/OtfdAnq6kESPw= go.yaml.in/yaml/v3 v3.0.5/go.mod h1:HVTZu1O7/Vkt2N+BFy8Zza+lnLsABggaTM2ZpNIGuKg= -golang.org/x/exp v0.0.0-20260820142414-ca536658362e h1:01Ju2A/fZKkci4zqx0eZxw//DnRYOnBiGJG14hFBhO8= -golang.org/x/exp v0.0.0-20260820142414-ca536658362e/go.mod h1:zeBbvyFKDaLwa7CH/zI8KXt7gTl14SF7sO08Pl5jBCM= +golang.org/x/exp v0.0.0-20260908205506-85c1c2202aba h1:Ck8QetSgk912qxWLMCKxd0in+aiyBQyDSMae6e/xmpU= +golang.org/x/exp v0.0.0-20260908205506-85c1c2202aba/go.mod h1:50RgIsmK7OwqzTTeqcSXQW8SswW0o8fRcDxmqGluJ8E= golang.org/x/mod v0.42.0 h1:ICeL3t2L30ljSPHHxDnR4fqVcBt/zR2zJAb9juavmQg= golang.org/x/mod v0.42.0/go.mod h1:u5fzIrRInkL8MaO1cbRkUHT64v303YIT5KEqpNr7jRs= golang.org/x/net v0.61.0 h1:RR+6j/BTBCrggOLugxa+66R8FvoN6MHlzDlZIbN9YFw= @@ -64,11 +46,11 @@ golang.org/x/tools v0.52.0 h1:ryxg4U63oaUYk7uOLTF37n43f4qgtGvqV4Ioit1BaEs= golang.org/x/tools v0.52.0/go.mod h1:ItcP5UNaVGG+Yc4eIYmaFLNJ4soEopkx5Y2d4lcEurs= gonum.org/v1/gonum v0.17.0 h1:VbpOemQlsSMrYmn7T2OUvQ4dqxQXU+ouZFQsZOx50z4= gonum.org/v1/gonum v0.17.0/go.mod h1:El3tOrEuMpv2UdMrbNlKEh9vd86bmQ6vqIcDwxEOc1E= -google.golang.org/genproto/googleapis/api v0.0.0-20260819154853-08b0e4226688 h1:ax2KzoSRIZU/M0cIxri3pKxy99vniH1PVxWC6si/eZI= -google.golang.org/genproto/googleapis/api v0.0.0-20260819154853-08b0e4226688/go.mod h1:1RJ9BQGyNdZwkGc1eTqkErfRZ6RJyYPHZo73BZ1vQqI= -google.golang.org/genproto/googleapis/rpc v0.0.0-20260825221802-da73d73af1c5 h1:1VUiZAXyC+zmiFYi+WLtBzr68Cj8wOofHjjrA/kkizc= -google.golang.org/genproto/googleapis/rpc v0.0.0-20260825221802-da73d73af1c5/go.mod h1:DjtHYE8FKJLivXcBEjGwndXfIC23G0VpXiXKqG179uA= -google.golang.org/grpc v1.83.2 h1:EManeRomTObA0BU7I8vXgg/78uE5MJ9M8B39EX2WscU= -google.golang.org/grpc v1.83.2/go.mod h1:YPI1hK3kDked6iHvgX3tR0y+nX/qpMFKhPgFsokw1S8= +google.golang.org/genproto/googleapis/api v0.0.0-20260928230214-8a89bd6388cc h1:rZHRz0ogq4Pid1IKtA/ivHi8XONVF5tqUQXA2TtgpkE= +google.golang.org/genproto/googleapis/api v0.0.0-20260928230214-8a89bd6388cc/go.mod h1:K/n0XLazCJHjD73YuMyNJsN38BPPy1kfFnKxUXaThFU= +google.golang.org/genproto/googleapis/rpc v0.0.0-20260928230214-8a89bd6388cc h1:4bNTbnb44EqGVy9HaQxSY2jnafSUdgV3qHtedvNpDKg= +google.golang.org/genproto/googleapis/rpc v0.0.0-20260928230214-8a89bd6388cc/go.mod h1:OaIUM3+LpYcK2GXM4FTmhWoIq371Owdr+Cc7/BsYHHc= +google.golang.org/grpc v1.84.0 h1:soMyaPJ8pAak5PIQ0DGBUir0XRo2fRoMqhNWMLlLxO0= +google.golang.org/grpc v1.84.0/go.mod h1:ljCht0DrxQrXBDRTZp52Qxh3Ffk8CdYm2sj4O2QN2C0= google.golang.org/protobuf v1.36.12 h1:pJOKDDOyeXErUroCihFAd5LQuwXBSpVnKGrj5o/fwxc= google.golang.org/protobuf v1.36.12/go.mod h1:HTf+CrKn2C3g5S8VImy6tdcUvCska2kB7j23XfzDpco= diff --git a/moduleauthority/host_fake_test.go b/moduleauthority/host_fake_test.go index e2c5d6f..dcb962a 100644 --- a/moduleauthority/host_fake_test.go +++ b/moduleauthority/host_fake_test.go @@ -54,11 +54,11 @@ import ( // an extra or misnamed field is visible to an exact-body assertion; the // real gateway decodes into a struct and drops unknown keys silently. // - D5: a test may inject any refusal on any path. The real gateway never -// answers 403 (or 412) on /modules/_work-context — accounts' +// answers 403 on the SDK's /modules/_work-context path — accounts' // PermissionDenied is a 401 there — so no test here injects one. // - D6: accounts' Unauthenticated and FailedPrecondition on the work-context -// mint (a 502 from the real gateway) are not modelled; only injected -// statuses are. +// mint (502 and 412 respectively from the real gateway) are not modelled; +// only injected statuses are. Conformance holds both mappings at SOURCE.txt. // - D7: it accepts one internal token; the real gateway also accepts the // previous one during rotation. // - D8: refusal bodies are whatever a test injects; the real gateway sends From c4a25cdaefa6023ea60916b80c04afbf37184884 Mon Sep 17 00:00:00 2001 From: Antoine Toussaint <312536060+antoinetoussaint-byte@users.noreply.github.com> Date: Wed, 14 Oct 2026 00:31:38 -0400 Subject: [PATCH 2/5] feat(moduleauthority): expose one uncached broker mint and expiry --- CHANGELOG.md | 11 ++ README.md | 43 +++-- moduleauthority/broker_errors.go | 5 + moduleauthority/broker_errors_test.go | 1 + .../broker_transport_errors_test.go | 13 +- moduleauthority/client.go | 40 +++-- moduleauthority/module_mint_test.go | 152 ++++++++++++++++++ 7 files changed, 243 insertions(+), 22 deletions(-) create mode 100644 moduleauthority/module_mint_test.go diff --git a/CHANGELOG.md b/CHANGELOG.md index 18784f7..1f212fe 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -59,6 +59,17 @@ `CodeFailedPrecondition` ("the issuer decided; mint again") from `CodeUnavailable` ("the lookup failed; retry"). +- `moduleauthority.Client.MintModuleWorkContext(ctx)` returns + `ModuleContext{Token, ExpiresAt}` without caching, coalescing or retrying. + `ExpiresAt` is the broker's reported expiry, not a decoded token claim. + Existing `ModuleWorkContext(ctx) (string, error)` retains its cache and + shared refresh through the same mint implementation; organization binding, + bounded reads, Core-backed sealed-shape checking and safe refusals are shared. +- `BrokerTransportConnectionReset` classifies wrapped `syscall.ECONNRESET` + through error identity with a fixed diagnostic, retaining no underlying + cause. It is appended so existing transport category values remain stable; + callers can choose to retry without accessing sensitive transport errors. + - Generated source-trigger declaration, delegation, reconciliation and lookup messages and RPCs; installation retry and pending/failed status values; solution workload mint `Upstream` and `Manifest` fields; and authorization diff --git a/README.md b/README.md index d5ad2ad..a2d914c 100644 --- a/README.md +++ b/README.md @@ -219,7 +219,7 @@ The SDK surfaces are: This call surface uses the four host RPCs from [module-saas-starter#1052](https://github.com/codefly-dev/module-saas-starter/pull/1052). - `SOURCE.txt` records the released host tag `v0.0.94` used to regenerate + `SOURCE.txt` records the released host tag `v0.0.97` used to regenerate the bindings. This regeneration does not publish an SDK release. The host's runtime-scheduled `PruneSourceOperationReceipts` and `LookupPruneSourceOperationReceipts` are included in the generated bindings @@ -242,8 +242,31 @@ The SDK surfaces are: `ErrInvalidCapability`; a `Parent` core does not decode is refused as invalid input (`ErrInvalidExchange`, `ErrInvalidArtifact`, `ErrInvalidInstallation`) before anything is sent. **This needs a host whose accounts mints core-format - Work Contexts** (module-saas-starter#1093); the v0.0.94 host recorded in - `SOURCE.txt` mints the pre-cutover format, and this client refuses it. + Work Contexts** (module-saas-starter#1093); the former v0.0.94 source mints + the pre-cutover format, which this client refuses. `SOURCE.txt` now records + v0.0.97. + + `Client.ModuleWorkContext(ctx)` returns a cached token, sharing refreshes + between concurrent callers. Consumers that already own their expiry and + refresh controller use `Client.MintModuleWorkContext(ctx)` instead: + + ```go + issued, err := authority.MintModuleWorkContext(ctx) + if err != nil { + return err + } + // issued.Token is opaque; issued.ExpiresAt is the broker's reported expiry. + ``` + + This returns `ModuleContext{Token string, ExpiresAt time.Time}` and mints + once per call. It neither reads nor updates the cached token, coalesces + concurrent calls, nor retries failures. Both methods use the same broker + request, bounded response reader, expiry parser and refusal mapping. The + projected credential is reread for each mint; the organization remains the + client's `Credentials.OrganizationID`, so keep a client per organization. + The returned expiry comes from the broker, never from decoded token claims. + It does not prove authority or override a verifier's lifetime limit; Core + owns authority validation, and consumers own their refresh/deadline policy. It talks to the two seams the host serves a composed module, and takes both explicitly — the consumer passes what Codefly resolved, nothing is defaulted: @@ -312,7 +335,7 @@ The SDK surfaces are: sends exactly one `Authorization: Bearer ` header alongside the internal perimeter token; the removed module-secret credential has no fallback. - The REST bodies match [the v0.0.94 gateway](https://github.com/codefly-dev/module-saas-starter/blob/v0.0.94/module/services/auth-gateway/code/gateway_modules.go): + The REST bodies match [the v0.0.97 gateway](https://github.com/codefly-dev/module-saas-starter/blob/v0.0.97/module/services/auth-gateway/code/gateway_modules.go): | Mint path | JSON fields sent | | --- | --- | @@ -670,11 +693,11 @@ the module can serve its install endpoint while waiting for installation. Transport and response read failures return `*moduleauthority.BrokerTransportError` with a fixed message and a `Category`: `BrokerTransportTimeout`, -`BrokerTransportConnectionRefused`, `BrokerTransportTLS`, or -`BrokerTransportOther`. It retains no underlying error and has no `Unwrap` -method. Callers use `errors.As` and the category for retry decisions, and check +`BrokerTransportConnectionRefused`, `BrokerTransportConnectionReset`, +`BrokerTransportTLS`, or `BrokerTransportOther`. It retains no underlying +error and has no `Unwrap` method. Callers use `errors.As` and the category for retry decisions, and check their context's `Err()` for cancellation. For example, a caller may retry a 502, -503, timeout or refused connection, while surfacing a 401/403 denial. The SDK -does not automatically retry broker failures. Malformed initial HTTP headers -provide no usable status and produce a transport error; malformed bodies cannot +503, timeout, refused connection or connection reset, while surfacing a 401/403 +denial. The SDK does not automatically retry broker failures. Malformed initial +HTTP headers provide no usable status and produce a transport error; malformed bodies cannot change a successfully parsed non-200 status into a transport failure. diff --git a/moduleauthority/broker_errors.go b/moduleauthority/broker_errors.go index ad481b2..654b708 100644 --- a/moduleauthority/broker_errors.go +++ b/moduleauthority/broker_errors.go @@ -64,6 +64,7 @@ const ( BrokerTransportTimeout // Deadline exceeded or a net.Error reporting Timeout. BrokerTransportConnectionRefused // errors.Is(err, syscall.ECONNREFUSED). BrokerTransportTLS // A recognized crypto/tls or crypto/x509 error type. + BrokerTransportConnectionReset // errors.Is(err, syscall.ECONNRESET). ) // BrokerTransportError reports a failure to obtain or read a broker response. @@ -85,6 +86,8 @@ func (e *BrokerTransportError) Error() string { return "module broker: connection refused" case BrokerTransportTLS: return "module broker: TLS failure" + case BrokerTransportConnectionReset: + return "module broker: connection reset" default: return "module broker: transport or response read failed" } @@ -108,6 +111,8 @@ func brokerTransportError(err error) *BrokerTransportError { errors.As(err, &unknownAuthority), errors.As(err, &hostname), errors.As(err, &invalidCertificate), errors.As(err, &roots): category = BrokerTransportTLS + case errors.Is(err, syscall.ECONNRESET): + category = BrokerTransportConnectionReset } return &BrokerTransportError{Category: category} } diff --git a/moduleauthority/broker_errors_test.go b/moduleauthority/broker_errors_test.go index a37e228..7731abf 100644 --- a/moduleauthority/broker_errors_test.go +++ b/moduleauthority/broker_errors_test.go @@ -29,6 +29,7 @@ type brokerMintCase struct { func brokerMints(t *testing.T) []brokerMintCase { return []brokerMintCase{ {hostWorkContextPath, func(c *Client) error { _, err := c.ModuleWorkContext(t.Context()); return err }, ErrPermissionDenied, ErrNoHostStateToMintFor}, + {hostWorkContextPath, func(c *Client) error { _, err := c.MintModuleWorkContext(t.Context()); return err }, ErrPermissionDenied, ErrNoHostStateToMintFor}, {hostOperationContextPath, func(c *Client) error { _, err := c.MintModuleOperationContext(t.Context(), "binding") return err diff --git a/moduleauthority/broker_transport_errors_test.go b/moduleauthority/broker_transport_errors_test.go index 0923b4b..025dcb3 100644 --- a/moduleauthority/broker_transport_errors_test.go +++ b/moduleauthority/broker_transport_errors_test.go @@ -36,6 +36,10 @@ func TestBrokerTransportFailuresExcludeCauses(t *testing.T) { {"wrapped timeout", fmt.Errorf("%s: %w", leak, &net.DNSError{Name: leak, Err: leak, IsTimeout: true}), BrokerTransportTimeout}, {"joined timeout", errors.Join(&net.DNSError{Name: leak}, &net.DNSError{Name: leak, IsTimeout: true}), BrokerTransportTimeout}, {"connection refused", &net.OpError{Op: leak, Net: leak, Err: &os.SyscallError{Syscall: leak, Err: syscall.ECONNREFUSED}}, BrokerTransportConnectionRefused}, + {"connection reset", &net.OpError{Op: leak, Net: leak, Err: &os.SyscallError{Syscall: leak, Err: syscall.ECONNRESET}}, BrokerTransportConnectionReset}, + {"wrapped reset", fmt.Errorf("%s: %w", leak, syscall.ECONNRESET), BrokerTransportConnectionReset}, + {"joined reset", errors.Join(errors.New(leak), syscall.ECONNRESET), BrokerTransportConnectionReset}, + {"reset and deadline", errors.Join(syscall.ECONNRESET, context.DeadlineExceeded), BrokerTransportTimeout}, {"TLS verification", &tls.CertificateVerificationError{Err: errors.New(leak)}, BrokerTransportTLS}, {"TLS record", tls.RecordHeaderError{Msg: leak}, BrokerTransportTLS}, {"TLS alert", fmt.Errorf("%s: %w", leak, tls.AlertError(42)), BrokerTransportTLS}, @@ -45,7 +49,7 @@ func TestBrokerTransportFailuresExcludeCauses(t *testing.T) { {"x509 roots", x509.SystemRootsError{Err: errors.New(leak)}, BrokerTransportTLS}, {"canceled", fmt.Errorf("%s: %w", leak, context.Canceled), BrokerTransportOther}, {"parser", errors.New("malformed MIME header: " + leak), BrokerTransportOther}, - {"text is not a category", errors.New("TLS timeout connection refused: " + leak), BrokerTransportOther}, + {"text is not a category", errors.New("TLS timeout connection refused reset: " + leak), BrokerTransportOther}, } { for _, mint := range brokerMints(t) { for _, phase := range []string{"transport", "read"} { @@ -96,6 +100,7 @@ func TestBrokerTransportClassificationNeverFormatsCause(t *testing.T) { {brokerUnprintableError{context.DeadlineExceeded}, BrokerTransportTimeout}, {brokerUnprintableTimeout{}, BrokerTransportTimeout}, {brokerUnprintableError{syscall.ECONNREFUSED}, BrokerTransportConnectionRefused}, + {brokerUnprintableError{syscall.ECONNRESET}, BrokerTransportConnectionReset}, {brokerUnprintableError{tls.RecordHeaderError{}}, BrokerTransportTLS}, {brokerUnprintableError{errors.New("timeout TLS connection refused")}, BrokerTransportOther}, } { @@ -114,6 +119,7 @@ func assertBrokerTransportError(t *testing.T, err error, category BrokerTranspor BrokerTransportTimeout: "module broker: transport or response read timed out", BrokerTransportConnectionRefused: "module broker: connection refused", BrokerTransportTLS: "module broker: TLS failure", + BrokerTransportConnectionReset: "module broker: connection reset", }[category] if te.Error() != want || fmt.Sprintf("%+v", te) != want { t.Error("transport diagnostic is not the fixed category message") @@ -122,7 +128,7 @@ func assertBrokerTransportError(t *testing.T, err error, category BrokerTranspor assertNoBrokerCause(t, te) var be *BrokerError var netErr net.Error - if errors.As(err, &be) || errors.As(err, &netErr) || errors.Is(err, context.DeadlineExceeded) || errors.Is(err, context.Canceled) { + if errors.As(err, &be) || errors.As(err, &netErr) || errors.Is(err, context.DeadlineExceeded) || errors.Is(err, context.Canceled) || errors.Is(err, syscall.ECONNRESET) { t.Error("transport failure exposes a status or an underlying cause") } } @@ -205,7 +211,7 @@ func TestBrokerCallersCanDecideRetries(t *testing.T) { return be.Classification == BrokerErrorNotEstablished || be.StatusCode == 502 } var te *BrokerTransportError - return errors.As(err, &te) && (te.Category == BrokerTransportTimeout || te.Category == BrokerTransportConnectionRefused) + return errors.As(err, &te) && (te.Category == BrokerTransportTimeout || te.Category == BrokerTransportConnectionRefused || te.Category == BrokerTransportConnectionReset) } for _, mint := range brokerMints(t) { for _, status := range []int{401, 403, 503, 502, 400, 412} { @@ -222,6 +228,7 @@ func TestBrokerCallersCanDecideRetries(t *testing.T) { }{ {context.DeadlineExceeded, true}, {syscall.ECONNREFUSED, true}, + {syscall.ECONNRESET, true}, {tls.RecordHeaderError{}, false}, {errors.New("unknown parser failure"), false}, {context.Canceled, false}, diff --git a/moduleauthority/client.go b/moduleauthority/client.go index eb31e88..18663e2 100644 --- a/moduleauthority/client.go +++ b/moduleauthority/client.go @@ -290,8 +290,9 @@ type ExchangeRequest struct { DelegationID string } -// Client keeps only the module's short-lived Work Context in memory. Parent -// and exchanged capabilities are request-local and are never cached. +// Client caches the module's short-lived Work Context for ModuleWorkContext +// and authority calls. Explicit Mint calls, parents and exchanged capabilities +// are request-local and are never cached. type Client struct { broker broker authority authorityEndpoint @@ -439,27 +440,48 @@ func (c *Client) moduleWorkContextLocked(ctx context.Context) (string, error) { if c.module != "" && c.now().Add(c.refreshSkew).Before(c.expiresAt) { return c.module, nil } - projected, err := c.credentials.projectedToken() + issued, err := c.MintModuleWorkContext(ctx) if err != nil { return "", err } + c.module = issued.Token + c.expiresAt = issued.ExpiresAt + return issued.Token, nil +} + +// ModuleContext is an opaque module Work Context and the expiry reported by +// the broker. ExpiresAt is not derived from decoded claims or a verification +// of the token's authority. +type ModuleContext struct { + Token string + ExpiresAt time.Time +} + +// MintModuleWorkContext mints once through the gateway broker, using this +// client's Credentials.OrganizationID and the current projected token. It +// neither reads nor updates the ModuleWorkContext cache and does not coalesce +// calls or retry. Consumers that own expiry and refresh use this method; +// callers that want the client's shared cache use ModuleWorkContext. +func (c *Client) MintModuleWorkContext(ctx context.Context) (ModuleContext, error) { + projected, err := c.credentials.projectedToken() + if err != nil { + return ModuleContext{}, err + } var issued workContextResponse if err := c.broker.post(ctx, workContextPath, projected, workContextRequest{ Prefix: c.credentials.Prefix, OrganizationID: c.credentials.OrganizationID, }, &issued); err != nil { - return "", fmt.Errorf("module authority: mint module Work Context: %w", brokerRefusal(err)) + return ModuleContext{}, fmt.Errorf("module authority: mint module Work Context: %w", brokerRefusal(err)) } expiresAt, err := parseExpiry(issued.ExpiresAt, c.now()) if err != nil { - return "", err + return ModuleContext{}, err } if !sealed(issued.Token) { - return "", fmt.Errorf("%w: malformed token", ErrInvalidCapability) + return ModuleContext{}, fmt.Errorf("%w: malformed token", ErrInvalidCapability) } - c.module = issued.Token - c.expiresAt = expiresAt - return issued.Token, nil + return ModuleContext{Token: issued.Token, ExpiresAt: expiresAt}, nil } // forgetModuleWorkContext drops the cached module capability if it is still diff --git a/moduleauthority/module_mint_test.go b/moduleauthority/module_mint_test.go new file mode 100644 index 0000000..58b1e75 --- /dev/null +++ b/moduleauthority/module_mint_test.go @@ -0,0 +1,152 @@ +package moduleauthority + +import ( + "encoding/json" + "errors" + "io" + "net/http" + "strings" + "testing" + "time" +) + +func TestMintModuleWorkContextDoesNotShareTheCache(t *testing.T) { + h := newHost(t) + now := time.Now().UTC().Truncate(time.Second) + h.gateway.expires = now.Add(5 * time.Minute) // The sealed fixture lives an hour. + client := h.client(t, moduleCredentials) + client.now = func() time.Time { return now } + + for _, name := range []string{"module.token1", "module.token2"} { + issued, err := client.MintModuleWorkContext(t.Context()) + if err != nil || issued.Token != sealedToken(name) || !issued.ExpiresAt.Equal(h.gateway.expires) { + t.Fatalf("uncached mint %s: unexpected token/expiry or error %v", name, err) + } + } + cached, err := client.ModuleWorkContext(t.Context()) + if err != nil || cached != sealedToken("module.token3") { + t.Fatalf("uncached mint populated cache: %v", err) + } + issued, err := client.MintModuleWorkContext(t.Context()) + if err != nil || issued.Token != sealedToken("module.token4") { + t.Fatalf("uncached mint reused cache: %v", err) + } + if got, err := client.ModuleWorkContext(t.Context()); err != nil || got != cached { + t.Fatalf("uncached mint replaced cache: %v", err) + } + // Refresh follows the broker's shorter expiry, not the opaque token's claims. + now = h.gateway.expires.Add(-20 * time.Second) + if got, err := client.ModuleWorkContext(t.Context()); err != nil || got != sealedToken("module.token5") { + t.Fatalf("cached mint did not refresh at broker expiry: %v", err) + } + if calls, _, _, _ := h.gateway.snapshot(); len(calls) != 5 { + t.Fatalf("broker calls = %v, want five mints", calls) + } +} + +func TestModuleWorkContextConcurrentCallsShareMint(t *testing.T) { + h := newHost(t) + client := h.client(t, moduleCredentials) + type result struct { + token string + err error + } + results := make(chan result, 8) + start := make(chan struct{}) + for range cap(results) { + go func() { + <-start + token, err := client.ModuleWorkContext(t.Context()) + results <- result{token, err} + }() + } + close(start) + for range cap(results) { + r := <-results + if r.err != nil || r.token != sealedToken("module.token1") { + t.Errorf("concurrent cached mint: unexpected token or error %v", r.err) + } + } + if calls, _, _, _ := h.gateway.snapshot(); len(calls) != 1 { + t.Fatalf("broker calls = %v, want one shared mint", calls) + } +} + +func TestMintModuleWorkContextKeepsClientOrganization(t *testing.T) { + h := newHost(t) + organizations := []string{"11111111-1111-4111-8111-111111111111", "22222222-2222-4222-8222-222222222222"} + for _, org := range organizations { + client := h.client(t, Credentials{Prefix: testPrefix, Token: staticToken(testProjectedToken), OrganizationID: org}) + if _, err := client.MintModuleWorkContext(t.Context()); err != nil { + t.Fatal(err) + } + } + calls, _, bodies, headers := h.gateway.snapshot() + if len(calls) != len(organizations) { + t.Fatalf("broker calls = %v", calls) + } + for i, org := range organizations { + body := bodies[hostWorkContextPath][i] + if len(body) != 2 || body["prefix"] != testPrefix || body["organization_id"] != org { + t.Fatalf("client %d sent unexpected body: %v", i, body) + } + assertProjectedBearer(t, headers[i], testProjectedToken) + } + h.assertNoStrayPaths(t) +} + +func TestMintModuleWorkContextReturnsExactBrokerExpiry(t *testing.T) { + now := time.Now().UTC() + expires := now.Add(2*time.Minute + 123456789*time.Nanosecond).In(time.FixedZone("broker", 2*60*60)) + token := sealedToken("broker-expiry") + raw, err := json.Marshal(workContextResponse{Token: token, ExpiresAt: expires.Format(time.RFC3339Nano)}) + if err != nil { + t.Fatal(err) + } + client := brokerErrorClient(t, 200, testProjectedToken, func(*http.Request) io.ReadCloser { + return io.NopCloser(strings.NewReader(string(raw))) + }) + client.now = func() time.Time { return now } + issued, err := client.MintModuleWorkContext(t.Context()) + if err != nil || issued.Token != token || !issued.ExpiresAt.Equal(expires) { + t.Fatalf("mint did not retain exact broker token/expiry: %v", err) + } +} + +func TestMintModuleWorkContextRejectsInvalidAnswers(t *testing.T) { + now := time.Now().UTC() + token := sealedToken("invalid-answer") + for _, tc := range []struct { + name, token, expiry string + }{ + {"missing expiry", token, ""}, + {"malformed expiry", token, "not-a-time"}, + {"expired", token, now.Add(-time.Second).Format(time.RFC3339Nano)}, + {"expires now", token, now.Format(time.RFC3339Nano)}, + {"missing token", "", now.Add(time.Minute).Format(time.RFC3339Nano)}, + {"unsealed token", "opaque.but-not-core", now.Add(time.Minute).Format(time.RFC3339Nano)}, + } { + t.Run(tc.name, func(t *testing.T) { + raw, err := json.Marshal(workContextResponse{Token: tc.token, ExpiresAt: tc.expiry}) + if err != nil { + t.Fatal(err) + } + client := brokerErrorClient(t, 200, testProjectedToken, func(*http.Request) io.ReadCloser { + return io.NopCloser(strings.NewReader(string(raw))) + }) + client.now = func() time.Time { return now } + if issued, err := client.MintModuleWorkContext(t.Context()); !errors.Is(err, ErrInvalidCapability) || issued != (ModuleContext{}) { + t.Fatalf("invalid answer returned a capability or wrong error: %v", err) + } + }) + } +} + +func TestMintModuleWorkContextBoundsResponseRead(t *testing.T) { + body := &brokerDiagnosticBody{Reader: strings.NewReader(strings.Repeat(" ", 2*maxBrokerResponse))} + client := brokerErrorClient(t, 200, testProjectedToken, func(*http.Request) io.ReadCloser { return body }) + issued, err := client.MintModuleWorkContext(t.Context()) + if err == nil || issued != (ModuleContext{}) || !body.closed || body.read != maxBrokerResponse+1 { + t.Fatalf("oversized answer: err=%v, closed=%v, read=%d", err, body.closed, body.read) + } +} From 222d445e1c91cad4841d55b8073ac81ea04ba12f Mon Sep 17 00:00:00 2001 From: Antoine Toussaint <312536060+antoinetoussaint-byte@users.noreply.github.com> Date: Wed, 21 Oct 2026 14:37:42 -0400 Subject: [PATCH 3/5] fix!: build on Core main and host v0.0.103 Core 22ddde98 removed the approved build from a Work Context: SealSource lost ApprovedBuild and ErrNoApprovedBuild is gone, so verifier_sources.go no longer compiled for any consumer whose build selects Core main. The floor moves to b81d92e6feda, the Core host v0.0.103's gateway requires; WorkContextSources drops ApprovedBuild rather than keeping a local sentinel. Core v0.19.5 still requires that method, so no single source builds against both. gen/ regenerates from released module-saas-starter v0.0.103 with the pinned buf.gen.yaml toolchain and reproduces byte-for-byte. conformance/hostgateway re-binds to the host's workloadListener (af5cef9a serves the mints on the workload endpoint alone) and realigns the two expectations that commit changed: Unauthenticated on the work-context mint is 401, and that mint no longer holds the internal token. moduleauthority's fake follows. Co-Authored-By: Claude Opus 5.5 (1M context) --- SOURCE.txt | 11 +- conformance/hostgateway/AGENTS.md | 23 +- .../testdata/sdk_conformance_test.go | 30 +- .../accountsv1connect/datasource.connect.go | 39 + .../platform_admin.connect.go | 6 +- .../solution_registry_service.connect.go | 36 +- gen/saas/accounts/v1/authorization.pb.go | 48 +- gen/saas/accounts/v1/datasource.pb.go | 1235 ++++++++++------- gen/saas/accounts/v1/installations.pb.go | 864 ++++++++++-- gen/saas/accounts/v1/invitations.pb.go | 27 +- .../accounts/v1/module_registration.pb.go | 37 +- gen/saas/accounts/v1/platform_admin.pb.go | 362 +++-- gen/saas/accounts/v1/solution_registry.pb.go | 536 ++++--- .../v1/solution_registry_service.pb.go | 25 +- gen/saas/accounts/v1/work_contexts.pb.go | 31 +- go.mod | 2 +- go.sum | 4 +- moduleauthority/broker_test.go | 2 +- moduleauthority/client.go | 5 +- moduleauthority/host_fake_test.go | 33 +- moduleauthority/sealed_test.go | 8 +- moduleauthority/verifier_sources.go | 40 +- moduleauthority/verifier_sources_test.go | 17 - 23 files changed, 2366 insertions(+), 1055 deletions(-) diff --git a/SOURCE.txt b/SOURCE.txt index 3ec3a21..1e2661d 100644 --- a/SOURCE.txt +++ b/SOURCE.txt @@ -1,14 +1,11 @@ -gen/ generated from codefly-dev/module-saas-starter@9ab36e7efff8cfd15d48f319dfa540e52c630725 +gen/ generated from codefly-dev/module-saas-starter@v0.0.103 (accounts public proto: module/services/accounts/proto) (auth gateway: module/services/auth-gateway/code) module version: 0.1.0 (module/module.package.codefly.yaml) This SDK's release is matched to the saas-starter module version above. -Released upstream tag: none — this is the merge commit of -codefly-dev/module-saas-starter#1119 on `main`, which is where -ResolveWorkContextAuthority first exists. A commit is a ref this repository's -gen-drift job resolves, so the SDK does not wait on a deploy tag to carry a -contract its consumers need; the next regeneration moves to whichever tag -overtakes it. +Released upstream tag: v0.0.103 (2cb00737ed56c79c823bc82f4055681a51919e7c). +Its auth gateway requires codefly-dev/core at b81d92e6feda, the floor this +SDK's go.mod records. Regeneration does not publish an SDK release. diff --git a/conformance/hostgateway/AGENTS.md b/conformance/hostgateway/AGENTS.md index 1ac42f9..e63924b 100644 --- a/conformance/hostgateway/AGENTS.md +++ b/conformance/hostgateway/AGENTS.md @@ -46,7 +46,7 @@ The script fails, rather than passes, when: `go.mod` passed with `-modfile`. The host checkout must be at the recorded ref and is checked to be unmodified before and after. Nothing of the host is copied here. -- The file binds to four unexported host names, listed at its top. A host +- The file binds to five unexported host names, listed at its top. A host rename breaks the compile — red, never a silent pass. The fix for that coupling is an exported harness in the host, not a copy here. - Only accounts' three `Mint*` RPCs are faked, on a real gRPC listener, as the @@ -76,11 +76,20 @@ duplicate, non-Bearer or empty bearer refused before accounts; the 64 KiB token bound; and the three gateway answers the fake copies (D1, D3, D4 in `moduleauthority/host_fake_test.go`). -At host v0.0.97 (`640ee503617a0130abdba79d8eeb11dc4d8be723`), a work-context -mint's `FailedPrecondition` maps to HTTP 412 (installation pending), preserved -as `BrokerError` without a delegation sentinel. This differs from the source -mint's 412 (`ErrDelegationMissing`). The host's `gateway_modules.go` and -`TestGateway_ModuleWorkContext_RelaysAccountsOutcome` define that mapping. +A work-context mint's `FailedPrecondition` maps to HTTP 412 (nothing to mint +against, installation pending among them), which the SDK reads as +`ErrNoHostStateToMintFor`. This differs from the source mint's 412 +(`ErrDelegationMissing`). + +Since host `af5cef9a` (module-saas-starter#1120, in v0.0.103) the three mints +are served on the gateway's workload endpoint alone and answer 404 on the +public one, so the harness serves the gateway through the host's own +`workloadListener`, as a native run's workload server does. A cell wraps that +listener in a waypoint-authenticated presenter check the SDK never sees, and +which is not under test here. The same commit dropped the internal token from +the work-context mint — that endpoint is its perimeter — and relays accounts' +`Unauthenticated` there as 401 (`ErrInvalidCredentials`), as it already did +`PermissionDenied`. The two operation mints still hold the internal token. ## When it goes red @@ -90,7 +99,7 @@ move and need opposite fixes. - **The test file does not compile** (`[setup failed]` / `build failed`, pointing into `zz_saas_sdk_go_conformance_test.go`). The host changed what the file is bound to: - - one of the four unexported names; + - one of the five unexported names; - `newGatewayHarness`'s results; - an `accountsv1` request or response field the fake accounts reads or answers with. diff --git a/conformance/hostgateway/testdata/sdk_conformance_test.go b/conformance/hostgateway/testdata/sdk_conformance_test.go index 350a428..576d614 100644 --- a/conformance/hostgateway/testdata/sdk_conformance_test.go +++ b/conformance/hostgateway/testdata/sdk_conformance_test.go @@ -18,6 +18,11 @@ package main // unexported names of the host package, and to nothing else of it: // // - newGatewayHarness (gateway_test.go): the host's own gateway under test; +// - workloadListener (workload_listener.go): the mark the gateway's workload +// endpoint puts on every request it serves, the only endpoint the three +// mints are served on (module-saas-starter#1120). The harness serves the +// gateway through it as a native run's workload server does; a cell's +// waypoint-authenticated wrapper around it is not under test here; // - (*Gateway).authz, (*ExtAuthz).backendConn: where the harness's accounts // connection is set, as the host's own tests set it; // - (*ExtAuthz).internalToken: the perimeter credential the harness chose; @@ -129,17 +134,11 @@ func sdkSealed(name string) string { } ctx := context.Background() _, key := sdkcorework.FixtureKeyPair() - seals := sdkcorework.FixtureSeals() - digest, incarnation, err := seals.ApprovedBuild(ctx, sdkcorework.FixturePrincipal) - if err != nil { - panic(err) - } authority := &sdkcorework.Authority{ Issuer: sdkcorework.FixtureIssuer, KeyID: sdkcorework.FixtureKeyID, Key: key, - Revisions: sdkcorework.FixtureRevisions(), Seals: seals, + Revisions: sdkcorework.FixtureRevisions(), Seals: sdkcorework.FixtureSeals(), } token, _, err := authority.Start(ctx, sdkcorework.StartInput{ - Execution: sdkcorework.Execution{ImageDigest: digest, BuildIncarnation: incarnation}, TenantID: sdkcorework.FixtureTenant, OwnerPrincipalID: sdkcorework.FixturePrincipal, OwnerPrincipalKind: "service", @@ -271,11 +270,12 @@ func newRealGateway(t *testing.T) *realGateway { gw.authz.backendConn = conn g := &realGateway{internalToken: gw.authz.internalToken, accounts: accounts} + workload := workloadListener(gw) g.server = httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { g.mu.Lock() g.edge = append(g.edge, edgeRequest{path: r.URL.Path, header: r.Header.Clone()}) g.mu.Unlock() - gw.ServeHTTP(w, r) + workload.ServeHTTP(w, r) })) t.Cleanup(g.server.Close) if g.internalToken == "" { @@ -548,7 +548,9 @@ func TestSDKConformanceRefusals(t *testing.T) { {"work unproven or wrong organization", mintWork, refusal(codes.PermissionDenied, ""), 401, moduleauthority.ErrInvalidCredentials}, {"work execution unestablished", mintWork, refusal(codes.Unavailable, ""), 503, moduleauthority.ErrExecutionUnestablished}, {"work invalid request", mintWork, refusal(codes.InvalidArgument, ""), 400, nil}, - {"work unauthenticated", mintWork, refusal(codes.Unauthenticated, ""), 502, nil}, + // Host af5cef9a (module-saas-starter#1120, #1118): a refused token is + // a 401 on the work-context exchange, as PermissionDenied is. + {"work unauthenticated", mintWork, refusal(codes.Unauthenticated, ""), 401, moduleauthority.ErrInvalidCredentials}, {"work failed precondition", mintWork, refusal(codes.FailedPrecondition, ""), 412, moduleauthority.ErrNoHostStateToMintFor}, {"operation unproven", mintOperation, refusal(codes.Unauthenticated, ""), 401, moduleauthority.ErrInvalidCredentials}, @@ -599,7 +601,12 @@ func TestSDKConformanceWrongInternalToken(t *testing.T) { if err != nil { t.Fatal(err) } - for _, method := range []string{mintWork, mintOperation, mintSource} { + // The operation and source mints still hold the internal token. Host + // af5cef9a (module-saas-starter#1120) serves the three mints on the + // workload endpoint alone and dropped the token from the work-context + // mint: that endpoint is its perimeter, and the projected token its one + // credential. + for _, method := range []string{mintOperation, mintSource} { var be *moduleauthority.BrokerError if err := mint(t.Context(), client, method); !errors.Is(err, moduleauthority.ErrInvalidCredentials) || !errors.As(err, &be) || be.StatusCode != 401 { t.Fatalf("%s: %v, want ErrInvalidCredentials with HTTP 401", method, err) @@ -608,6 +615,9 @@ func TestSDKConformanceWrongInternalToken(t *testing.T) { if calls := g.accounts.snapshot(); len(calls) != 0 { t.Fatalf("accounts was called %d time(s) behind a wrong internal token", len(calls)) } + if err := mint(t.Context(), client, mintWork); err != nil { + t.Fatalf("%s behind a wrong internal token: %v, want it minted on the projected token alone", mintWork, err) + } } func post(t *testing.T, g *realGateway, path, body string, headers func(http.Header)) int { diff --git a/gen/saas/accounts/v1/accountsv1connect/datasource.connect.go b/gen/saas/accounts/v1/accountsv1connect/datasource.connect.go index 8ec894d..d1c38c7 100644 --- a/gen/saas/accounts/v1/accountsv1connect/datasource.connect.go +++ b/gen/saas/accounts/v1/accountsv1connect/datasource.connect.go @@ -57,6 +57,9 @@ const ( // DatasourceServiceAddSourceProcedure is the fully-qualified name of the DatasourceService's // AddSource RPC. DatasourceServiceAddSourceProcedure = "/saas.accounts.v1.DatasourceService/AddSource" + // DatasourceServiceUpdateSourceProcedure is the fully-qualified name of the DatasourceService's + // UpdateSource RPC. + DatasourceServiceUpdateSourceProcedure = "/saas.accounts.v1.DatasourceService/UpdateSource" // DatasourceServiceGetDatasourceCatalogProcedure is the fully-qualified name of the // DatasourceService's GetDatasourceCatalog RPC. DatasourceServiceGetDatasourceCatalogProcedure = "/saas.accounts.v1.DatasourceService/GetDatasourceCatalog" @@ -170,6 +173,12 @@ type DatasourceServiceClient interface { // by provider, stores the config and the encrypted credential (and optional // webhook signing secret), and returns the non-secret projection. AddSource(context.Context, *connect.Request[v1.AddSourceRequest]) (*connect.Response[v1.AddSourceResponse], error) + // UpdateSource changes what an already-connected source fetches — its branch + // and its path and file-type filters — keeping its identity, its credential, + // its sync history and the collection it writes into. A change that moves + // what is fetched enqueues a sync, whose progress reports the reconfigured + // trigger so a reader can tell a re-snapshot from an ordinary one. + UpdateSource(context.Context, *connect.Request[v1.UpdateSourceRequest]) (*connect.Response[v1.UpdateSourceResponse], error) // GetDatasourceCatalog returns the host's connector registry: every provider, // its connect metadata, whether it conforms to the datasource connector // envelope, and whether it accepts a new source, so a client can render the @@ -352,6 +361,12 @@ func NewDatasourceServiceClient(httpClient connect.HTTPClient, baseURL string, o connect.WithSchema(datasourceServiceMethods.ByName("AddSource")), connect.WithClientOptions(opts...), ), + updateSource: connect.NewClient[v1.UpdateSourceRequest, v1.UpdateSourceResponse]( + httpClient, + baseURL+DatasourceServiceUpdateSourceProcedure, + connect.WithSchema(datasourceServiceMethods.ByName("UpdateSource")), + connect.WithClientOptions(opts...), + ), getDatasourceCatalog: connect.NewClient[v1.GetDatasourceCatalogRequest, v1.GetDatasourceCatalogResponse]( httpClient, baseURL+DatasourceServiceGetDatasourceCatalogProcedure, @@ -515,6 +530,7 @@ type datasourceServiceClient struct { declareSourceOperations *connect.Client[v1.DeclareSourceOperationsRequest, v1.DeclareSourceOperationsResponse] addGitHubSource *connect.Client[v1.AddGitHubSourceRequest, v1.AddGitHubSourceResponse] addSource *connect.Client[v1.AddSourceRequest, v1.AddSourceResponse] + updateSource *connect.Client[v1.UpdateSourceRequest, v1.UpdateSourceResponse] getDatasourceCatalog *connect.Client[v1.GetDatasourceCatalogRequest, v1.GetDatasourceCatalogResponse] listSources *connect.Client[v1.ListSourcesRequest, v1.ListSourcesResponse] getSource *connect.Client[v1.GetSourceRequest, v1.GetSourceResponse] @@ -584,6 +600,11 @@ func (c *datasourceServiceClient) AddSource(ctx context.Context, req *connect.Re return c.addSource.CallUnary(ctx, req) } +// UpdateSource calls saas.accounts.v1.DatasourceService.UpdateSource. +func (c *datasourceServiceClient) UpdateSource(ctx context.Context, req *connect.Request[v1.UpdateSourceRequest]) (*connect.Response[v1.UpdateSourceResponse], error) { + return c.updateSource.CallUnary(ctx, req) +} + // GetDatasourceCatalog calls saas.accounts.v1.DatasourceService.GetDatasourceCatalog. func (c *datasourceServiceClient) GetDatasourceCatalog(ctx context.Context, req *connect.Request[v1.GetDatasourceCatalogRequest]) (*connect.Response[v1.GetDatasourceCatalogResponse], error) { return c.getDatasourceCatalog.CallUnary(ctx, req) @@ -747,6 +768,12 @@ type DatasourceServiceHandler interface { // by provider, stores the config and the encrypted credential (and optional // webhook signing secret), and returns the non-secret projection. AddSource(context.Context, *connect.Request[v1.AddSourceRequest]) (*connect.Response[v1.AddSourceResponse], error) + // UpdateSource changes what an already-connected source fetches — its branch + // and its path and file-type filters — keeping its identity, its credential, + // its sync history and the collection it writes into. A change that moves + // what is fetched enqueues a sync, whose progress reports the reconfigured + // trigger so a reader can tell a re-snapshot from an ordinary one. + UpdateSource(context.Context, *connect.Request[v1.UpdateSourceRequest]) (*connect.Response[v1.UpdateSourceResponse], error) // GetDatasourceCatalog returns the host's connector registry: every provider, // its connect metadata, whether it conforms to the datasource connector // envelope, and whether it accepts a new source, so a client can render the @@ -925,6 +952,12 @@ func NewDatasourceServiceHandler(svc DatasourceServiceHandler, opts ...connect.H connect.WithSchema(datasourceServiceMethods.ByName("AddSource")), connect.WithHandlerOptions(opts...), ) + datasourceServiceUpdateSourceHandler := connect.NewUnaryHandler( + DatasourceServiceUpdateSourceProcedure, + svc.UpdateSource, + connect.WithSchema(datasourceServiceMethods.ByName("UpdateSource")), + connect.WithHandlerOptions(opts...), + ) datasourceServiceGetDatasourceCatalogHandler := connect.NewUnaryHandler( DatasourceServiceGetDatasourceCatalogProcedure, svc.GetDatasourceCatalog, @@ -1093,6 +1126,8 @@ func NewDatasourceServiceHandler(svc DatasourceServiceHandler, opts ...connect.H datasourceServiceAddGitHubSourceHandler.ServeHTTP(w, r) case DatasourceServiceAddSourceProcedure: datasourceServiceAddSourceHandler.ServeHTTP(w, r) + case DatasourceServiceUpdateSourceProcedure: + datasourceServiceUpdateSourceHandler.ServeHTTP(w, r) case DatasourceServiceGetDatasourceCatalogProcedure: datasourceServiceGetDatasourceCatalogHandler.ServeHTTP(w, r) case DatasourceServiceListSourcesProcedure: @@ -1184,6 +1219,10 @@ func (UnimplementedDatasourceServiceHandler) AddSource(context.Context, *connect return nil, connect.NewError(connect.CodeUnimplemented, errors.New("saas.accounts.v1.DatasourceService.AddSource is not implemented")) } +func (UnimplementedDatasourceServiceHandler) UpdateSource(context.Context, *connect.Request[v1.UpdateSourceRequest]) (*connect.Response[v1.UpdateSourceResponse], error) { + return nil, connect.NewError(connect.CodeUnimplemented, errors.New("saas.accounts.v1.DatasourceService.UpdateSource is not implemented")) +} + func (UnimplementedDatasourceServiceHandler) GetDatasourceCatalog(context.Context, *connect.Request[v1.GetDatasourceCatalogRequest]) (*connect.Response[v1.GetDatasourceCatalogResponse], error) { return nil, connect.NewError(connect.CodeUnimplemented, errors.New("saas.accounts.v1.DatasourceService.GetDatasourceCatalog is not implemented")) } diff --git a/gen/saas/accounts/v1/accountsv1connect/platform_admin.connect.go b/gen/saas/accounts/v1/accountsv1connect/platform_admin.connect.go index d8d88d5..07a7cd6 100644 --- a/gen/saas/accounts/v1/accountsv1connect/platform_admin.connect.go +++ b/gen/saas/accounts/v1/accountsv1connect/platform_admin.connect.go @@ -167,7 +167,8 @@ type PlatformAdminServiceClient interface { // it declares, what runs, and which organizations have it installed. ListPlatformCatalogue(context.Context, *connect.Request[v1.ListPlatformCatalogueRequest]) (*connect.Response[v1.ListPlatformCatalogueResponse], error) // GetModuleEnvelope reads the current module envelope: the authority ceiling - // every module principal on this host is derived inside. + // every module principal on this host is derived inside, beside what the + // applied module manifests ask for of it. GetModuleEnvelope(context.Context, *connect.Request[v1.GetModuleEnvelopeRequest]) (*connect.Response[v1.GetModuleEnvelopeResponse], error) // PutModuleEnvelope writes the next revision of the module envelope. It takes // effect at the next check with no restart: the module registry is derived @@ -550,7 +551,8 @@ type PlatformAdminServiceHandler interface { // it declares, what runs, and which organizations have it installed. ListPlatformCatalogue(context.Context, *connect.Request[v1.ListPlatformCatalogueRequest]) (*connect.Response[v1.ListPlatformCatalogueResponse], error) // GetModuleEnvelope reads the current module envelope: the authority ceiling - // every module principal on this host is derived inside. + // every module principal on this host is derived inside, beside what the + // applied module manifests ask for of it. GetModuleEnvelope(context.Context, *connect.Request[v1.GetModuleEnvelopeRequest]) (*connect.Response[v1.GetModuleEnvelopeResponse], error) // PutModuleEnvelope writes the next revision of the module envelope. It takes // effect at the next check with no restart: the module registry is derived diff --git a/gen/saas/accounts/v1/accountsv1connect/solution_registry_service.connect.go b/gen/saas/accounts/v1/accountsv1connect/solution_registry_service.connect.go index 702a871..e79b7d4 100644 --- a/gen/saas/accounts/v1/accountsv1connect/solution_registry_service.connect.go +++ b/gen/saas/accounts/v1/accountsv1connect/solution_registry_service.connect.go @@ -39,6 +39,9 @@ const ( // SolutionRegistryServiceListSolutionRegistrationsProcedure is the fully-qualified name of the // SolutionRegistryService's ListSolutionRegistrations RPC. SolutionRegistryServiceListSolutionRegistrationsProcedure = "/saas.accounts.v1.SolutionRegistryService/ListSolutionRegistrations" + // SolutionRegistryServiceGetRetainedSolutionFrontendProcedure is the fully-qualified name of the + // SolutionRegistryService's GetRetainedSolutionFrontend RPC. + SolutionRegistryServiceGetRetainedSolutionFrontendProcedure = "/saas.accounts.v1.SolutionRegistryService/GetRetainedSolutionFrontend" ) // SolutionRegistryServiceClient is a client for the saas.accounts.v1.SolutionRegistryService @@ -53,6 +56,8 @@ type SolutionRegistryServiceClient interface { // ListSolutionRegistrations returns the whole registry so a restarted or // lagging replica can rebuild its routing cache from authoritative state. ListSolutionRegistrations(context.Context, *connect.Request[v1.ListSolutionRegistrationsRequest]) (*connect.Response[v1.ListSolutionRegistrationsResponse], error) + // Read one retained frontend on a live target, without granting API access. + GetRetainedSolutionFrontend(context.Context, *connect.Request[v1.GetRetainedSolutionFrontendRequest]) (*connect.Response[v1.GetRetainedSolutionFrontendResponse], error) } // NewSolutionRegistryServiceClient constructs a client for the @@ -78,13 +83,20 @@ func NewSolutionRegistryServiceClient(httpClient connect.HTTPClient, baseURL str connect.WithSchema(solutionRegistryServiceMethods.ByName("ListSolutionRegistrations")), connect.WithClientOptions(opts...), ), + getRetainedSolutionFrontend: connect.NewClient[v1.GetRetainedSolutionFrontendRequest, v1.GetRetainedSolutionFrontendResponse]( + httpClient, + baseURL+SolutionRegistryServiceGetRetainedSolutionFrontendProcedure, + connect.WithSchema(solutionRegistryServiceMethods.ByName("GetRetainedSolutionFrontend")), + connect.WithClientOptions(opts...), + ), } } // solutionRegistryServiceClient implements SolutionRegistryServiceClient. type solutionRegistryServiceClient struct { - listSolutionHostBindings *connect.Client[v1.ListSolutionHostBindingsRequest, v1.ListSolutionHostBindingsResponse] - listSolutionRegistrations *connect.Client[v1.ListSolutionRegistrationsRequest, v1.ListSolutionRegistrationsResponse] + listSolutionHostBindings *connect.Client[v1.ListSolutionHostBindingsRequest, v1.ListSolutionHostBindingsResponse] + listSolutionRegistrations *connect.Client[v1.ListSolutionRegistrationsRequest, v1.ListSolutionRegistrationsResponse] + getRetainedSolutionFrontend *connect.Client[v1.GetRetainedSolutionFrontendRequest, v1.GetRetainedSolutionFrontendResponse] } // ListSolutionHostBindings calls saas.accounts.v1.SolutionRegistryService.ListSolutionHostBindings. @@ -98,6 +110,12 @@ func (c *solutionRegistryServiceClient) ListSolutionRegistrations(ctx context.Co return c.listSolutionRegistrations.CallUnary(ctx, req) } +// GetRetainedSolutionFrontend calls +// saas.accounts.v1.SolutionRegistryService.GetRetainedSolutionFrontend. +func (c *solutionRegistryServiceClient) GetRetainedSolutionFrontend(ctx context.Context, req *connect.Request[v1.GetRetainedSolutionFrontendRequest]) (*connect.Response[v1.GetRetainedSolutionFrontendResponse], error) { + return c.getRetainedSolutionFrontend.CallUnary(ctx, req) +} + // SolutionRegistryServiceHandler is an implementation of the // saas.accounts.v1.SolutionRegistryService service. type SolutionRegistryServiceHandler interface { @@ -110,6 +128,8 @@ type SolutionRegistryServiceHandler interface { // ListSolutionRegistrations returns the whole registry so a restarted or // lagging replica can rebuild its routing cache from authoritative state. ListSolutionRegistrations(context.Context, *connect.Request[v1.ListSolutionRegistrationsRequest]) (*connect.Response[v1.ListSolutionRegistrationsResponse], error) + // Read one retained frontend on a live target, without granting API access. + GetRetainedSolutionFrontend(context.Context, *connect.Request[v1.GetRetainedSolutionFrontendRequest]) (*connect.Response[v1.GetRetainedSolutionFrontendResponse], error) } // NewSolutionRegistryServiceHandler builds an HTTP handler from the service implementation. It @@ -131,12 +151,20 @@ func NewSolutionRegistryServiceHandler(svc SolutionRegistryServiceHandler, opts connect.WithSchema(solutionRegistryServiceMethods.ByName("ListSolutionRegistrations")), connect.WithHandlerOptions(opts...), ) + solutionRegistryServiceGetRetainedSolutionFrontendHandler := connect.NewUnaryHandler( + SolutionRegistryServiceGetRetainedSolutionFrontendProcedure, + svc.GetRetainedSolutionFrontend, + connect.WithSchema(solutionRegistryServiceMethods.ByName("GetRetainedSolutionFrontend")), + connect.WithHandlerOptions(opts...), + ) return "/saas.accounts.v1.SolutionRegistryService/", http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { switch r.URL.Path { case SolutionRegistryServiceListSolutionHostBindingsProcedure: solutionRegistryServiceListSolutionHostBindingsHandler.ServeHTTP(w, r) case SolutionRegistryServiceListSolutionRegistrationsProcedure: solutionRegistryServiceListSolutionRegistrationsHandler.ServeHTTP(w, r) + case SolutionRegistryServiceGetRetainedSolutionFrontendProcedure: + solutionRegistryServiceGetRetainedSolutionFrontendHandler.ServeHTTP(w, r) default: http.NotFound(w, r) } @@ -153,3 +181,7 @@ func (UnimplementedSolutionRegistryServiceHandler) ListSolutionHostBindings(cont func (UnimplementedSolutionRegistryServiceHandler) ListSolutionRegistrations(context.Context, *connect.Request[v1.ListSolutionRegistrationsRequest]) (*connect.Response[v1.ListSolutionRegistrationsResponse], error) { return nil, connect.NewError(connect.CodeUnimplemented, errors.New("saas.accounts.v1.SolutionRegistryService.ListSolutionRegistrations is not implemented")) } + +func (UnimplementedSolutionRegistryServiceHandler) GetRetainedSolutionFrontend(context.Context, *connect.Request[v1.GetRetainedSolutionFrontendRequest]) (*connect.Response[v1.GetRetainedSolutionFrontendResponse], error) { + return nil, connect.NewError(connect.CodeUnimplemented, errors.New("saas.accounts.v1.SolutionRegistryService.GetRetainedSolutionFrontend is not implemented")) +} diff --git a/gen/saas/accounts/v1/authorization.pb.go b/gen/saas/accounts/v1/authorization.pb.go index 7e80acc..b9dd9f2 100644 --- a/gen/saas/accounts/v1/authorization.pb.go +++ b/gen/saas/accounts/v1/authorization.pb.go @@ -1457,18 +1457,29 @@ func (x *RegisterScopeNodeResponse) GetNode() *ScopeNode { } type ScopeGrant struct { - state protoimpl.MessageState `protogen:"open.v1"` - Id string `protobuf:"bytes,1,opt,name=id,proto3" json:"id,omitempty"` - OrgId string `protobuf:"bytes,2,opt,name=org_id,json=orgId,proto3" json:"org_id,omitempty"` - SubjectId string `protobuf:"bytes,3,opt,name=subject_id,json=subjectId,proto3" json:"subject_id,omitempty"` - SubjectKind SubjectKind `protobuf:"varint,4,opt,name=subject_kind,json=subjectKind,proto3,enum=saas.accounts.v1.SubjectKind" json:"subject_kind,omitempty"` - ScopePath string `protobuf:"bytes,5,opt,name=scope_path,json=scopePath,proto3" json:"scope_path,omitempty"` - RoleId string `protobuf:"bytes,6,opt,name=role_id,json=roleId,proto3" json:"role_id,omitempty"` - GrantedBy string `protobuf:"bytes,7,opt,name=granted_by,json=grantedBy,proto3" json:"granted_by,omitempty"` - ExpiresAt *timestamppb.Timestamp `protobuf:"bytes,8,opt,name=expires_at,json=expiresAt,proto3" json:"expires_at,omitempty"` - CreatedAt *timestamppb.Timestamp `protobuf:"bytes,9,opt,name=created_at,json=createdAt,proto3" json:"created_at,omitempty"` - unknownFields protoimpl.UnknownFields - sizeCache protoimpl.SizeCache + state protoimpl.MessageState `protogen:"open.v1"` + Id string `protobuf:"bytes,1,opt,name=id,proto3" json:"id,omitempty"` + OrgId string `protobuf:"bytes,2,opt,name=org_id,json=orgId,proto3" json:"org_id,omitempty"` + SubjectId string `protobuf:"bytes,3,opt,name=subject_id,json=subjectId,proto3" json:"subject_id,omitempty"` + SubjectKind SubjectKind `protobuf:"varint,4,opt,name=subject_kind,json=subjectKind,proto3,enum=saas.accounts.v1.SubjectKind" json:"subject_kind,omitempty"` + ScopePath string `protobuf:"bytes,5,opt,name=scope_path,json=scopePath,proto3" json:"scope_path,omitempty"` + RoleId string `protobuf:"bytes,6,opt,name=role_id,json=roleId,proto3" json:"role_id,omitempty"` + GrantedBy string `protobuf:"bytes,7,opt,name=granted_by,json=grantedBy,proto3" json:"granted_by,omitempty"` + ExpiresAt *timestamppb.Timestamp `protobuf:"bytes,8,opt,name=expires_at,json=expiresAt,proto3" json:"expires_at,omitempty"` + CreatedAt *timestamppb.Timestamp `protobuf:"bytes,9,opt,name=created_at,json=createdAt,proto3" json:"created_at,omitempty"` + // The grant that CAUSED this one, when this grant was derived rather than + // written by an administrator: the exposure grant of a solution whose applied + // manifest declares it reaches this node's module on the asking person's own + // session. Empty for every grant an administrator wrote. + // + // A derived grant is an ordinary grant in every other respect — same node, + // same resolution, same events — so this is the one field that says a surface + // must name the solution rather than offer a revoke: it goes when its cause + // goes, and removing it by hand only breaks the solution until the next grant + // of that cause re-derives it. + DerivedFromGrantId string `protobuf:"bytes,10,opt,name=derived_from_grant_id,json=derivedFromGrantId,proto3" json:"derived_from_grant_id,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache } func (x *ScopeGrant) Reset() { @@ -1564,6 +1575,13 @@ func (x *ScopeGrant) GetCreatedAt() *timestamppb.Timestamp { return nil } +func (x *ScopeGrant) GetDerivedFromGrantId() string { + if x != nil { + return x.DerivedFromGrantId + } + return "" +} + type CollectionReadGrant struct { state protoimpl.MessageState `protogen:"open.v1"` Grant *ScopeGrant `protobuf:"bytes,1,opt,name=grant,proto3" json:"grant,omitempty"` @@ -3233,7 +3251,7 @@ const file_saas_accounts_v1_authorization_proto_rawDesc = "" + "\vresource_id\x18\x06 \x01(\tR\n" + "resourceId\"L\n" + "\x19RegisterScopeNodeResponse\x12/\n" + - "\x04node\x18\x01 \x01(\v2\x1b.saas.accounts.v1.ScopeNodeR\x04node\"\xe1\x02\n" + + "\x04node\x18\x01 \x01(\v2\x1b.saas.accounts.v1.ScopeNodeR\x04node\"\x94\x03\n" + "\n" + "ScopeGrant\x12\x0e\n" + "\x02id\x18\x01 \x01(\tR\x02id\x12\x15\n" + @@ -3249,7 +3267,9 @@ const file_saas_accounts_v1_authorization_proto_rawDesc = "" + "\n" + "expires_at\x18\b \x01(\v2\x1a.google.protobuf.TimestampR\texpiresAt\x129\n" + "\n" + - "created_at\x18\t \x01(\v2\x1a.google.protobuf.TimestampR\tcreatedAt\"\xac\x01\n" + + "created_at\x18\t \x01(\v2\x1a.google.protobuf.TimestampR\tcreatedAt\x121\n" + + "\x15derived_from_grant_id\x18\n" + + " \x01(\tR\x12derivedFromGrantId\"\xac\x01\n" + "\x13CollectionReadGrant\x122\n" + "\x05grant\x18\x01 \x01(\v2\x1c.saas.accounts.v1.ScopeGrantR\x05grant\x12#\n" + "\rsubject_label\x18\x02 \x01(\tR\fsubjectLabel\x12\x1b\n" + diff --git a/gen/saas/accounts/v1/datasource.pb.go b/gen/saas/accounts/v1/datasource.pb.go index ea8ce23..ba4782c 100644 --- a/gen/saas/accounts/v1/datasource.pb.go +++ b/gen/saas/accounts/v1/datasource.pb.go @@ -642,6 +642,11 @@ const ( SourceSyncTrigger_SOURCE_SYNC_TRIGGER_SCHEDULED SourceSyncTrigger = 2 // A webhook delivery from the provider. SourceSyncTrigger_SOURCE_SYNC_TRIGGER_WEBHOOK SourceSyncTrigger = 3 + // The source was reconfigured — its branch or its path/file-type filters + // changed — so this sync re-snapshots it at the new scope. It is the one + // trigger that tells a reader the change set is large because the source + // moved rather than because the repository did. + SourceSyncTrigger_SOURCE_SYNC_TRIGGER_RECONFIGURED SourceSyncTrigger = 4 ) // Enum value maps for SourceSyncTrigger. @@ -651,12 +656,14 @@ var ( 1: "SOURCE_SYNC_TRIGGER_MANUAL", 2: "SOURCE_SYNC_TRIGGER_SCHEDULED", 3: "SOURCE_SYNC_TRIGGER_WEBHOOK", + 4: "SOURCE_SYNC_TRIGGER_RECONFIGURED", } SourceSyncTrigger_value = map[string]int32{ - "SOURCE_SYNC_TRIGGER_UNSPECIFIED": 0, - "SOURCE_SYNC_TRIGGER_MANUAL": 1, - "SOURCE_SYNC_TRIGGER_SCHEDULED": 2, - "SOURCE_SYNC_TRIGGER_WEBHOOK": 3, + "SOURCE_SYNC_TRIGGER_UNSPECIFIED": 0, + "SOURCE_SYNC_TRIGGER_MANUAL": 1, + "SOURCE_SYNC_TRIGGER_SCHEDULED": 2, + "SOURCE_SYNC_TRIGGER_WEBHOOK": 3, + "SOURCE_SYNC_TRIGGER_RECONFIGURED": 4, } ) @@ -913,7 +920,7 @@ func (x SourceOperation_Effect) Number() protoreflect.EnumNumber { // Deprecated: Use SourceOperation_Effect.Descriptor instead. func (SourceOperation_Effect) EnumDescriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{77, 0} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{80, 0} } // GitHubDatasourceConfig is the public, non-secret configuration of a GitHub @@ -2034,6 +2041,250 @@ func (x *AddSourceResponse) GetDatasource() *Datasource { return nil } +// UpdateSourceRequest changes what an already-connected source fetches, in +// place: its branch and its path and file-type filters. Nothing else about a +// source is mutable here — the repository, the provider, the collection it +// writes into and its credential are each the identity of something a consumer +// already holds, and changing one of those is a different source. +// +// Every field is a WHOLE-FIELD REPLACEMENT, not a patch: the source is left +// fetching exactly what this request names, so an empty `paths` ingests the +// whole repository and an empty `file_extensions` admits every file type, +// exactly as they mean on connect. A repeated proto3 field cannot tell "not +// sent" from "sent empty", so a request that meant to leave a filter alone +// must repeat it; naming that here is what keeps a clearing from reading as an +// omission, and an omission from being silently preserved. +// +// Because every field is a whole-field replacement, every request asserts the +// source's complete scope — so one is accepted only against the scope its +// author was actually shown. `expected` carries that scope back, and a request +// whose expectation no longer matches the stored row is REFUSED rather than +// applied: without it, a form opened while the source read one way and saved +// after someone else narrowed it would silently restore the wider scope and +// re-ingest everything the other person had just excluded. +type UpdateSourceRequest struct { + state protoimpl.MessageState `protogen:"open.v1"` + OrgId string `protobuf:"bytes,1,opt,name=org_id,json=orgId,proto3" json:"org_id,omitempty"` + Id string `protobuf:"bytes,2,opt,name=id,proto3" json:"id,omitempty"` + // Git ref (branch) to pull. Empty resolves to the repository default branch, + // as on connect. A branch the source's own credential cannot read is refused + // before anything is written. + Branch string `protobuf:"bytes,3,opt,name=branch,proto3" json:"branch,omitempty"` + // Repository-relative path prefixes to ingest. Empty ingests the whole repo. + Paths []string `protobuf:"bytes,4,rep,name=paths,proto3" json:"paths,omitempty"` + // Case-insensitive file suffixes, e.g. [".md", ".mdx"]. Empty admits every + // file type within paths. + FileExtensions []string `protobuf:"bytes,5,rep,name=file_extensions,json=fileExtensions,proto3" json:"file_extensions,omitempty"` + // The scope the caller was shown, as it read it. Required: an unconditional + // whole-field replacement is exactly how one editor's save erases another's, + // so there is no "just apply it" mode to fall back to. + // + // It is the scope and not the row's `updated_at` because `updated_at` moves + // on every successful sync, which would refuse a perfectly good edit for the + // sole reason that the source had reconciled since the form was opened. What + // an editor needs guarded is what they were looking at. + Expected *SourceFetchScope `protobuf:"bytes,6,opt,name=expected,proto3" json:"expected,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *UpdateSourceRequest) Reset() { + *x = UpdateSourceRequest{} + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[10] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *UpdateSourceRequest) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*UpdateSourceRequest) ProtoMessage() {} + +func (x *UpdateSourceRequest) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[10] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use UpdateSourceRequest.ProtoReflect.Descriptor instead. +func (*UpdateSourceRequest) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{10} +} + +func (x *UpdateSourceRequest) GetOrgId() string { + if x != nil { + return x.OrgId + } + return "" +} + +func (x *UpdateSourceRequest) GetId() string { + if x != nil { + return x.Id + } + return "" +} + +func (x *UpdateSourceRequest) GetBranch() string { + if x != nil { + return x.Branch + } + return "" +} + +func (x *UpdateSourceRequest) GetPaths() []string { + if x != nil { + return x.Paths + } + return nil +} + +func (x *UpdateSourceRequest) GetFileExtensions() []string { + if x != nil { + return x.FileExtensions + } + return nil +} + +func (x *UpdateSourceRequest) GetExpected() *SourceFetchScope { + if x != nil { + return x.Expected + } + return nil +} + +// SourceFetchScope is what a source fetches — the three values UpdateSource +// replaces — carried on its own so a request can state the scope it expects to +// be replacing as well as the one it wants. +// +// Its bounds are deliberately looser than the mutable fields': an expectation +// is only ever compared against the stored row, never stored, so holding it to +// today's shape would make a source that predates that shape impossible to +// edit at all. Size is still bounded, because the comparison reads the whole +// thing. +type SourceFetchScope struct { + state protoimpl.MessageState `protogen:"open.v1"` + Branch string `protobuf:"bytes,1,opt,name=branch,proto3" json:"branch,omitempty"` + Paths []string `protobuf:"bytes,2,rep,name=paths,proto3" json:"paths,omitempty"` + FileExtensions []string `protobuf:"bytes,3,rep,name=file_extensions,json=fileExtensions,proto3" json:"file_extensions,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *SourceFetchScope) Reset() { + *x = SourceFetchScope{} + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[11] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *SourceFetchScope) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*SourceFetchScope) ProtoMessage() {} + +func (x *SourceFetchScope) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[11] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use SourceFetchScope.ProtoReflect.Descriptor instead. +func (*SourceFetchScope) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{11} +} + +func (x *SourceFetchScope) GetBranch() string { + if x != nil { + return x.Branch + } + return "" +} + +func (x *SourceFetchScope) GetPaths() []string { + if x != nil { + return x.Paths + } + return nil +} + +func (x *SourceFetchScope) GetFileExtensions() []string { + if x != nil { + return x.FileExtensions + } + return nil +} + +type UpdateSourceResponse struct { + state protoimpl.MessageState `protogen:"open.v1"` + Datasource *Datasource `protobuf:"bytes,1,opt,name=datasource,proto3" json:"datasource,omitempty"` + // The sync enqueued because the update moved what the source fetches, which + // for a consumer is a new snapshot of the collection. Empty when the request + // changed nothing, which is the only case where no sync runs: every mutable + // field here selects content, so any real change re-snapshots the source. + JobId string `protobuf:"bytes,2,opt,name=job_id,json=jobId,proto3" json:"job_id,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *UpdateSourceResponse) Reset() { + *x = UpdateSourceResponse{} + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[12] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *UpdateSourceResponse) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*UpdateSourceResponse) ProtoMessage() {} + +func (x *UpdateSourceResponse) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[12] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use UpdateSourceResponse.ProtoReflect.Descriptor instead. +func (*UpdateSourceResponse) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{12} +} + +func (x *UpdateSourceResponse) GetDatasource() *Datasource { + if x != nil { + return x.Datasource + } + return nil +} + +func (x *UpdateSourceResponse) GetJobId() string { + if x != nil { + return x.JobId + } + return "" +} + // DatasourceConfigField describes one non-secret config input a provider needs, // so the UI can render the connect form from the catalog rather than hardcoding // it per provider. @@ -2050,7 +2301,7 @@ type DatasourceConfigField struct { func (x *DatasourceConfigField) Reset() { *x = DatasourceConfigField{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[10] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[13] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2062,7 +2313,7 @@ func (x *DatasourceConfigField) String() string { func (*DatasourceConfigField) ProtoMessage() {} func (x *DatasourceConfigField) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[10] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[13] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2075,7 +2326,7 @@ func (x *DatasourceConfigField) ProtoReflect() protoreflect.Message { // Deprecated: Use DatasourceConfigField.ProtoReflect.Descriptor instead. func (*DatasourceConfigField) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{10} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{13} } func (x *DatasourceConfigField) GetKey() string { @@ -2124,7 +2375,7 @@ type DatasourceConnectorBudget struct { func (x *DatasourceConnectorBudget) Reset() { *x = DatasourceConnectorBudget{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[11] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[14] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2136,7 +2387,7 @@ func (x *DatasourceConnectorBudget) String() string { func (*DatasourceConnectorBudget) ProtoMessage() {} func (x *DatasourceConnectorBudget) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[11] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[14] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2149,7 +2400,7 @@ func (x *DatasourceConnectorBudget) ProtoReflect() protoreflect.Message { // Deprecated: Use DatasourceConnectorBudget.ProtoReflect.Descriptor instead. func (*DatasourceConnectorBudget) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{11} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{14} } func (x *DatasourceConnectorBudget) GetMaxItemsPerCall() uint32 { @@ -2244,7 +2495,7 @@ type DatasourceProviderDescriptor struct { func (x *DatasourceProviderDescriptor) Reset() { *x = DatasourceProviderDescriptor{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[12] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[15] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2256,7 +2507,7 @@ func (x *DatasourceProviderDescriptor) String() string { func (*DatasourceProviderDescriptor) ProtoMessage() {} func (x *DatasourceProviderDescriptor) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[12] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[15] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2269,7 +2520,7 @@ func (x *DatasourceProviderDescriptor) ProtoReflect() protoreflect.Message { // Deprecated: Use DatasourceProviderDescriptor.ProtoReflect.Descriptor instead. func (*DatasourceProviderDescriptor) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{12} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{15} } func (x *DatasourceProviderDescriptor) GetProvider() DatasourceProvider { @@ -2420,7 +2671,7 @@ type GetDatasourceCatalogRequest struct { func (x *GetDatasourceCatalogRequest) Reset() { *x = GetDatasourceCatalogRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[13] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[16] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2432,7 +2683,7 @@ func (x *GetDatasourceCatalogRequest) String() string { func (*GetDatasourceCatalogRequest) ProtoMessage() {} func (x *GetDatasourceCatalogRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[13] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[16] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2445,7 +2696,7 @@ func (x *GetDatasourceCatalogRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use GetDatasourceCatalogRequest.ProtoReflect.Descriptor instead. func (*GetDatasourceCatalogRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{13} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{16} } type GetDatasourceCatalogResponse struct { @@ -2457,7 +2708,7 @@ type GetDatasourceCatalogResponse struct { func (x *GetDatasourceCatalogResponse) Reset() { *x = GetDatasourceCatalogResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[14] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[17] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2469,7 +2720,7 @@ func (x *GetDatasourceCatalogResponse) String() string { func (*GetDatasourceCatalogResponse) ProtoMessage() {} func (x *GetDatasourceCatalogResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[14] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[17] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2482,7 +2733,7 @@ func (x *GetDatasourceCatalogResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use GetDatasourceCatalogResponse.ProtoReflect.Descriptor instead. func (*GetDatasourceCatalogResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{14} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{17} } func (x *GetDatasourceCatalogResponse) GetProviders() []*DatasourceProviderDescriptor { @@ -2501,7 +2752,7 @@ type ListSourcesRequest struct { func (x *ListSourcesRequest) Reset() { *x = ListSourcesRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[15] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[18] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2513,7 +2764,7 @@ func (x *ListSourcesRequest) String() string { func (*ListSourcesRequest) ProtoMessage() {} func (x *ListSourcesRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[15] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[18] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2526,7 +2777,7 @@ func (x *ListSourcesRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use ListSourcesRequest.ProtoReflect.Descriptor instead. func (*ListSourcesRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{15} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{18} } func (x *ListSourcesRequest) GetOrgId() string { @@ -2545,7 +2796,7 @@ type ListSourcesResponse struct { func (x *ListSourcesResponse) Reset() { *x = ListSourcesResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[16] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[19] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2557,7 +2808,7 @@ func (x *ListSourcesResponse) String() string { func (*ListSourcesResponse) ProtoMessage() {} func (x *ListSourcesResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[16] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[19] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2570,7 +2821,7 @@ func (x *ListSourcesResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ListSourcesResponse.ProtoReflect.Descriptor instead. func (*ListSourcesResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{16} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{19} } func (x *ListSourcesResponse) GetDatasources() []*Datasource { @@ -2590,7 +2841,7 @@ type GetSourceRequest struct { func (x *GetSourceRequest) Reset() { *x = GetSourceRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[17] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[20] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2602,7 +2853,7 @@ func (x *GetSourceRequest) String() string { func (*GetSourceRequest) ProtoMessage() {} func (x *GetSourceRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[17] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[20] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2615,7 +2866,7 @@ func (x *GetSourceRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use GetSourceRequest.ProtoReflect.Descriptor instead. func (*GetSourceRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{17} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{20} } func (x *GetSourceRequest) GetOrgId() string { @@ -2641,7 +2892,7 @@ type GetSourceResponse struct { func (x *GetSourceResponse) Reset() { *x = GetSourceResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[18] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[21] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2653,7 +2904,7 @@ func (x *GetSourceResponse) String() string { func (*GetSourceResponse) ProtoMessage() {} func (x *GetSourceResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[18] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[21] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2666,7 +2917,7 @@ func (x *GetSourceResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use GetSourceResponse.ProtoReflect.Descriptor instead. func (*GetSourceResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{18} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{21} } func (x *GetSourceResponse) GetDatasource() *Datasource { @@ -2697,7 +2948,7 @@ type SyncSourceRequest struct { func (x *SyncSourceRequest) Reset() { *x = SyncSourceRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[19] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[22] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2709,7 +2960,7 @@ func (x *SyncSourceRequest) String() string { func (*SyncSourceRequest) ProtoMessage() {} func (x *SyncSourceRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[19] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[22] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2722,7 +2973,7 @@ func (x *SyncSourceRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use SyncSourceRequest.ProtoReflect.Descriptor instead. func (*SyncSourceRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{19} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{22} } func (x *SyncSourceRequest) GetOrgId() string { @@ -2764,7 +3015,7 @@ type SyncSourceResponse struct { func (x *SyncSourceResponse) Reset() { *x = SyncSourceResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[20] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[23] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2776,7 +3027,7 @@ func (x *SyncSourceResponse) String() string { func (*SyncSourceResponse) ProtoMessage() {} func (x *SyncSourceResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[20] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[23] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2789,7 +3040,7 @@ func (x *SyncSourceResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use SyncSourceResponse.ProtoReflect.Descriptor instead. func (*SyncSourceResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{20} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{23} } func (x *SyncSourceResponse) GetJobId() string { @@ -2814,7 +3065,7 @@ type GetSourceSyncRequest struct { func (x *GetSourceSyncRequest) Reset() { *x = GetSourceSyncRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[21] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[24] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2826,7 +3077,7 @@ func (x *GetSourceSyncRequest) String() string { func (*GetSourceSyncRequest) ProtoMessage() {} func (x *GetSourceSyncRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[21] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[24] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2839,7 +3090,7 @@ func (x *GetSourceSyncRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use GetSourceSyncRequest.ProtoReflect.Descriptor instead. func (*GetSourceSyncRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{21} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{24} } func (x *GetSourceSyncRequest) GetOrgId() string { @@ -2874,7 +3125,7 @@ type SourceSyncDelivery struct { func (x *SourceSyncDelivery) Reset() { *x = SourceSyncDelivery{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[22] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[25] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2886,7 +3137,7 @@ func (x *SourceSyncDelivery) String() string { func (*SourceSyncDelivery) ProtoMessage() {} func (x *SourceSyncDelivery) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[22] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[25] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2899,7 +3150,7 @@ func (x *SourceSyncDelivery) ProtoReflect() protoreflect.Message { // Deprecated: Use SourceSyncDelivery.ProtoReflect.Descriptor instead. func (*SourceSyncDelivery) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{22} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{25} } func (x *SourceSyncDelivery) GetJobId() string { @@ -2947,7 +3198,7 @@ type SourceSyncChanges struct { func (x *SourceSyncChanges) Reset() { *x = SourceSyncChanges{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[23] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[26] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -2959,7 +3210,7 @@ func (x *SourceSyncChanges) String() string { func (*SourceSyncChanges) ProtoMessage() {} func (x *SourceSyncChanges) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[23] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[26] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -2972,7 +3223,7 @@ func (x *SourceSyncChanges) ProtoReflect() protoreflect.Message { // Deprecated: Use SourceSyncChanges.ProtoReflect.Descriptor instead. func (*SourceSyncChanges) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{23} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{26} } func (x *SourceSyncChanges) GetFiles() uint32 { @@ -3043,7 +3294,7 @@ type SourceSyncFailure struct { func (x *SourceSyncFailure) Reset() { *x = SourceSyncFailure{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[24] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[27] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3055,7 +3306,7 @@ func (x *SourceSyncFailure) String() string { func (*SourceSyncFailure) ProtoMessage() {} func (x *SourceSyncFailure) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[24] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[27] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3068,7 +3319,7 @@ func (x *SourceSyncFailure) ProtoReflect() protoreflect.Message { // Deprecated: Use SourceSyncFailure.ProtoReflect.Descriptor instead. func (*SourceSyncFailure) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{24} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{27} } func (x *SourceSyncFailure) GetReason() SourceSyncFailureReason { @@ -3136,7 +3387,7 @@ type SourceSyncProgress struct { func (x *SourceSyncProgress) Reset() { *x = SourceSyncProgress{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[25] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[28] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3148,7 +3399,7 @@ func (x *SourceSyncProgress) String() string { func (*SourceSyncProgress) ProtoMessage() {} func (x *SourceSyncProgress) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[25] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[28] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3161,7 +3412,7 @@ func (x *SourceSyncProgress) ProtoReflect() protoreflect.Message { // Deprecated: Use SourceSyncProgress.ProtoReflect.Descriptor instead. func (*SourceSyncProgress) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{25} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{28} } func (x *SourceSyncProgress) GetPhase() SourceSyncPhase { @@ -3253,7 +3504,7 @@ type GetSourceSyncResponse struct { func (x *GetSourceSyncResponse) Reset() { *x = GetSourceSyncResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[26] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[29] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3265,7 +3516,7 @@ func (x *GetSourceSyncResponse) String() string { func (*GetSourceSyncResponse) ProtoMessage() {} func (x *GetSourceSyncResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[26] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[29] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3278,7 +3529,7 @@ func (x *GetSourceSyncResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use GetSourceSyncResponse.ProtoReflect.Descriptor instead. func (*GetSourceSyncResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{26} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{29} } func (x *GetSourceSyncResponse) GetJobId() string { @@ -3319,7 +3570,7 @@ type DeleteSourceRequest struct { func (x *DeleteSourceRequest) Reset() { *x = DeleteSourceRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[27] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[30] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3331,7 +3582,7 @@ func (x *DeleteSourceRequest) String() string { func (*DeleteSourceRequest) ProtoMessage() {} func (x *DeleteSourceRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[27] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[30] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3344,7 +3595,7 @@ func (x *DeleteSourceRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use DeleteSourceRequest.ProtoReflect.Descriptor instead. func (*DeleteSourceRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{27} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{30} } func (x *DeleteSourceRequest) GetOrgId() string { @@ -3369,7 +3620,7 @@ type DeleteSourceResponse struct { func (x *DeleteSourceResponse) Reset() { *x = DeleteSourceResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[28] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[31] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3381,7 +3632,7 @@ func (x *DeleteSourceResponse) String() string { func (*DeleteSourceResponse) ProtoMessage() {} func (x *DeleteSourceResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[28] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[31] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3394,7 +3645,7 @@ func (x *DeleteSourceResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use DeleteSourceResponse.ProtoReflect.Descriptor instead. func (*DeleteSourceResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{28} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{31} } // GitHubAppRepository is one repository a verified App installation grants this @@ -3415,7 +3666,7 @@ type GitHubAppRepository struct { func (x *GitHubAppRepository) Reset() { *x = GitHubAppRepository{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[29] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[32] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3427,7 +3678,7 @@ func (x *GitHubAppRepository) String() string { func (*GitHubAppRepository) ProtoMessage() {} func (x *GitHubAppRepository) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[29] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[32] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3440,7 +3691,7 @@ func (x *GitHubAppRepository) ProtoReflect() protoreflect.Message { // Deprecated: Use GitHubAppRepository.ProtoReflect.Descriptor instead. func (*GitHubAppRepository) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{29} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{32} } func (x *GitHubAppRepository) GetRepo() string { @@ -3473,7 +3724,7 @@ type BeginGitHubAppSetupRequest struct { func (x *BeginGitHubAppSetupRequest) Reset() { *x = BeginGitHubAppSetupRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[30] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[33] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3485,7 +3736,7 @@ func (x *BeginGitHubAppSetupRequest) String() string { func (*BeginGitHubAppSetupRequest) ProtoMessage() {} func (x *BeginGitHubAppSetupRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[30] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[33] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3498,7 +3749,7 @@ func (x *BeginGitHubAppSetupRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use BeginGitHubAppSetupRequest.ProtoReflect.Descriptor instead. func (*BeginGitHubAppSetupRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{30} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{33} } func (x *BeginGitHubAppSetupRequest) GetOrgId() string { @@ -3525,7 +3776,7 @@ type BeginGitHubAppSetupResponse struct { func (x *BeginGitHubAppSetupResponse) Reset() { *x = BeginGitHubAppSetupResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[31] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[34] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3537,7 +3788,7 @@ func (x *BeginGitHubAppSetupResponse) String() string { func (*BeginGitHubAppSetupResponse) ProtoMessage() {} func (x *BeginGitHubAppSetupResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[31] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[34] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3550,7 +3801,7 @@ func (x *BeginGitHubAppSetupResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use BeginGitHubAppSetupResponse.ProtoReflect.Descriptor instead. func (*BeginGitHubAppSetupResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{31} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{34} } func (x *BeginGitHubAppSetupResponse) GetInstallUrl() string { @@ -3599,7 +3850,7 @@ type CompleteGitHubAppSetupRequest struct { func (x *CompleteGitHubAppSetupRequest) Reset() { *x = CompleteGitHubAppSetupRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[32] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[35] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3611,7 +3862,7 @@ func (x *CompleteGitHubAppSetupRequest) String() string { func (*CompleteGitHubAppSetupRequest) ProtoMessage() {} func (x *CompleteGitHubAppSetupRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[32] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[35] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3624,7 +3875,7 @@ func (x *CompleteGitHubAppSetupRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use CompleteGitHubAppSetupRequest.ProtoReflect.Descriptor instead. func (*CompleteGitHubAppSetupRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{32} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{35} } func (x *CompleteGitHubAppSetupRequest) GetOrgId() string { @@ -3667,7 +3918,7 @@ type CompleteGitHubAppSetupResponse struct { func (x *CompleteGitHubAppSetupResponse) Reset() { *x = CompleteGitHubAppSetupResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[33] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[36] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3679,7 +3930,7 @@ func (x *CompleteGitHubAppSetupResponse) String() string { func (*CompleteGitHubAppSetupResponse) ProtoMessage() {} func (x *CompleteGitHubAppSetupResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[33] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[36] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3692,7 +3943,7 @@ func (x *CompleteGitHubAppSetupResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use CompleteGitHubAppSetupResponse.ProtoReflect.Descriptor instead. func (*CompleteGitHubAppSetupResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{33} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{36} } func (x *CompleteGitHubAppSetupResponse) GetInstallationId() string { @@ -3719,7 +3970,7 @@ type MigrateGitHubSourceToAppRequest struct { func (x *MigrateGitHubSourceToAppRequest) Reset() { *x = MigrateGitHubSourceToAppRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[34] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[37] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3731,7 +3982,7 @@ func (x *MigrateGitHubSourceToAppRequest) String() string { func (*MigrateGitHubSourceToAppRequest) ProtoMessage() {} func (x *MigrateGitHubSourceToAppRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[34] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[37] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3744,7 +3995,7 @@ func (x *MigrateGitHubSourceToAppRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use MigrateGitHubSourceToAppRequest.ProtoReflect.Descriptor instead. func (*MigrateGitHubSourceToAppRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{34} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{37} } func (x *MigrateGitHubSourceToAppRequest) GetOrgId() string { @@ -3770,7 +4021,7 @@ type MigrateGitHubSourceToAppResponse struct { func (x *MigrateGitHubSourceToAppResponse) Reset() { *x = MigrateGitHubSourceToAppResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[35] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[38] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3782,7 +4033,7 @@ func (x *MigrateGitHubSourceToAppResponse) String() string { func (*MigrateGitHubSourceToAppResponse) ProtoMessage() {} func (x *MigrateGitHubSourceToAppResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[35] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[38] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3795,7 +4046,7 @@ func (x *MigrateGitHubSourceToAppResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use MigrateGitHubSourceToAppResponse.ProtoReflect.Descriptor instead. func (*MigrateGitHubSourceToAppResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{35} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{38} } func (x *MigrateGitHubSourceToAppResponse) GetDatasource() *Datasource { @@ -3825,7 +4076,7 @@ type DatasourceAccountLink struct { func (x *DatasourceAccountLink) Reset() { *x = DatasourceAccountLink{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[36] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[39] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3837,7 +4088,7 @@ func (x *DatasourceAccountLink) String() string { func (*DatasourceAccountLink) ProtoMessage() {} func (x *DatasourceAccountLink) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[36] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[39] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3850,7 +4101,7 @@ func (x *DatasourceAccountLink) ProtoReflect() protoreflect.Message { // Deprecated: Use DatasourceAccountLink.ProtoReflect.Descriptor instead. func (*DatasourceAccountLink) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{36} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{39} } func (x *DatasourceAccountLink) GetId() string { @@ -3920,7 +4171,7 @@ type DatasourceGroupBinding struct { func (x *DatasourceGroupBinding) Reset() { *x = DatasourceGroupBinding{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[37] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[40] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3932,7 +4183,7 @@ func (x *DatasourceGroupBinding) String() string { func (*DatasourceGroupBinding) ProtoMessage() {} func (x *DatasourceGroupBinding) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[37] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[40] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3945,7 +4196,7 @@ func (x *DatasourceGroupBinding) ProtoReflect() protoreflect.Message { // Deprecated: Use DatasourceGroupBinding.ProtoReflect.Descriptor instead. func (*DatasourceGroupBinding) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{37} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{40} } func (x *DatasourceGroupBinding) GetId() string { @@ -4020,7 +4271,7 @@ type DatasourceVerifiedDomain struct { func (x *DatasourceVerifiedDomain) Reset() { *x = DatasourceVerifiedDomain{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[38] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[41] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4032,7 +4283,7 @@ func (x *DatasourceVerifiedDomain) String() string { func (*DatasourceVerifiedDomain) ProtoMessage() {} func (x *DatasourceVerifiedDomain) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[38] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[41] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4045,7 +4296,7 @@ func (x *DatasourceVerifiedDomain) ProtoReflect() protoreflect.Message { // Deprecated: Use DatasourceVerifiedDomain.ProtoReflect.Descriptor instead. func (*DatasourceVerifiedDomain) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{38} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{41} } func (x *DatasourceVerifiedDomain) GetId() string { @@ -4115,7 +4366,7 @@ type DatasourceDirectoryTeam struct { func (x *DatasourceDirectoryTeam) Reset() { *x = DatasourceDirectoryTeam{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[39] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[42] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4127,7 +4378,7 @@ func (x *DatasourceDirectoryTeam) String() string { func (*DatasourceDirectoryTeam) ProtoMessage() {} func (x *DatasourceDirectoryTeam) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[39] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[42] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4140,7 +4391,7 @@ func (x *DatasourceDirectoryTeam) ProtoReflect() protoreflect.Message { // Deprecated: Use DatasourceDirectoryTeam.ProtoReflect.Descriptor instead. func (*DatasourceDirectoryTeam) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{39} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{42} } func (x *DatasourceDirectoryTeam) GetId() string { @@ -4172,7 +4423,7 @@ type BeginDatasourceAccountLinkRequest struct { func (x *BeginDatasourceAccountLinkRequest) Reset() { *x = BeginDatasourceAccountLinkRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[40] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[43] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4184,7 +4435,7 @@ func (x *BeginDatasourceAccountLinkRequest) String() string { func (*BeginDatasourceAccountLinkRequest) ProtoMessage() {} func (x *BeginDatasourceAccountLinkRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[40] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[43] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4197,7 +4448,7 @@ func (x *BeginDatasourceAccountLinkRequest) ProtoReflect() protoreflect.Message // Deprecated: Use BeginDatasourceAccountLinkRequest.ProtoReflect.Descriptor instead. func (*BeginDatasourceAccountLinkRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{40} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{43} } func (x *BeginDatasourceAccountLinkRequest) GetOrgId() string { @@ -4242,7 +4493,7 @@ type BeginDatasourceAccountLinkResponse struct { func (x *BeginDatasourceAccountLinkResponse) Reset() { *x = BeginDatasourceAccountLinkResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[41] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[44] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4254,7 +4505,7 @@ func (x *BeginDatasourceAccountLinkResponse) String() string { func (*BeginDatasourceAccountLinkResponse) ProtoMessage() {} func (x *BeginDatasourceAccountLinkResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[41] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[44] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4267,7 +4518,7 @@ func (x *BeginDatasourceAccountLinkResponse) ProtoReflect() protoreflect.Message // Deprecated: Use BeginDatasourceAccountLinkResponse.ProtoReflect.Descriptor instead. func (*BeginDatasourceAccountLinkResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{41} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{44} } func (x *BeginDatasourceAccountLinkResponse) GetAuthorizeUrl() string { @@ -4302,7 +4553,7 @@ type CompleteDatasourceAccountLinkRequest struct { func (x *CompleteDatasourceAccountLinkRequest) Reset() { *x = CompleteDatasourceAccountLinkRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[42] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[45] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4314,7 +4565,7 @@ func (x *CompleteDatasourceAccountLinkRequest) String() string { func (*CompleteDatasourceAccountLinkRequest) ProtoMessage() {} func (x *CompleteDatasourceAccountLinkRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[42] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[45] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4327,7 +4578,7 @@ func (x *CompleteDatasourceAccountLinkRequest) ProtoReflect() protoreflect.Messa // Deprecated: Use CompleteDatasourceAccountLinkRequest.ProtoReflect.Descriptor instead. func (*CompleteDatasourceAccountLinkRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{42} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{45} } func (x *CompleteDatasourceAccountLinkRequest) GetOrgId() string { @@ -4360,7 +4611,7 @@ type CompleteDatasourceAccountLinkResponse struct { func (x *CompleteDatasourceAccountLinkResponse) Reset() { *x = CompleteDatasourceAccountLinkResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[43] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[46] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4372,7 +4623,7 @@ func (x *CompleteDatasourceAccountLinkResponse) String() string { func (*CompleteDatasourceAccountLinkResponse) ProtoMessage() {} func (x *CompleteDatasourceAccountLinkResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[43] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[46] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4385,7 +4636,7 @@ func (x *CompleteDatasourceAccountLinkResponse) ProtoReflect() protoreflect.Mess // Deprecated: Use CompleteDatasourceAccountLinkResponse.ProtoReflect.Descriptor instead. func (*CompleteDatasourceAccountLinkResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{43} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{46} } func (x *CompleteDatasourceAccountLinkResponse) GetLink() *DatasourceAccountLink { @@ -4404,7 +4655,7 @@ type ListMyDatasourceAccountLinksRequest struct { func (x *ListMyDatasourceAccountLinksRequest) Reset() { *x = ListMyDatasourceAccountLinksRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[44] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[47] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4416,7 +4667,7 @@ func (x *ListMyDatasourceAccountLinksRequest) String() string { func (*ListMyDatasourceAccountLinksRequest) ProtoMessage() {} func (x *ListMyDatasourceAccountLinksRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[44] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[47] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4429,7 +4680,7 @@ func (x *ListMyDatasourceAccountLinksRequest) ProtoReflect() protoreflect.Messag // Deprecated: Use ListMyDatasourceAccountLinksRequest.ProtoReflect.Descriptor instead. func (*ListMyDatasourceAccountLinksRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{44} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{47} } func (x *ListMyDatasourceAccountLinksRequest) GetOrgId() string { @@ -4448,7 +4699,7 @@ type ListMyDatasourceAccountLinksResponse struct { func (x *ListMyDatasourceAccountLinksResponse) Reset() { *x = ListMyDatasourceAccountLinksResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[45] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[48] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4460,7 +4711,7 @@ func (x *ListMyDatasourceAccountLinksResponse) String() string { func (*ListMyDatasourceAccountLinksResponse) ProtoMessage() {} func (x *ListMyDatasourceAccountLinksResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[45] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[48] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4473,7 +4724,7 @@ func (x *ListMyDatasourceAccountLinksResponse) ProtoReflect() protoreflect.Messa // Deprecated: Use ListMyDatasourceAccountLinksResponse.ProtoReflect.Descriptor instead. func (*ListMyDatasourceAccountLinksResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{45} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{48} } func (x *ListMyDatasourceAccountLinksResponse) GetLinks() []*DatasourceAccountLink { @@ -4493,7 +4744,7 @@ type DeleteDatasourceAccountLinkRequest struct { func (x *DeleteDatasourceAccountLinkRequest) Reset() { *x = DeleteDatasourceAccountLinkRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[46] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[49] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4505,7 +4756,7 @@ func (x *DeleteDatasourceAccountLinkRequest) String() string { func (*DeleteDatasourceAccountLinkRequest) ProtoMessage() {} func (x *DeleteDatasourceAccountLinkRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[46] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[49] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4518,7 +4769,7 @@ func (x *DeleteDatasourceAccountLinkRequest) ProtoReflect() protoreflect.Message // Deprecated: Use DeleteDatasourceAccountLinkRequest.ProtoReflect.Descriptor instead. func (*DeleteDatasourceAccountLinkRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{46} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{49} } func (x *DeleteDatasourceAccountLinkRequest) GetOrgId() string { @@ -4543,7 +4794,7 @@ type DeleteDatasourceAccountLinkResponse struct { func (x *DeleteDatasourceAccountLinkResponse) Reset() { *x = DeleteDatasourceAccountLinkResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[47] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[50] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4555,7 +4806,7 @@ func (x *DeleteDatasourceAccountLinkResponse) String() string { func (*DeleteDatasourceAccountLinkResponse) ProtoMessage() {} func (x *DeleteDatasourceAccountLinkResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[47] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[50] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4568,7 +4819,7 @@ func (x *DeleteDatasourceAccountLinkResponse) ProtoReflect() protoreflect.Messag // Deprecated: Use DeleteDatasourceAccountLinkResponse.ProtoReflect.Descriptor instead. func (*DeleteDatasourceAccountLinkResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{47} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{50} } type GetDatasourceDirectoryRequest struct { @@ -4580,7 +4831,7 @@ type GetDatasourceDirectoryRequest struct { func (x *GetDatasourceDirectoryRequest) Reset() { *x = GetDatasourceDirectoryRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[48] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[51] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4592,7 +4843,7 @@ func (x *GetDatasourceDirectoryRequest) String() string { func (*GetDatasourceDirectoryRequest) ProtoMessage() {} func (x *GetDatasourceDirectoryRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[48] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[51] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4605,7 +4856,7 @@ func (x *GetDatasourceDirectoryRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use GetDatasourceDirectoryRequest.ProtoReflect.Descriptor instead. func (*GetDatasourceDirectoryRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{48} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{51} } func (x *GetDatasourceDirectoryRequest) GetOrgId() string { @@ -4628,7 +4879,7 @@ type GetDatasourceDirectoryResponse struct { func (x *GetDatasourceDirectoryResponse) Reset() { *x = GetDatasourceDirectoryResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[49] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[52] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4640,7 +4891,7 @@ func (x *GetDatasourceDirectoryResponse) String() string { func (*GetDatasourceDirectoryResponse) ProtoMessage() {} func (x *GetDatasourceDirectoryResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[49] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[52] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4653,7 +4904,7 @@ func (x *GetDatasourceDirectoryResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use GetDatasourceDirectoryResponse.ProtoReflect.Descriptor instead. func (*GetDatasourceDirectoryResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{49} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{52} } func (x *GetDatasourceDirectoryResponse) GetLinks() []*DatasourceAccountLink { @@ -4696,7 +4947,7 @@ type BindDatasourceGroupRequest struct { func (x *BindDatasourceGroupRequest) Reset() { *x = BindDatasourceGroupRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[50] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[53] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4708,7 +4959,7 @@ func (x *BindDatasourceGroupRequest) String() string { func (*BindDatasourceGroupRequest) ProtoMessage() {} func (x *BindDatasourceGroupRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[50] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[53] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4721,7 +4972,7 @@ func (x *BindDatasourceGroupRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use BindDatasourceGroupRequest.ProtoReflect.Descriptor instead. func (*BindDatasourceGroupRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{50} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{53} } func (x *BindDatasourceGroupRequest) GetOrgId() string { @@ -4761,7 +5012,7 @@ type BindDatasourceGroupResponse struct { func (x *BindDatasourceGroupResponse) Reset() { *x = BindDatasourceGroupResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[51] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[54] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4773,7 +5024,7 @@ func (x *BindDatasourceGroupResponse) String() string { func (*BindDatasourceGroupResponse) ProtoMessage() {} func (x *BindDatasourceGroupResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[51] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[54] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4786,7 +5037,7 @@ func (x *BindDatasourceGroupResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use BindDatasourceGroupResponse.ProtoReflect.Descriptor instead. func (*BindDatasourceGroupResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{51} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{54} } func (x *BindDatasourceGroupResponse) GetBinding() *DatasourceGroupBinding { @@ -4806,7 +5057,7 @@ type UnbindDatasourceGroupRequest struct { func (x *UnbindDatasourceGroupRequest) Reset() { *x = UnbindDatasourceGroupRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[52] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[55] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4818,7 +5069,7 @@ func (x *UnbindDatasourceGroupRequest) String() string { func (*UnbindDatasourceGroupRequest) ProtoMessage() {} func (x *UnbindDatasourceGroupRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[52] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[55] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4831,7 +5082,7 @@ func (x *UnbindDatasourceGroupRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use UnbindDatasourceGroupRequest.ProtoReflect.Descriptor instead. func (*UnbindDatasourceGroupRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{52} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{55} } func (x *UnbindDatasourceGroupRequest) GetOrgId() string { @@ -4856,7 +5107,7 @@ type UnbindDatasourceGroupResponse struct { func (x *UnbindDatasourceGroupResponse) Reset() { *x = UnbindDatasourceGroupResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[53] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[56] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4868,7 +5119,7 @@ func (x *UnbindDatasourceGroupResponse) String() string { func (*UnbindDatasourceGroupResponse) ProtoMessage() {} func (x *UnbindDatasourceGroupResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[53] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[56] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4881,7 +5132,7 @@ func (x *UnbindDatasourceGroupResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use UnbindDatasourceGroupResponse.ProtoReflect.Descriptor instead. func (*UnbindDatasourceGroupResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{53} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{56} } type ClaimDatasourceDomainRequest struct { @@ -4894,7 +5145,7 @@ type ClaimDatasourceDomainRequest struct { func (x *ClaimDatasourceDomainRequest) Reset() { *x = ClaimDatasourceDomainRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[54] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[57] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4906,7 +5157,7 @@ func (x *ClaimDatasourceDomainRequest) String() string { func (*ClaimDatasourceDomainRequest) ProtoMessage() {} func (x *ClaimDatasourceDomainRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[54] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[57] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4919,7 +5170,7 @@ func (x *ClaimDatasourceDomainRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use ClaimDatasourceDomainRequest.ProtoReflect.Descriptor instead. func (*ClaimDatasourceDomainRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{54} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{57} } func (x *ClaimDatasourceDomainRequest) GetOrgId() string { @@ -4945,7 +5196,7 @@ type ClaimDatasourceDomainResponse struct { func (x *ClaimDatasourceDomainResponse) Reset() { *x = ClaimDatasourceDomainResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[55] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[58] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -4957,7 +5208,7 @@ func (x *ClaimDatasourceDomainResponse) String() string { func (*ClaimDatasourceDomainResponse) ProtoMessage() {} func (x *ClaimDatasourceDomainResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[55] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[58] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -4970,7 +5221,7 @@ func (x *ClaimDatasourceDomainResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ClaimDatasourceDomainResponse.ProtoReflect.Descriptor instead. func (*ClaimDatasourceDomainResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{55} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{58} } func (x *ClaimDatasourceDomainResponse) GetDomain() *DatasourceVerifiedDomain { @@ -4990,7 +5241,7 @@ type VerifyDatasourceDomainRequest struct { func (x *VerifyDatasourceDomainRequest) Reset() { *x = VerifyDatasourceDomainRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[56] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[59] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5002,7 +5253,7 @@ func (x *VerifyDatasourceDomainRequest) String() string { func (*VerifyDatasourceDomainRequest) ProtoMessage() {} func (x *VerifyDatasourceDomainRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[56] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[59] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5015,7 +5266,7 @@ func (x *VerifyDatasourceDomainRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use VerifyDatasourceDomainRequest.ProtoReflect.Descriptor instead. func (*VerifyDatasourceDomainRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{56} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{59} } func (x *VerifyDatasourceDomainRequest) GetOrgId() string { @@ -5041,7 +5292,7 @@ type VerifyDatasourceDomainResponse struct { func (x *VerifyDatasourceDomainResponse) Reset() { *x = VerifyDatasourceDomainResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[57] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[60] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5053,7 +5304,7 @@ func (x *VerifyDatasourceDomainResponse) String() string { func (*VerifyDatasourceDomainResponse) ProtoMessage() {} func (x *VerifyDatasourceDomainResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[57] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[60] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5066,7 +5317,7 @@ func (x *VerifyDatasourceDomainResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use VerifyDatasourceDomainResponse.ProtoReflect.Descriptor instead. func (*VerifyDatasourceDomainResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{57} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{60} } func (x *VerifyDatasourceDomainResponse) GetDomain() *DatasourceVerifiedDomain { @@ -5086,7 +5337,7 @@ type DeleteDatasourceDomainRequest struct { func (x *DeleteDatasourceDomainRequest) Reset() { *x = DeleteDatasourceDomainRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[58] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[61] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5098,7 +5349,7 @@ func (x *DeleteDatasourceDomainRequest) String() string { func (*DeleteDatasourceDomainRequest) ProtoMessage() {} func (x *DeleteDatasourceDomainRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[58] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[61] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5111,7 +5362,7 @@ func (x *DeleteDatasourceDomainRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use DeleteDatasourceDomainRequest.ProtoReflect.Descriptor instead. func (*DeleteDatasourceDomainRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{58} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{61} } func (x *DeleteDatasourceDomainRequest) GetOrgId() string { @@ -5136,7 +5387,7 @@ type DeleteDatasourceDomainResponse struct { func (x *DeleteDatasourceDomainResponse) Reset() { *x = DeleteDatasourceDomainResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[59] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[62] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5148,7 +5399,7 @@ func (x *DeleteDatasourceDomainResponse) String() string { func (*DeleteDatasourceDomainResponse) ProtoMessage() {} func (x *DeleteDatasourceDomainResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[59] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[62] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5161,7 +5412,7 @@ func (x *DeleteDatasourceDomainResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use DeleteDatasourceDomainResponse.ProtoReflect.Descriptor instead. func (*DeleteDatasourceDomainResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{59} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{62} } // SourceDelegation records that a person, by connecting a source, delegated @@ -5191,7 +5442,7 @@ type SourceDelegation struct { func (x *SourceDelegation) Reset() { *x = SourceDelegation{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[60] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[63] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5203,7 +5454,7 @@ func (x *SourceDelegation) String() string { func (*SourceDelegation) ProtoMessage() {} func (x *SourceDelegation) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[60] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[63] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5216,7 +5467,7 @@ func (x *SourceDelegation) ProtoReflect() protoreflect.Message { // Deprecated: Use SourceDelegation.ProtoReflect.Descriptor instead. func (*SourceDelegation) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{60} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{63} } func (x *SourceDelegation) GetId() string { @@ -5295,7 +5546,7 @@ type ListSourceDelegationsRequest struct { func (x *ListSourceDelegationsRequest) Reset() { *x = ListSourceDelegationsRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[61] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[64] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5307,7 +5558,7 @@ func (x *ListSourceDelegationsRequest) String() string { func (*ListSourceDelegationsRequest) ProtoMessage() {} func (x *ListSourceDelegationsRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[61] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[64] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5320,7 +5571,7 @@ func (x *ListSourceDelegationsRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use ListSourceDelegationsRequest.ProtoReflect.Descriptor instead. func (*ListSourceDelegationsRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{61} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{64} } func (x *ListSourceDelegationsRequest) GetOrgId() string { @@ -5354,7 +5605,7 @@ type ListSourceDelegationsResponse struct { func (x *ListSourceDelegationsResponse) Reset() { *x = ListSourceDelegationsResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[62] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[65] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5366,7 +5617,7 @@ func (x *ListSourceDelegationsResponse) String() string { func (*ListSourceDelegationsResponse) ProtoMessage() {} func (x *ListSourceDelegationsResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[62] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[65] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5379,7 +5630,7 @@ func (x *ListSourceDelegationsResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ListSourceDelegationsResponse.ProtoReflect.Descriptor instead. func (*ListSourceDelegationsResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{62} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{65} } func (x *ListSourceDelegationsResponse) GetDelegations() []*SourceDelegation { @@ -5399,7 +5650,7 @@ type RevokeSourceDelegationRequest struct { func (x *RevokeSourceDelegationRequest) Reset() { *x = RevokeSourceDelegationRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[63] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[66] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5411,7 +5662,7 @@ func (x *RevokeSourceDelegationRequest) String() string { func (*RevokeSourceDelegationRequest) ProtoMessage() {} func (x *RevokeSourceDelegationRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[63] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[66] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5424,7 +5675,7 @@ func (x *RevokeSourceDelegationRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use RevokeSourceDelegationRequest.ProtoReflect.Descriptor instead. func (*RevokeSourceDelegationRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{63} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{66} } func (x *RevokeSourceDelegationRequest) GetOrgId() string { @@ -5450,7 +5701,7 @@ type RevokeSourceDelegationResponse struct { func (x *RevokeSourceDelegationResponse) Reset() { *x = RevokeSourceDelegationResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[64] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[67] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5462,7 +5713,7 @@ func (x *RevokeSourceDelegationResponse) String() string { func (*RevokeSourceDelegationResponse) ProtoMessage() {} func (x *RevokeSourceDelegationResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[64] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[67] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5475,7 +5726,7 @@ func (x *RevokeSourceDelegationResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use RevokeSourceDelegationResponse.ProtoReflect.Descriptor instead. func (*RevokeSourceDelegationResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{64} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{67} } func (x *RevokeSourceDelegationResponse) GetDelegation() *SourceDelegation { @@ -5533,7 +5784,7 @@ type TriggerIdentity struct { func (x *TriggerIdentity) Reset() { *x = TriggerIdentity{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[65] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[68] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5545,7 +5796,7 @@ func (x *TriggerIdentity) String() string { func (*TriggerIdentity) ProtoMessage() {} func (x *TriggerIdentity) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[65] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[68] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5558,7 +5809,7 @@ func (x *TriggerIdentity) ProtoReflect() protoreflect.Message { // Deprecated: Use TriggerIdentity.ProtoReflect.Descriptor instead. func (*TriggerIdentity) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{65} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{68} } func (x *TriggerIdentity) GetSource() string { @@ -5610,7 +5861,7 @@ type DeclaredTriggerSchedule struct { func (x *DeclaredTriggerSchedule) Reset() { *x = DeclaredTriggerSchedule{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[66] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[69] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5622,7 +5873,7 @@ func (x *DeclaredTriggerSchedule) String() string { func (*DeclaredTriggerSchedule) ProtoMessage() {} func (x *DeclaredTriggerSchedule) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[66] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[69] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5635,7 +5886,7 @@ func (x *DeclaredTriggerSchedule) ProtoReflect() protoreflect.Message { // Deprecated: Use DeclaredTriggerSchedule.ProtoReflect.Descriptor instead. func (*DeclaredTriggerSchedule) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{66} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{69} } func (x *DeclaredTriggerSchedule) GetCron() string { @@ -5720,7 +5971,7 @@ type TriggerDelegationReference struct { func (x *TriggerDelegationReference) Reset() { *x = TriggerDelegationReference{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[67] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[70] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5732,7 +5983,7 @@ func (x *TriggerDelegationReference) String() string { func (*TriggerDelegationReference) ProtoMessage() {} func (x *TriggerDelegationReference) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[67] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[70] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5745,7 +5996,7 @@ func (x *TriggerDelegationReference) ProtoReflect() protoreflect.Message { // Deprecated: Use TriggerDelegationReference.ProtoReflect.Descriptor instead. func (*TriggerDelegationReference) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{67} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{70} } func (x *TriggerDelegationReference) GetReference() string { @@ -5857,7 +6108,7 @@ type TriggerChildContext struct { func (x *TriggerChildContext) Reset() { *x = TriggerChildContext{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[68] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[71] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5869,7 +6120,7 @@ func (x *TriggerChildContext) String() string { func (*TriggerChildContext) ProtoMessage() {} func (x *TriggerChildContext) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[68] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[71] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5882,7 +6133,7 @@ func (x *TriggerChildContext) ProtoReflect() protoreflect.Message { // Deprecated: Use TriggerChildContext.ProtoReflect.Descriptor instead. func (*TriggerChildContext) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{68} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{71} } func (x *TriggerChildContext) GetDelegationId() string { @@ -5974,7 +6225,7 @@ type SourceTriggerDeclaration struct { func (x *SourceTriggerDeclaration) Reset() { *x = SourceTriggerDeclaration{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[69] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[72] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -5986,7 +6237,7 @@ func (x *SourceTriggerDeclaration) String() string { func (*SourceTriggerDeclaration) ProtoMessage() {} func (x *SourceTriggerDeclaration) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[69] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[72] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -5999,7 +6250,7 @@ func (x *SourceTriggerDeclaration) ProtoReflect() protoreflect.Message { // Deprecated: Use SourceTriggerDeclaration.ProtoReflect.Descriptor instead. func (*SourceTriggerDeclaration) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{69} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{72} } func (x *SourceTriggerDeclaration) GetRelease() string { @@ -6068,7 +6319,7 @@ type DelegateSourceTriggersRequest struct { func (x *DelegateSourceTriggersRequest) Reset() { *x = DelegateSourceTriggersRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[70] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[73] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6080,7 +6331,7 @@ func (x *DelegateSourceTriggersRequest) String() string { func (*DelegateSourceTriggersRequest) ProtoMessage() {} func (x *DelegateSourceTriggersRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[70] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[73] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6093,7 +6344,7 @@ func (x *DelegateSourceTriggersRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use DelegateSourceTriggersRequest.ProtoReflect.Descriptor instead. func (*DelegateSourceTriggersRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{70} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{73} } func (x *DelegateSourceTriggersRequest) GetOrgId() string { @@ -6122,7 +6373,7 @@ type DelegateSourceTriggersResponse struct { func (x *DelegateSourceTriggersResponse) Reset() { *x = DelegateSourceTriggersResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[71] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[74] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6134,7 +6385,7 @@ func (x *DelegateSourceTriggersResponse) String() string { func (*DelegateSourceTriggersResponse) ProtoMessage() {} func (x *DelegateSourceTriggersResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[71] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[74] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6147,7 +6398,7 @@ func (x *DelegateSourceTriggersResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use DelegateSourceTriggersResponse.ProtoReflect.Descriptor instead. func (*DelegateSourceTriggersResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{71} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{74} } func (x *DelegateSourceTriggersResponse) GetDelegations() []*TriggerDelegationReference { @@ -6167,7 +6418,7 @@ type GetSourceTriggerDeclarationRequest struct { func (x *GetSourceTriggerDeclarationRequest) Reset() { *x = GetSourceTriggerDeclarationRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[72] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[75] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6179,7 +6430,7 @@ func (x *GetSourceTriggerDeclarationRequest) String() string { func (*GetSourceTriggerDeclarationRequest) ProtoMessage() {} func (x *GetSourceTriggerDeclarationRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[72] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[75] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6192,7 +6443,7 @@ func (x *GetSourceTriggerDeclarationRequest) ProtoReflect() protoreflect.Message // Deprecated: Use GetSourceTriggerDeclarationRequest.ProtoReflect.Descriptor instead. func (*GetSourceTriggerDeclarationRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{72} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{75} } func (x *GetSourceTriggerDeclarationRequest) GetOrgId() string { @@ -6224,7 +6475,7 @@ type GetSourceTriggerDeclarationResponse struct { func (x *GetSourceTriggerDeclarationResponse) Reset() { *x = GetSourceTriggerDeclarationResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[73] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[76] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6236,7 +6487,7 @@ func (x *GetSourceTriggerDeclarationResponse) String() string { func (*GetSourceTriggerDeclarationResponse) ProtoMessage() {} func (x *GetSourceTriggerDeclarationResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[73] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[76] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6249,7 +6500,7 @@ func (x *GetSourceTriggerDeclarationResponse) ProtoReflect() protoreflect.Messag // Deprecated: Use GetSourceTriggerDeclarationResponse.ProtoReflect.Descriptor instead. func (*GetSourceTriggerDeclarationResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{73} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{76} } func (x *GetSourceTriggerDeclarationResponse) GetDeclaration() *SourceTriggerDeclaration { @@ -6286,7 +6537,7 @@ type ReconcileSourceRequest struct { func (x *ReconcileSourceRequest) Reset() { *x = ReconcileSourceRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[74] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[77] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6298,7 +6549,7 @@ func (x *ReconcileSourceRequest) String() string { func (*ReconcileSourceRequest) ProtoMessage() {} func (x *ReconcileSourceRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[74] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[77] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6311,7 +6562,7 @@ func (x *ReconcileSourceRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use ReconcileSourceRequest.ProtoReflect.Descriptor instead. func (*ReconcileSourceRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{74} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{77} } func (x *ReconcileSourceRequest) GetOrgId() string { @@ -6351,7 +6602,7 @@ type ReconcileSourceResponse struct { func (x *ReconcileSourceResponse) Reset() { *x = ReconcileSourceResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[75] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[78] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6363,7 +6614,7 @@ func (x *ReconcileSourceResponse) String() string { func (*ReconcileSourceResponse) ProtoMessage() {} func (x *ReconcileSourceResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[75] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[78] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6376,7 +6627,7 @@ func (x *ReconcileSourceResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ReconcileSourceResponse.ProtoReflect.Descriptor instead. func (*ReconcileSourceResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{75} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{78} } func (x *ReconcileSourceResponse) GetEffectId() string { @@ -6409,7 +6660,7 @@ type LookupReconcileSourceRequest struct { func (x *LookupReconcileSourceRequest) Reset() { *x = LookupReconcileSourceRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[76] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[79] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6421,7 +6672,7 @@ func (x *LookupReconcileSourceRequest) String() string { func (*LookupReconcileSourceRequest) ProtoMessage() {} func (x *LookupReconcileSourceRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[76] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[79] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6434,7 +6685,7 @@ func (x *LookupReconcileSourceRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use LookupReconcileSourceRequest.ProtoReflect.Descriptor instead. func (*LookupReconcileSourceRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{76} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{79} } func (x *LookupReconcileSourceRequest) GetEffectId() string { @@ -6465,7 +6716,7 @@ type SourceOperation struct { func (x *SourceOperation) Reset() { *x = SourceOperation{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[77] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[80] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6477,7 +6728,7 @@ func (x *SourceOperation) String() string { func (*SourceOperation) ProtoMessage() {} func (x *SourceOperation) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[77] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[80] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6490,7 +6741,7 @@ func (x *SourceOperation) ProtoReflect() protoreflect.Message { // Deprecated: Use SourceOperation.ProtoReflect.Descriptor instead. func (*SourceOperation) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{77} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{80} } func (x *SourceOperation) GetName() string { @@ -6574,7 +6825,7 @@ type DeclareSourceOperationsRequest struct { func (x *DeclareSourceOperationsRequest) Reset() { *x = DeclareSourceOperationsRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[78] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[81] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6586,7 +6837,7 @@ func (x *DeclareSourceOperationsRequest) String() string { func (*DeclareSourceOperationsRequest) ProtoMessage() {} func (x *DeclareSourceOperationsRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[78] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[81] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6599,7 +6850,7 @@ func (x *DeclareSourceOperationsRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use DeclareSourceOperationsRequest.ProtoReflect.Descriptor instead. func (*DeclareSourceOperationsRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{78} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{81} } func (x *DeclareSourceOperationsRequest) GetOrgId() string { @@ -6632,7 +6883,7 @@ type DeclareSourceOperationsResponse struct { func (x *DeclareSourceOperationsResponse) Reset() { *x = DeclareSourceOperationsResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[79] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[82] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6644,7 +6895,7 @@ func (x *DeclareSourceOperationsResponse) String() string { func (*DeclareSourceOperationsResponse) ProtoMessage() {} func (x *DeclareSourceOperationsResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[79] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[82] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6657,7 +6908,7 @@ func (x *DeclareSourceOperationsResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use DeclareSourceOperationsResponse.ProtoReflect.Descriptor instead. func (*DeclareSourceOperationsResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{79} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{82} } func (x *DeclareSourceOperationsResponse) GetOperations() []*SourceOperation { @@ -6677,7 +6928,7 @@ type ListSourceOperationsRequest struct { func (x *ListSourceOperationsRequest) Reset() { *x = ListSourceOperationsRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[80] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[83] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6689,7 +6940,7 @@ func (x *ListSourceOperationsRequest) String() string { func (*ListSourceOperationsRequest) ProtoMessage() {} func (x *ListSourceOperationsRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[80] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[83] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6702,7 +6953,7 @@ func (x *ListSourceOperationsRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use ListSourceOperationsRequest.ProtoReflect.Descriptor instead. func (*ListSourceOperationsRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{80} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{83} } func (x *ListSourceOperationsRequest) GetOrgId() string { @@ -6728,7 +6979,7 @@ type ListSourceOperationsResponse struct { func (x *ListSourceOperationsResponse) Reset() { *x = ListSourceOperationsResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[81] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[84] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6740,7 +6991,7 @@ func (x *ListSourceOperationsResponse) String() string { func (*ListSourceOperationsResponse) ProtoMessage() {} func (x *ListSourceOperationsResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[81] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[84] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6753,7 +7004,7 @@ func (x *ListSourceOperationsResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ListSourceOperationsResponse.ProtoReflect.Descriptor instead. func (*ListSourceOperationsResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{81} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{84} } func (x *ListSourceOperationsResponse) GetOperations() []*SourceOperation { @@ -6778,7 +7029,7 @@ type InvokeSourceOperationRequest struct { func (x *InvokeSourceOperationRequest) Reset() { *x = InvokeSourceOperationRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[82] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[85] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6790,7 +7041,7 @@ func (x *InvokeSourceOperationRequest) String() string { func (*InvokeSourceOperationRequest) ProtoMessage() {} func (x *InvokeSourceOperationRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[82] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[85] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6803,7 +7054,7 @@ func (x *InvokeSourceOperationRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use InvokeSourceOperationRequest.ProtoReflect.Descriptor instead. func (*InvokeSourceOperationRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{82} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{85} } func (x *InvokeSourceOperationRequest) GetOrgId() string { @@ -6855,7 +7106,7 @@ type SourceOperationReceipt struct { func (x *SourceOperationReceipt) Reset() { *x = SourceOperationReceipt{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[83] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[86] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6867,7 +7118,7 @@ func (x *SourceOperationReceipt) String() string { func (*SourceOperationReceipt) ProtoMessage() {} func (x *SourceOperationReceipt) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[83] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[86] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6880,7 +7131,7 @@ func (x *SourceOperationReceipt) ProtoReflect() protoreflect.Message { // Deprecated: Use SourceOperationReceipt.ProtoReflect.Descriptor instead. func (*SourceOperationReceipt) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{83} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{86} } func (x *SourceOperationReceipt) GetEffectId() string { @@ -6928,7 +7179,7 @@ type InvokeSourceOperationResponse struct { func (x *InvokeSourceOperationResponse) Reset() { *x = InvokeSourceOperationResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[84] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[87] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6940,7 +7191,7 @@ func (x *InvokeSourceOperationResponse) String() string { func (*InvokeSourceOperationResponse) ProtoMessage() {} func (x *InvokeSourceOperationResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[84] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[87] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -6953,7 +7204,7 @@ func (x *InvokeSourceOperationResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use InvokeSourceOperationResponse.ProtoReflect.Descriptor instead. func (*InvokeSourceOperationResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{84} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{87} } func (x *InvokeSourceOperationResponse) GetOutputJson() string { @@ -6981,7 +7232,7 @@ type LookupInvokeSourceOperationRequest struct { func (x *LookupInvokeSourceOperationRequest) Reset() { *x = LookupInvokeSourceOperationRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[85] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[88] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -6993,7 +7244,7 @@ func (x *LookupInvokeSourceOperationRequest) String() string { func (*LookupInvokeSourceOperationRequest) ProtoMessage() {} func (x *LookupInvokeSourceOperationRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[85] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[88] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -7006,7 +7257,7 @@ func (x *LookupInvokeSourceOperationRequest) ProtoReflect() protoreflect.Message // Deprecated: Use LookupInvokeSourceOperationRequest.ProtoReflect.Descriptor instead. func (*LookupInvokeSourceOperationRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{85} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{88} } func (x *LookupInvokeSourceOperationRequest) GetEffectId() string { @@ -7028,7 +7279,7 @@ type PruneSourceOperationReceiptsRequest struct { func (x *PruneSourceOperationReceiptsRequest) Reset() { *x = PruneSourceOperationReceiptsRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[86] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[89] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -7040,7 +7291,7 @@ func (x *PruneSourceOperationReceiptsRequest) String() string { func (*PruneSourceOperationReceiptsRequest) ProtoMessage() {} func (x *PruneSourceOperationReceiptsRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[86] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[89] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -7053,7 +7304,7 @@ func (x *PruneSourceOperationReceiptsRequest) ProtoReflect() protoreflect.Messag // Deprecated: Use PruneSourceOperationReceiptsRequest.ProtoReflect.Descriptor instead. func (*PruneSourceOperationReceiptsRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{86} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{89} } func (x *PruneSourceOperationReceiptsRequest) GetOrgId() string { @@ -7088,7 +7339,7 @@ type PruneSourceOperationReceiptsResponse struct { func (x *PruneSourceOperationReceiptsResponse) Reset() { *x = PruneSourceOperationReceiptsResponse{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[87] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[90] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -7100,7 +7351,7 @@ func (x *PruneSourceOperationReceiptsResponse) String() string { func (*PruneSourceOperationReceiptsResponse) ProtoMessage() {} func (x *PruneSourceOperationReceiptsResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[87] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[90] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -7113,7 +7364,7 @@ func (x *PruneSourceOperationReceiptsResponse) ProtoReflect() protoreflect.Messa // Deprecated: Use PruneSourceOperationReceiptsResponse.ProtoReflect.Descriptor instead. func (*PruneSourceOperationReceiptsResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{87} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{90} } func (x *PruneSourceOperationReceiptsResponse) GetEffectId() string { @@ -7146,7 +7397,7 @@ type LookupPruneSourceOperationReceiptsRequest struct { func (x *LookupPruneSourceOperationReceiptsRequest) Reset() { *x = LookupPruneSourceOperationReceiptsRequest{} - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[88] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[91] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -7158,7 +7409,7 @@ func (x *LookupPruneSourceOperationReceiptsRequest) String() string { func (*LookupPruneSourceOperationReceiptsRequest) ProtoMessage() {} func (x *LookupPruneSourceOperationReceiptsRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_datasource_proto_msgTypes[88] + mi := &file_saas_accounts_v1_datasource_proto_msgTypes[91] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -7171,7 +7422,7 @@ func (x *LookupPruneSourceOperationReceiptsRequest) ProtoReflect() protoreflect. // Deprecated: Use LookupPruneSourceOperationReceiptsRequest.ProtoReflect.Descriptor instead. func (*LookupPruneSourceOperationReceiptsRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{88} + return file_saas_accounts_v1_datasource_proto_rawDescGZIP(), []int{91} } func (x *LookupPruneSourceOperationReceiptsRequest) GetEffectId() string { @@ -7287,7 +7538,24 @@ const file_saas_accounts_v1_datasource_proto_rawDesc = "" + "\x11AddSourceResponse\x12<\n" + "\n" + "datasource\x18\x01 \x01(\v2\x1c.saas.accounts.v1.DatasourceR\n" + - "datasource\"|\n" + + "datasource\"\xbe\x02\n" + + "\x13UpdateSourceRequest\x12\x1f\n" + + "\x06org_id\x18\x01 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x05orgId\x12\x18\n" + + "\x02id\x18\x02 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x02id\x12 \n" + + "\x06branch\x18\x03 \x01(\tB\b\xbaH\x05r\x03\x18\xff\x01R\x06branch\x12'\n" + + "\x05paths\x18\x04 \x03(\tB\x11\xbaH\x0e\x92\x01\v\x10@\"\ar\x05\x10\x01\x18\x80\x04R\x05paths\x12Y\n" + + "\x0ffile_extensions\x18\x05 \x03(\tB0\xbaH-\x92\x01*\x10 \"&r$\x10\x02\x18!2\x1e^\\.[A-Za-z0-9][A-Za-z0-9._-]*$R\x0efileExtensions\x12F\n" + + "\bexpected\x18\x06 \x01(\v2\".saas.accounts.v1.SourceFetchScopeB\x06\xbaH\x03\xc8\x01\x01R\bexpected\"\x98\x01\n" + + "\x10SourceFetchScope\x12 \n" + + "\x06branch\x18\x01 \x01(\tB\b\xbaH\x05r\x03\x18\xff\x01R\x06branch\x12'\n" + + "\x05paths\x18\x02 \x03(\tB\x11\xbaH\x0e\x92\x01\v\x10@\"\ar\x05\x10\x01\x18\x80\x04R\x05paths\x129\n" + + "\x0ffile_extensions\x18\x03 \x03(\tB\x10\xbaH\r\x92\x01\n" + + "\x10 \"\x06r\x04\x10\x01\x18!R\x0efileExtensions\"k\n" + + "\x14UpdateSourceResponse\x12<\n" + + "\n" + + "datasource\x18\x01 \x01(\v2\x1c.saas.accounts.v1.DatasourceR\n" + + "datasource\x12\x15\n" + + "\x06job_id\x18\x02 \x01(\tR\x05jobId\"|\n" + "\x15DatasourceConfigField\x12\x10\n" + "\x03key\x18\x01 \x01(\tR\x03key\x12!\n" + "\fdisplay_name\x18\x02 \x01(\tR\vdisplayName\x12\x12\n" + @@ -7741,12 +8009,13 @@ const file_saas_accounts_v1_datasource_proto_rawDesc = "" + "$SOURCE_SYNC_FAILURE_REASON_TOO_LARGE\x10\x05\x12/\n" + "+SOURCE_SYNC_FAILURE_REASON_HOST_UNAVAILABLE\x10\x06\x12$\n" + " SOURCE_SYNC_FAILURE_REASON_OTHER\x10\a\x12.\n" + - "*SOURCE_SYNC_FAILURE_REASON_DELIVERY_FAILED\x10\b*\x9c\x01\n" + + "*SOURCE_SYNC_FAILURE_REASON_DELIVERY_FAILED\x10\b*\xc2\x01\n" + "\x11SourceSyncTrigger\x12#\n" + "\x1fSOURCE_SYNC_TRIGGER_UNSPECIFIED\x10\x00\x12\x1e\n" + "\x1aSOURCE_SYNC_TRIGGER_MANUAL\x10\x01\x12!\n" + "\x1dSOURCE_SYNC_TRIGGER_SCHEDULED\x10\x02\x12\x1f\n" + - "\x1bSOURCE_SYNC_TRIGGER_WEBHOOK\x10\x03*\x8f\x01\n" + + "\x1bSOURCE_SYNC_TRIGGER_WEBHOOK\x10\x03\x12$\n" + + " SOURCE_SYNC_TRIGGER_RECONFIGURED\x10\x04*\x8f\x01\n" + "\x16DatasourceDomainStatus\x12(\n" + "$DATASOURCE_DOMAIN_STATUS_UNSPECIFIED\x10\x00\x12$\n" + " DATASOURCE_DOMAIN_STATUS_PENDING\x10\x01\x12%\n" + @@ -7759,7 +8028,7 @@ const file_saas_accounts_v1_datasource_proto_rawDesc = "" + "+SOURCE_DELEGATION_REVOCATION_MEMBER_REMOVED\x10\x04\x120\n" + ",SOURCE_DELEGATION_REVOCATION_PERMISSION_LOST\x10\x05\x12.\n" + "*SOURCE_DELEGATION_REVOCATION_USER_INACTIVE\x10\x06\x120\n" + - ",SOURCE_DELEGATION_REVOCATION_BINDING_CHANGED\x10\a2\x898\n" + + ",SOURCE_DELEGATION_REVOCATION_BINDING_CHANGED\x10\a2\xb19\n" + "\x11DatasourceService\x12\xb9\x03\n" + "\x1cPruneSourceOperationReceipts\x125.saas.accounts.v1.PruneSourceOperationReceiptsRequest\x1a6.saas.accounts.v1.PruneSourceOperationReceiptsResponse\"\xa9\x02\xc2\xf3\x18l\b\x02\x10\x03\x1a\x11datasource:invoke\"\x11datasource:invoke*\x0f\n" + "\tsource_id\x10\x04\x18\x030\x01:#\n" + @@ -7785,7 +8054,10 @@ const file_saas_accounts_v1_datasource_proto_rawDesc = "" + "\x1csaas.datasource.source.added\x10\x02@\x01H\x04P\x04X\x03`\x01\x12\x9a\x01\n" + "\tAddSource\x12\".saas.accounts.v1.AddSourceRequest\x1a#.saas.accounts.v1.AddSourceResponse\"D\xc2\xf3\x18@\b\x02\x10\x04*\f\n" + "\x06org_id\x10\x02\x18\x010\x01: \n" + - "\x1csaas.datasource.source.added\x10\x02@\x01H\x04P\x04X\x03`\x01\x12\x8f\x01\n" + + "\x1csaas.datasource.source.added\x10\x02@\x01H\x04P\x04X\x03`\x01\x12\xa5\x01\n" + + "\fUpdateSource\x12%.saas.accounts.v1.UpdateSourceRequest\x1a&.saas.accounts.v1.UpdateSourceResponse\"F\xc2\xf3\x18B\b\x02\x10\x04*\f\n" + + "\x06org_id\x10\x02\x18\x010\x01:\"\n" + + "\x1esaas.datasource.source.updated\x10\x02@\x01H\x04P\x02X\x03`\x01\x12\x8f\x01\n" + "\x14GetDatasourceCatalog\x12-.saas.accounts.v1.GetDatasourceCatalogRequest\x1a..saas.accounts.v1.GetDatasourceCatalogResponse\"\x18\xc2\xf3\x18\x14\b\x02\x10\x010\x01:\x02\x10\x01@\x01H\x03P\x02X\x02`\x01\x12\x82\x01\n" + "\vListSources\x12$.saas.accounts.v1.ListSourcesRequest\x1a%.saas.accounts.v1.ListSourcesResponse\"&\xc2\xf3\x18\"\b\x02\x10\x03*\f\n" + "\x06org_id\x10\x02\x18\x010\x01:\x02\x10\x01@\x01H\x03P\x02X\x03`\x01\x12|\n" + @@ -7870,7 +8142,7 @@ func file_saas_accounts_v1_datasource_proto_rawDescGZIP() []byte { } var file_saas_accounts_v1_datasource_proto_enumTypes = make([]protoimpl.EnumInfo, 14) -var file_saas_accounts_v1_datasource_proto_msgTypes = make([]protoimpl.MessageInfo, 89) +var file_saas_accounts_v1_datasource_proto_msgTypes = make([]protoimpl.MessageInfo, 92) var file_saas_accounts_v1_datasource_proto_goTypes = []any{ (DatasourceProvider)(0), // 0: saas.accounts.v1.DatasourceProvider (DatasourceStatus)(0), // 1: saas.accounts.v1.DatasourceStatus @@ -7896,90 +8168,93 @@ var file_saas_accounts_v1_datasource_proto_goTypes = []any{ (*AddGitHubSourceResponse)(nil), // 21: saas.accounts.v1.AddGitHubSourceResponse (*AddSourceRequest)(nil), // 22: saas.accounts.v1.AddSourceRequest (*AddSourceResponse)(nil), // 23: saas.accounts.v1.AddSourceResponse - (*DatasourceConfigField)(nil), // 24: saas.accounts.v1.DatasourceConfigField - (*DatasourceConnectorBudget)(nil), // 25: saas.accounts.v1.DatasourceConnectorBudget - (*DatasourceProviderDescriptor)(nil), // 26: saas.accounts.v1.DatasourceProviderDescriptor - (*GetDatasourceCatalogRequest)(nil), // 27: saas.accounts.v1.GetDatasourceCatalogRequest - (*GetDatasourceCatalogResponse)(nil), // 28: saas.accounts.v1.GetDatasourceCatalogResponse - (*ListSourcesRequest)(nil), // 29: saas.accounts.v1.ListSourcesRequest - (*ListSourcesResponse)(nil), // 30: saas.accounts.v1.ListSourcesResponse - (*GetSourceRequest)(nil), // 31: saas.accounts.v1.GetSourceRequest - (*GetSourceResponse)(nil), // 32: saas.accounts.v1.GetSourceResponse - (*SyncSourceRequest)(nil), // 33: saas.accounts.v1.SyncSourceRequest - (*SyncSourceResponse)(nil), // 34: saas.accounts.v1.SyncSourceResponse - (*GetSourceSyncRequest)(nil), // 35: saas.accounts.v1.GetSourceSyncRequest - (*SourceSyncDelivery)(nil), // 36: saas.accounts.v1.SourceSyncDelivery - (*SourceSyncChanges)(nil), // 37: saas.accounts.v1.SourceSyncChanges - (*SourceSyncFailure)(nil), // 38: saas.accounts.v1.SourceSyncFailure - (*SourceSyncProgress)(nil), // 39: saas.accounts.v1.SourceSyncProgress - (*GetSourceSyncResponse)(nil), // 40: saas.accounts.v1.GetSourceSyncResponse - (*DeleteSourceRequest)(nil), // 41: saas.accounts.v1.DeleteSourceRequest - (*DeleteSourceResponse)(nil), // 42: saas.accounts.v1.DeleteSourceResponse - (*GitHubAppRepository)(nil), // 43: saas.accounts.v1.GitHubAppRepository - (*BeginGitHubAppSetupRequest)(nil), // 44: saas.accounts.v1.BeginGitHubAppSetupRequest - (*BeginGitHubAppSetupResponse)(nil), // 45: saas.accounts.v1.BeginGitHubAppSetupResponse - (*CompleteGitHubAppSetupRequest)(nil), // 46: saas.accounts.v1.CompleteGitHubAppSetupRequest - (*CompleteGitHubAppSetupResponse)(nil), // 47: saas.accounts.v1.CompleteGitHubAppSetupResponse - (*MigrateGitHubSourceToAppRequest)(nil), // 48: saas.accounts.v1.MigrateGitHubSourceToAppRequest - (*MigrateGitHubSourceToAppResponse)(nil), // 49: saas.accounts.v1.MigrateGitHubSourceToAppResponse - (*DatasourceAccountLink)(nil), // 50: saas.accounts.v1.DatasourceAccountLink - (*DatasourceGroupBinding)(nil), // 51: saas.accounts.v1.DatasourceGroupBinding - (*DatasourceVerifiedDomain)(nil), // 52: saas.accounts.v1.DatasourceVerifiedDomain - (*DatasourceDirectoryTeam)(nil), // 53: saas.accounts.v1.DatasourceDirectoryTeam - (*BeginDatasourceAccountLinkRequest)(nil), // 54: saas.accounts.v1.BeginDatasourceAccountLinkRequest - (*BeginDatasourceAccountLinkResponse)(nil), // 55: saas.accounts.v1.BeginDatasourceAccountLinkResponse - (*CompleteDatasourceAccountLinkRequest)(nil), // 56: saas.accounts.v1.CompleteDatasourceAccountLinkRequest - (*CompleteDatasourceAccountLinkResponse)(nil), // 57: saas.accounts.v1.CompleteDatasourceAccountLinkResponse - (*ListMyDatasourceAccountLinksRequest)(nil), // 58: saas.accounts.v1.ListMyDatasourceAccountLinksRequest - (*ListMyDatasourceAccountLinksResponse)(nil), // 59: saas.accounts.v1.ListMyDatasourceAccountLinksResponse - (*DeleteDatasourceAccountLinkRequest)(nil), // 60: saas.accounts.v1.DeleteDatasourceAccountLinkRequest - (*DeleteDatasourceAccountLinkResponse)(nil), // 61: saas.accounts.v1.DeleteDatasourceAccountLinkResponse - (*GetDatasourceDirectoryRequest)(nil), // 62: saas.accounts.v1.GetDatasourceDirectoryRequest - (*GetDatasourceDirectoryResponse)(nil), // 63: saas.accounts.v1.GetDatasourceDirectoryResponse - (*BindDatasourceGroupRequest)(nil), // 64: saas.accounts.v1.BindDatasourceGroupRequest - (*BindDatasourceGroupResponse)(nil), // 65: saas.accounts.v1.BindDatasourceGroupResponse - (*UnbindDatasourceGroupRequest)(nil), // 66: saas.accounts.v1.UnbindDatasourceGroupRequest - (*UnbindDatasourceGroupResponse)(nil), // 67: saas.accounts.v1.UnbindDatasourceGroupResponse - (*ClaimDatasourceDomainRequest)(nil), // 68: saas.accounts.v1.ClaimDatasourceDomainRequest - (*ClaimDatasourceDomainResponse)(nil), // 69: saas.accounts.v1.ClaimDatasourceDomainResponse - (*VerifyDatasourceDomainRequest)(nil), // 70: saas.accounts.v1.VerifyDatasourceDomainRequest - (*VerifyDatasourceDomainResponse)(nil), // 71: saas.accounts.v1.VerifyDatasourceDomainResponse - (*DeleteDatasourceDomainRequest)(nil), // 72: saas.accounts.v1.DeleteDatasourceDomainRequest - (*DeleteDatasourceDomainResponse)(nil), // 73: saas.accounts.v1.DeleteDatasourceDomainResponse - (*SourceDelegation)(nil), // 74: saas.accounts.v1.SourceDelegation - (*ListSourceDelegationsRequest)(nil), // 75: saas.accounts.v1.ListSourceDelegationsRequest - (*ListSourceDelegationsResponse)(nil), // 76: saas.accounts.v1.ListSourceDelegationsResponse - (*RevokeSourceDelegationRequest)(nil), // 77: saas.accounts.v1.RevokeSourceDelegationRequest - (*RevokeSourceDelegationResponse)(nil), // 78: saas.accounts.v1.RevokeSourceDelegationResponse - (*TriggerIdentity)(nil), // 79: saas.accounts.v1.TriggerIdentity - (*DeclaredTriggerSchedule)(nil), // 80: saas.accounts.v1.DeclaredTriggerSchedule - (*TriggerDelegationReference)(nil), // 81: saas.accounts.v1.TriggerDelegationReference - (*TriggerChildContext)(nil), // 82: saas.accounts.v1.TriggerChildContext - (*SourceTriggerDeclaration)(nil), // 83: saas.accounts.v1.SourceTriggerDeclaration - (*DelegateSourceTriggersRequest)(nil), // 84: saas.accounts.v1.DelegateSourceTriggersRequest - (*DelegateSourceTriggersResponse)(nil), // 85: saas.accounts.v1.DelegateSourceTriggersResponse - (*GetSourceTriggerDeclarationRequest)(nil), // 86: saas.accounts.v1.GetSourceTriggerDeclarationRequest - (*GetSourceTriggerDeclarationResponse)(nil), // 87: saas.accounts.v1.GetSourceTriggerDeclarationResponse - (*ReconcileSourceRequest)(nil), // 88: saas.accounts.v1.ReconcileSourceRequest - (*ReconcileSourceResponse)(nil), // 89: saas.accounts.v1.ReconcileSourceResponse - (*LookupReconcileSourceRequest)(nil), // 90: saas.accounts.v1.LookupReconcileSourceRequest - (*SourceOperation)(nil), // 91: saas.accounts.v1.SourceOperation - (*DeclareSourceOperationsRequest)(nil), // 92: saas.accounts.v1.DeclareSourceOperationsRequest - (*DeclareSourceOperationsResponse)(nil), // 93: saas.accounts.v1.DeclareSourceOperationsResponse - (*ListSourceOperationsRequest)(nil), // 94: saas.accounts.v1.ListSourceOperationsRequest - (*ListSourceOperationsResponse)(nil), // 95: saas.accounts.v1.ListSourceOperationsResponse - (*InvokeSourceOperationRequest)(nil), // 96: saas.accounts.v1.InvokeSourceOperationRequest - (*SourceOperationReceipt)(nil), // 97: saas.accounts.v1.SourceOperationReceipt - (*InvokeSourceOperationResponse)(nil), // 98: saas.accounts.v1.InvokeSourceOperationResponse - (*LookupInvokeSourceOperationRequest)(nil), // 99: saas.accounts.v1.LookupInvokeSourceOperationRequest - (*PruneSourceOperationReceiptsRequest)(nil), // 100: saas.accounts.v1.PruneSourceOperationReceiptsRequest - (*PruneSourceOperationReceiptsResponse)(nil), // 101: saas.accounts.v1.PruneSourceOperationReceiptsResponse - (*LookupPruneSourceOperationReceiptsRequest)(nil), // 102: saas.accounts.v1.LookupPruneSourceOperationReceiptsRequest - (*timestamppb.Timestamp)(nil), // 103: google.protobuf.Timestamp - (*durationpb.Duration)(nil), // 104: google.protobuf.Duration - (v1.JobState)(0), // 105: saas.jobs.v1.JobState - (*v1.JobExecutionReference)(nil), // 106: saas.jobs.v1.JobExecutionReference - (*structpb.Struct)(nil), // 107: google.protobuf.Struct + (*UpdateSourceRequest)(nil), // 24: saas.accounts.v1.UpdateSourceRequest + (*SourceFetchScope)(nil), // 25: saas.accounts.v1.SourceFetchScope + (*UpdateSourceResponse)(nil), // 26: saas.accounts.v1.UpdateSourceResponse + (*DatasourceConfigField)(nil), // 27: saas.accounts.v1.DatasourceConfigField + (*DatasourceConnectorBudget)(nil), // 28: saas.accounts.v1.DatasourceConnectorBudget + (*DatasourceProviderDescriptor)(nil), // 29: saas.accounts.v1.DatasourceProviderDescriptor + (*GetDatasourceCatalogRequest)(nil), // 30: saas.accounts.v1.GetDatasourceCatalogRequest + (*GetDatasourceCatalogResponse)(nil), // 31: saas.accounts.v1.GetDatasourceCatalogResponse + (*ListSourcesRequest)(nil), // 32: saas.accounts.v1.ListSourcesRequest + (*ListSourcesResponse)(nil), // 33: saas.accounts.v1.ListSourcesResponse + (*GetSourceRequest)(nil), // 34: saas.accounts.v1.GetSourceRequest + (*GetSourceResponse)(nil), // 35: saas.accounts.v1.GetSourceResponse + (*SyncSourceRequest)(nil), // 36: saas.accounts.v1.SyncSourceRequest + (*SyncSourceResponse)(nil), // 37: saas.accounts.v1.SyncSourceResponse + (*GetSourceSyncRequest)(nil), // 38: saas.accounts.v1.GetSourceSyncRequest + (*SourceSyncDelivery)(nil), // 39: saas.accounts.v1.SourceSyncDelivery + (*SourceSyncChanges)(nil), // 40: saas.accounts.v1.SourceSyncChanges + (*SourceSyncFailure)(nil), // 41: saas.accounts.v1.SourceSyncFailure + (*SourceSyncProgress)(nil), // 42: saas.accounts.v1.SourceSyncProgress + (*GetSourceSyncResponse)(nil), // 43: saas.accounts.v1.GetSourceSyncResponse + (*DeleteSourceRequest)(nil), // 44: saas.accounts.v1.DeleteSourceRequest + (*DeleteSourceResponse)(nil), // 45: saas.accounts.v1.DeleteSourceResponse + (*GitHubAppRepository)(nil), // 46: saas.accounts.v1.GitHubAppRepository + (*BeginGitHubAppSetupRequest)(nil), // 47: saas.accounts.v1.BeginGitHubAppSetupRequest + (*BeginGitHubAppSetupResponse)(nil), // 48: saas.accounts.v1.BeginGitHubAppSetupResponse + (*CompleteGitHubAppSetupRequest)(nil), // 49: saas.accounts.v1.CompleteGitHubAppSetupRequest + (*CompleteGitHubAppSetupResponse)(nil), // 50: saas.accounts.v1.CompleteGitHubAppSetupResponse + (*MigrateGitHubSourceToAppRequest)(nil), // 51: saas.accounts.v1.MigrateGitHubSourceToAppRequest + (*MigrateGitHubSourceToAppResponse)(nil), // 52: saas.accounts.v1.MigrateGitHubSourceToAppResponse + (*DatasourceAccountLink)(nil), // 53: saas.accounts.v1.DatasourceAccountLink + (*DatasourceGroupBinding)(nil), // 54: saas.accounts.v1.DatasourceGroupBinding + (*DatasourceVerifiedDomain)(nil), // 55: saas.accounts.v1.DatasourceVerifiedDomain + (*DatasourceDirectoryTeam)(nil), // 56: saas.accounts.v1.DatasourceDirectoryTeam + (*BeginDatasourceAccountLinkRequest)(nil), // 57: saas.accounts.v1.BeginDatasourceAccountLinkRequest + (*BeginDatasourceAccountLinkResponse)(nil), // 58: saas.accounts.v1.BeginDatasourceAccountLinkResponse + (*CompleteDatasourceAccountLinkRequest)(nil), // 59: saas.accounts.v1.CompleteDatasourceAccountLinkRequest + (*CompleteDatasourceAccountLinkResponse)(nil), // 60: saas.accounts.v1.CompleteDatasourceAccountLinkResponse + (*ListMyDatasourceAccountLinksRequest)(nil), // 61: saas.accounts.v1.ListMyDatasourceAccountLinksRequest + (*ListMyDatasourceAccountLinksResponse)(nil), // 62: saas.accounts.v1.ListMyDatasourceAccountLinksResponse + (*DeleteDatasourceAccountLinkRequest)(nil), // 63: saas.accounts.v1.DeleteDatasourceAccountLinkRequest + (*DeleteDatasourceAccountLinkResponse)(nil), // 64: saas.accounts.v1.DeleteDatasourceAccountLinkResponse + (*GetDatasourceDirectoryRequest)(nil), // 65: saas.accounts.v1.GetDatasourceDirectoryRequest + (*GetDatasourceDirectoryResponse)(nil), // 66: saas.accounts.v1.GetDatasourceDirectoryResponse + (*BindDatasourceGroupRequest)(nil), // 67: saas.accounts.v1.BindDatasourceGroupRequest + (*BindDatasourceGroupResponse)(nil), // 68: saas.accounts.v1.BindDatasourceGroupResponse + (*UnbindDatasourceGroupRequest)(nil), // 69: saas.accounts.v1.UnbindDatasourceGroupRequest + (*UnbindDatasourceGroupResponse)(nil), // 70: saas.accounts.v1.UnbindDatasourceGroupResponse + (*ClaimDatasourceDomainRequest)(nil), // 71: saas.accounts.v1.ClaimDatasourceDomainRequest + (*ClaimDatasourceDomainResponse)(nil), // 72: saas.accounts.v1.ClaimDatasourceDomainResponse + (*VerifyDatasourceDomainRequest)(nil), // 73: saas.accounts.v1.VerifyDatasourceDomainRequest + (*VerifyDatasourceDomainResponse)(nil), // 74: saas.accounts.v1.VerifyDatasourceDomainResponse + (*DeleteDatasourceDomainRequest)(nil), // 75: saas.accounts.v1.DeleteDatasourceDomainRequest + (*DeleteDatasourceDomainResponse)(nil), // 76: saas.accounts.v1.DeleteDatasourceDomainResponse + (*SourceDelegation)(nil), // 77: saas.accounts.v1.SourceDelegation + (*ListSourceDelegationsRequest)(nil), // 78: saas.accounts.v1.ListSourceDelegationsRequest + (*ListSourceDelegationsResponse)(nil), // 79: saas.accounts.v1.ListSourceDelegationsResponse + (*RevokeSourceDelegationRequest)(nil), // 80: saas.accounts.v1.RevokeSourceDelegationRequest + (*RevokeSourceDelegationResponse)(nil), // 81: saas.accounts.v1.RevokeSourceDelegationResponse + (*TriggerIdentity)(nil), // 82: saas.accounts.v1.TriggerIdentity + (*DeclaredTriggerSchedule)(nil), // 83: saas.accounts.v1.DeclaredTriggerSchedule + (*TriggerDelegationReference)(nil), // 84: saas.accounts.v1.TriggerDelegationReference + (*TriggerChildContext)(nil), // 85: saas.accounts.v1.TriggerChildContext + (*SourceTriggerDeclaration)(nil), // 86: saas.accounts.v1.SourceTriggerDeclaration + (*DelegateSourceTriggersRequest)(nil), // 87: saas.accounts.v1.DelegateSourceTriggersRequest + (*DelegateSourceTriggersResponse)(nil), // 88: saas.accounts.v1.DelegateSourceTriggersResponse + (*GetSourceTriggerDeclarationRequest)(nil), // 89: saas.accounts.v1.GetSourceTriggerDeclarationRequest + (*GetSourceTriggerDeclarationResponse)(nil), // 90: saas.accounts.v1.GetSourceTriggerDeclarationResponse + (*ReconcileSourceRequest)(nil), // 91: saas.accounts.v1.ReconcileSourceRequest + (*ReconcileSourceResponse)(nil), // 92: saas.accounts.v1.ReconcileSourceResponse + (*LookupReconcileSourceRequest)(nil), // 93: saas.accounts.v1.LookupReconcileSourceRequest + (*SourceOperation)(nil), // 94: saas.accounts.v1.SourceOperation + (*DeclareSourceOperationsRequest)(nil), // 95: saas.accounts.v1.DeclareSourceOperationsRequest + (*DeclareSourceOperationsResponse)(nil), // 96: saas.accounts.v1.DeclareSourceOperationsResponse + (*ListSourceOperationsRequest)(nil), // 97: saas.accounts.v1.ListSourceOperationsRequest + (*ListSourceOperationsResponse)(nil), // 98: saas.accounts.v1.ListSourceOperationsResponse + (*InvokeSourceOperationRequest)(nil), // 99: saas.accounts.v1.InvokeSourceOperationRequest + (*SourceOperationReceipt)(nil), // 100: saas.accounts.v1.SourceOperationReceipt + (*InvokeSourceOperationResponse)(nil), // 101: saas.accounts.v1.InvokeSourceOperationResponse + (*LookupInvokeSourceOperationRequest)(nil), // 102: saas.accounts.v1.LookupInvokeSourceOperationRequest + (*PruneSourceOperationReceiptsRequest)(nil), // 103: saas.accounts.v1.PruneSourceOperationReceiptsRequest + (*PruneSourceOperationReceiptsResponse)(nil), // 104: saas.accounts.v1.PruneSourceOperationReceiptsResponse + (*LookupPruneSourceOperationReceiptsRequest)(nil), // 105: saas.accounts.v1.LookupPruneSourceOperationReceiptsRequest + (*timestamppb.Timestamp)(nil), // 106: google.protobuf.Timestamp + (*durationpb.Duration)(nil), // 107: google.protobuf.Duration + (v1.JobState)(0), // 108: saas.jobs.v1.JobState + (*v1.JobExecutionReference)(nil), // 109: saas.jobs.v1.JobExecutionReference + (*structpb.Struct)(nil), // 110: google.protobuf.Struct } var file_saas_accounts_v1_datasource_proto_depIdxs = []int32{ 12, // 0: saas.accounts.v1.ApiOAuth2Config.grant:type_name -> saas.accounts.v1.ApiOAuth2Config.Grant @@ -7988,15 +8263,15 @@ var file_saas_accounts_v1_datasource_proto_depIdxs = []int32{ 0, // 3: saas.accounts.v1.Datasource.provider:type_name -> saas.accounts.v1.DatasourceProvider 14, // 4: saas.accounts.v1.Datasource.github:type_name -> saas.accounts.v1.GitHubDatasourceConfig 1, // 5: saas.accounts.v1.Datasource.status:type_name -> saas.accounts.v1.DatasourceStatus - 103, // 6: saas.accounts.v1.Datasource.created_at:type_name -> google.protobuf.Timestamp - 103, // 7: saas.accounts.v1.Datasource.updated_at:type_name -> google.protobuf.Timestamp - 103, // 8: saas.accounts.v1.Datasource.last_synced_at:type_name -> google.protobuf.Timestamp + 106, // 6: saas.accounts.v1.Datasource.created_at:type_name -> google.protobuf.Timestamp + 106, // 7: saas.accounts.v1.Datasource.updated_at:type_name -> google.protobuf.Timestamp + 106, // 8: saas.accounts.v1.Datasource.last_synced_at:type_name -> google.protobuf.Timestamp 16, // 9: saas.accounts.v1.Datasource.api:type_name -> saas.accounts.v1.ApiDatasourceConfig 17, // 10: saas.accounts.v1.Datasource.crawler:type_name -> saas.accounts.v1.CrawlerDatasourceConfig 18, // 11: saas.accounts.v1.Datasource.upload:type_name -> saas.accounts.v1.UploadDatasourceConfig - 103, // 12: saas.accounts.v1.Datasource.last_ingested_at:type_name -> google.protobuf.Timestamp + 106, // 12: saas.accounts.v1.Datasource.last_ingested_at:type_name -> google.protobuf.Timestamp 2, // 13: saas.accounts.v1.Datasource.live_delivery:type_name -> saas.accounts.v1.DatasourceLiveDelivery - 104, // 14: saas.accounts.v1.Datasource.reconcile_interval:type_name -> google.protobuf.Duration + 107, // 14: saas.accounts.v1.Datasource.reconcile_interval:type_name -> google.protobuf.Duration 19, // 15: saas.accounts.v1.AddGitHubSourceResponse.datasource:type_name -> saas.accounts.v1.Datasource 0, // 16: saas.accounts.v1.AddSourceRequest.provider:type_name -> saas.accounts.v1.DatasourceProvider 14, // 17: saas.accounts.v1.AddSourceRequest.github:type_name -> saas.accounts.v1.GitHubDatasourceConfig @@ -8004,145 +8279,149 @@ var file_saas_accounts_v1_datasource_proto_depIdxs = []int32{ 17, // 19: saas.accounts.v1.AddSourceRequest.crawler:type_name -> saas.accounts.v1.CrawlerDatasourceConfig 18, // 20: saas.accounts.v1.AddSourceRequest.upload:type_name -> saas.accounts.v1.UploadDatasourceConfig 19, // 21: saas.accounts.v1.AddSourceResponse.datasource:type_name -> saas.accounts.v1.Datasource - 0, // 22: saas.accounts.v1.DatasourceProviderDescriptor.provider:type_name -> saas.accounts.v1.DatasourceProvider - 24, // 23: saas.accounts.v1.DatasourceProviderDescriptor.config_fields:type_name -> saas.accounts.v1.DatasourceConfigField - 3, // 24: saas.accounts.v1.DatasourceProviderDescriptor.supported_credential_kinds:type_name -> saas.accounts.v1.ApiCredentialKind - 4, // 25: saas.accounts.v1.DatasourceProviderDescriptor.interface:type_name -> saas.accounts.v1.DatasourceConnectorInterface - 5, // 26: saas.accounts.v1.DatasourceProviderDescriptor.credential_modes:type_name -> saas.accounts.v1.DatasourceCredentialMode - 6, // 27: saas.accounts.v1.DatasourceProviderDescriptor.readers_model:type_name -> saas.accounts.v1.DatasourceReadersModel - 25, // 28: saas.accounts.v1.DatasourceProviderDescriptor.budget:type_name -> saas.accounts.v1.DatasourceConnectorBudget - 26, // 29: saas.accounts.v1.GetDatasourceCatalogResponse.providers:type_name -> saas.accounts.v1.DatasourceProviderDescriptor - 19, // 30: saas.accounts.v1.ListSourcesResponse.datasources:type_name -> saas.accounts.v1.Datasource - 19, // 31: saas.accounts.v1.GetSourceResponse.datasource:type_name -> saas.accounts.v1.Datasource - 105, // 32: saas.accounts.v1.SourceSyncDelivery.state:type_name -> saas.jobs.v1.JobState - 106, // 33: saas.accounts.v1.SourceSyncDelivery.execution:type_name -> saas.jobs.v1.JobExecutionReference - 8, // 34: saas.accounts.v1.SourceSyncFailure.reason:type_name -> saas.accounts.v1.SourceSyncFailureReason - 103, // 35: saas.accounts.v1.SourceSyncFailure.retry_at:type_name -> google.protobuf.Timestamp - 7, // 36: saas.accounts.v1.SourceSyncProgress.phase:type_name -> saas.accounts.v1.SourceSyncPhase - 9, // 37: saas.accounts.v1.SourceSyncProgress.trigger:type_name -> saas.accounts.v1.SourceSyncTrigger - 103, // 38: saas.accounts.v1.SourceSyncProgress.queued_at:type_name -> google.protobuf.Timestamp - 103, // 39: saas.accounts.v1.SourceSyncProgress.fetching_at:type_name -> google.protobuf.Timestamp - 103, // 40: saas.accounts.v1.SourceSyncProgress.compiled_at:type_name -> google.protobuf.Timestamp - 103, // 41: saas.accounts.v1.SourceSyncProgress.handed_off_at:type_name -> google.protobuf.Timestamp - 103, // 42: saas.accounts.v1.SourceSyncProgress.finished_at:type_name -> google.protobuf.Timestamp - 37, // 43: saas.accounts.v1.SourceSyncProgress.changes:type_name -> saas.accounts.v1.SourceSyncChanges - 38, // 44: saas.accounts.v1.SourceSyncProgress.failure:type_name -> saas.accounts.v1.SourceSyncFailure - 105, // 45: saas.accounts.v1.GetSourceSyncResponse.state:type_name -> saas.jobs.v1.JobState - 36, // 46: saas.accounts.v1.GetSourceSyncResponse.deliveries:type_name -> saas.accounts.v1.SourceSyncDelivery - 39, // 47: saas.accounts.v1.GetSourceSyncResponse.progress:type_name -> saas.accounts.v1.SourceSyncProgress - 103, // 48: saas.accounts.v1.BeginGitHubAppSetupResponse.expires_at:type_name -> google.protobuf.Timestamp - 43, // 49: saas.accounts.v1.CompleteGitHubAppSetupResponse.repositories:type_name -> saas.accounts.v1.GitHubAppRepository - 19, // 50: saas.accounts.v1.MigrateGitHubSourceToAppResponse.datasource:type_name -> saas.accounts.v1.Datasource - 103, // 51: saas.accounts.v1.DatasourceAccountLink.created_at:type_name -> google.protobuf.Timestamp - 103, // 52: saas.accounts.v1.DatasourceGroupBinding.created_at:type_name -> google.protobuf.Timestamp - 10, // 53: saas.accounts.v1.DatasourceVerifiedDomain.status:type_name -> saas.accounts.v1.DatasourceDomainStatus - 103, // 54: saas.accounts.v1.DatasourceVerifiedDomain.verified_at:type_name -> google.protobuf.Timestamp - 103, // 55: saas.accounts.v1.DatasourceVerifiedDomain.created_at:type_name -> google.protobuf.Timestamp - 103, // 56: saas.accounts.v1.BeginDatasourceAccountLinkResponse.expires_at:type_name -> google.protobuf.Timestamp - 50, // 57: saas.accounts.v1.CompleteDatasourceAccountLinkResponse.link:type_name -> saas.accounts.v1.DatasourceAccountLink - 50, // 58: saas.accounts.v1.ListMyDatasourceAccountLinksResponse.links:type_name -> saas.accounts.v1.DatasourceAccountLink - 50, // 59: saas.accounts.v1.GetDatasourceDirectoryResponse.links:type_name -> saas.accounts.v1.DatasourceAccountLink - 51, // 60: saas.accounts.v1.GetDatasourceDirectoryResponse.bindings:type_name -> saas.accounts.v1.DatasourceGroupBinding - 52, // 61: saas.accounts.v1.GetDatasourceDirectoryResponse.domains:type_name -> saas.accounts.v1.DatasourceVerifiedDomain - 53, // 62: saas.accounts.v1.GetDatasourceDirectoryResponse.teams:type_name -> saas.accounts.v1.DatasourceDirectoryTeam - 51, // 63: saas.accounts.v1.BindDatasourceGroupResponse.binding:type_name -> saas.accounts.v1.DatasourceGroupBinding - 52, // 64: saas.accounts.v1.ClaimDatasourceDomainResponse.domain:type_name -> saas.accounts.v1.DatasourceVerifiedDomain - 52, // 65: saas.accounts.v1.VerifyDatasourceDomainResponse.domain:type_name -> saas.accounts.v1.DatasourceVerifiedDomain - 103, // 66: saas.accounts.v1.SourceDelegation.created_at:type_name -> google.protobuf.Timestamp - 103, // 67: saas.accounts.v1.SourceDelegation.revoked_at:type_name -> google.protobuf.Timestamp - 11, // 68: saas.accounts.v1.SourceDelegation.revocation:type_name -> saas.accounts.v1.SourceDelegationRevocation - 74, // 69: saas.accounts.v1.ListSourceDelegationsResponse.delegations:type_name -> saas.accounts.v1.SourceDelegation - 74, // 70: saas.accounts.v1.RevokeSourceDelegationResponse.delegation:type_name -> saas.accounts.v1.SourceDelegation - 103, // 71: saas.accounts.v1.TriggerDelegationReference.created_at:type_name -> google.protobuf.Timestamp - 103, // 72: saas.accounts.v1.TriggerDelegationReference.revoked_at:type_name -> google.protobuf.Timestamp - 11, // 73: saas.accounts.v1.TriggerDelegationReference.revocation:type_name -> saas.accounts.v1.SourceDelegationRevocation - 103, // 74: saas.accounts.v1.TriggerChildContext.minted_at:type_name -> google.protobuf.Timestamp - 80, // 75: saas.accounts.v1.SourceTriggerDeclaration.schedule:type_name -> saas.accounts.v1.DeclaredTriggerSchedule - 79, // 76: saas.accounts.v1.SourceTriggerDeclaration.identity:type_name -> saas.accounts.v1.TriggerIdentity - 103, // 77: saas.accounts.v1.SourceTriggerDeclaration.last_occurrence_at:type_name -> google.protobuf.Timestamp - 103, // 78: saas.accounts.v1.SourceTriggerDeclaration.next_occurrence_at:type_name -> google.protobuf.Timestamp - 81, // 79: saas.accounts.v1.DelegateSourceTriggersResponse.delegations:type_name -> saas.accounts.v1.TriggerDelegationReference - 83, // 80: saas.accounts.v1.GetSourceTriggerDeclarationResponse.declaration:type_name -> saas.accounts.v1.SourceTriggerDeclaration - 81, // 81: saas.accounts.v1.GetSourceTriggerDeclarationResponse.delegations:type_name -> saas.accounts.v1.TriggerDelegationReference - 82, // 82: saas.accounts.v1.GetSourceTriggerDeclarationResponse.children:type_name -> saas.accounts.v1.TriggerChildContext - 107, // 83: saas.accounts.v1.SourceOperation.input_schema:type_name -> google.protobuf.Struct - 107, // 84: saas.accounts.v1.SourceOperation.output_schema:type_name -> google.protobuf.Struct - 13, // 85: saas.accounts.v1.SourceOperation.effect:type_name -> saas.accounts.v1.SourceOperation.Effect - 91, // 86: saas.accounts.v1.DeclareSourceOperationsRequest.operations:type_name -> saas.accounts.v1.SourceOperation - 91, // 87: saas.accounts.v1.DeclareSourceOperationsResponse.operations:type_name -> saas.accounts.v1.SourceOperation - 91, // 88: saas.accounts.v1.ListSourceOperationsResponse.operations:type_name -> saas.accounts.v1.SourceOperation - 97, // 89: saas.accounts.v1.InvokeSourceOperationResponse.receipt:type_name -> saas.accounts.v1.SourceOperationReceipt - 100, // 90: saas.accounts.v1.DatasourceService.PruneSourceOperationReceipts:input_type -> saas.accounts.v1.PruneSourceOperationReceiptsRequest - 102, // 91: saas.accounts.v1.DatasourceService.LookupPruneSourceOperationReceipts:input_type -> saas.accounts.v1.LookupPruneSourceOperationReceiptsRequest - 96, // 92: saas.accounts.v1.DatasourceService.InvokeSourceOperation:input_type -> saas.accounts.v1.InvokeSourceOperationRequest - 99, // 93: saas.accounts.v1.DatasourceService.LookupInvokeSourceOperation:input_type -> saas.accounts.v1.LookupInvokeSourceOperationRequest - 94, // 94: saas.accounts.v1.DatasourceService.ListSourceOperations:input_type -> saas.accounts.v1.ListSourceOperationsRequest - 92, // 95: saas.accounts.v1.DatasourceService.DeclareSourceOperations:input_type -> saas.accounts.v1.DeclareSourceOperationsRequest - 20, // 96: saas.accounts.v1.DatasourceService.AddGitHubSource:input_type -> saas.accounts.v1.AddGitHubSourceRequest - 22, // 97: saas.accounts.v1.DatasourceService.AddSource:input_type -> saas.accounts.v1.AddSourceRequest - 27, // 98: saas.accounts.v1.DatasourceService.GetDatasourceCatalog:input_type -> saas.accounts.v1.GetDatasourceCatalogRequest - 29, // 99: saas.accounts.v1.DatasourceService.ListSources:input_type -> saas.accounts.v1.ListSourcesRequest - 31, // 100: saas.accounts.v1.DatasourceService.GetSource:input_type -> saas.accounts.v1.GetSourceRequest - 33, // 101: saas.accounts.v1.DatasourceService.SyncSource:input_type -> saas.accounts.v1.SyncSourceRequest - 35, // 102: saas.accounts.v1.DatasourceService.GetSourceSync:input_type -> saas.accounts.v1.GetSourceSyncRequest - 41, // 103: saas.accounts.v1.DatasourceService.DeleteSource:input_type -> saas.accounts.v1.DeleteSourceRequest - 44, // 104: saas.accounts.v1.DatasourceService.BeginGitHubAppSetup:input_type -> saas.accounts.v1.BeginGitHubAppSetupRequest - 46, // 105: saas.accounts.v1.DatasourceService.CompleteGitHubAppSetup:input_type -> saas.accounts.v1.CompleteGitHubAppSetupRequest - 48, // 106: saas.accounts.v1.DatasourceService.MigrateGitHubSourceToApp:input_type -> saas.accounts.v1.MigrateGitHubSourceToAppRequest - 54, // 107: saas.accounts.v1.DatasourceService.BeginDatasourceAccountLink:input_type -> saas.accounts.v1.BeginDatasourceAccountLinkRequest - 56, // 108: saas.accounts.v1.DatasourceService.CompleteDatasourceAccountLink:input_type -> saas.accounts.v1.CompleteDatasourceAccountLinkRequest - 58, // 109: saas.accounts.v1.DatasourceService.ListMyDatasourceAccountLinks:input_type -> saas.accounts.v1.ListMyDatasourceAccountLinksRequest - 60, // 110: saas.accounts.v1.DatasourceService.DeleteDatasourceAccountLink:input_type -> saas.accounts.v1.DeleteDatasourceAccountLinkRequest - 62, // 111: saas.accounts.v1.DatasourceService.GetDatasourceDirectory:input_type -> saas.accounts.v1.GetDatasourceDirectoryRequest - 64, // 112: saas.accounts.v1.DatasourceService.BindDatasourceGroup:input_type -> saas.accounts.v1.BindDatasourceGroupRequest - 66, // 113: saas.accounts.v1.DatasourceService.UnbindDatasourceGroup:input_type -> saas.accounts.v1.UnbindDatasourceGroupRequest - 68, // 114: saas.accounts.v1.DatasourceService.ClaimDatasourceDomain:input_type -> saas.accounts.v1.ClaimDatasourceDomainRequest - 70, // 115: saas.accounts.v1.DatasourceService.VerifyDatasourceDomain:input_type -> saas.accounts.v1.VerifyDatasourceDomainRequest - 72, // 116: saas.accounts.v1.DatasourceService.DeleteDatasourceDomain:input_type -> saas.accounts.v1.DeleteDatasourceDomainRequest - 75, // 117: saas.accounts.v1.DatasourceService.ListSourceDelegations:input_type -> saas.accounts.v1.ListSourceDelegationsRequest - 77, // 118: saas.accounts.v1.DatasourceService.RevokeSourceDelegation:input_type -> saas.accounts.v1.RevokeSourceDelegationRequest - 84, // 119: saas.accounts.v1.DatasourceService.DelegateSourceTriggers:input_type -> saas.accounts.v1.DelegateSourceTriggersRequest - 86, // 120: saas.accounts.v1.DatasourceService.GetSourceTriggerDeclaration:input_type -> saas.accounts.v1.GetSourceTriggerDeclarationRequest - 88, // 121: saas.accounts.v1.DatasourceService.ReconcileSource:input_type -> saas.accounts.v1.ReconcileSourceRequest - 90, // 122: saas.accounts.v1.DatasourceService.LookupReconcileSource:input_type -> saas.accounts.v1.LookupReconcileSourceRequest - 101, // 123: saas.accounts.v1.DatasourceService.PruneSourceOperationReceipts:output_type -> saas.accounts.v1.PruneSourceOperationReceiptsResponse - 101, // 124: saas.accounts.v1.DatasourceService.LookupPruneSourceOperationReceipts:output_type -> saas.accounts.v1.PruneSourceOperationReceiptsResponse - 98, // 125: saas.accounts.v1.DatasourceService.InvokeSourceOperation:output_type -> saas.accounts.v1.InvokeSourceOperationResponse - 98, // 126: saas.accounts.v1.DatasourceService.LookupInvokeSourceOperation:output_type -> saas.accounts.v1.InvokeSourceOperationResponse - 95, // 127: saas.accounts.v1.DatasourceService.ListSourceOperations:output_type -> saas.accounts.v1.ListSourceOperationsResponse - 93, // 128: saas.accounts.v1.DatasourceService.DeclareSourceOperations:output_type -> saas.accounts.v1.DeclareSourceOperationsResponse - 21, // 129: saas.accounts.v1.DatasourceService.AddGitHubSource:output_type -> saas.accounts.v1.AddGitHubSourceResponse - 23, // 130: saas.accounts.v1.DatasourceService.AddSource:output_type -> saas.accounts.v1.AddSourceResponse - 28, // 131: saas.accounts.v1.DatasourceService.GetDatasourceCatalog:output_type -> saas.accounts.v1.GetDatasourceCatalogResponse - 30, // 132: saas.accounts.v1.DatasourceService.ListSources:output_type -> saas.accounts.v1.ListSourcesResponse - 32, // 133: saas.accounts.v1.DatasourceService.GetSource:output_type -> saas.accounts.v1.GetSourceResponse - 34, // 134: saas.accounts.v1.DatasourceService.SyncSource:output_type -> saas.accounts.v1.SyncSourceResponse - 40, // 135: saas.accounts.v1.DatasourceService.GetSourceSync:output_type -> saas.accounts.v1.GetSourceSyncResponse - 42, // 136: saas.accounts.v1.DatasourceService.DeleteSource:output_type -> saas.accounts.v1.DeleteSourceResponse - 45, // 137: saas.accounts.v1.DatasourceService.BeginGitHubAppSetup:output_type -> saas.accounts.v1.BeginGitHubAppSetupResponse - 47, // 138: saas.accounts.v1.DatasourceService.CompleteGitHubAppSetup:output_type -> saas.accounts.v1.CompleteGitHubAppSetupResponse - 49, // 139: saas.accounts.v1.DatasourceService.MigrateGitHubSourceToApp:output_type -> saas.accounts.v1.MigrateGitHubSourceToAppResponse - 55, // 140: saas.accounts.v1.DatasourceService.BeginDatasourceAccountLink:output_type -> saas.accounts.v1.BeginDatasourceAccountLinkResponse - 57, // 141: saas.accounts.v1.DatasourceService.CompleteDatasourceAccountLink:output_type -> saas.accounts.v1.CompleteDatasourceAccountLinkResponse - 59, // 142: saas.accounts.v1.DatasourceService.ListMyDatasourceAccountLinks:output_type -> saas.accounts.v1.ListMyDatasourceAccountLinksResponse - 61, // 143: saas.accounts.v1.DatasourceService.DeleteDatasourceAccountLink:output_type -> saas.accounts.v1.DeleteDatasourceAccountLinkResponse - 63, // 144: saas.accounts.v1.DatasourceService.GetDatasourceDirectory:output_type -> saas.accounts.v1.GetDatasourceDirectoryResponse - 65, // 145: saas.accounts.v1.DatasourceService.BindDatasourceGroup:output_type -> saas.accounts.v1.BindDatasourceGroupResponse - 67, // 146: saas.accounts.v1.DatasourceService.UnbindDatasourceGroup:output_type -> saas.accounts.v1.UnbindDatasourceGroupResponse - 69, // 147: saas.accounts.v1.DatasourceService.ClaimDatasourceDomain:output_type -> saas.accounts.v1.ClaimDatasourceDomainResponse - 71, // 148: saas.accounts.v1.DatasourceService.VerifyDatasourceDomain:output_type -> saas.accounts.v1.VerifyDatasourceDomainResponse - 73, // 149: saas.accounts.v1.DatasourceService.DeleteDatasourceDomain:output_type -> saas.accounts.v1.DeleteDatasourceDomainResponse - 76, // 150: saas.accounts.v1.DatasourceService.ListSourceDelegations:output_type -> saas.accounts.v1.ListSourceDelegationsResponse - 78, // 151: saas.accounts.v1.DatasourceService.RevokeSourceDelegation:output_type -> saas.accounts.v1.RevokeSourceDelegationResponse - 85, // 152: saas.accounts.v1.DatasourceService.DelegateSourceTriggers:output_type -> saas.accounts.v1.DelegateSourceTriggersResponse - 87, // 153: saas.accounts.v1.DatasourceService.GetSourceTriggerDeclaration:output_type -> saas.accounts.v1.GetSourceTriggerDeclarationResponse - 89, // 154: saas.accounts.v1.DatasourceService.ReconcileSource:output_type -> saas.accounts.v1.ReconcileSourceResponse - 89, // 155: saas.accounts.v1.DatasourceService.LookupReconcileSource:output_type -> saas.accounts.v1.ReconcileSourceResponse - 123, // [123:156] is the sub-list for method output_type - 90, // [90:123] is the sub-list for method input_type - 90, // [90:90] is the sub-list for extension type_name - 90, // [90:90] is the sub-list for extension extendee - 0, // [0:90] is the sub-list for field type_name + 25, // 22: saas.accounts.v1.UpdateSourceRequest.expected:type_name -> saas.accounts.v1.SourceFetchScope + 19, // 23: saas.accounts.v1.UpdateSourceResponse.datasource:type_name -> saas.accounts.v1.Datasource + 0, // 24: saas.accounts.v1.DatasourceProviderDescriptor.provider:type_name -> saas.accounts.v1.DatasourceProvider + 27, // 25: saas.accounts.v1.DatasourceProviderDescriptor.config_fields:type_name -> saas.accounts.v1.DatasourceConfigField + 3, // 26: saas.accounts.v1.DatasourceProviderDescriptor.supported_credential_kinds:type_name -> saas.accounts.v1.ApiCredentialKind + 4, // 27: saas.accounts.v1.DatasourceProviderDescriptor.interface:type_name -> saas.accounts.v1.DatasourceConnectorInterface + 5, // 28: saas.accounts.v1.DatasourceProviderDescriptor.credential_modes:type_name -> saas.accounts.v1.DatasourceCredentialMode + 6, // 29: saas.accounts.v1.DatasourceProviderDescriptor.readers_model:type_name -> saas.accounts.v1.DatasourceReadersModel + 28, // 30: saas.accounts.v1.DatasourceProviderDescriptor.budget:type_name -> saas.accounts.v1.DatasourceConnectorBudget + 29, // 31: saas.accounts.v1.GetDatasourceCatalogResponse.providers:type_name -> saas.accounts.v1.DatasourceProviderDescriptor + 19, // 32: saas.accounts.v1.ListSourcesResponse.datasources:type_name -> saas.accounts.v1.Datasource + 19, // 33: saas.accounts.v1.GetSourceResponse.datasource:type_name -> saas.accounts.v1.Datasource + 108, // 34: saas.accounts.v1.SourceSyncDelivery.state:type_name -> saas.jobs.v1.JobState + 109, // 35: saas.accounts.v1.SourceSyncDelivery.execution:type_name -> saas.jobs.v1.JobExecutionReference + 8, // 36: saas.accounts.v1.SourceSyncFailure.reason:type_name -> saas.accounts.v1.SourceSyncFailureReason + 106, // 37: saas.accounts.v1.SourceSyncFailure.retry_at:type_name -> google.protobuf.Timestamp + 7, // 38: saas.accounts.v1.SourceSyncProgress.phase:type_name -> saas.accounts.v1.SourceSyncPhase + 9, // 39: saas.accounts.v1.SourceSyncProgress.trigger:type_name -> saas.accounts.v1.SourceSyncTrigger + 106, // 40: saas.accounts.v1.SourceSyncProgress.queued_at:type_name -> google.protobuf.Timestamp + 106, // 41: saas.accounts.v1.SourceSyncProgress.fetching_at:type_name -> google.protobuf.Timestamp + 106, // 42: saas.accounts.v1.SourceSyncProgress.compiled_at:type_name -> google.protobuf.Timestamp + 106, // 43: saas.accounts.v1.SourceSyncProgress.handed_off_at:type_name -> google.protobuf.Timestamp + 106, // 44: saas.accounts.v1.SourceSyncProgress.finished_at:type_name -> google.protobuf.Timestamp + 40, // 45: saas.accounts.v1.SourceSyncProgress.changes:type_name -> saas.accounts.v1.SourceSyncChanges + 41, // 46: saas.accounts.v1.SourceSyncProgress.failure:type_name -> saas.accounts.v1.SourceSyncFailure + 108, // 47: saas.accounts.v1.GetSourceSyncResponse.state:type_name -> saas.jobs.v1.JobState + 39, // 48: saas.accounts.v1.GetSourceSyncResponse.deliveries:type_name -> saas.accounts.v1.SourceSyncDelivery + 42, // 49: saas.accounts.v1.GetSourceSyncResponse.progress:type_name -> saas.accounts.v1.SourceSyncProgress + 106, // 50: saas.accounts.v1.BeginGitHubAppSetupResponse.expires_at:type_name -> google.protobuf.Timestamp + 46, // 51: saas.accounts.v1.CompleteGitHubAppSetupResponse.repositories:type_name -> saas.accounts.v1.GitHubAppRepository + 19, // 52: saas.accounts.v1.MigrateGitHubSourceToAppResponse.datasource:type_name -> saas.accounts.v1.Datasource + 106, // 53: saas.accounts.v1.DatasourceAccountLink.created_at:type_name -> google.protobuf.Timestamp + 106, // 54: saas.accounts.v1.DatasourceGroupBinding.created_at:type_name -> google.protobuf.Timestamp + 10, // 55: saas.accounts.v1.DatasourceVerifiedDomain.status:type_name -> saas.accounts.v1.DatasourceDomainStatus + 106, // 56: saas.accounts.v1.DatasourceVerifiedDomain.verified_at:type_name -> google.protobuf.Timestamp + 106, // 57: saas.accounts.v1.DatasourceVerifiedDomain.created_at:type_name -> google.protobuf.Timestamp + 106, // 58: saas.accounts.v1.BeginDatasourceAccountLinkResponse.expires_at:type_name -> google.protobuf.Timestamp + 53, // 59: saas.accounts.v1.CompleteDatasourceAccountLinkResponse.link:type_name -> saas.accounts.v1.DatasourceAccountLink + 53, // 60: saas.accounts.v1.ListMyDatasourceAccountLinksResponse.links:type_name -> saas.accounts.v1.DatasourceAccountLink + 53, // 61: saas.accounts.v1.GetDatasourceDirectoryResponse.links:type_name -> saas.accounts.v1.DatasourceAccountLink + 54, // 62: saas.accounts.v1.GetDatasourceDirectoryResponse.bindings:type_name -> saas.accounts.v1.DatasourceGroupBinding + 55, // 63: saas.accounts.v1.GetDatasourceDirectoryResponse.domains:type_name -> saas.accounts.v1.DatasourceVerifiedDomain + 56, // 64: saas.accounts.v1.GetDatasourceDirectoryResponse.teams:type_name -> saas.accounts.v1.DatasourceDirectoryTeam + 54, // 65: saas.accounts.v1.BindDatasourceGroupResponse.binding:type_name -> saas.accounts.v1.DatasourceGroupBinding + 55, // 66: saas.accounts.v1.ClaimDatasourceDomainResponse.domain:type_name -> saas.accounts.v1.DatasourceVerifiedDomain + 55, // 67: saas.accounts.v1.VerifyDatasourceDomainResponse.domain:type_name -> saas.accounts.v1.DatasourceVerifiedDomain + 106, // 68: saas.accounts.v1.SourceDelegation.created_at:type_name -> google.protobuf.Timestamp + 106, // 69: saas.accounts.v1.SourceDelegation.revoked_at:type_name -> google.protobuf.Timestamp + 11, // 70: saas.accounts.v1.SourceDelegation.revocation:type_name -> saas.accounts.v1.SourceDelegationRevocation + 77, // 71: saas.accounts.v1.ListSourceDelegationsResponse.delegations:type_name -> saas.accounts.v1.SourceDelegation + 77, // 72: saas.accounts.v1.RevokeSourceDelegationResponse.delegation:type_name -> saas.accounts.v1.SourceDelegation + 106, // 73: saas.accounts.v1.TriggerDelegationReference.created_at:type_name -> google.protobuf.Timestamp + 106, // 74: saas.accounts.v1.TriggerDelegationReference.revoked_at:type_name -> google.protobuf.Timestamp + 11, // 75: saas.accounts.v1.TriggerDelegationReference.revocation:type_name -> saas.accounts.v1.SourceDelegationRevocation + 106, // 76: saas.accounts.v1.TriggerChildContext.minted_at:type_name -> google.protobuf.Timestamp + 83, // 77: saas.accounts.v1.SourceTriggerDeclaration.schedule:type_name -> saas.accounts.v1.DeclaredTriggerSchedule + 82, // 78: saas.accounts.v1.SourceTriggerDeclaration.identity:type_name -> saas.accounts.v1.TriggerIdentity + 106, // 79: saas.accounts.v1.SourceTriggerDeclaration.last_occurrence_at:type_name -> google.protobuf.Timestamp + 106, // 80: saas.accounts.v1.SourceTriggerDeclaration.next_occurrence_at:type_name -> google.protobuf.Timestamp + 84, // 81: saas.accounts.v1.DelegateSourceTriggersResponse.delegations:type_name -> saas.accounts.v1.TriggerDelegationReference + 86, // 82: saas.accounts.v1.GetSourceTriggerDeclarationResponse.declaration:type_name -> saas.accounts.v1.SourceTriggerDeclaration + 84, // 83: saas.accounts.v1.GetSourceTriggerDeclarationResponse.delegations:type_name -> saas.accounts.v1.TriggerDelegationReference + 85, // 84: saas.accounts.v1.GetSourceTriggerDeclarationResponse.children:type_name -> saas.accounts.v1.TriggerChildContext + 110, // 85: saas.accounts.v1.SourceOperation.input_schema:type_name -> google.protobuf.Struct + 110, // 86: saas.accounts.v1.SourceOperation.output_schema:type_name -> google.protobuf.Struct + 13, // 87: saas.accounts.v1.SourceOperation.effect:type_name -> saas.accounts.v1.SourceOperation.Effect + 94, // 88: saas.accounts.v1.DeclareSourceOperationsRequest.operations:type_name -> saas.accounts.v1.SourceOperation + 94, // 89: saas.accounts.v1.DeclareSourceOperationsResponse.operations:type_name -> saas.accounts.v1.SourceOperation + 94, // 90: saas.accounts.v1.ListSourceOperationsResponse.operations:type_name -> saas.accounts.v1.SourceOperation + 100, // 91: saas.accounts.v1.InvokeSourceOperationResponse.receipt:type_name -> saas.accounts.v1.SourceOperationReceipt + 103, // 92: saas.accounts.v1.DatasourceService.PruneSourceOperationReceipts:input_type -> saas.accounts.v1.PruneSourceOperationReceiptsRequest + 105, // 93: saas.accounts.v1.DatasourceService.LookupPruneSourceOperationReceipts:input_type -> saas.accounts.v1.LookupPruneSourceOperationReceiptsRequest + 99, // 94: saas.accounts.v1.DatasourceService.InvokeSourceOperation:input_type -> saas.accounts.v1.InvokeSourceOperationRequest + 102, // 95: saas.accounts.v1.DatasourceService.LookupInvokeSourceOperation:input_type -> saas.accounts.v1.LookupInvokeSourceOperationRequest + 97, // 96: saas.accounts.v1.DatasourceService.ListSourceOperations:input_type -> saas.accounts.v1.ListSourceOperationsRequest + 95, // 97: saas.accounts.v1.DatasourceService.DeclareSourceOperations:input_type -> saas.accounts.v1.DeclareSourceOperationsRequest + 20, // 98: saas.accounts.v1.DatasourceService.AddGitHubSource:input_type -> saas.accounts.v1.AddGitHubSourceRequest + 22, // 99: saas.accounts.v1.DatasourceService.AddSource:input_type -> saas.accounts.v1.AddSourceRequest + 24, // 100: saas.accounts.v1.DatasourceService.UpdateSource:input_type -> saas.accounts.v1.UpdateSourceRequest + 30, // 101: saas.accounts.v1.DatasourceService.GetDatasourceCatalog:input_type -> saas.accounts.v1.GetDatasourceCatalogRequest + 32, // 102: saas.accounts.v1.DatasourceService.ListSources:input_type -> saas.accounts.v1.ListSourcesRequest + 34, // 103: saas.accounts.v1.DatasourceService.GetSource:input_type -> saas.accounts.v1.GetSourceRequest + 36, // 104: saas.accounts.v1.DatasourceService.SyncSource:input_type -> saas.accounts.v1.SyncSourceRequest + 38, // 105: saas.accounts.v1.DatasourceService.GetSourceSync:input_type -> saas.accounts.v1.GetSourceSyncRequest + 44, // 106: saas.accounts.v1.DatasourceService.DeleteSource:input_type -> saas.accounts.v1.DeleteSourceRequest + 47, // 107: saas.accounts.v1.DatasourceService.BeginGitHubAppSetup:input_type -> saas.accounts.v1.BeginGitHubAppSetupRequest + 49, // 108: saas.accounts.v1.DatasourceService.CompleteGitHubAppSetup:input_type -> saas.accounts.v1.CompleteGitHubAppSetupRequest + 51, // 109: saas.accounts.v1.DatasourceService.MigrateGitHubSourceToApp:input_type -> saas.accounts.v1.MigrateGitHubSourceToAppRequest + 57, // 110: saas.accounts.v1.DatasourceService.BeginDatasourceAccountLink:input_type -> saas.accounts.v1.BeginDatasourceAccountLinkRequest + 59, // 111: saas.accounts.v1.DatasourceService.CompleteDatasourceAccountLink:input_type -> saas.accounts.v1.CompleteDatasourceAccountLinkRequest + 61, // 112: saas.accounts.v1.DatasourceService.ListMyDatasourceAccountLinks:input_type -> saas.accounts.v1.ListMyDatasourceAccountLinksRequest + 63, // 113: saas.accounts.v1.DatasourceService.DeleteDatasourceAccountLink:input_type -> saas.accounts.v1.DeleteDatasourceAccountLinkRequest + 65, // 114: saas.accounts.v1.DatasourceService.GetDatasourceDirectory:input_type -> saas.accounts.v1.GetDatasourceDirectoryRequest + 67, // 115: saas.accounts.v1.DatasourceService.BindDatasourceGroup:input_type -> saas.accounts.v1.BindDatasourceGroupRequest + 69, // 116: saas.accounts.v1.DatasourceService.UnbindDatasourceGroup:input_type -> saas.accounts.v1.UnbindDatasourceGroupRequest + 71, // 117: saas.accounts.v1.DatasourceService.ClaimDatasourceDomain:input_type -> saas.accounts.v1.ClaimDatasourceDomainRequest + 73, // 118: saas.accounts.v1.DatasourceService.VerifyDatasourceDomain:input_type -> saas.accounts.v1.VerifyDatasourceDomainRequest + 75, // 119: saas.accounts.v1.DatasourceService.DeleteDatasourceDomain:input_type -> saas.accounts.v1.DeleteDatasourceDomainRequest + 78, // 120: saas.accounts.v1.DatasourceService.ListSourceDelegations:input_type -> saas.accounts.v1.ListSourceDelegationsRequest + 80, // 121: saas.accounts.v1.DatasourceService.RevokeSourceDelegation:input_type -> saas.accounts.v1.RevokeSourceDelegationRequest + 87, // 122: saas.accounts.v1.DatasourceService.DelegateSourceTriggers:input_type -> saas.accounts.v1.DelegateSourceTriggersRequest + 89, // 123: saas.accounts.v1.DatasourceService.GetSourceTriggerDeclaration:input_type -> saas.accounts.v1.GetSourceTriggerDeclarationRequest + 91, // 124: saas.accounts.v1.DatasourceService.ReconcileSource:input_type -> saas.accounts.v1.ReconcileSourceRequest + 93, // 125: saas.accounts.v1.DatasourceService.LookupReconcileSource:input_type -> saas.accounts.v1.LookupReconcileSourceRequest + 104, // 126: saas.accounts.v1.DatasourceService.PruneSourceOperationReceipts:output_type -> saas.accounts.v1.PruneSourceOperationReceiptsResponse + 104, // 127: saas.accounts.v1.DatasourceService.LookupPruneSourceOperationReceipts:output_type -> saas.accounts.v1.PruneSourceOperationReceiptsResponse + 101, // 128: saas.accounts.v1.DatasourceService.InvokeSourceOperation:output_type -> saas.accounts.v1.InvokeSourceOperationResponse + 101, // 129: saas.accounts.v1.DatasourceService.LookupInvokeSourceOperation:output_type -> saas.accounts.v1.InvokeSourceOperationResponse + 98, // 130: saas.accounts.v1.DatasourceService.ListSourceOperations:output_type -> saas.accounts.v1.ListSourceOperationsResponse + 96, // 131: saas.accounts.v1.DatasourceService.DeclareSourceOperations:output_type -> saas.accounts.v1.DeclareSourceOperationsResponse + 21, // 132: saas.accounts.v1.DatasourceService.AddGitHubSource:output_type -> saas.accounts.v1.AddGitHubSourceResponse + 23, // 133: saas.accounts.v1.DatasourceService.AddSource:output_type -> saas.accounts.v1.AddSourceResponse + 26, // 134: saas.accounts.v1.DatasourceService.UpdateSource:output_type -> saas.accounts.v1.UpdateSourceResponse + 31, // 135: saas.accounts.v1.DatasourceService.GetDatasourceCatalog:output_type -> saas.accounts.v1.GetDatasourceCatalogResponse + 33, // 136: saas.accounts.v1.DatasourceService.ListSources:output_type -> saas.accounts.v1.ListSourcesResponse + 35, // 137: saas.accounts.v1.DatasourceService.GetSource:output_type -> saas.accounts.v1.GetSourceResponse + 37, // 138: saas.accounts.v1.DatasourceService.SyncSource:output_type -> saas.accounts.v1.SyncSourceResponse + 43, // 139: saas.accounts.v1.DatasourceService.GetSourceSync:output_type -> saas.accounts.v1.GetSourceSyncResponse + 45, // 140: saas.accounts.v1.DatasourceService.DeleteSource:output_type -> saas.accounts.v1.DeleteSourceResponse + 48, // 141: saas.accounts.v1.DatasourceService.BeginGitHubAppSetup:output_type -> saas.accounts.v1.BeginGitHubAppSetupResponse + 50, // 142: saas.accounts.v1.DatasourceService.CompleteGitHubAppSetup:output_type -> saas.accounts.v1.CompleteGitHubAppSetupResponse + 52, // 143: saas.accounts.v1.DatasourceService.MigrateGitHubSourceToApp:output_type -> saas.accounts.v1.MigrateGitHubSourceToAppResponse + 58, // 144: saas.accounts.v1.DatasourceService.BeginDatasourceAccountLink:output_type -> saas.accounts.v1.BeginDatasourceAccountLinkResponse + 60, // 145: saas.accounts.v1.DatasourceService.CompleteDatasourceAccountLink:output_type -> saas.accounts.v1.CompleteDatasourceAccountLinkResponse + 62, // 146: saas.accounts.v1.DatasourceService.ListMyDatasourceAccountLinks:output_type -> saas.accounts.v1.ListMyDatasourceAccountLinksResponse + 64, // 147: saas.accounts.v1.DatasourceService.DeleteDatasourceAccountLink:output_type -> saas.accounts.v1.DeleteDatasourceAccountLinkResponse + 66, // 148: saas.accounts.v1.DatasourceService.GetDatasourceDirectory:output_type -> saas.accounts.v1.GetDatasourceDirectoryResponse + 68, // 149: saas.accounts.v1.DatasourceService.BindDatasourceGroup:output_type -> saas.accounts.v1.BindDatasourceGroupResponse + 70, // 150: saas.accounts.v1.DatasourceService.UnbindDatasourceGroup:output_type -> saas.accounts.v1.UnbindDatasourceGroupResponse + 72, // 151: saas.accounts.v1.DatasourceService.ClaimDatasourceDomain:output_type -> saas.accounts.v1.ClaimDatasourceDomainResponse + 74, // 152: saas.accounts.v1.DatasourceService.VerifyDatasourceDomain:output_type -> saas.accounts.v1.VerifyDatasourceDomainResponse + 76, // 153: saas.accounts.v1.DatasourceService.DeleteDatasourceDomain:output_type -> saas.accounts.v1.DeleteDatasourceDomainResponse + 79, // 154: saas.accounts.v1.DatasourceService.ListSourceDelegations:output_type -> saas.accounts.v1.ListSourceDelegationsResponse + 81, // 155: saas.accounts.v1.DatasourceService.RevokeSourceDelegation:output_type -> saas.accounts.v1.RevokeSourceDelegationResponse + 88, // 156: saas.accounts.v1.DatasourceService.DelegateSourceTriggers:output_type -> saas.accounts.v1.DelegateSourceTriggersResponse + 90, // 157: saas.accounts.v1.DatasourceService.GetSourceTriggerDeclaration:output_type -> saas.accounts.v1.GetSourceTriggerDeclarationResponse + 92, // 158: saas.accounts.v1.DatasourceService.ReconcileSource:output_type -> saas.accounts.v1.ReconcileSourceResponse + 92, // 159: saas.accounts.v1.DatasourceService.LookupReconcileSource:output_type -> saas.accounts.v1.ReconcileSourceResponse + 126, // [126:160] is the sub-list for method output_type + 92, // [92:126] is the sub-list for method input_type + 92, // [92:92] is the sub-list for extension type_name + 92, // [92:92] is the sub-list for extension extendee + 0, // [0:92] is the sub-list for field type_name } func init() { file_saas_accounts_v1_datasource_proto_init() } @@ -8162,14 +8441,14 @@ func file_saas_accounts_v1_datasource_proto_init() { (*AddSourceRequest_BoundaryNodeId)(nil), (*AddSourceRequest_CollectionLabel)(nil), } - file_saas_accounts_v1_datasource_proto_msgTypes[61].OneofWrappers = []any{} + file_saas_accounts_v1_datasource_proto_msgTypes[64].OneofWrappers = []any{} type x struct{} out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: unsafe.Slice(unsafe.StringData(file_saas_accounts_v1_datasource_proto_rawDesc), len(file_saas_accounts_v1_datasource_proto_rawDesc)), NumEnums: 14, - NumMessages: 89, + NumMessages: 92, NumExtensions: 0, NumServices: 1, }, diff --git a/gen/saas/accounts/v1/installations.pb.go b/gen/saas/accounts/v1/installations.pb.go index 90a3ec8..20eaeab 100644 --- a/gen/saas/accounts/v1/installations.pb.go +++ b/gen/saas/accounts/v1/installations.pb.go @@ -152,6 +152,222 @@ func (InstallationHealth) EnumDescriptor() ([]byte, []int) { return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{1} } +// ReadinessConditionKind is what kind of thing is unmet. A reader acts on the +// words in `detail`; the kind is for the surface to choose an action and for a +// consumer to count one kind without parsing prose. +type ReadinessConditionKind int32 + +const ( + ReadinessConditionKind_READINESS_CONDITION_KIND_UNSPECIFIED ReadinessConditionKind = 0 + // The solution has not acknowledged its standard install step yet. + ReadinessConditionKind_READINESS_CONDITION_KIND_INSTALL_STEP_PENDING ReadinessConditionKind = 1 + // It refused the install step, or never answered within the attempt budget. + ReadinessConditionKind_READINESS_CONDITION_KIND_INSTALL_STEP_FAILED ReadinessConditionKind = 2 + // The installation record itself is not healthy: the InstallationHealth + // value, restated as a condition so one list holds every reason it will not + // work rather than two places a reader has to join. + ReadinessConditionKind_READINESS_CONDITION_KIND_RECORD_UNHEALTHY ReadinessConditionKind = 3 + // The module registry holds no principal for this target's module at all, so + // every Work Context it asks for is denied. + ReadinessConditionKind_READINESS_CONDITION_KIND_MODULE_PRINCIPAL_OMITTED ReadinessConditionKind = 4 + // An operation binding the applied manifest asks for derived nothing: the + // envelope allows no such binding, or allows nothing of it. This is the + // condition that reported HEALTHY on a validation cell while four bindings were + // dropped. + ReadinessConditionKind_READINESS_CONDITION_KIND_OPERATION_BINDING_OMITTED ReadinessConditionKind = 5 + // A source this organisation has connected holds no active delegation to a + // module that accepts them, so that module cannot read it on anyone's behalf. + ReadinessConditionKind_READINESS_CONDITION_KIND_SOURCE_NOT_DELEGATED ReadinessConditionKind = 6 + // A module this target declares it reaches is not installed in this + // organisation, so every call it makes there is refused. + ReadinessConditionKind_READINESS_CONDITION_KIND_REACHED_MODULE_NOT_INSTALLED ReadinessConditionKind = 7 + // A grant of this solution could not CARRY the access it declares it consumes + // on one reached module, so the team holds nothing there and the pages that + // reach it will be refused. `detail` says which of the two reasons it is: the + // chosen role permits none of what the solution consumes there, or the + // declared scope is narrowed to named resources, which a role cannot express. + ReadinessConditionKind_READINESS_CONDITION_KIND_CARRIED_MODULE_ACCESS_NOT_DERIVED ReadinessConditionKind = 8 +) + +// Enum value maps for ReadinessConditionKind. +var ( + ReadinessConditionKind_name = map[int32]string{ + 0: "READINESS_CONDITION_KIND_UNSPECIFIED", + 1: "READINESS_CONDITION_KIND_INSTALL_STEP_PENDING", + 2: "READINESS_CONDITION_KIND_INSTALL_STEP_FAILED", + 3: "READINESS_CONDITION_KIND_RECORD_UNHEALTHY", + 4: "READINESS_CONDITION_KIND_MODULE_PRINCIPAL_OMITTED", + 5: "READINESS_CONDITION_KIND_OPERATION_BINDING_OMITTED", + 6: "READINESS_CONDITION_KIND_SOURCE_NOT_DELEGATED", + 7: "READINESS_CONDITION_KIND_REACHED_MODULE_NOT_INSTALLED", + 8: "READINESS_CONDITION_KIND_CARRIED_MODULE_ACCESS_NOT_DERIVED", + } + ReadinessConditionKind_value = map[string]int32{ + "READINESS_CONDITION_KIND_UNSPECIFIED": 0, + "READINESS_CONDITION_KIND_INSTALL_STEP_PENDING": 1, + "READINESS_CONDITION_KIND_INSTALL_STEP_FAILED": 2, + "READINESS_CONDITION_KIND_RECORD_UNHEALTHY": 3, + "READINESS_CONDITION_KIND_MODULE_PRINCIPAL_OMITTED": 4, + "READINESS_CONDITION_KIND_OPERATION_BINDING_OMITTED": 5, + "READINESS_CONDITION_KIND_SOURCE_NOT_DELEGATED": 6, + "READINESS_CONDITION_KIND_REACHED_MODULE_NOT_INSTALLED": 7, + "READINESS_CONDITION_KIND_CARRIED_MODULE_ACCESS_NOT_DERIVED": 8, + } +) + +func (x ReadinessConditionKind) Enum() *ReadinessConditionKind { + p := new(ReadinessConditionKind) + *p = x + return p +} + +func (x ReadinessConditionKind) String() string { + return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x)) +} + +func (ReadinessConditionKind) Descriptor() protoreflect.EnumDescriptor { + return file_saas_accounts_v1_installations_proto_enumTypes[2].Descriptor() +} + +func (ReadinessConditionKind) Type() protoreflect.EnumType { + return &file_saas_accounts_v1_installations_proto_enumTypes[2] +} + +func (x ReadinessConditionKind) Number() protoreflect.EnumNumber { + return protoreflect.EnumNumber(x) +} + +// Deprecated: Use ReadinessConditionKind.Descriptor instead. +func (ReadinessConditionKind) EnumDescriptor() ([]byte, []int) { + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{2} +} + +// ReadinessClearedBy is who can clear a condition. It is stated rather than +// implied by the action, because "nobody at this surface can" is itself the +// answer a reader needs — an envelope that withholds a binding is the platform +// operator's, and offering an administrator a button would be a lie. +type ReadinessClearedBy int32 + +const ( + ReadinessClearedBy_READINESS_CLEARED_BY_UNSPECIFIED ReadinessClearedBy = 0 + // The person reading the page, acting as themselves: their own delegation. + ReadinessClearedBy_READINESS_CLEARED_BY_VIEWER ReadinessClearedBy = 1 + ReadinessClearedBy_READINESS_CLEARED_BY_ORGANIZATION_ADMIN ReadinessClearedBy = 2 + ReadinessClearedBy_READINESS_CLEARED_BY_PLATFORM_OPERATOR ReadinessClearedBy = 3 + // Nobody: the host is waiting for the solution itself to answer. + ReadinessClearedBy_READINESS_CLEARED_BY_NOBODY ReadinessClearedBy = 4 +) + +// Enum value maps for ReadinessClearedBy. +var ( + ReadinessClearedBy_name = map[int32]string{ + 0: "READINESS_CLEARED_BY_UNSPECIFIED", + 1: "READINESS_CLEARED_BY_VIEWER", + 2: "READINESS_CLEARED_BY_ORGANIZATION_ADMIN", + 3: "READINESS_CLEARED_BY_PLATFORM_OPERATOR", + 4: "READINESS_CLEARED_BY_NOBODY", + } + ReadinessClearedBy_value = map[string]int32{ + "READINESS_CLEARED_BY_UNSPECIFIED": 0, + "READINESS_CLEARED_BY_VIEWER": 1, + "READINESS_CLEARED_BY_ORGANIZATION_ADMIN": 2, + "READINESS_CLEARED_BY_PLATFORM_OPERATOR": 3, + "READINESS_CLEARED_BY_NOBODY": 4, + } +) + +func (x ReadinessClearedBy) Enum() *ReadinessClearedBy { + p := new(ReadinessClearedBy) + *p = x + return p +} + +func (x ReadinessClearedBy) String() string { + return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x)) +} + +func (ReadinessClearedBy) Descriptor() protoreflect.EnumDescriptor { + return file_saas_accounts_v1_installations_proto_enumTypes[3].Descriptor() +} + +func (ReadinessClearedBy) Type() protoreflect.EnumType { + return &file_saas_accounts_v1_installations_proto_enumTypes[3] +} + +func (x ReadinessClearedBy) Number() protoreflect.EnumNumber { + return protoreflect.EnumNumber(x) +} + +// Deprecated: Use ReadinessClearedBy.Descriptor instead. +func (ReadinessClearedBy) EnumDescriptor() ([]byte, []int) { + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{3} +} + +// ReadinessAction is what clears the condition, named as the act rather than as +// a control, so a surface that cannot offer one still reports the same fact. +type ReadinessAction int32 + +const ( + ReadinessAction_READINESS_ACTION_UNSPECIFIED ReadinessAction = 0 + // No act at this surface clears it. The condition says where it is cleared. + ReadinessAction_READINESS_ACTION_NONE_AT_THIS_SURFACE ReadinessAction = 1 + ReadinessAction_READINESS_ACTION_RETRY_INSTALL_STEP ReadinessAction = 2 + ReadinessAction_READINESS_ACTION_RECONNECT_SOURCE ReadinessAction = 3 + ReadinessAction_READINESS_ACTION_TRANSFER_OWNERSHIP ReadinessAction = 4 + ReadinessAction_READINESS_ACTION_INSTALL_REACHED_MODULE ReadinessAction = 5 + // Wait: the host is expecting an answer and no act brings it forward. + ReadinessAction_READINESS_ACTION_WAIT ReadinessAction = 6 +) + +// Enum value maps for ReadinessAction. +var ( + ReadinessAction_name = map[int32]string{ + 0: "READINESS_ACTION_UNSPECIFIED", + 1: "READINESS_ACTION_NONE_AT_THIS_SURFACE", + 2: "READINESS_ACTION_RETRY_INSTALL_STEP", + 3: "READINESS_ACTION_RECONNECT_SOURCE", + 4: "READINESS_ACTION_TRANSFER_OWNERSHIP", + 5: "READINESS_ACTION_INSTALL_REACHED_MODULE", + 6: "READINESS_ACTION_WAIT", + } + ReadinessAction_value = map[string]int32{ + "READINESS_ACTION_UNSPECIFIED": 0, + "READINESS_ACTION_NONE_AT_THIS_SURFACE": 1, + "READINESS_ACTION_RETRY_INSTALL_STEP": 2, + "READINESS_ACTION_RECONNECT_SOURCE": 3, + "READINESS_ACTION_TRANSFER_OWNERSHIP": 4, + "READINESS_ACTION_INSTALL_REACHED_MODULE": 5, + "READINESS_ACTION_WAIT": 6, + } +) + +func (x ReadinessAction) Enum() *ReadinessAction { + p := new(ReadinessAction) + *p = x + return p +} + +func (x ReadinessAction) String() string { + return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x)) +} + +func (ReadinessAction) Descriptor() protoreflect.EnumDescriptor { + return file_saas_accounts_v1_installations_proto_enumTypes[4].Descriptor() +} + +func (ReadinessAction) Type() protoreflect.EnumType { + return &file_saas_accounts_v1_installations_proto_enumTypes[4] +} + +func (x ReadinessAction) Number() protoreflect.EnumNumber { + return protoreflect.EnumNumber(x) +} + +// Deprecated: Use ReadinessAction.Descriptor instead. +func (ReadinessAction) EnumDescriptor() ([]byte, []int) { + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{4} +} + // Installation is one solution's bound identity in an org. Server-assigned ids; // the browser cannot attest to tenancy, the agent principal, or the scope node. type Installation struct { @@ -1082,6 +1298,14 @@ type OrganizationInstallation struct { // installation; RevokeInstallationFromTeam removes those. GrantedTeams []*CollectionReadGrant `protobuf:"bytes,5,rep,name=granted_teams,json=grantedTeams,proto3" json:"granted_teams,omitempty"` InheritedTeams []*CollectionReadGrant `protobuf:"bytes,6,rep,name=inherited_teams,json=inheritedTeams,proto3" json:"inherited_teams,omitempty"` + // Whether this installation will actually work, and what is unmet if it will + // not. Resolved live from the same facts health is resolved from plus the + // module registry and this organisation's sources; never stored. + Readiness *InstallationReadiness `protobuf:"bytes,7,opt,name=readiness,proto3" json:"readiness,omitempty"` + // The modules this installed target declares it reaches, and this + // organisation's installation of each. Empty for a target whose applied + // manifest declares no operation binding it redeems on a person's behalf. + ReachedModules []*ReachedModule `protobuf:"bytes,8,rep,name=reached_modules,json=reachedModules,proto3" json:"reached_modules,omitempty"` unknownFields protoimpl.UnknownFields sizeCache protoimpl.SizeCache } @@ -1158,6 +1382,248 @@ func (x *OrganizationInstallation) GetInheritedTeams() []*CollectionReadGrant { return nil } +func (x *OrganizationInstallation) GetReadiness() *InstallationReadiness { + if x != nil { + return x.Readiness + } + return nil +} + +func (x *OrganizationInstallation) GetReachedModules() []*ReachedModule { + if x != nil { + return x.ReachedModules + } + return nil +} + +// ReadinessCondition is one thing that is unmet, in the words of whoever owns +// it, with who can clear it and what clears it. +type ReadinessCondition struct { + state protoimpl.MessageState `protogen:"open.v1"` + Kind ReadinessConditionKind `protobuf:"varint,1,opt,name=kind,proto3,enum=saas.accounts.v1.ReadinessConditionKind" json:"kind,omitempty"` + // What the condition is about: the binding, the source, the module. Empty when + // the condition is about the installation as a whole. + Subject string `protobuf:"bytes,2,opt,name=subject,proto3" json:"subject,omitempty"` + // Why it is unmet, as the part of the host that owns the fact words it. Never + // a generic "not ready": the reason is the whole value of the condition. + Detail string `protobuf:"bytes,3,opt,name=detail,proto3" json:"detail,omitempty"` + ClearedBy ReadinessClearedBy `protobuf:"varint,4,opt,name=cleared_by,json=clearedBy,proto3,enum=saas.accounts.v1.ReadinessClearedBy" json:"cleared_by,omitempty"` + Action ReadinessAction `protobuf:"varint,5,opt,name=action,proto3,enum=saas.accounts.v1.ReadinessAction" json:"action,omitempty"` + // The source the action addresses, for RECONNECT_SOURCE. Empty otherwise. + SourceId string `protobuf:"bytes,6,opt,name=source_id,json=sourceId,proto3" json:"source_id,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *ReadinessCondition) Reset() { + *x = ReadinessCondition{} + mi := &file_saas_accounts_v1_installations_proto_msgTypes[13] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *ReadinessCondition) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*ReadinessCondition) ProtoMessage() {} + +func (x *ReadinessCondition) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_installations_proto_msgTypes[13] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use ReadinessCondition.ProtoReflect.Descriptor instead. +func (*ReadinessCondition) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{13} +} + +func (x *ReadinessCondition) GetKind() ReadinessConditionKind { + if x != nil { + return x.Kind + } + return ReadinessConditionKind_READINESS_CONDITION_KIND_UNSPECIFIED +} + +func (x *ReadinessCondition) GetSubject() string { + if x != nil { + return x.Subject + } + return "" +} + +func (x *ReadinessCondition) GetDetail() string { + if x != nil { + return x.Detail + } + return "" +} + +func (x *ReadinessCondition) GetClearedBy() ReadinessClearedBy { + if x != nil { + return x.ClearedBy + } + return ReadinessClearedBy_READINESS_CLEARED_BY_UNSPECIFIED +} + +func (x *ReadinessCondition) GetAction() ReadinessAction { + if x != nil { + return x.Action + } + return ReadinessAction_READINESS_ACTION_UNSPECIFIED +} + +func (x *ReadinessCondition) GetSourceId() string { + if x != nil { + return x.SourceId + } + return "" +} + +// InstallationReadiness is whether the installation will work, which is NOT +// whether its record exists. InstallationHealth answers about the record — it +// is active, its owner is an admin, its standing grant is there — and on +// a validation cell it reported HEALTHY for ten installations while four declared +// operation bindings had derived nothing. Readiness is the other question, and +// it is false while any condition below is unmet. +type InstallationReadiness struct { + state protoimpl.MessageState `protogen:"open.v1"` + // True only when `unmet` is empty. + Ready bool `protobuf:"varint,1,opt,name=ready,proto3" json:"ready,omitempty"` + Unmet []*ReadinessCondition `protobuf:"bytes,2,rep,name=unmet,proto3" json:"unmet,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *InstallationReadiness) Reset() { + *x = InstallationReadiness{} + mi := &file_saas_accounts_v1_installations_proto_msgTypes[14] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *InstallationReadiness) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*InstallationReadiness) ProtoMessage() {} + +func (x *InstallationReadiness) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_installations_proto_msgTypes[14] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use InstallationReadiness.ProtoReflect.Descriptor instead. +func (*InstallationReadiness) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{14} +} + +func (x *InstallationReadiness) GetReady() bool { + if x != nil { + return x.Ready + } + return false +} + +func (x *InstallationReadiness) GetUnmet() []*ReadinessCondition { + if x != nil { + return x.Unmet + } + return nil +} + +// ReachedModule is one module an installed target declares it reaches on the +// asking person's own session, and this organisation's installation of that +// module. +// +// A solution granted to a team was refused by every module it reaches that the +// same team was not granted — four separate refusals on a validation cell, each +// a bare Forbidden. The set is the applied manifest's own declaration, and a +// grant of the solution now CARRIES it: GrantInstallationToTeam derives a grant +// at each reached module from this very set, traceable to the solution's grant +// and revoked with it (CarriedModuleAccess). This field stays a read, so the +// setup page can state the set a grant will carry before anyone grants it. It is +// never a per-module grant step a person performs — that is the trail this ends. +type ReachedModule struct { + state protoimpl.MessageState `protogen:"open.v1"` + // The audience the manifest names: the module reached. + Audience string `protobuf:"bytes,1,opt,name=audience,proto3" json:"audience,omitempty"` + // This organisation's ACTIVE installation of that module, which is where the + // team grant is written. Empty when it has not installed it — then the + // readiness condition says so and no grant is offered. + InstallationId string `protobuf:"bytes,2,opt,name=installation_id,json=installationId,proto3" json:"installation_id,omitempty"` + // The route alias of the installed module, for the reader. Empty with + // installation_id. + RouteAlias string `protobuf:"bytes,3,opt,name=route_alias,json=routeAlias,proto3" json:"route_alias,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *ReachedModule) Reset() { + *x = ReachedModule{} + mi := &file_saas_accounts_v1_installations_proto_msgTypes[15] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *ReachedModule) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*ReachedModule) ProtoMessage() {} + +func (x *ReachedModule) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_installations_proto_msgTypes[15] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use ReachedModule.ProtoReflect.Descriptor instead. +func (*ReachedModule) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{15} +} + +func (x *ReachedModule) GetAudience() string { + if x != nil { + return x.Audience + } + return "" +} + +func (x *ReachedModule) GetInstallationId() string { + if x != nil { + return x.InstallationId + } + return "" +} + +func (x *ReachedModule) GetRouteAlias() string { + if x != nil { + return x.RouteAlias + } + return "" +} + type ListOrganizationInstallationsResponse struct { state protoimpl.MessageState `protogen:"open.v1"` Installations []*OrganizationInstallation `protobuf:"bytes,1,rep,name=installations,proto3" json:"installations,omitempty"` @@ -1169,7 +1635,7 @@ type ListOrganizationInstallationsResponse struct { func (x *ListOrganizationInstallationsResponse) Reset() { *x = ListOrganizationInstallationsResponse{} - mi := &file_saas_accounts_v1_installations_proto_msgTypes[13] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[16] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1181,7 +1647,7 @@ func (x *ListOrganizationInstallationsResponse) String() string { func (*ListOrganizationInstallationsResponse) ProtoMessage() {} func (x *ListOrganizationInstallationsResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_installations_proto_msgTypes[13] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[16] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1194,7 +1660,7 @@ func (x *ListOrganizationInstallationsResponse) ProtoReflect() protoreflect.Mess // Deprecated: Use ListOrganizationInstallationsResponse.ProtoReflect.Descriptor instead. func (*ListOrganizationInstallationsResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{13} + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{16} } func (x *ListOrganizationInstallationsResponse) GetInstallations() []*OrganizationInstallation { @@ -1227,7 +1693,7 @@ type GrantInstallationToTeamRequest struct { func (x *GrantInstallationToTeamRequest) Reset() { *x = GrantInstallationToTeamRequest{} - mi := &file_saas_accounts_v1_installations_proto_msgTypes[14] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[17] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1239,7 +1705,7 @@ func (x *GrantInstallationToTeamRequest) String() string { func (*GrantInstallationToTeamRequest) ProtoMessage() {} func (x *GrantInstallationToTeamRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_installations_proto_msgTypes[14] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[17] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1252,7 +1718,7 @@ func (x *GrantInstallationToTeamRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use GrantInstallationToTeamRequest.ProtoReflect.Descriptor instead. func (*GrantInstallationToTeamRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{14} + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{17} } func (x *GrantInstallationToTeamRequest) GetOrgId() string { @@ -1283,16 +1749,123 @@ func (x *GrantInstallationToTeamRequest) GetRoleId() string { return "" } +// CarriedModuleAccess is one derived grant a solution's grant carried: the +// access the solution declares it consumes on one module it reaches, intersected +// with the role the administrator chose, written at that module's own +// authority-root node. +// +// The role is this host's own, derived and owned by it: it appears in no picker, +// cannot be edited, deleted, assigned organisation-wide or granted by hand, and +// is revoked with the grant that caused it. What it permits is the intersection +// and never the chosen role, which is the whole property — a person's own direct +// reach into a reached module is exactly what the solution declared, not +// whatever the administrator's role would have permitted there. +type CarriedModuleAccess struct { + state protoimpl.MessageState `protogen:"open.v1"` + // The module reached, as the applied manifest's binding names its audience. + Audience string `protobuf:"bytes,1,opt,name=audience,proto3" json:"audience,omitempty"` + // This organisation's installation of that module, whose authority root the + // derived grant is written at. + InstallationId string `protobuf:"bytes,2,opt,name=installation_id,json=installationId,proto3" json:"installation_id,omitempty"` + // The node the derived grant was written at: that installation's authority + // root, resolved from the installation and never supplied by a caller. + ScopePath string `protobuf:"bytes,3,opt,name=scope_path,json=scopePath,proto3" json:"scope_path,omitempty"` + // The derived role. Read it to learn what was carried; never grant it. + RoleId string `protobuf:"bytes,4,opt,name=role_id,json=roleId,proto3" json:"role_id,omitempty"` + // What the derived role permits, each written ":" — the + // declared consumption intersected with the chosen role, in the words the + // declaration uses. + Scopes []string `protobuf:"bytes,5,rep,name=scopes,proto3" json:"scopes,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *CarriedModuleAccess) Reset() { + *x = CarriedModuleAccess{} + mi := &file_saas_accounts_v1_installations_proto_msgTypes[18] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *CarriedModuleAccess) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*CarriedModuleAccess) ProtoMessage() {} + +func (x *CarriedModuleAccess) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_installations_proto_msgTypes[18] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use CarriedModuleAccess.ProtoReflect.Descriptor instead. +func (*CarriedModuleAccess) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{18} +} + +func (x *CarriedModuleAccess) GetAudience() string { + if x != nil { + return x.Audience + } + return "" +} + +func (x *CarriedModuleAccess) GetInstallationId() string { + if x != nil { + return x.InstallationId + } + return "" +} + +func (x *CarriedModuleAccess) GetScopePath() string { + if x != nil { + return x.ScopePath + } + return "" +} + +func (x *CarriedModuleAccess) GetRoleId() string { + if x != nil { + return x.RoleId + } + return "" +} + +func (x *CarriedModuleAccess) GetScopes() []string { + if x != nil { + return x.Scopes + } + return nil +} + type GrantInstallationToTeamResponse struct { - state protoimpl.MessageState `protogen:"open.v1"` - Grant *ScopeGrant `protobuf:"bytes,1,opt,name=grant,proto3" json:"grant,omitempty"` + state protoimpl.MessageState `protogen:"open.v1"` + Grant *ScopeGrant `protobuf:"bytes,1,opt,name=grant,proto3" json:"grant,omitempty"` + // The module access this grant carried, one entry per module the solution + // declares it reaches and this organisation has installed. A team granted a + // solution reaches every module the solution reaches on its members' own + // sessions, by construction: there is no per-module grant step for a person to + // discover by being refused. + Carried []*CarriedModuleAccess `protobuf:"bytes,2,rep,name=carried,proto3" json:"carried,omitempty"` + // Where it carried nothing, and why — in the same response as the grant, + // because a refusal a person learns about by hitting a Forbidden later is the + // failure this replaces. Stated in the same condition vocabulary the setup + // page reads, so one reader works through one list. + Unmet []*ReadinessCondition `protobuf:"bytes,3,rep,name=unmet,proto3" json:"unmet,omitempty"` unknownFields protoimpl.UnknownFields sizeCache protoimpl.SizeCache } func (x *GrantInstallationToTeamResponse) Reset() { *x = GrantInstallationToTeamResponse{} - mi := &file_saas_accounts_v1_installations_proto_msgTypes[15] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[19] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1304,7 +1877,7 @@ func (x *GrantInstallationToTeamResponse) String() string { func (*GrantInstallationToTeamResponse) ProtoMessage() {} func (x *GrantInstallationToTeamResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_installations_proto_msgTypes[15] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[19] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1317,7 +1890,7 @@ func (x *GrantInstallationToTeamResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use GrantInstallationToTeamResponse.ProtoReflect.Descriptor instead. func (*GrantInstallationToTeamResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{15} + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{19} } func (x *GrantInstallationToTeamResponse) GetGrant() *ScopeGrant { @@ -1327,6 +1900,20 @@ func (x *GrantInstallationToTeamResponse) GetGrant() *ScopeGrant { return nil } +func (x *GrantInstallationToTeamResponse) GetCarried() []*CarriedModuleAccess { + if x != nil { + return x.Carried + } + return nil +} + +func (x *GrantInstallationToTeamResponse) GetUnmet() []*ReadinessCondition { + if x != nil { + return x.Unmet + } + return nil +} + type RevokeInstallationFromTeamRequest struct { state protoimpl.MessageState `protogen:"open.v1"` OrgId string `protobuf:"bytes,1,opt,name=org_id,json=orgId,proto3" json:"org_id,omitempty"` @@ -1341,7 +1928,7 @@ type RevokeInstallationFromTeamRequest struct { func (x *RevokeInstallationFromTeamRequest) Reset() { *x = RevokeInstallationFromTeamRequest{} - mi := &file_saas_accounts_v1_installations_proto_msgTypes[16] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[20] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1353,7 +1940,7 @@ func (x *RevokeInstallationFromTeamRequest) String() string { func (*RevokeInstallationFromTeamRequest) ProtoMessage() {} func (x *RevokeInstallationFromTeamRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_installations_proto_msgTypes[16] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[20] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1366,7 +1953,7 @@ func (x *RevokeInstallationFromTeamRequest) ProtoReflect() protoreflect.Message // Deprecated: Use RevokeInstallationFromTeamRequest.ProtoReflect.Descriptor instead. func (*RevokeInstallationFromTeamRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{16} + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{20} } func (x *RevokeInstallationFromTeamRequest) GetOrgId() string { @@ -1422,14 +2009,20 @@ type AvailableSolution struct { // target. A catalogue shows it as installed rather than offering it twice; the // unique index over (org_id, target_id) would refuse the second install anyway, // and an administrator should not have to discover that by being refused. - Installed bool `protobuf:"varint,9,opt,name=installed,proto3" json:"installed,omitempty"` + Installed bool `protobuf:"varint,9,opt,name=installed,proto3" json:"installed,omitempty"` + // What this target is, as its registration declared it: `module` or + // `solution`. Read from the registration in the same statement as the rest of + // the row; a reader is told rather than inferring it from the alias, because a + // module and a solution are set up differently and the page says which it is. + // Empty when the registration declared neither. + Kind string `protobuf:"bytes,10,opt,name=kind,proto3" json:"kind,omitempty"` unknownFields protoimpl.UnknownFields sizeCache protoimpl.SizeCache } func (x *AvailableSolution) Reset() { *x = AvailableSolution{} - mi := &file_saas_accounts_v1_installations_proto_msgTypes[17] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[21] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1441,7 +2034,7 @@ func (x *AvailableSolution) String() string { func (*AvailableSolution) ProtoMessage() {} func (x *AvailableSolution) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_installations_proto_msgTypes[17] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[21] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1454,7 +2047,7 @@ func (x *AvailableSolution) ProtoReflect() protoreflect.Message { // Deprecated: Use AvailableSolution.ProtoReflect.Descriptor instead. func (*AvailableSolution) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{17} + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{21} } func (x *AvailableSolution) GetTargetId() string { @@ -1520,6 +2113,13 @@ func (x *AvailableSolution) GetInstalled() bool { return false } +func (x *AvailableSolution) GetKind() string { + if x != nil { + return x.Kind + } + return "" +} + type ListAvailableSolutionsRequest struct { state protoimpl.MessageState `protogen:"open.v1"` OrgId string `protobuf:"bytes,1,opt,name=org_id,json=orgId,proto3" json:"org_id,omitempty"` @@ -1533,7 +2133,7 @@ type ListAvailableSolutionsRequest struct { func (x *ListAvailableSolutionsRequest) Reset() { *x = ListAvailableSolutionsRequest{} - mi := &file_saas_accounts_v1_installations_proto_msgTypes[18] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[22] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1545,7 +2145,7 @@ func (x *ListAvailableSolutionsRequest) String() string { func (*ListAvailableSolutionsRequest) ProtoMessage() {} func (x *ListAvailableSolutionsRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_installations_proto_msgTypes[18] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[22] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1558,7 +2158,7 @@ func (x *ListAvailableSolutionsRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use ListAvailableSolutionsRequest.ProtoReflect.Descriptor instead. func (*ListAvailableSolutionsRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{18} + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{22} } func (x *ListAvailableSolutionsRequest) GetOrgId() string { @@ -1592,7 +2192,7 @@ type ListAvailableSolutionsResponse struct { func (x *ListAvailableSolutionsResponse) Reset() { *x = ListAvailableSolutionsResponse{} - mi := &file_saas_accounts_v1_installations_proto_msgTypes[19] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[23] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -1604,7 +2204,7 @@ func (x *ListAvailableSolutionsResponse) String() string { func (*ListAvailableSolutionsResponse) ProtoMessage() {} func (x *ListAvailableSolutionsResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_installations_proto_msgTypes[19] + mi := &file_saas_accounts_v1_installations_proto_msgTypes[23] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -1617,7 +2217,7 @@ func (x *ListAvailableSolutionsResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ListAvailableSolutionsResponse.ProtoReflect.Descriptor instead. func (*ListAvailableSolutionsResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{19} + return file_saas_accounts_v1_installations_proto_rawDescGZIP(), []int{23} } func (x *ListAvailableSolutionsResponse) GetSolutions() []*AvailableSolution { @@ -1710,14 +2310,32 @@ const file_saas_accounts_v1_installations_proto_rawDesc = "" + "\tpage_size\x18\x02 \x01(\x05B\n" + "\xbaH\a\x1a\x05\x18\xf4\x03(\x00R\bpageSize\x12\x1d\n" + "\n" + - "page_token\x18\x03 \x01(\tR\tpageToken\"\x9d\x03\n" + + "page_token\x18\x03 \x01(\tR\tpageToken\"\xae\x04\n" + "\x18OrganizationInstallation\x12B\n" + "\finstallation\x18\x01 \x01(\v2\x1e.saas.accounts.v1.InstallationR\finstallation\x12<\n" + "\x06health\x18\x02 \x01(\x0e2$.saas.accounts.v1.InstallationHealthR\x06health\x12;\n" + "\x06target\x18\x03 \x01(\v2#.saas.accounts.v1.AvailableSolutionR\x06target\x12&\n" + "\x0froot_scope_path\x18\x04 \x01(\tR\rrootScopePath\x12J\n" + "\rgranted_teams\x18\x05 \x03(\v2%.saas.accounts.v1.CollectionReadGrantR\fgrantedTeams\x12N\n" + - "\x0finherited_teams\x18\x06 \x03(\v2%.saas.accounts.v1.CollectionReadGrantR\x0einheritedTeams\"\xa1\x01\n" + + "\x0finherited_teams\x18\x06 \x03(\v2%.saas.accounts.v1.CollectionReadGrantR\x0einheritedTeams\x12E\n" + + "\treadiness\x18\a \x01(\v2'.saas.accounts.v1.InstallationReadinessR\treadiness\x12H\n" + + "\x0freached_modules\x18\b \x03(\v2\x1f.saas.accounts.v1.ReachedModuleR\x0ereachedModules\"\xa1\x02\n" + + "\x12ReadinessCondition\x12<\n" + + "\x04kind\x18\x01 \x01(\x0e2(.saas.accounts.v1.ReadinessConditionKindR\x04kind\x12\x18\n" + + "\asubject\x18\x02 \x01(\tR\asubject\x12\x16\n" + + "\x06detail\x18\x03 \x01(\tR\x06detail\x12C\n" + + "\n" + + "cleared_by\x18\x04 \x01(\x0e2$.saas.accounts.v1.ReadinessClearedByR\tclearedBy\x129\n" + + "\x06action\x18\x05 \x01(\x0e2!.saas.accounts.v1.ReadinessActionR\x06action\x12\x1b\n" + + "\tsource_id\x18\x06 \x01(\tR\bsourceId\"i\n" + + "\x15InstallationReadiness\x12\x14\n" + + "\x05ready\x18\x01 \x01(\bR\x05ready\x12:\n" + + "\x05unmet\x18\x02 \x03(\v2$.saas.accounts.v1.ReadinessConditionR\x05unmet\"u\n" + + "\rReachedModule\x12\x1a\n" + + "\baudience\x18\x01 \x01(\tR\baudience\x12'\n" + + "\x0finstallation_id\x18\x02 \x01(\tR\x0einstallationId\x12\x1f\n" + + "\vroute_alias\x18\x03 \x01(\tR\n" + + "routeAlias\"\xa1\x01\n" + "%ListOrganizationInstallationsResponse\x12P\n" + "\rinstallations\x18\x01 \x03(\v2*.saas.accounts.v1.OrganizationInstallationR\rinstallations\x12&\n" + "\x0fnext_page_token\x18\x02 \x01(\tR\rnextPageToken\"\xba\x01\n" + @@ -1725,14 +2343,23 @@ const file_saas_accounts_v1_installations_proto_rawDesc = "" + "\x06org_id\x18\x01 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x05orgId\x121\n" + "\x0finstallation_id\x18\x02 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x0einstallationId\x12!\n" + "\ateam_id\x18\x03 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x06teamId\x12!\n" + - "\arole_id\x18\x04 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x06roleId\"U\n" + + "\arole_id\x18\x04 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x06roleId\"\xaa\x01\n" + + "\x13CarriedModuleAccess\x12\x1a\n" + + "\baudience\x18\x01 \x01(\tR\baudience\x12'\n" + + "\x0finstallation_id\x18\x02 \x01(\tR\x0einstallationId\x12\x1d\n" + + "\n" + + "scope_path\x18\x03 \x01(\tR\tscopePath\x12\x17\n" + + "\arole_id\x18\x04 \x01(\tR\x06roleId\x12\x16\n" + + "\x06scopes\x18\x05 \x03(\tR\x06scopes\"\xd2\x01\n" + "\x1fGrantInstallationToTeamResponse\x122\n" + - "\x05grant\x18\x01 \x01(\v2\x1c.saas.accounts.v1.ScopeGrantR\x05grant\"\xbd\x01\n" + + "\x05grant\x18\x01 \x01(\v2\x1c.saas.accounts.v1.ScopeGrantR\x05grant\x12?\n" + + "\acarried\x18\x02 \x03(\v2%.saas.accounts.v1.CarriedModuleAccessR\acarried\x12:\n" + + "\x05unmet\x18\x03 \x03(\v2$.saas.accounts.v1.ReadinessConditionR\x05unmet\"\xbd\x01\n" + "!RevokeInstallationFromTeamRequest\x12\x1f\n" + "\x06org_id\x18\x01 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x05orgId\x121\n" + "\x0finstallation_id\x18\x02 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x0einstallationId\x12!\n" + "\ateam_id\x18\x03 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x06teamId\x12!\n" + - "\arole_id\x18\x04 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x06roleId\"\xed\x02\n" + + "\arole_id\x18\x04 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x06roleId\"\x8a\x03\n" + "\x11AvailableSolution\x12%\n" + "\ttarget_id\x18\x01 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\btargetId\x12\x1d\n" + "\n" + @@ -1744,7 +2371,9 @@ const file_saas_accounts_v1_installations_proto_rawDesc = "" + "\x0frelease_version\x18\x06 \x01(\tR\x0ereleaseVersion\x12+\n" + "\x11opened_generation\x18\a \x01(\x04R\x10openedGeneration\x12-\n" + "\x12applied_generation\x18\b \x01(\x04R\x11appliedGeneration\x12\x1c\n" + - "\tinstalled\x18\t \x01(\bR\tinstalled\"\x88\x01\n" + + "\tinstalled\x18\t \x01(\bR\tinstalled\x12\x1b\n" + + "\x04kind\x18\n" + + " \x01(\tB\a\xbaH\x04r\x02\x18 R\x04kind\"\x88\x01\n" + "\x1dListAvailableSolutionsRequest\x12\x1f\n" + "\x06org_id\x18\x01 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x05orgId\x12'\n" + "\tpage_size\x18\x02 \x01(\x05B\n" + @@ -1766,7 +2395,31 @@ const file_saas_accounts_v1_installations_proto_rawDesc = "" + "%INSTALLATION_HEALTH_NO_ELIGIBLE_OWNER\x10\x02\x12%\n" + "!INSTALLATION_HEALTH_AGENT_REVOKED\x10\x03\x12&\n" + "\"INSTALLATION_HEALTH_AGENT_DISABLED\x10\x04\x12.\n" + - "*INSTALLATION_HEALTH_STANDING_GRANT_MISSING\x10\x052\xaa\x12\n" + + "*INSTALLATION_HEALTH_STANDING_GRANT_MISSING\x10\x05*\xf3\x03\n" + + "\x16ReadinessConditionKind\x12(\n" + + "$READINESS_CONDITION_KIND_UNSPECIFIED\x10\x00\x121\n" + + "-READINESS_CONDITION_KIND_INSTALL_STEP_PENDING\x10\x01\x120\n" + + ",READINESS_CONDITION_KIND_INSTALL_STEP_FAILED\x10\x02\x12-\n" + + ")READINESS_CONDITION_KIND_RECORD_UNHEALTHY\x10\x03\x125\n" + + "1READINESS_CONDITION_KIND_MODULE_PRINCIPAL_OMITTED\x10\x04\x126\n" + + "2READINESS_CONDITION_KIND_OPERATION_BINDING_OMITTED\x10\x05\x121\n" + + "-READINESS_CONDITION_KIND_SOURCE_NOT_DELEGATED\x10\x06\x129\n" + + "5READINESS_CONDITION_KIND_REACHED_MODULE_NOT_INSTALLED\x10\a\x12>\n" + + ":READINESS_CONDITION_KIND_CARRIED_MODULE_ACCESS_NOT_DERIVED\x10\b*\xd5\x01\n" + + "\x12ReadinessClearedBy\x12$\n" + + " READINESS_CLEARED_BY_UNSPECIFIED\x10\x00\x12\x1f\n" + + "\x1bREADINESS_CLEARED_BY_VIEWER\x10\x01\x12+\n" + + "'READINESS_CLEARED_BY_ORGANIZATION_ADMIN\x10\x02\x12*\n" + + "&READINESS_CLEARED_BY_PLATFORM_OPERATOR\x10\x03\x12\x1f\n" + + "\x1bREADINESS_CLEARED_BY_NOBODY\x10\x04*\x9f\x02\n" + + "\x0fReadinessAction\x12 \n" + + "\x1cREADINESS_ACTION_UNSPECIFIED\x10\x00\x12)\n" + + "%READINESS_ACTION_NONE_AT_THIS_SURFACE\x10\x01\x12'\n" + + "#READINESS_ACTION_RETRY_INSTALL_STEP\x10\x02\x12%\n" + + "!READINESS_ACTION_RECONNECT_SOURCE\x10\x03\x12'\n" + + "#READINESS_ACTION_TRANSFER_OWNERSHIP\x10\x04\x12+\n" + + "'READINESS_ACTION_INSTALL_REACHED_MODULE\x10\x05\x12\x19\n" + + "\x15READINESS_ACTION_WAIT\x10\x062\xaa\x12\n" + "\x13InstallationService\x12\xba\x01\n" + "\x0fInstallSolution\x12(.saas.accounts.v1.InstallSolutionRequest\x1a\x1e.saas.accounts.v1.Installation\"]\xc2\xf3\x18=\b\x02\x10\x04*\f\n" + "\x06org_id\x10\x02\x18\x010\x01:\x1d\n" + @@ -1810,81 +2463,96 @@ func file_saas_accounts_v1_installations_proto_rawDescGZIP() []byte { return file_saas_accounts_v1_installations_proto_rawDescData } -var file_saas_accounts_v1_installations_proto_enumTypes = make([]protoimpl.EnumInfo, 2) -var file_saas_accounts_v1_installations_proto_msgTypes = make([]protoimpl.MessageInfo, 20) +var file_saas_accounts_v1_installations_proto_enumTypes = make([]protoimpl.EnumInfo, 5) +var file_saas_accounts_v1_installations_proto_msgTypes = make([]protoimpl.MessageInfo, 24) var file_saas_accounts_v1_installations_proto_goTypes = []any{ (InstallationStatus)(0), // 0: saas.accounts.v1.InstallationStatus (InstallationHealth)(0), // 1: saas.accounts.v1.InstallationHealth - (*Installation)(nil), // 2: saas.accounts.v1.Installation - (*InstallSolutionRequest)(nil), // 3: saas.accounts.v1.InstallSolutionRequest - (*NarrowInstallationRequest)(nil), // 4: saas.accounts.v1.NarrowInstallationRequest - (*RetryInstallationRequest)(nil), // 5: saas.accounts.v1.RetryInstallationRequest - (*UninstallSolutionRequest)(nil), // 6: saas.accounts.v1.UninstallSolutionRequest - (*TransferInstallationOwnershipRequest)(nil), // 7: saas.accounts.v1.TransferInstallationOwnershipRequest - (*GetInstallationRequest)(nil), // 8: saas.accounts.v1.GetInstallationRequest - (*GetInstallationResponse)(nil), // 9: saas.accounts.v1.GetInstallationResponse - (*ListInstallationsRequest)(nil), // 10: saas.accounts.v1.ListInstallationsRequest - (*InstallationSummary)(nil), // 11: saas.accounts.v1.InstallationSummary - (*ListInstallationsResponse)(nil), // 12: saas.accounts.v1.ListInstallationsResponse - (*ListOrganizationInstallationsRequest)(nil), // 13: saas.accounts.v1.ListOrganizationInstallationsRequest - (*OrganizationInstallation)(nil), // 14: saas.accounts.v1.OrganizationInstallation - (*ListOrganizationInstallationsResponse)(nil), // 15: saas.accounts.v1.ListOrganizationInstallationsResponse - (*GrantInstallationToTeamRequest)(nil), // 16: saas.accounts.v1.GrantInstallationToTeamRequest - (*GrantInstallationToTeamResponse)(nil), // 17: saas.accounts.v1.GrantInstallationToTeamResponse - (*RevokeInstallationFromTeamRequest)(nil), // 18: saas.accounts.v1.RevokeInstallationFromTeamRequest - (*AvailableSolution)(nil), // 19: saas.accounts.v1.AvailableSolution - (*ListAvailableSolutionsRequest)(nil), // 20: saas.accounts.v1.ListAvailableSolutionsRequest - (*ListAvailableSolutionsResponse)(nil), // 21: saas.accounts.v1.ListAvailableSolutionsResponse - (*timestamppb.Timestamp)(nil), // 22: google.protobuf.Timestamp - (*CollectionReadGrant)(nil), // 23: saas.accounts.v1.CollectionReadGrant - (*ScopeGrant)(nil), // 24: saas.accounts.v1.ScopeGrant - (*emptypb.Empty)(nil), // 25: google.protobuf.Empty + (ReadinessConditionKind)(0), // 2: saas.accounts.v1.ReadinessConditionKind + (ReadinessClearedBy)(0), // 3: saas.accounts.v1.ReadinessClearedBy + (ReadinessAction)(0), // 4: saas.accounts.v1.ReadinessAction + (*Installation)(nil), // 5: saas.accounts.v1.Installation + (*InstallSolutionRequest)(nil), // 6: saas.accounts.v1.InstallSolutionRequest + (*NarrowInstallationRequest)(nil), // 7: saas.accounts.v1.NarrowInstallationRequest + (*RetryInstallationRequest)(nil), // 8: saas.accounts.v1.RetryInstallationRequest + (*UninstallSolutionRequest)(nil), // 9: saas.accounts.v1.UninstallSolutionRequest + (*TransferInstallationOwnershipRequest)(nil), // 10: saas.accounts.v1.TransferInstallationOwnershipRequest + (*GetInstallationRequest)(nil), // 11: saas.accounts.v1.GetInstallationRequest + (*GetInstallationResponse)(nil), // 12: saas.accounts.v1.GetInstallationResponse + (*ListInstallationsRequest)(nil), // 13: saas.accounts.v1.ListInstallationsRequest + (*InstallationSummary)(nil), // 14: saas.accounts.v1.InstallationSummary + (*ListInstallationsResponse)(nil), // 15: saas.accounts.v1.ListInstallationsResponse + (*ListOrganizationInstallationsRequest)(nil), // 16: saas.accounts.v1.ListOrganizationInstallationsRequest + (*OrganizationInstallation)(nil), // 17: saas.accounts.v1.OrganizationInstallation + (*ReadinessCondition)(nil), // 18: saas.accounts.v1.ReadinessCondition + (*InstallationReadiness)(nil), // 19: saas.accounts.v1.InstallationReadiness + (*ReachedModule)(nil), // 20: saas.accounts.v1.ReachedModule + (*ListOrganizationInstallationsResponse)(nil), // 21: saas.accounts.v1.ListOrganizationInstallationsResponse + (*GrantInstallationToTeamRequest)(nil), // 22: saas.accounts.v1.GrantInstallationToTeamRequest + (*CarriedModuleAccess)(nil), // 23: saas.accounts.v1.CarriedModuleAccess + (*GrantInstallationToTeamResponse)(nil), // 24: saas.accounts.v1.GrantInstallationToTeamResponse + (*RevokeInstallationFromTeamRequest)(nil), // 25: saas.accounts.v1.RevokeInstallationFromTeamRequest + (*AvailableSolution)(nil), // 26: saas.accounts.v1.AvailableSolution + (*ListAvailableSolutionsRequest)(nil), // 27: saas.accounts.v1.ListAvailableSolutionsRequest + (*ListAvailableSolutionsResponse)(nil), // 28: saas.accounts.v1.ListAvailableSolutionsResponse + (*timestamppb.Timestamp)(nil), // 29: google.protobuf.Timestamp + (*CollectionReadGrant)(nil), // 30: saas.accounts.v1.CollectionReadGrant + (*ScopeGrant)(nil), // 31: saas.accounts.v1.ScopeGrant + (*emptypb.Empty)(nil), // 32: google.protobuf.Empty } var file_saas_accounts_v1_installations_proto_depIdxs = []int32{ 0, // 0: saas.accounts.v1.Installation.status:type_name -> saas.accounts.v1.InstallationStatus - 22, // 1: saas.accounts.v1.Installation.created_at:type_name -> google.protobuf.Timestamp - 22, // 2: saas.accounts.v1.Installation.revoked_at:type_name -> google.protobuf.Timestamp - 2, // 3: saas.accounts.v1.GetInstallationResponse.installation:type_name -> saas.accounts.v1.Installation + 29, // 1: saas.accounts.v1.Installation.created_at:type_name -> google.protobuf.Timestamp + 29, // 2: saas.accounts.v1.Installation.revoked_at:type_name -> google.protobuf.Timestamp + 5, // 3: saas.accounts.v1.GetInstallationResponse.installation:type_name -> saas.accounts.v1.Installation 1, // 4: saas.accounts.v1.GetInstallationResponse.health:type_name -> saas.accounts.v1.InstallationHealth 0, // 5: saas.accounts.v1.ListInstallationsRequest.status:type_name -> saas.accounts.v1.InstallationStatus - 2, // 6: saas.accounts.v1.InstallationSummary.installation:type_name -> saas.accounts.v1.Installation + 5, // 6: saas.accounts.v1.InstallationSummary.installation:type_name -> saas.accounts.v1.Installation 1, // 7: saas.accounts.v1.InstallationSummary.health:type_name -> saas.accounts.v1.InstallationHealth - 11, // 8: saas.accounts.v1.ListInstallationsResponse.installations:type_name -> saas.accounts.v1.InstallationSummary - 2, // 9: saas.accounts.v1.OrganizationInstallation.installation:type_name -> saas.accounts.v1.Installation + 14, // 8: saas.accounts.v1.ListInstallationsResponse.installations:type_name -> saas.accounts.v1.InstallationSummary + 5, // 9: saas.accounts.v1.OrganizationInstallation.installation:type_name -> saas.accounts.v1.Installation 1, // 10: saas.accounts.v1.OrganizationInstallation.health:type_name -> saas.accounts.v1.InstallationHealth - 19, // 11: saas.accounts.v1.OrganizationInstallation.target:type_name -> saas.accounts.v1.AvailableSolution - 23, // 12: saas.accounts.v1.OrganizationInstallation.granted_teams:type_name -> saas.accounts.v1.CollectionReadGrant - 23, // 13: saas.accounts.v1.OrganizationInstallation.inherited_teams:type_name -> saas.accounts.v1.CollectionReadGrant - 14, // 14: saas.accounts.v1.ListOrganizationInstallationsResponse.installations:type_name -> saas.accounts.v1.OrganizationInstallation - 24, // 15: saas.accounts.v1.GrantInstallationToTeamResponse.grant:type_name -> saas.accounts.v1.ScopeGrant - 19, // 16: saas.accounts.v1.ListAvailableSolutionsResponse.solutions:type_name -> saas.accounts.v1.AvailableSolution - 3, // 17: saas.accounts.v1.InstallationService.InstallSolution:input_type -> saas.accounts.v1.InstallSolutionRequest - 6, // 18: saas.accounts.v1.InstallationService.UninstallSolution:input_type -> saas.accounts.v1.UninstallSolutionRequest - 4, // 19: saas.accounts.v1.InstallationService.NarrowInstallation:input_type -> saas.accounts.v1.NarrowInstallationRequest - 5, // 20: saas.accounts.v1.InstallationService.RetryInstallation:input_type -> saas.accounts.v1.RetryInstallationRequest - 7, // 21: saas.accounts.v1.InstallationService.TransferInstallationOwnership:input_type -> saas.accounts.v1.TransferInstallationOwnershipRequest - 8, // 22: saas.accounts.v1.InstallationService.GetInstallation:input_type -> saas.accounts.v1.GetInstallationRequest - 10, // 23: saas.accounts.v1.InstallationService.ListInstallations:input_type -> saas.accounts.v1.ListInstallationsRequest - 20, // 24: saas.accounts.v1.InstallationService.ListAvailableSolutions:input_type -> saas.accounts.v1.ListAvailableSolutionsRequest - 13, // 25: saas.accounts.v1.InstallationService.ListOrganizationInstallations:input_type -> saas.accounts.v1.ListOrganizationInstallationsRequest - 16, // 26: saas.accounts.v1.InstallationService.GrantInstallationToTeam:input_type -> saas.accounts.v1.GrantInstallationToTeamRequest - 18, // 27: saas.accounts.v1.InstallationService.RevokeInstallationFromTeam:input_type -> saas.accounts.v1.RevokeInstallationFromTeamRequest - 2, // 28: saas.accounts.v1.InstallationService.InstallSolution:output_type -> saas.accounts.v1.Installation - 25, // 29: saas.accounts.v1.InstallationService.UninstallSolution:output_type -> google.protobuf.Empty - 25, // 30: saas.accounts.v1.InstallationService.NarrowInstallation:output_type -> google.protobuf.Empty - 2, // 31: saas.accounts.v1.InstallationService.RetryInstallation:output_type -> saas.accounts.v1.Installation - 2, // 32: saas.accounts.v1.InstallationService.TransferInstallationOwnership:output_type -> saas.accounts.v1.Installation - 9, // 33: saas.accounts.v1.InstallationService.GetInstallation:output_type -> saas.accounts.v1.GetInstallationResponse - 12, // 34: saas.accounts.v1.InstallationService.ListInstallations:output_type -> saas.accounts.v1.ListInstallationsResponse - 21, // 35: saas.accounts.v1.InstallationService.ListAvailableSolutions:output_type -> saas.accounts.v1.ListAvailableSolutionsResponse - 15, // 36: saas.accounts.v1.InstallationService.ListOrganizationInstallations:output_type -> saas.accounts.v1.ListOrganizationInstallationsResponse - 17, // 37: saas.accounts.v1.InstallationService.GrantInstallationToTeam:output_type -> saas.accounts.v1.GrantInstallationToTeamResponse - 25, // 38: saas.accounts.v1.InstallationService.RevokeInstallationFromTeam:output_type -> google.protobuf.Empty - 28, // [28:39] is the sub-list for method output_type - 17, // [17:28] is the sub-list for method input_type - 17, // [17:17] is the sub-list for extension type_name - 17, // [17:17] is the sub-list for extension extendee - 0, // [0:17] is the sub-list for field type_name + 26, // 11: saas.accounts.v1.OrganizationInstallation.target:type_name -> saas.accounts.v1.AvailableSolution + 30, // 12: saas.accounts.v1.OrganizationInstallation.granted_teams:type_name -> saas.accounts.v1.CollectionReadGrant + 30, // 13: saas.accounts.v1.OrganizationInstallation.inherited_teams:type_name -> saas.accounts.v1.CollectionReadGrant + 19, // 14: saas.accounts.v1.OrganizationInstallation.readiness:type_name -> saas.accounts.v1.InstallationReadiness + 20, // 15: saas.accounts.v1.OrganizationInstallation.reached_modules:type_name -> saas.accounts.v1.ReachedModule + 2, // 16: saas.accounts.v1.ReadinessCondition.kind:type_name -> saas.accounts.v1.ReadinessConditionKind + 3, // 17: saas.accounts.v1.ReadinessCondition.cleared_by:type_name -> saas.accounts.v1.ReadinessClearedBy + 4, // 18: saas.accounts.v1.ReadinessCondition.action:type_name -> saas.accounts.v1.ReadinessAction + 18, // 19: saas.accounts.v1.InstallationReadiness.unmet:type_name -> saas.accounts.v1.ReadinessCondition + 17, // 20: saas.accounts.v1.ListOrganizationInstallationsResponse.installations:type_name -> saas.accounts.v1.OrganizationInstallation + 31, // 21: saas.accounts.v1.GrantInstallationToTeamResponse.grant:type_name -> saas.accounts.v1.ScopeGrant + 23, // 22: saas.accounts.v1.GrantInstallationToTeamResponse.carried:type_name -> saas.accounts.v1.CarriedModuleAccess + 18, // 23: saas.accounts.v1.GrantInstallationToTeamResponse.unmet:type_name -> saas.accounts.v1.ReadinessCondition + 26, // 24: saas.accounts.v1.ListAvailableSolutionsResponse.solutions:type_name -> saas.accounts.v1.AvailableSolution + 6, // 25: saas.accounts.v1.InstallationService.InstallSolution:input_type -> saas.accounts.v1.InstallSolutionRequest + 9, // 26: saas.accounts.v1.InstallationService.UninstallSolution:input_type -> saas.accounts.v1.UninstallSolutionRequest + 7, // 27: saas.accounts.v1.InstallationService.NarrowInstallation:input_type -> saas.accounts.v1.NarrowInstallationRequest + 8, // 28: saas.accounts.v1.InstallationService.RetryInstallation:input_type -> saas.accounts.v1.RetryInstallationRequest + 10, // 29: saas.accounts.v1.InstallationService.TransferInstallationOwnership:input_type -> saas.accounts.v1.TransferInstallationOwnershipRequest + 11, // 30: saas.accounts.v1.InstallationService.GetInstallation:input_type -> saas.accounts.v1.GetInstallationRequest + 13, // 31: saas.accounts.v1.InstallationService.ListInstallations:input_type -> saas.accounts.v1.ListInstallationsRequest + 27, // 32: saas.accounts.v1.InstallationService.ListAvailableSolutions:input_type -> saas.accounts.v1.ListAvailableSolutionsRequest + 16, // 33: saas.accounts.v1.InstallationService.ListOrganizationInstallations:input_type -> saas.accounts.v1.ListOrganizationInstallationsRequest + 22, // 34: saas.accounts.v1.InstallationService.GrantInstallationToTeam:input_type -> saas.accounts.v1.GrantInstallationToTeamRequest + 25, // 35: saas.accounts.v1.InstallationService.RevokeInstallationFromTeam:input_type -> saas.accounts.v1.RevokeInstallationFromTeamRequest + 5, // 36: saas.accounts.v1.InstallationService.InstallSolution:output_type -> saas.accounts.v1.Installation + 32, // 37: saas.accounts.v1.InstallationService.UninstallSolution:output_type -> google.protobuf.Empty + 32, // 38: saas.accounts.v1.InstallationService.NarrowInstallation:output_type -> google.protobuf.Empty + 5, // 39: saas.accounts.v1.InstallationService.RetryInstallation:output_type -> saas.accounts.v1.Installation + 5, // 40: saas.accounts.v1.InstallationService.TransferInstallationOwnership:output_type -> saas.accounts.v1.Installation + 12, // 41: saas.accounts.v1.InstallationService.GetInstallation:output_type -> saas.accounts.v1.GetInstallationResponse + 15, // 42: saas.accounts.v1.InstallationService.ListInstallations:output_type -> saas.accounts.v1.ListInstallationsResponse + 28, // 43: saas.accounts.v1.InstallationService.ListAvailableSolutions:output_type -> saas.accounts.v1.ListAvailableSolutionsResponse + 21, // 44: saas.accounts.v1.InstallationService.ListOrganizationInstallations:output_type -> saas.accounts.v1.ListOrganizationInstallationsResponse + 24, // 45: saas.accounts.v1.InstallationService.GrantInstallationToTeam:output_type -> saas.accounts.v1.GrantInstallationToTeamResponse + 32, // 46: saas.accounts.v1.InstallationService.RevokeInstallationFromTeam:output_type -> google.protobuf.Empty + 36, // [36:47] is the sub-list for method output_type + 25, // [25:36] is the sub-list for method input_type + 25, // [25:25] is the sub-list for extension type_name + 25, // [25:25] is the sub-list for extension extendee + 0, // [0:25] is the sub-list for field type_name } func init() { file_saas_accounts_v1_installations_proto_init() } @@ -1900,8 +2568,8 @@ func file_saas_accounts_v1_installations_proto_init() { File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: unsafe.Slice(unsafe.StringData(file_saas_accounts_v1_installations_proto_rawDesc), len(file_saas_accounts_v1_installations_proto_rawDesc)), - NumEnums: 2, - NumMessages: 20, + NumEnums: 5, + NumMessages: 24, NumExtensions: 0, NumServices: 1, }, diff --git a/gen/saas/accounts/v1/invitations.pb.go b/gen/saas/accounts/v1/invitations.pb.go index a5b27a2..2d6a1c0 100644 --- a/gen/saas/accounts/v1/invitations.pb.go +++ b/gen/saas/accounts/v1/invitations.pb.go @@ -324,11 +324,16 @@ func (x *Invitation) GetSendCount() uint32 { } type InvitationSummary struct { - state protoimpl.MessageState `protogen:"open.v1"` - Status InvitationStatus `protobuf:"varint,1,opt,name=status,proto3,enum=saas.accounts.v1.InvitationStatus" json:"status,omitempty"` - Role InvitationRole `protobuf:"varint,2,opt,name=role,proto3,enum=saas.accounts.v1.InvitationRole" json:"role,omitempty"` - EmailHint string `protobuf:"bytes,3,opt,name=email_hint,json=emailHint,proto3" json:"email_hint,omitempty"` - ExpiresAt *timestamppb.Timestamp `protobuf:"bytes,4,opt,name=expires_at,json=expiresAt,proto3" json:"expires_at,omitempty"` + state protoimpl.MessageState `protogen:"open.v1"` + Status InvitationStatus `protobuf:"varint,1,opt,name=status,proto3,enum=saas.accounts.v1.InvitationStatus" json:"status,omitempty"` + Role InvitationRole `protobuf:"varint,2,opt,name=role,proto3,enum=saas.accounts.v1.InvitationRole" json:"role,omitempty"` + EmailHint string `protobuf:"bytes,3,opt,name=email_hint,json=emailHint,proto3" json:"email_hint,omitempty"` + ExpiresAt *timestamppb.Timestamp `protobuf:"bytes,4,opt,name=expires_at,json=expiresAt,proto3" json:"expires_at,omitempty"` + // The invitation's own id, so a caller holding only the emailed token can + // name the invitation afterwards without keeping the token. It grants + // nothing on its own: the id credential is accepted only for a signed-in + // caller whose primary email matches the invitation's. + Id string `protobuf:"bytes,5,opt,name=id,proto3" json:"id,omitempty"` unknownFields protoimpl.UnknownFields sizeCache protoimpl.SizeCache } @@ -391,6 +396,13 @@ func (x *InvitationSummary) GetExpiresAt() *timestamppb.Timestamp { return nil } +func (x *InvitationSummary) GetId() string { + if x != nil { + return x.Id + } + return "" +} + type CreateInvitationRequest struct { state protoimpl.MessageState `protogen:"open.v1"` OrgId string `protobuf:"bytes,1,opt,name=org_id,json=orgId,proto3" json:"org_id,omitempty"` @@ -1034,14 +1046,15 @@ const file_saas_accounts_v1_invitations_proto_rawDesc = "" + "\flast_sent_at\x18\v \x01(\v2\x1a.google.protobuf.TimestampR\n" + "lastSentAt\x12\x1d\n" + "\n" + - "send_count\x18\f \x01(\rR\tsendCount\"\xf3\x01\n" + + "send_count\x18\f \x01(\rR\tsendCount\"\x83\x02\n" + "\x11InvitationSummary\x12D\n" + "\x06status\x18\x01 \x01(\x0e2\".saas.accounts.v1.InvitationStatusB\b\xbaH\x05\x82\x01\x02\x10\x01R\x06status\x12>\n" + "\x04role\x18\x02 \x01(\x0e2 .saas.accounts.v1.InvitationRoleB\b\xbaH\x05\x82\x01\x02\x10\x01R\x04role\x12\x1d\n" + "\n" + "email_hint\x18\x03 \x01(\tR\temailHint\x129\n" + "\n" + - "expires_at\x18\x04 \x01(\v2\x1a.google.protobuf.TimestampR\texpiresAt\"\x9b\x01\n" + + "expires_at\x18\x04 \x01(\v2\x1a.google.protobuf.TimestampR\texpiresAt\x12\x0e\n" + + "\x02id\x18\x05 \x01(\tR\x02id\"\x9b\x01\n" + "\x17CreateInvitationRequest\x12\x1f\n" + "\x06org_id\x18\x01 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x05orgId\x12\x1d\n" + "\x05email\x18\x02 \x01(\tB\a\xbaH\x04r\x02`\x01R\x05email\x12@\n" + diff --git a/gen/saas/accounts/v1/module_registration.pb.go b/gen/saas/accounts/v1/module_registration.pb.go index 7cc184f..33cab47 100644 --- a/gen/saas/accounts/v1/module_registration.pb.go +++ b/gen/saas/accounts/v1/module_registration.pb.go @@ -43,21 +43,8 @@ type ModuleMintWorkContextRequest struct { // tenant-pinned principal, omit or match its tenant. Accounts validates the // requested organization's live installation after authenticating execution. OrganizationId string `protobuf:"bytes,4,opt,name=organization_id,json=organizationId,proto3" json:"organization_id,omitempty"` - // upstream is where the minting workload serves its backend, as an absolute - // https origin with no path: the dynamic half of its registration, reported - // by the runtime that proved its identity with the token above (#952). The - // gateway reaches it only under the SVID the applied presence names for the - // workload, so a claimed origin that is not that workload serves nothing. - // Empty leaves the registration's backend half as it is. - Upstream string `protobuf:"bytes,5,opt,name=upstream,proto3" json:"upstream,omitempty"` - // manifest is the solution's frontend manifest as its runtime serves it: the - // other dynamic half of a solution's registration (a module has none), the - // document the host's frontend renders the solution's page from. Reported - // with the same proven identity as upstream. Empty leaves the frontend half - // as it is. - Manifest string `protobuf:"bytes,6,opt,name=manifest,proto3" json:"manifest,omitempty"` - unknownFields protoimpl.UnknownFields - sizeCache protoimpl.SizeCache + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache } func (x *ModuleMintWorkContextRequest) Reset() { @@ -111,20 +98,6 @@ func (x *ModuleMintWorkContextRequest) GetOrganizationId() string { return "" } -func (x *ModuleMintWorkContextRequest) GetUpstream() string { - if x != nil { - return x.Upstream - } - return "" -} - -func (x *ModuleMintWorkContextRequest) GetManifest() string { - if x != nil { - return x.Manifest - } - return "" -} - // ModuleMintWorkContextResponse carries the signed capability plus the identity // it asserts, so a module can attribute its own work without parsing the token. type ModuleMintWorkContextResponse struct { @@ -601,13 +574,11 @@ var File_saas_accounts_v1_module_registration_proto protoreflect.FileDescriptor const file_saas_accounts_v1_module_registration_proto_rawDesc = "" + "\n" + - "*saas/accounts/v1/module_registration.proto\x12\x10saas.accounts.v1\x1a\x1bbuf/validate/validate.proto\x1a\x1fgoogle/protobuf/timestamp.proto\"\xbf\x02\n" + + "*saas/accounts/v1/module_registration.proto\x12\x10saas.accounts.v1\x1a\x1bbuf/validate/validate.proto\x1a\x1fgoogle/protobuf/timestamp.proto\"\x89\x02\n" + "\x1cModuleMintWorkContextRequest\x12D\n" + "\x06prefix\x18\x01 \x01(\tB,\xbaH)r'\x10\x01\x18?2!^[a-z0-9](?:[a-z0-9-]*[a-z0-9])?$R\x06prefix\x12?\n" + "\x15service_account_token\x18\x03 \x01(\tB\v\xbaH\br\x06\x10\x01\x18\x80\x80\x04R\x13serviceAccountToken\x124\n" + - "\x0forganization_id\x18\x04 \x01(\tB\v\xbaH\b\xd8\x01\x01r\x03\xb0\x01\x01R\x0eorganizationId\x12*\n" + - "\bupstream\x18\x05 \x01(\tB\x0e\xbaH\v\xd8\x01\x01r\x06\x18\x80\x04\x88\x01\x01R\bupstream\x12(\n" + - "\bmanifest\x18\x06 \x01(\tB\f\xbaH\t\xd8\x01\x01r\x04\x18\x80\x80\x04R\bmanifestJ\x04\b\x02\x10\x03R\x06secret\"\xab\x01\n" + + "\x0forganization_id\x18\x04 \x01(\tB\v\xbaH\b\xd8\x01\x01r\x03\xb0\x01\x01R\x0eorganizationIdJ\x04\b\x02\x10\x03J\x04\b\x05\x10\x06J\x04\b\x06\x10\aR\x06secretR\bupstreamR\bmanifest\"\xab\x01\n" + "\x1dModuleMintWorkContextResponse\x12\x14\n" + "\x05token\x18\x01 \x01(\tR\x05token\x129\n" + "\n" + diff --git a/gen/saas/accounts/v1/platform_admin.pb.go b/gen/saas/accounts/v1/platform_admin.pb.go index 5caaea1..e3f3c1c 100644 --- a/gen/saas/accounts/v1/platform_admin.pb.go +++ b/gen/saas/accounts/v1/platform_admin.pb.go @@ -3494,14 +3494,12 @@ type ModuleEnvelope struct { // The revision, from 1. A delivered authority document names the revision // it was rendered against and is inside this one only. Revision int64 `protobuf:"varint,1,opt,name=revision,proto3" json:"revision,omitempty"` - // The whole ceiling at this revision, as JSON: `revision`, - // `approved_builds`, and `principals` keyed by module prefix, each with the - // whole authority units this host admits (`bindings`: id, revision, scope, - // queue, namespace, binding_key, lookup_method), the workloads it may run as - // (`workload_identities`: spiffe_id, container), its `scope_ceilings` and its - // `grant` ceiling (tenant, cross_tenant, queues, namespaces, - // external_namespaces, resources, read_audiences, operation_audiences, - // artifact_policies). + // The whole ceiling at this revision, as JSON: `revision`, and `principals` + // keyed by module principal, each holding only its `grant` ceiling (tenant, + // cross_tenant, queues, namespaces, external_namespaces, resources, + // read_audiences, operation_audiences, artifact_policies). It names no + // workload and approves no build: which workloads a principal runs as is its + // applied module manifest's, and any other key is refused. Document string `protobuf:"bytes,2,opt,name=document,proto3" json:"document,omitempty"` // The platform administrator who wrote this revision. WrittenBy string `protobuf:"bytes,3,opt,name=written_by,json=writtenBy,proto3" json:"written_by,omitempty"` @@ -3608,7 +3606,10 @@ type GetModuleEnvelopeResponse struct { state protoimpl.MessageState `protogen:"open.v1"` // The current revision. Absent when no envelope has been written, which // grants no module anything. - Envelope *ModuleEnvelope `protobuf:"bytes,1,opt,name=envelope,proto3,oneof" json:"envelope,omitempty"` + Envelope *ModuleEnvelope `protobuf:"bytes,1,opt,name=envelope,proto3,oneof" json:"envelope,omitempty"` + // What the applied module manifests ask for: one entry per applied, live + // manifest that asks for authority, ordered by principal then binding. + Requested []*ModuleAuthorityRequest `protobuf:"bytes,2,rep,name=requested,proto3" json:"requested,omitempty"` unknownFields protoimpl.UnknownFields sizeCache protoimpl.SizeCache } @@ -3650,6 +3651,111 @@ func (x *GetModuleEnvelopeResponse) GetEnvelope() *ModuleEnvelope { return nil } +func (x *GetModuleEnvelopeResponse) GetRequested() []*ModuleAuthorityRequest { + if x != nil { + return x.Requested + } + return nil +} + +// ModuleAuthorityRequest is the authority one applied module manifest asks +// for. It is a request, never a grant: a principal holds only what the +// envelope allows of it, and only while its manifest's carrier still verifies. +type ModuleAuthorityRequest struct { + state protoimpl.MessageState `protogen:"open.v1"` + // The module principal the manifest asks under: the key its ceiling is + // filed under in the envelope's `principals`. + Principal string `protobuf:"bytes,1,opt,name=principal,proto3" json:"principal,omitempty"` + // The host binding whose applied manifest asks. + Binding string `protobuf:"bytes,2,opt,name=binding,proto3" json:"binding,omitempty"` + // The applied generation of that binding. + Generation int64 `protobuf:"varint,3,opt,name=generation,proto3" json:"generation,omitempty"` + // The module's route alias. + Alias string `protobuf:"bytes,4,opt,name=alias,proto3" json:"alias,omitempty"` + // Whether the returned envelope declares a ceiling for the principal. A + // principal it declares none for is denied every Work Context. A declared + // ceiling can still leave out an operation binding the manifest asks for; + // the reconcile pass names each one in the host's log. + Allowed bool `protobuf:"varint,5,opt,name=allowed,proto3" json:"allowed,omitempty"` + // What the manifest asks for, as JSON: its `authority` block (principal, + // bindings, queues, namespaces, resource_kinds). + Authority string `protobuf:"bytes,6,opt,name=authority,proto3" json:"authority,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *ModuleAuthorityRequest) Reset() { + *x = ModuleAuthorityRequest{} + mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[50] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *ModuleAuthorityRequest) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*ModuleAuthorityRequest) ProtoMessage() {} + +func (x *ModuleAuthorityRequest) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[50] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use ModuleAuthorityRequest.ProtoReflect.Descriptor instead. +func (*ModuleAuthorityRequest) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_platform_admin_proto_rawDescGZIP(), []int{50} +} + +func (x *ModuleAuthorityRequest) GetPrincipal() string { + if x != nil { + return x.Principal + } + return "" +} + +func (x *ModuleAuthorityRequest) GetBinding() string { + if x != nil { + return x.Binding + } + return "" +} + +func (x *ModuleAuthorityRequest) GetGeneration() int64 { + if x != nil { + return x.Generation + } + return 0 +} + +func (x *ModuleAuthorityRequest) GetAlias() string { + if x != nil { + return x.Alias + } + return "" +} + +func (x *ModuleAuthorityRequest) GetAllowed() bool { + if x != nil { + return x.Allowed + } + return false +} + +func (x *ModuleAuthorityRequest) GetAuthority() string { + if x != nil { + return x.Authority + } + return "" +} + type PutModuleEnvelopeRequest struct { state protoimpl.MessageState `protogen:"open.v1"` // The revision this write replaces: the one the caller read, 0 when none has @@ -3664,7 +3770,7 @@ type PutModuleEnvelopeRequest struct { func (x *PutModuleEnvelopeRequest) Reset() { *x = PutModuleEnvelopeRequest{} - mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[50] + mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[51] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3676,7 +3782,7 @@ func (x *PutModuleEnvelopeRequest) String() string { func (*PutModuleEnvelopeRequest) ProtoMessage() {} func (x *PutModuleEnvelopeRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[50] + mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[51] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3689,7 +3795,7 @@ func (x *PutModuleEnvelopeRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use PutModuleEnvelopeRequest.ProtoReflect.Descriptor instead. func (*PutModuleEnvelopeRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_platform_admin_proto_rawDescGZIP(), []int{50} + return file_saas_accounts_v1_platform_admin_proto_rawDescGZIP(), []int{51} } func (x *PutModuleEnvelopeRequest) GetExpectedRevision() int64 { @@ -3715,7 +3821,7 @@ type PutModuleEnvelopeResponse struct { func (x *PutModuleEnvelopeResponse) Reset() { *x = PutModuleEnvelopeResponse{} - mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[51] + mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[52] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -3727,7 +3833,7 @@ func (x *PutModuleEnvelopeResponse) String() string { func (*PutModuleEnvelopeResponse) ProtoMessage() {} func (x *PutModuleEnvelopeResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[51] + mi := &file_saas_accounts_v1_platform_admin_proto_msgTypes[52] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -3740,7 +3846,7 @@ func (x *PutModuleEnvelopeResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use PutModuleEnvelopeResponse.ProtoReflect.Descriptor instead. func (*PutModuleEnvelopeResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_platform_admin_proto_rawDescGZIP(), []int{51} + return file_saas_accounts_v1_platform_admin_proto_rawDescGZIP(), []int{52} } func (x *PutModuleEnvelopeResponse) GetEnvelope() *ModuleEnvelope { @@ -3984,10 +4090,20 @@ const file_saas_accounts_v1_platform_admin_proto_rawDesc = "" + "written_by\x18\x03 \x01(\tR\twrittenBy\x129\n" + "\n" + "written_at\x18\x04 \x01(\v2\x1a.google.protobuf.TimestampR\twrittenAt\"\x1a\n" + - "\x18GetModuleEnvelopeRequest\"k\n" + + "\x18GetModuleEnvelopeRequest\"\xb3\x01\n" + "\x19GetModuleEnvelopeResponse\x12A\n" + - "\benvelope\x18\x01 \x01(\v2 .saas.accounts.v1.ModuleEnvelopeH\x00R\benvelope\x88\x01\x01B\v\n" + - "\t_envelope\"y\n" + + "\benvelope\x18\x01 \x01(\v2 .saas.accounts.v1.ModuleEnvelopeH\x00R\benvelope\x88\x01\x01\x12F\n" + + "\trequested\x18\x02 \x03(\v2(.saas.accounts.v1.ModuleAuthorityRequestR\trequestedB\v\n" + + "\t_envelope\"\xbe\x01\n" + + "\x16ModuleAuthorityRequest\x12\x1c\n" + + "\tprincipal\x18\x01 \x01(\tR\tprincipal\x12\x18\n" + + "\abinding\x18\x02 \x01(\tR\abinding\x12\x1e\n" + + "\n" + + "generation\x18\x03 \x01(\x03R\n" + + "generation\x12\x14\n" + + "\x05alias\x18\x04 \x01(\tR\x05alias\x12\x18\n" + + "\aallowed\x18\x05 \x01(\bR\aallowed\x12\x1c\n" + + "\tauthority\x18\x06 \x01(\tR\tauthority\"y\n" + "\x18PutModuleEnvelopeRequest\x124\n" + "\x11expected_revision\x18\x01 \x01(\x03B\a\xbaH\x04\"\x02(\x00R\x10expectedRevision\x12'\n" + "\bdocument\x18\x02 \x01(\tB\v\xbaH\br\x06\x10\x01(\x80\x80@R\bdocument\"Y\n" + @@ -4006,7 +4122,7 @@ const file_saas_accounts_v1_platform_admin_proto_rawDesc = "" + "&CATALOGUE_OBSERVED_VERDICT_UNSPECIFIED\x10\x00\x121\n" + "-CATALOGUE_OBSERVED_VERDICT_RUNNING_AUTHORIZED\x10\x01\x12.\n" + "*CATALOGUE_OBSERVED_VERDICT_RUNNING_DIFFERS\x10\x02\x123\n" + - "/CATALOGUE_OBSERVED_VERDICT_RUNNING_UNAUTHORIZED\x10\x032\xf5\"\n" + + "/CATALOGUE_OBSERVED_VERDICT_RUNNING_UNAUTHORIZED\x10\x032\xa2#\n" + "\x14PlatformAdminService\x12\x8e\x01\n" + "\vSearchUsers\x12$.saas.accounts.v1.SearchUsersRequest\x1a%.saas.accounts.v1.SearchUsersResponse\"2\xc2\xf3\x18\x14\b\x02\x10\x010\x01:\x02\x10\x01@\x01H\x05P\x03X\x03`\x03\x82\xd3\xe4\x93\x02\x14\x12\x12/v1/platform/users\x12\xab\x01\n" + "\vSuspendUser\x12$.saas.accounts.v1.SuspendUserRequest\x1a\x16.google.protobuf.Empty\"^\xc2\xf3\x18+\b\x02\x10\x010\x01:\x17\n" + @@ -4041,9 +4157,9 @@ const file_saas_accounts_v1_platform_admin_proto_rawDesc = "" + "\x11saas.job.replayed\x10\x02@\x03H\x05P\x03X\x03`\x05\x82\xd3\xe4\x93\x02-:\x01*\"(/v1/platform/jobs/{source_job_id}:replay\x12\xab\x01\n" + "\x12GetEventOperations\x12).saas.events.v1.GetEventOperationsRequest\x1a*.saas.events.v1.GetEventOperationsResponse\">\xc2\xf3\x18\x14\b\x02\x10\x010\x01:\x02\x10\x01@\x01H\x05P\x03X\x03`\x05\x82\xd3\xe4\x93\x02 \x12\x1e/v1/platform/events/operations\x12\xba\x01\n" + "\x16ListEventSubscriptions\x12-.saas.events.v1.ListEventSubscriptionsRequest\x1a..saas.events.v1.ListEventSubscriptionsResponse\"A\xc2\xf3\x18\x14\b\x02\x10\x010\x01:\x02\x10\x01@\x01H\x05P\x03X\x03`\x05\x82\xd3\xe4\x93\x02#\x12!/v1/platform/events/subscriptions\x12\xb0\x01\n" + - "\x15ListPlatformCatalogue\x12..saas.accounts.v1.ListPlatformCatalogueRequest\x1a/.saas.accounts.v1.ListPlatformCatalogueResponse\"6\xc2\xf3\x18\x14\b\x02\x10\x010\x01:\x02\x10\x01@\x01H\x05P\x03X\x03`\x05\x82\xd3\xe4\x93\x02\x18\x12\x16/v1/platform/catalogue\x12\xaa\x01\n" + - "\x11GetModuleEnvelope\x12*.saas.accounts.v1.GetModuleEnvelopeRequest\x1a+.saas.accounts.v1.GetModuleEnvelopeResponse\"<\xc2\xf3\x18\x14\b\x02\x10\x010\x01:\x02\x10\x01@\x01H\x05P\x03X\x03`\x05\x82\xd3\xe4\x93\x02\x1e\x12\x1c/v1/platform/module-envelope\x12\xd6\x01\n" + - "\x11PutModuleEnvelope\x12*.saas.accounts.v1.PutModuleEnvelopeRequest\x1a+.saas.accounts.v1.PutModuleEnvelopeResponse\"h\xc2\xf3\x18=\b\x02\x10\x010\x03:)\n" + + "\x15ListPlatformCatalogue\x12..saas.accounts.v1.ListPlatformCatalogueRequest\x1a/.saas.accounts.v1.ListPlatformCatalogueResponse\"6\xc2\xf3\x18\x14\b\x02\x10\x010\x01:\x02\x10\x01@\x01H\x05P\x03X\x03`\x05\x82\xd3\xe4\x93\x02\x18\x12\x16/v1/platform/catalogue\x12\xc0\x01\n" + + "\x11GetModuleEnvelope\x12*.saas.accounts.v1.GetModuleEnvelopeRequest\x1a+.saas.accounts.v1.GetModuleEnvelopeResponse\"R\xc2\xf3\x18*\b\x02\x10\x01\"\x14module_envelope:read0\x01:\x02\x10\x01@\x01H\x05P\x03X\x03`\x05\x82\xd3\xe4\x93\x02\x1e\x12\x1c/v1/platform/module-envelope\x12\xed\x01\n" + + "\x11PutModuleEnvelope\x12*.saas.accounts.v1.PutModuleEnvelopeRequest\x1a+.saas.accounts.v1.PutModuleEnvelopeResponse\"\x7f\xc2\xf3\x18T\b\x02\x10\x01\"\x15module_envelope:write0\x03:)\n" + "%saas.platform.module_envelope_written\x10\x02@\x01H\x05P\x03X\x03`\x05x\x02\x82\xd3\xe4\x93\x02!:\x01*\x1a\x1c/v1/platform/module-envelopeB\xd0\x01\n" + "\x14com.saas.accounts.v1B\x12PlatformAdminProtoP\x01ZBgithub.com/codefly-dev/saas-sdk-go/gen/saas/accounts/v1;accountsv1\xa2\x02\x03SAX\xaa\x02\x10Saas.Accounts.V1\xca\x02\x10Saas\\Accounts\\V1\xe2\x02\x1cSaas\\Accounts\\V1\\GPBMetadata\xea\x02\x12Saas::Accounts::V1b\x06proto3" @@ -4060,7 +4176,7 @@ func file_saas_accounts_v1_platform_admin_proto_rawDescGZIP() []byte { } var file_saas_accounts_v1_platform_admin_proto_enumTypes = make([]protoimpl.EnumInfo, 3) -var file_saas_accounts_v1_platform_admin_proto_msgTypes = make([]protoimpl.MessageInfo, 55) +var file_saas_accounts_v1_platform_admin_proto_msgTypes = make([]protoimpl.MessageInfo, 56) var file_saas_accounts_v1_platform_admin_proto_goTypes = []any{ (CatalogueEntryKind)(0), // 0: saas.accounts.v1.CatalogueEntryKind (CatalogueGapReason)(0), // 1: saas.accounts.v1.CatalogueGapReason @@ -4115,45 +4231,46 @@ var file_saas_accounts_v1_platform_admin_proto_goTypes = []any{ (*ModuleEnvelope)(nil), // 50: saas.accounts.v1.ModuleEnvelope (*GetModuleEnvelopeRequest)(nil), // 51: saas.accounts.v1.GetModuleEnvelopeRequest (*GetModuleEnvelopeResponse)(nil), // 52: saas.accounts.v1.GetModuleEnvelopeResponse - (*PutModuleEnvelopeRequest)(nil), // 53: saas.accounts.v1.PutModuleEnvelopeRequest - (*PutModuleEnvelopeResponse)(nil), // 54: saas.accounts.v1.PutModuleEnvelopeResponse - nil, // 55: saas.accounts.v1.SessionInfo.DeviceInfoEntry - nil, // 56: saas.accounts.v1.CatalogueObservedExecution.ContainerImageDigestsEntry - nil, // 57: saas.accounts.v1.ListPlatformCatalogueResponse.ApprovedInventoriesEntry - (*User)(nil), // 58: saas.accounts.v1.User - (*Organization)(nil), // 59: saas.accounts.v1.Organization - (*OrgMembership)(nil), // 60: saas.accounts.v1.OrgMembership - (*timestamppb.Timestamp)(nil), // 61: google.protobuf.Timestamp - (*Installation)(nil), // 62: saas.accounts.v1.Installation - (*CollectionReadGrant)(nil), // 63: saas.accounts.v1.CollectionReadGrant - (*SolutionRegistration)(nil), // 64: saas.accounts.v1.SolutionRegistration - (*v1.GetJobOperationsRequest)(nil), // 65: saas.jobs.v1.GetJobOperationsRequest - (*v1.ListJobsRequest)(nil), // 66: saas.jobs.v1.ListJobsRequest - (*v1.GetJobRequest)(nil), // 67: saas.jobs.v1.GetJobRequest - (*v1.ReplayJobRequest)(nil), // 68: saas.jobs.v1.ReplayJobRequest - (*v11.GetEventOperationsRequest)(nil), // 69: saas.events.v1.GetEventOperationsRequest - (*v11.ListEventSubscriptionsRequest)(nil), // 70: saas.events.v1.ListEventSubscriptionsRequest - (*emptypb.Empty)(nil), // 71: google.protobuf.Empty - (*v1.GetJobOperationsResponse)(nil), // 72: saas.jobs.v1.GetJobOperationsResponse - (*v1.ListJobsResponse)(nil), // 73: saas.jobs.v1.ListJobsResponse - (*v1.GetJobResponse)(nil), // 74: saas.jobs.v1.GetJobResponse - (*v1.ReplayJobResponse)(nil), // 75: saas.jobs.v1.ReplayJobResponse - (*v11.GetEventOperationsResponse)(nil), // 76: saas.events.v1.GetEventOperationsResponse - (*v11.ListEventSubscriptionsResponse)(nil), // 77: saas.events.v1.ListEventSubscriptionsResponse + (*ModuleAuthorityRequest)(nil), // 53: saas.accounts.v1.ModuleAuthorityRequest + (*PutModuleEnvelopeRequest)(nil), // 54: saas.accounts.v1.PutModuleEnvelopeRequest + (*PutModuleEnvelopeResponse)(nil), // 55: saas.accounts.v1.PutModuleEnvelopeResponse + nil, // 56: saas.accounts.v1.SessionInfo.DeviceInfoEntry + nil, // 57: saas.accounts.v1.CatalogueObservedExecution.ContainerImageDigestsEntry + nil, // 58: saas.accounts.v1.ListPlatformCatalogueResponse.ApprovedInventoriesEntry + (*User)(nil), // 59: saas.accounts.v1.User + (*Organization)(nil), // 60: saas.accounts.v1.Organization + (*OrgMembership)(nil), // 61: saas.accounts.v1.OrgMembership + (*timestamppb.Timestamp)(nil), // 62: google.protobuf.Timestamp + (*Installation)(nil), // 63: saas.accounts.v1.Installation + (*CollectionReadGrant)(nil), // 64: saas.accounts.v1.CollectionReadGrant + (*SolutionRegistration)(nil), // 65: saas.accounts.v1.SolutionRegistration + (*v1.GetJobOperationsRequest)(nil), // 66: saas.jobs.v1.GetJobOperationsRequest + (*v1.ListJobsRequest)(nil), // 67: saas.jobs.v1.ListJobsRequest + (*v1.GetJobRequest)(nil), // 68: saas.jobs.v1.GetJobRequest + (*v1.ReplayJobRequest)(nil), // 69: saas.jobs.v1.ReplayJobRequest + (*v11.GetEventOperationsRequest)(nil), // 70: saas.events.v1.GetEventOperationsRequest + (*v11.ListEventSubscriptionsRequest)(nil), // 71: saas.events.v1.ListEventSubscriptionsRequest + (*emptypb.Empty)(nil), // 72: google.protobuf.Empty + (*v1.GetJobOperationsResponse)(nil), // 73: saas.jobs.v1.GetJobOperationsResponse + (*v1.ListJobsResponse)(nil), // 74: saas.jobs.v1.ListJobsResponse + (*v1.GetJobResponse)(nil), // 75: saas.jobs.v1.GetJobResponse + (*v1.ReplayJobResponse)(nil), // 76: saas.jobs.v1.ReplayJobResponse + (*v11.GetEventOperationsResponse)(nil), // 77: saas.events.v1.GetEventOperationsResponse + (*v11.ListEventSubscriptionsResponse)(nil), // 78: saas.events.v1.ListEventSubscriptionsResponse } var file_saas_accounts_v1_platform_admin_proto_depIdxs = []int32{ - 58, // 0: saas.accounts.v1.SearchUsersResponse.users:type_name -> saas.accounts.v1.User - 59, // 1: saas.accounts.v1.PlatformOrganization.organization:type_name -> saas.accounts.v1.Organization + 59, // 0: saas.accounts.v1.SearchUsersResponse.users:type_name -> saas.accounts.v1.User + 60, // 1: saas.accounts.v1.PlatformOrganization.organization:type_name -> saas.accounts.v1.Organization 6, // 2: saas.accounts.v1.ListAllOrganizationsResponse.organizations:type_name -> saas.accounts.v1.PlatformOrganization - 60, // 3: saas.accounts.v1.GetOrganizationRosterResponse.members:type_name -> saas.accounts.v1.OrgMembership - 55, // 4: saas.accounts.v1.SessionInfo.device_info:type_name -> saas.accounts.v1.SessionInfo.DeviceInfoEntry - 61, // 5: saas.accounts.v1.SessionInfo.created_at:type_name -> google.protobuf.Timestamp - 61, // 6: saas.accounts.v1.SessionInfo.last_active_at:type_name -> google.protobuf.Timestamp - 61, // 7: saas.accounts.v1.SessionInfo.expires_at:type_name -> google.protobuf.Timestamp - 61, // 8: saas.accounts.v1.SessionInfo.idle_expires_at:type_name -> google.protobuf.Timestamp + 61, // 3: saas.accounts.v1.GetOrganizationRosterResponse.members:type_name -> saas.accounts.v1.OrgMembership + 56, // 4: saas.accounts.v1.SessionInfo.device_info:type_name -> saas.accounts.v1.SessionInfo.DeviceInfoEntry + 62, // 5: saas.accounts.v1.SessionInfo.created_at:type_name -> google.protobuf.Timestamp + 62, // 6: saas.accounts.v1.SessionInfo.last_active_at:type_name -> google.protobuf.Timestamp + 62, // 7: saas.accounts.v1.SessionInfo.expires_at:type_name -> google.protobuf.Timestamp + 62, // 8: saas.accounts.v1.SessionInfo.idle_expires_at:type_name -> google.protobuf.Timestamp 17, // 9: saas.accounts.v1.ListActiveSessionsResponse.sessions:type_name -> saas.accounts.v1.SessionInfo 22, // 10: saas.accounts.v1.GetOrgEntitlementsResponse.entitlements:type_name -> saas.accounts.v1.EntitlementInfo - 61, // 11: saas.accounts.v1.PlatformAdminEntry.granted_at:type_name -> google.protobuf.Timestamp + 62, // 11: saas.accounts.v1.PlatformAdminEntry.granted_at:type_name -> google.protobuf.Timestamp 28, // 12: saas.accounts.v1.ListPlatformAdminsResponse.admins:type_name -> saas.accounts.v1.PlatformAdminEntry 31, // 13: saas.accounts.v1.ListFeatureFlagsResponse.flags:type_name -> saas.accounts.v1.FeatureFlagEntry 1, // 14: saas.accounts.v1.CatalogueGap.reason:type_name -> saas.accounts.v1.CatalogueGapReason @@ -4164,9 +4281,9 @@ var file_saas_accounts_v1_platform_admin_proto_depIdxs = []int32{ 39, // 19: saas.accounts.v1.CatalogueAuthorized.not_authorized:type_name -> saas.accounts.v1.CatalogueNotAuthorized 35, // 20: saas.accounts.v1.CatalogueAuthorized.authorization_gap:type_name -> saas.accounts.v1.CatalogueGap 35, // 21: saas.accounts.v1.CatalogueApplied.applied_revision_gap:type_name -> saas.accounts.v1.CatalogueGap - 56, // 22: saas.accounts.v1.CatalogueObservedExecution.container_image_digests:type_name -> saas.accounts.v1.CatalogueObservedExecution.ContainerImageDigestsEntry + 57, // 22: saas.accounts.v1.CatalogueObservedExecution.container_image_digests:type_name -> saas.accounts.v1.CatalogueObservedExecution.ContainerImageDigestsEntry 35, // 23: saas.accounts.v1.CatalogueObserved.observed_revision_gap:type_name -> saas.accounts.v1.CatalogueGap - 61, // 24: saas.accounts.v1.CatalogueObserved.observed_at:type_name -> google.protobuf.Timestamp + 62, // 24: saas.accounts.v1.CatalogueObserved.observed_at:type_name -> google.protobuf.Timestamp 35, // 25: saas.accounts.v1.CatalogueObserved.observation_freshness_gap:type_name -> saas.accounts.v1.CatalogueGap 42, // 26: saas.accounts.v1.CatalogueObserved.observed_execution:type_name -> saas.accounts.v1.CatalogueObservedExecution 35, // 27: saas.accounts.v1.CatalogueObserved.observed_execution_gap:type_name -> saas.accounts.v1.CatalogueGap @@ -4175,12 +4292,12 @@ var file_saas_accounts_v1_platform_admin_proto_depIdxs = []int32{ 35, // 30: saas.accounts.v1.CatalogueWithdrawing.withdrawal_state_gap:type_name -> saas.accounts.v1.CatalogueGap 35, // 31: saas.accounts.v1.CatalogueWithdrawing.credential_revocation_state_gap:type_name -> saas.accounts.v1.CatalogueGap 35, // 32: saas.accounts.v1.CatalogueRetired.retirement_state_gap:type_name -> saas.accounts.v1.CatalogueGap - 62, // 33: saas.accounts.v1.CatalogueInstallation.installation:type_name -> saas.accounts.v1.Installation + 63, // 33: saas.accounts.v1.CatalogueInstallation.installation:type_name -> saas.accounts.v1.Installation 36, // 34: saas.accounts.v1.CatalogueInstallation.agent_release:type_name -> saas.accounts.v1.CatalogueRelease 35, // 35: saas.accounts.v1.CatalogueInstallation.agent_release_gap:type_name -> saas.accounts.v1.CatalogueGap 35, // 36: saas.accounts.v1.CatalogueInstallation.revision_gap:type_name -> saas.accounts.v1.CatalogueGap - 63, // 37: saas.accounts.v1.CatalogueInstallation.granted_teams:type_name -> saas.accounts.v1.CollectionReadGrant - 63, // 38: saas.accounts.v1.CatalogueInstallation.inherited_teams:type_name -> saas.accounts.v1.CollectionReadGrant + 64, // 37: saas.accounts.v1.CatalogueInstallation.granted_teams:type_name -> saas.accounts.v1.CollectionReadGrant + 64, // 38: saas.accounts.v1.CatalogueInstallation.inherited_teams:type_name -> saas.accounts.v1.CollectionReadGrant 0, // 39: saas.accounts.v1.CatalogueEntry.kind:type_name -> saas.accounts.v1.CatalogueEntryKind 35, // 40: saas.accounts.v1.CatalogueEntry.publisher_gap:type_name -> saas.accounts.v1.CatalogueGap 37, // 41: saas.accounts.v1.CatalogueEntry.desired:type_name -> saas.accounts.v1.CatalogueDesired @@ -4190,68 +4307,69 @@ var file_saas_accounts_v1_platform_admin_proto_depIdxs = []int32{ 44, // 45: saas.accounts.v1.CatalogueEntry.withdrawing:type_name -> saas.accounts.v1.CatalogueWithdrawing 45, // 46: saas.accounts.v1.CatalogueEntry.retired:type_name -> saas.accounts.v1.CatalogueRetired 35, // 47: saas.accounts.v1.CatalogueEntry.build_size_gap:type_name -> saas.accounts.v1.CatalogueGap - 64, // 48: saas.accounts.v1.CatalogueEntry.registration:type_name -> saas.accounts.v1.SolutionRegistration + 65, // 48: saas.accounts.v1.CatalogueEntry.registration:type_name -> saas.accounts.v1.SolutionRegistration 46, // 49: saas.accounts.v1.CatalogueEntry.installations:type_name -> saas.accounts.v1.CatalogueInstallation 47, // 50: saas.accounts.v1.ListPlatformCatalogueResponse.entries:type_name -> saas.accounts.v1.CatalogueEntry - 57, // 51: saas.accounts.v1.ListPlatformCatalogueResponse.approved_inventories:type_name -> saas.accounts.v1.ListPlatformCatalogueResponse.ApprovedInventoriesEntry - 61, // 52: saas.accounts.v1.ModuleEnvelope.written_at:type_name -> google.protobuf.Timestamp + 58, // 51: saas.accounts.v1.ListPlatformCatalogueResponse.approved_inventories:type_name -> saas.accounts.v1.ListPlatformCatalogueResponse.ApprovedInventoriesEntry + 62, // 52: saas.accounts.v1.ModuleEnvelope.written_at:type_name -> google.protobuf.Timestamp 50, // 53: saas.accounts.v1.GetModuleEnvelopeResponse.envelope:type_name -> saas.accounts.v1.ModuleEnvelope - 50, // 54: saas.accounts.v1.PutModuleEnvelopeResponse.envelope:type_name -> saas.accounts.v1.ModuleEnvelope - 3, // 55: saas.accounts.v1.PlatformAdminService.SearchUsers:input_type -> saas.accounts.v1.SearchUsersRequest - 10, // 56: saas.accounts.v1.PlatformAdminService.SuspendUser:input_type -> saas.accounts.v1.SuspendUserRequest - 11, // 57: saas.accounts.v1.PlatformAdminService.UnsuspendUser:input_type -> saas.accounts.v1.UnsuspendUserRequest - 12, // 58: saas.accounts.v1.PlatformAdminService.ImpersonateUser:input_type -> saas.accounts.v1.ImpersonateUserRequest - 14, // 59: saas.accounts.v1.PlatformAdminService.StopImpersonation:input_type -> saas.accounts.v1.StopImpersonationRequest - 16, // 60: saas.accounts.v1.PlatformAdminService.ListActiveSessions:input_type -> saas.accounts.v1.ListActiveSessionsRequest - 19, // 61: saas.accounts.v1.PlatformAdminService.RevokeSession:input_type -> saas.accounts.v1.RevokeSessionRequest - 20, // 62: saas.accounts.v1.PlatformAdminService.GetOrgEntitlements:input_type -> saas.accounts.v1.GetOrgEntitlementsRequest - 23, // 63: saas.accounts.v1.PlatformAdminService.OverrideEntitlement:input_type -> saas.accounts.v1.OverrideEntitlementRequest - 25, // 64: saas.accounts.v1.PlatformAdminService.GrantPlatformRole:input_type -> saas.accounts.v1.GrantPlatformRoleRequest - 26, // 65: saas.accounts.v1.PlatformAdminService.RevokePlatformRole:input_type -> saas.accounts.v1.RevokePlatformRoleRequest - 27, // 66: saas.accounts.v1.PlatformAdminService.ListPlatformAdmins:input_type -> saas.accounts.v1.ListPlatformAdminsRequest - 5, // 67: saas.accounts.v1.PlatformAdminService.ListAllOrganizations:input_type -> saas.accounts.v1.ListAllOrganizationsRequest - 8, // 68: saas.accounts.v1.PlatformAdminService.GetOrganizationRoster:input_type -> saas.accounts.v1.GetOrganizationRosterRequest - 30, // 69: saas.accounts.v1.PlatformAdminService.ListFeatureFlags:input_type -> saas.accounts.v1.ListFeatureFlagsRequest - 33, // 70: saas.accounts.v1.PlatformAdminService.UpsertFeatureFlag:input_type -> saas.accounts.v1.UpsertFeatureFlagRequest - 65, // 71: saas.accounts.v1.PlatformAdminService.GetJobOperations:input_type -> saas.jobs.v1.GetJobOperationsRequest - 66, // 72: saas.accounts.v1.PlatformAdminService.ListJobs:input_type -> saas.jobs.v1.ListJobsRequest - 67, // 73: saas.accounts.v1.PlatformAdminService.GetJob:input_type -> saas.jobs.v1.GetJobRequest - 68, // 74: saas.accounts.v1.PlatformAdminService.ReplayJob:input_type -> saas.jobs.v1.ReplayJobRequest - 69, // 75: saas.accounts.v1.PlatformAdminService.GetEventOperations:input_type -> saas.events.v1.GetEventOperationsRequest - 70, // 76: saas.accounts.v1.PlatformAdminService.ListEventSubscriptions:input_type -> saas.events.v1.ListEventSubscriptionsRequest - 48, // 77: saas.accounts.v1.PlatformAdminService.ListPlatformCatalogue:input_type -> saas.accounts.v1.ListPlatformCatalogueRequest - 51, // 78: saas.accounts.v1.PlatformAdminService.GetModuleEnvelope:input_type -> saas.accounts.v1.GetModuleEnvelopeRequest - 53, // 79: saas.accounts.v1.PlatformAdminService.PutModuleEnvelope:input_type -> saas.accounts.v1.PutModuleEnvelopeRequest - 4, // 80: saas.accounts.v1.PlatformAdminService.SearchUsers:output_type -> saas.accounts.v1.SearchUsersResponse - 71, // 81: saas.accounts.v1.PlatformAdminService.SuspendUser:output_type -> google.protobuf.Empty - 71, // 82: saas.accounts.v1.PlatformAdminService.UnsuspendUser:output_type -> google.protobuf.Empty - 13, // 83: saas.accounts.v1.PlatformAdminService.ImpersonateUser:output_type -> saas.accounts.v1.ImpersonateUserResponse - 15, // 84: saas.accounts.v1.PlatformAdminService.StopImpersonation:output_type -> saas.accounts.v1.StopImpersonationResponse - 18, // 85: saas.accounts.v1.PlatformAdminService.ListActiveSessions:output_type -> saas.accounts.v1.ListActiveSessionsResponse - 71, // 86: saas.accounts.v1.PlatformAdminService.RevokeSession:output_type -> google.protobuf.Empty - 21, // 87: saas.accounts.v1.PlatformAdminService.GetOrgEntitlements:output_type -> saas.accounts.v1.GetOrgEntitlementsResponse - 24, // 88: saas.accounts.v1.PlatformAdminService.OverrideEntitlement:output_type -> saas.accounts.v1.OverrideEntitlementResponse - 71, // 89: saas.accounts.v1.PlatformAdminService.GrantPlatformRole:output_type -> google.protobuf.Empty - 71, // 90: saas.accounts.v1.PlatformAdminService.RevokePlatformRole:output_type -> google.protobuf.Empty - 29, // 91: saas.accounts.v1.PlatformAdminService.ListPlatformAdmins:output_type -> saas.accounts.v1.ListPlatformAdminsResponse - 7, // 92: saas.accounts.v1.PlatformAdminService.ListAllOrganizations:output_type -> saas.accounts.v1.ListAllOrganizationsResponse - 9, // 93: saas.accounts.v1.PlatformAdminService.GetOrganizationRoster:output_type -> saas.accounts.v1.GetOrganizationRosterResponse - 32, // 94: saas.accounts.v1.PlatformAdminService.ListFeatureFlags:output_type -> saas.accounts.v1.ListFeatureFlagsResponse - 34, // 95: saas.accounts.v1.PlatformAdminService.UpsertFeatureFlag:output_type -> saas.accounts.v1.UpsertFeatureFlagResponse - 72, // 96: saas.accounts.v1.PlatformAdminService.GetJobOperations:output_type -> saas.jobs.v1.GetJobOperationsResponse - 73, // 97: saas.accounts.v1.PlatformAdminService.ListJobs:output_type -> saas.jobs.v1.ListJobsResponse - 74, // 98: saas.accounts.v1.PlatformAdminService.GetJob:output_type -> saas.jobs.v1.GetJobResponse - 75, // 99: saas.accounts.v1.PlatformAdminService.ReplayJob:output_type -> saas.jobs.v1.ReplayJobResponse - 76, // 100: saas.accounts.v1.PlatformAdminService.GetEventOperations:output_type -> saas.events.v1.GetEventOperationsResponse - 77, // 101: saas.accounts.v1.PlatformAdminService.ListEventSubscriptions:output_type -> saas.events.v1.ListEventSubscriptionsResponse - 49, // 102: saas.accounts.v1.PlatformAdminService.ListPlatformCatalogue:output_type -> saas.accounts.v1.ListPlatformCatalogueResponse - 52, // 103: saas.accounts.v1.PlatformAdminService.GetModuleEnvelope:output_type -> saas.accounts.v1.GetModuleEnvelopeResponse - 54, // 104: saas.accounts.v1.PlatformAdminService.PutModuleEnvelope:output_type -> saas.accounts.v1.PutModuleEnvelopeResponse - 80, // [80:105] is the sub-list for method output_type - 55, // [55:80] is the sub-list for method input_type - 55, // [55:55] is the sub-list for extension type_name - 55, // [55:55] is the sub-list for extension extendee - 0, // [0:55] is the sub-list for field type_name + 53, // 54: saas.accounts.v1.GetModuleEnvelopeResponse.requested:type_name -> saas.accounts.v1.ModuleAuthorityRequest + 50, // 55: saas.accounts.v1.PutModuleEnvelopeResponse.envelope:type_name -> saas.accounts.v1.ModuleEnvelope + 3, // 56: saas.accounts.v1.PlatformAdminService.SearchUsers:input_type -> saas.accounts.v1.SearchUsersRequest + 10, // 57: saas.accounts.v1.PlatformAdminService.SuspendUser:input_type -> saas.accounts.v1.SuspendUserRequest + 11, // 58: saas.accounts.v1.PlatformAdminService.UnsuspendUser:input_type -> saas.accounts.v1.UnsuspendUserRequest + 12, // 59: saas.accounts.v1.PlatformAdminService.ImpersonateUser:input_type -> saas.accounts.v1.ImpersonateUserRequest + 14, // 60: saas.accounts.v1.PlatformAdminService.StopImpersonation:input_type -> saas.accounts.v1.StopImpersonationRequest + 16, // 61: saas.accounts.v1.PlatformAdminService.ListActiveSessions:input_type -> saas.accounts.v1.ListActiveSessionsRequest + 19, // 62: saas.accounts.v1.PlatformAdminService.RevokeSession:input_type -> saas.accounts.v1.RevokeSessionRequest + 20, // 63: saas.accounts.v1.PlatformAdminService.GetOrgEntitlements:input_type -> saas.accounts.v1.GetOrgEntitlementsRequest + 23, // 64: saas.accounts.v1.PlatformAdminService.OverrideEntitlement:input_type -> saas.accounts.v1.OverrideEntitlementRequest + 25, // 65: saas.accounts.v1.PlatformAdminService.GrantPlatformRole:input_type -> saas.accounts.v1.GrantPlatformRoleRequest + 26, // 66: saas.accounts.v1.PlatformAdminService.RevokePlatformRole:input_type -> saas.accounts.v1.RevokePlatformRoleRequest + 27, // 67: saas.accounts.v1.PlatformAdminService.ListPlatformAdmins:input_type -> saas.accounts.v1.ListPlatformAdminsRequest + 5, // 68: saas.accounts.v1.PlatformAdminService.ListAllOrganizations:input_type -> saas.accounts.v1.ListAllOrganizationsRequest + 8, // 69: saas.accounts.v1.PlatformAdminService.GetOrganizationRoster:input_type -> saas.accounts.v1.GetOrganizationRosterRequest + 30, // 70: saas.accounts.v1.PlatformAdminService.ListFeatureFlags:input_type -> saas.accounts.v1.ListFeatureFlagsRequest + 33, // 71: saas.accounts.v1.PlatformAdminService.UpsertFeatureFlag:input_type -> saas.accounts.v1.UpsertFeatureFlagRequest + 66, // 72: saas.accounts.v1.PlatformAdminService.GetJobOperations:input_type -> saas.jobs.v1.GetJobOperationsRequest + 67, // 73: saas.accounts.v1.PlatformAdminService.ListJobs:input_type -> saas.jobs.v1.ListJobsRequest + 68, // 74: saas.accounts.v1.PlatformAdminService.GetJob:input_type -> saas.jobs.v1.GetJobRequest + 69, // 75: saas.accounts.v1.PlatformAdminService.ReplayJob:input_type -> saas.jobs.v1.ReplayJobRequest + 70, // 76: saas.accounts.v1.PlatformAdminService.GetEventOperations:input_type -> saas.events.v1.GetEventOperationsRequest + 71, // 77: saas.accounts.v1.PlatformAdminService.ListEventSubscriptions:input_type -> saas.events.v1.ListEventSubscriptionsRequest + 48, // 78: saas.accounts.v1.PlatformAdminService.ListPlatformCatalogue:input_type -> saas.accounts.v1.ListPlatformCatalogueRequest + 51, // 79: saas.accounts.v1.PlatformAdminService.GetModuleEnvelope:input_type -> saas.accounts.v1.GetModuleEnvelopeRequest + 54, // 80: saas.accounts.v1.PlatformAdminService.PutModuleEnvelope:input_type -> saas.accounts.v1.PutModuleEnvelopeRequest + 4, // 81: saas.accounts.v1.PlatformAdminService.SearchUsers:output_type -> saas.accounts.v1.SearchUsersResponse + 72, // 82: saas.accounts.v1.PlatformAdminService.SuspendUser:output_type -> google.protobuf.Empty + 72, // 83: saas.accounts.v1.PlatformAdminService.UnsuspendUser:output_type -> google.protobuf.Empty + 13, // 84: saas.accounts.v1.PlatformAdminService.ImpersonateUser:output_type -> saas.accounts.v1.ImpersonateUserResponse + 15, // 85: saas.accounts.v1.PlatformAdminService.StopImpersonation:output_type -> saas.accounts.v1.StopImpersonationResponse + 18, // 86: saas.accounts.v1.PlatformAdminService.ListActiveSessions:output_type -> saas.accounts.v1.ListActiveSessionsResponse + 72, // 87: saas.accounts.v1.PlatformAdminService.RevokeSession:output_type -> google.protobuf.Empty + 21, // 88: saas.accounts.v1.PlatformAdminService.GetOrgEntitlements:output_type -> saas.accounts.v1.GetOrgEntitlementsResponse + 24, // 89: saas.accounts.v1.PlatformAdminService.OverrideEntitlement:output_type -> saas.accounts.v1.OverrideEntitlementResponse + 72, // 90: saas.accounts.v1.PlatformAdminService.GrantPlatformRole:output_type -> google.protobuf.Empty + 72, // 91: saas.accounts.v1.PlatformAdminService.RevokePlatformRole:output_type -> google.protobuf.Empty + 29, // 92: saas.accounts.v1.PlatformAdminService.ListPlatformAdmins:output_type -> saas.accounts.v1.ListPlatformAdminsResponse + 7, // 93: saas.accounts.v1.PlatformAdminService.ListAllOrganizations:output_type -> saas.accounts.v1.ListAllOrganizationsResponse + 9, // 94: saas.accounts.v1.PlatformAdminService.GetOrganizationRoster:output_type -> saas.accounts.v1.GetOrganizationRosterResponse + 32, // 95: saas.accounts.v1.PlatformAdminService.ListFeatureFlags:output_type -> saas.accounts.v1.ListFeatureFlagsResponse + 34, // 96: saas.accounts.v1.PlatformAdminService.UpsertFeatureFlag:output_type -> saas.accounts.v1.UpsertFeatureFlagResponse + 73, // 97: saas.accounts.v1.PlatformAdminService.GetJobOperations:output_type -> saas.jobs.v1.GetJobOperationsResponse + 74, // 98: saas.accounts.v1.PlatformAdminService.ListJobs:output_type -> saas.jobs.v1.ListJobsResponse + 75, // 99: saas.accounts.v1.PlatformAdminService.GetJob:output_type -> saas.jobs.v1.GetJobResponse + 76, // 100: saas.accounts.v1.PlatformAdminService.ReplayJob:output_type -> saas.jobs.v1.ReplayJobResponse + 77, // 101: saas.accounts.v1.PlatformAdminService.GetEventOperations:output_type -> saas.events.v1.GetEventOperationsResponse + 78, // 102: saas.accounts.v1.PlatformAdminService.ListEventSubscriptions:output_type -> saas.events.v1.ListEventSubscriptionsResponse + 49, // 103: saas.accounts.v1.PlatformAdminService.ListPlatformCatalogue:output_type -> saas.accounts.v1.ListPlatformCatalogueResponse + 52, // 104: saas.accounts.v1.PlatformAdminService.GetModuleEnvelope:output_type -> saas.accounts.v1.GetModuleEnvelopeResponse + 55, // 105: saas.accounts.v1.PlatformAdminService.PutModuleEnvelope:output_type -> saas.accounts.v1.PutModuleEnvelopeResponse + 81, // [81:106] is the sub-list for method output_type + 56, // [56:81] is the sub-list for method input_type + 56, // [56:56] is the sub-list for extension type_name + 56, // [56:56] is the sub-list for extension extendee + 0, // [0:56] is the sub-list for field type_name } func init() { file_saas_accounts_v1_platform_admin_proto_init() } @@ -4312,7 +4430,7 @@ func file_saas_accounts_v1_platform_admin_proto_init() { GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: unsafe.Slice(unsafe.StringData(file_saas_accounts_v1_platform_admin_proto_rawDesc), len(file_saas_accounts_v1_platform_admin_proto_rawDesc)), NumEnums: 3, - NumMessages: 55, + NumMessages: 56, NumExtensions: 0, NumServices: 1, }, diff --git a/gen/saas/accounts/v1/solution_registry.pb.go b/gen/saas/accounts/v1/solution_registry.pb.go index 8854d92..3488800 100644 --- a/gen/saas/accounts/v1/solution_registry.pb.go +++ b/gen/saas/accounts/v1/solution_registry.pb.go @@ -7,6 +7,7 @@ package accountsv1 import ( + _ "buf.build/gen/go/bufbuild/protovalidate/protocolbuffers/go/buf/validate" protoreflect "google.golang.org/protobuf/reflect/protoreflect" protoimpl "google.golang.org/protobuf/runtime/protoimpl" timestamppb "google.golang.org/protobuf/types/known/timestamppb" @@ -22,21 +23,16 @@ const ( _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20) ) -// SolutionRegistrationStatus is derived from declared state and complete, -// compatible frontend/backend observations, never from an expiring lease. +// SolutionRegistrationStatus is derived from applied presence, never from an +// expiring registration lease or the existence of a frontend. type SolutionRegistrationStatus int32 const ( SolutionRegistrationStatus_SOLUTION_REGISTRATION_STATUS_UNSPECIFIED SolutionRegistrationStatus = 0 - // Both halves are present and their declared contract - // versions agree. This is the only status either surface serves. + // Presence is applied. Both modules and solutions may be headless. SolutionRegistrationStatus_SOLUTION_REGISTRATION_STATUS_ACTIVE SolutionRegistrationStatus = 1 - // A half has not been observed. The record is durable but incomplete, so no - // page advertises it and the gateway has nothing to route to. + // No applied declaration is available for this record. SolutionRegistrationStatus_SOLUTION_REGISTRATION_STATUS_PENDING SolutionRegistrationStatus = 2 - // The two halves declare different contract versions, so activating them - // together would serve a page against a backend it was not built for. - SolutionRegistrationStatus_SOLUTION_REGISTRATION_STATUS_INCOMPATIBLE SolutionRegistrationStatus = 4 // An applied removal keeps the declaration as a tombstone. SolutionRegistrationStatus_SOLUTION_REGISTRATION_STATUS_TOMBSTONED SolutionRegistrationStatus = 5 ) @@ -47,15 +43,13 @@ var ( 0: "SOLUTION_REGISTRATION_STATUS_UNSPECIFIED", 1: "SOLUTION_REGISTRATION_STATUS_ACTIVE", 2: "SOLUTION_REGISTRATION_STATUS_PENDING", - 4: "SOLUTION_REGISTRATION_STATUS_INCOMPATIBLE", 5: "SOLUTION_REGISTRATION_STATUS_TOMBSTONED", } SolutionRegistrationStatus_value = map[string]int32{ - "SOLUTION_REGISTRATION_STATUS_UNSPECIFIED": 0, - "SOLUTION_REGISTRATION_STATUS_ACTIVE": 1, - "SOLUTION_REGISTRATION_STATUS_PENDING": 2, - "SOLUTION_REGISTRATION_STATUS_INCOMPATIBLE": 4, - "SOLUTION_REGISTRATION_STATUS_TOMBSTONED": 5, + "SOLUTION_REGISTRATION_STATUS_UNSPECIFIED": 0, + "SOLUTION_REGISTRATION_STATUS_ACTIVE": 1, + "SOLUTION_REGISTRATION_STATUS_PENDING": 2, + "SOLUTION_REGISTRATION_STATUS_TOMBSTONED": 5, } ) @@ -152,16 +146,19 @@ func (SolutionDeclaredKind) EnumDescriptor() ([]byte, []int) { return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{1} } -// SolutionFrontendBinding is the stored frontend half. manifest is the document -// the frontend validates while reading the projection; accounts stores it -// verbatim and keeps presence authority separate from runtime compatibility. +// SolutionFrontendBinding is the stored frontend half: the `frontend` block of +// the applied presence, copied by accounts in the transaction that applies the +// generation. manifest carries that block as JSON (title, order, +// exposed_module, host_contract, dashboard, surfaces) — the author-declared +// half of the manifest the gateway's registry projection builds, adding the +// host's own constants. Present on either kind when its applied generation +// declares one; absent on a headless component. type SolutionFrontendBinding struct { - state protoimpl.MessageState `protogen:"open.v1"` - Revision int64 `protobuf:"varint,1,opt,name=revision,proto3" json:"revision,omitempty"` - Manifest string `protobuf:"bytes,2,opt,name=manifest,proto3" json:"manifest,omitempty"` - ContractVersion string `protobuf:"bytes,3,opt,name=contract_version,json=contractVersion,proto3" json:"contract_version,omitempty"` - unknownFields protoimpl.UnknownFields - sizeCache protoimpl.SizeCache + state protoimpl.MessageState `protogen:"open.v1"` + Revision int64 `protobuf:"varint,1,opt,name=revision,proto3" json:"revision,omitempty"` + Manifest string `protobuf:"bytes,2,opt,name=manifest,proto3" json:"manifest,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache } func (x *SolutionFrontendBinding) Reset() { @@ -208,83 +205,6 @@ func (x *SolutionFrontendBinding) GetManifest() string { return "" } -func (x *SolutionFrontendBinding) GetContractVersion() string { - if x != nil { - return x.ContractVersion - } - return "" -} - -// SolutionBackendBinding is the stored backend half: the upstream the gateway -// proxies to and the logical service alias it is addressed by. -type SolutionBackendBinding struct { - state protoimpl.MessageState `protogen:"open.v1"` - Revision int64 `protobuf:"varint,1,opt,name=revision,proto3" json:"revision,omitempty"` - Upstream string `protobuf:"bytes,2,opt,name=upstream,proto3" json:"upstream,omitempty"` - ServiceAlias string `protobuf:"bytes,3,opt,name=service_alias,json=serviceAlias,proto3" json:"service_alias,omitempty"` - ContractVersion string `protobuf:"bytes,4,opt,name=contract_version,json=contractVersion,proto3" json:"contract_version,omitempty"` - unknownFields protoimpl.UnknownFields - sizeCache protoimpl.SizeCache -} - -func (x *SolutionBackendBinding) Reset() { - *x = SolutionBackendBinding{} - mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[1] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) -} - -func (x *SolutionBackendBinding) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*SolutionBackendBinding) ProtoMessage() {} - -func (x *SolutionBackendBinding) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[1] - if x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use SolutionBackendBinding.ProtoReflect.Descriptor instead. -func (*SolutionBackendBinding) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{1} -} - -func (x *SolutionBackendBinding) GetRevision() int64 { - if x != nil { - return x.Revision - } - return 0 -} - -func (x *SolutionBackendBinding) GetUpstream() string { - if x != nil { - return x.Upstream - } - return "" -} - -func (x *SolutionBackendBinding) GetServiceAlias() string { - if x != nil { - return x.ServiceAlias - } - return "" -} - -func (x *SolutionBackendBinding) GetContractVersion() string { - if x != nil { - return x.ContractVersion - } - return "" -} - // SolutionRegistration is the canonical record. revision is drawn from one // registry-wide sequence, so revisions are comparable across records and a // consumer can order two snapshots without a wall clock. @@ -296,18 +216,21 @@ type SolutionRegistration struct { Revision int64 `protobuf:"varint,3,opt,name=revision,proto3" json:"revision,omitempty"` Status SolutionRegistrationStatus `protobuf:"varint,4,opt,name=status,proto3,enum=saas.accounts.v1.SolutionRegistrationStatus" json:"status,omitempty"` Frontend *SolutionFrontendBinding `protobuf:"bytes,5,opt,name=frontend,proto3,oneof" json:"frontend,omitempty"` - Backend *SolutionBackendBinding `protobuf:"bytes,6,opt,name=backend,proto3,oneof" json:"backend,omitempty"` UpdatedAt *timestamppb.Timestamp `protobuf:"bytes,7,opt,name=updated_at,json=updatedAt,proto3" json:"updated_at,omitempty"` TombstonedAt *timestamppb.Timestamp `protobuf:"bytes,8,opt,name=tombstoned_at,json=tombstonedAt,proto3,oneof" json:"tombstoned_at,omitempty"` // The binding and immutable target that declared this record. - Declared *SolutionDeclaredBinding `protobuf:"bytes,10,opt,name=declared,proto3,oneof" json:"declared,omitempty"` + Declared *SolutionDeclaredBinding `protobuf:"bytes,10,opt,name=declared,proto3,oneof" json:"declared,omitempty"` + // Presentation from the composing workspace's applied declaration. Present + // only for a solution, independently of its frontend. Membership grants no + // access, consent or installation; viewer lists filter solutions first. + Group *SolutionGroup `protobuf:"bytes,11,opt,name=group,proto3,oneof" json:"group,omitempty"` unknownFields protoimpl.UnknownFields sizeCache protoimpl.SizeCache } func (x *SolutionRegistration) Reset() { *x = SolutionRegistration{} - mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[2] + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[1] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -319,7 +242,7 @@ func (x *SolutionRegistration) String() string { func (*SolutionRegistration) ProtoMessage() {} func (x *SolutionRegistration) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[2] + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[1] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -332,7 +255,7 @@ func (x *SolutionRegistration) ProtoReflect() protoreflect.Message { // Deprecated: Use SolutionRegistration.ProtoReflect.Descriptor instead. func (*SolutionRegistration) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{2} + return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{1} } func (x *SolutionRegistration) GetSolutionId() string { @@ -370,13 +293,6 @@ func (x *SolutionRegistration) GetFrontend() *SolutionFrontendBinding { return nil } -func (x *SolutionRegistration) GetBackend() *SolutionBackendBinding { - if x != nil { - return x.Backend - } - return nil -} - func (x *SolutionRegistration) GetUpdatedAt() *timestamppb.Timestamp { if x != nil { return x.UpdatedAt @@ -398,6 +314,75 @@ func (x *SolutionRegistration) GetDeclared() *SolutionDeclaredBinding { return nil } +func (x *SolutionRegistration) GetGroup() *SolutionGroup { + if x != nil { + return x.Group + } + return nil +} + +// SolutionGroup organises solutions in navigation and the catalogue. It is not +// an authorization subject, installation target or scope. +type SolutionGroup struct { + state protoimpl.MessageState `protogen:"open.v1"` + Id string `protobuf:"bytes,1,opt,name=id,proto3" json:"id,omitempty"` + Title string `protobuf:"bytes,2,opt,name=title,proto3" json:"title,omitempty"` + Order int32 `protobuf:"varint,3,opt,name=order,proto3" json:"order,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *SolutionGroup) Reset() { + *x = SolutionGroup{} + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[2] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *SolutionGroup) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*SolutionGroup) ProtoMessage() {} + +func (x *SolutionGroup) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[2] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use SolutionGroup.ProtoReflect.Descriptor instead. +func (*SolutionGroup) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{2} +} + +func (x *SolutionGroup) GetId() string { + if x != nil { + return x.Id + } + return "" +} + +func (x *SolutionGroup) GetTitle() string { + if x != nil { + return x.Title + } + return "" +} + +func (x *SolutionGroup) GetOrder() int32 { + if x != nil { + return x.Order + } + return 0 +} + // ListSolutionRegistrationsRequest reads the whole registry. There is one // registry per deployment and it holds tens of records at most, so consumers // rebuild their cache from a full snapshot rather than tailing a change feed. @@ -684,10 +669,14 @@ type SolutionHostBindingAppliedGeneration struct { Routes []string `protobuf:"bytes,3,rep,name=routes,proto3" json:"routes,omitempty"` // The registration record this generation reconciled into. A tombstone keeps // the key it withdrew, which is the only way it knows what to withdraw. - SolutionId string `protobuf:"bytes,4,opt,name=solution_id,json=solutionId,proto3" json:"solution_id,omitempty"` - Release string `protobuf:"bytes,5,opt,name=release,proto3" json:"release,omitempty"` - unknownFields protoimpl.UnknownFields - sizeCache protoimpl.SizeCache + SolutionId string `protobuf:"bytes,4,opt,name=solution_id,json=solutionId,proto3" json:"solution_id,omitempty"` + Release string `protobuf:"bytes,5,opt,name=release,proto3" json:"release,omitempty"` + // Opaque Codefly endpoint delivery joined to this exact applied document. + // Only the Codefly SDK interprets it. Empty means no delivered route; neither + // desired state nor startup addresses are a fallback. + EndpointDelivery []byte `protobuf:"bytes,6,opt,name=endpoint_delivery,json=endpointDelivery,proto3" json:"endpoint_delivery,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache } func (x *SolutionHostBindingAppliedGeneration) Reset() { @@ -755,6 +744,13 @@ func (x *SolutionHostBindingAppliedGeneration) GetRelease() string { return "" } +func (x *SolutionHostBindingAppliedGeneration) GetEndpointDelivery() []byte { + if x != nil { + return x.EndpointDelivery + } + return nil +} + // SolutionHostBindingState is one binding's whole state: desired, applied, and // why they differ. Endpoint and manifest observations live on // SolutionRegistration, separate from the declaration that grants presence. @@ -883,6 +879,93 @@ func (x *SolutionHostBindingState) GetUpdatedAt() *timestamppb.Timestamp { return nil } +// One previously applied frontend for a still-live target. The targeted read +// joins exact admitted bytes to applied history, excluding delivered-only and +// closed-target identities. Public code confers no installation or API access. +type SolutionFrontendGeneration struct { + state protoimpl.MessageState `protogen:"open.v1"` + Generation uint64 `protobuf:"varint,1,opt,name=generation,proto3" json:"generation,omitempty"` + TargetId string `protobuf:"bytes,2,opt,name=target_id,json=targetId,proto3" json:"target_id,omitempty"` + BindingId string `protobuf:"bytes,3,opt,name=binding_id,json=bindingId,proto3" json:"binding_id,omitempty"` + Release string `protobuf:"bytes,4,opt,name=release,proto3" json:"release,omitempty"` + Frontend string `protobuf:"bytes,5,opt,name=frontend,proto3" json:"frontend,omitempty"` + AssetVersion string `protobuf:"bytes,6,opt,name=asset_version,json=assetVersion,proto3" json:"asset_version,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *SolutionFrontendGeneration) Reset() { + *x = SolutionFrontendGeneration{} + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[9] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *SolutionFrontendGeneration) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*SolutionFrontendGeneration) ProtoMessage() {} + +func (x *SolutionFrontendGeneration) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[9] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use SolutionFrontendGeneration.ProtoReflect.Descriptor instead. +func (*SolutionFrontendGeneration) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{9} +} + +func (x *SolutionFrontendGeneration) GetGeneration() uint64 { + if x != nil { + return x.Generation + } + return 0 +} + +func (x *SolutionFrontendGeneration) GetTargetId() string { + if x != nil { + return x.TargetId + } + return "" +} + +func (x *SolutionFrontendGeneration) GetBindingId() string { + if x != nil { + return x.BindingId + } + return "" +} + +func (x *SolutionFrontendGeneration) GetRelease() string { + if x != nil { + return x.Release + } + return "" +} + +func (x *SolutionFrontendGeneration) GetFrontend() string { + if x != nil { + return x.Frontend + } + return "" +} + +func (x *SolutionFrontendGeneration) GetAssetVersion() string { + if x != nil { + return x.AssetVersion + } + return "" +} + // ListSolutionHostBindingsRequest reads every declared binding. There is one set // per deployment and it holds tens of bindings at most, so a consumer rebuilds // its view from a full snapshot. @@ -894,7 +977,7 @@ type ListSolutionHostBindingsRequest struct { func (x *ListSolutionHostBindingsRequest) Reset() { *x = ListSolutionHostBindingsRequest{} - mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[9] + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[10] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -906,7 +989,7 @@ func (x *ListSolutionHostBindingsRequest) String() string { func (*ListSolutionHostBindingsRequest) ProtoMessage() {} func (x *ListSolutionHostBindingsRequest) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[9] + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[10] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -919,7 +1002,7 @@ func (x *ListSolutionHostBindingsRequest) ProtoReflect() protoreflect.Message { // Deprecated: Use ListSolutionHostBindingsRequest.ProtoReflect.Descriptor instead. func (*ListSolutionHostBindingsRequest) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{9} + return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{10} } type ListSolutionHostBindingsResponse struct { @@ -931,7 +1014,7 @@ type ListSolutionHostBindingsResponse struct { func (x *ListSolutionHostBindingsResponse) Reset() { *x = ListSolutionHostBindingsResponse{} - mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[10] + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[11] ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) ms.StoreMessageInfo(mi) } @@ -943,7 +1026,7 @@ func (x *ListSolutionHostBindingsResponse) String() string { func (*ListSolutionHostBindingsResponse) ProtoMessage() {} func (x *ListSolutionHostBindingsResponse) ProtoReflect() protoreflect.Message { - mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[10] + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[11] if x != nil { ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) if ms.LoadMessageInfo() == nil { @@ -956,7 +1039,7 @@ func (x *ListSolutionHostBindingsResponse) ProtoReflect() protoreflect.Message { // Deprecated: Use ListSolutionHostBindingsResponse.ProtoReflect.Descriptor instead. func (*ListSolutionHostBindingsResponse) Descriptor() ([]byte, []int) { - return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{10} + return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{11} } func (x *ListSolutionHostBindingsResponse) GetBindings() []*SolutionHostBindingState { @@ -966,39 +1049,134 @@ func (x *ListSolutionHostBindingsResponse) GetBindings() []*SolutionHostBindingS return nil } +// A retained frontend read returns at most one exact APPLIED identity. It never +// expands the shared registry snapshot by the number of retained generations. +type GetRetainedSolutionFrontendRequest struct { + state protoimpl.MessageState `protogen:"open.v1"` + BindingId string `protobuf:"bytes,1,opt,name=binding_id,json=bindingId,proto3" json:"binding_id,omitempty"` + AssetVersion string `protobuf:"bytes,2,opt,name=asset_version,json=assetVersion,proto3" json:"asset_version,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *GetRetainedSolutionFrontendRequest) Reset() { + *x = GetRetainedSolutionFrontendRequest{} + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[12] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *GetRetainedSolutionFrontendRequest) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*GetRetainedSolutionFrontendRequest) ProtoMessage() {} + +func (x *GetRetainedSolutionFrontendRequest) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[12] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use GetRetainedSolutionFrontendRequest.ProtoReflect.Descriptor instead. +func (*GetRetainedSolutionFrontendRequest) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{12} +} + +func (x *GetRetainedSolutionFrontendRequest) GetBindingId() string { + if x != nil { + return x.BindingId + } + return "" +} + +func (x *GetRetainedSolutionFrontendRequest) GetAssetVersion() string { + if x != nil { + return x.AssetVersion + } + return "" +} + +type GetRetainedSolutionFrontendResponse struct { + state protoimpl.MessageState `protogen:"open.v1"` + Frontend *SolutionFrontendGeneration `protobuf:"bytes,1,opt,name=frontend,proto3" json:"frontend,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache +} + +func (x *GetRetainedSolutionFrontendResponse) Reset() { + *x = GetRetainedSolutionFrontendResponse{} + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[13] + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + ms.StoreMessageInfo(mi) +} + +func (x *GetRetainedSolutionFrontendResponse) String() string { + return protoimpl.X.MessageStringOf(x) +} + +func (*GetRetainedSolutionFrontendResponse) ProtoMessage() {} + +func (x *GetRetainedSolutionFrontendResponse) ProtoReflect() protoreflect.Message { + mi := &file_saas_accounts_v1_solution_registry_proto_msgTypes[13] + if x != nil { + ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) + if ms.LoadMessageInfo() == nil { + ms.StoreMessageInfo(mi) + } + return ms + } + return mi.MessageOf(x) +} + +// Deprecated: Use GetRetainedSolutionFrontendResponse.ProtoReflect.Descriptor instead. +func (*GetRetainedSolutionFrontendResponse) Descriptor() ([]byte, []int) { + return file_saas_accounts_v1_solution_registry_proto_rawDescGZIP(), []int{13} +} + +func (x *GetRetainedSolutionFrontendResponse) GetFrontend() *SolutionFrontendGeneration { + if x != nil { + return x.Frontend + } + return nil +} + var File_saas_accounts_v1_solution_registry_proto protoreflect.FileDescriptor const file_saas_accounts_v1_solution_registry_proto_rawDesc = "" + "\n" + - "(saas/accounts/v1/solution_registry.proto\x12\x10saas.accounts.v1\x1a\x1fgoogle/protobuf/timestamp.proto\"\x94\x01\n" + + "(saas/accounts/v1/solution_registry.proto\x12\x10saas.accounts.v1\x1a\x1fgoogle/protobuf/timestamp.proto\x1a\x1bbuf/validate/validate.proto\"\x81\x01\n" + "\x17SolutionFrontendBinding\x12\x1a\n" + "\brevision\x18\x01 \x01(\x03R\brevision\x12\x1a\n" + - "\bmanifest\x18\x02 \x01(\tR\bmanifest\x12)\n" + - "\x10contract_version\x18\x03 \x01(\tR\x0fcontractVersionJ\x04\b\x04\x10\x05R\x10lease_expires_at\"\xb8\x01\n" + - "\x16SolutionBackendBinding\x12\x1a\n" + - "\brevision\x18\x01 \x01(\x03R\brevision\x12\x1a\n" + - "\bupstream\x18\x02 \x01(\tR\bupstream\x12#\n" + - "\rservice_alias\x18\x03 \x01(\tR\fserviceAlias\x12)\n" + - "\x10contract_version\x18\x04 \x01(\tR\x0fcontractVersionJ\x04\b\x05\x10\x06R\x10lease_expires_at\"\xe9\x04\n" + + "\bmanifest\x18\x02 \x01(\tR\bmanifestJ\x04\b\x03\x10\x04J\x04\b\x04\x10\x05R\x10contract_versionR\x10lease_expires_at\"\xe9\x04\n" + "\x14SolutionRegistration\x12\x1f\n" + "\vsolution_id\x18\x01 \x01(\tR\n" + "solutionId\x12\x1c\n" + "\tpublisher\x18\x02 \x01(\tR\tpublisher\x12\x1a\n" + "\brevision\x18\x03 \x01(\x03R\brevision\x12D\n" + "\x06status\x18\x04 \x01(\x0e2,.saas.accounts.v1.SolutionRegistrationStatusR\x06status\x12J\n" + - "\bfrontend\x18\x05 \x01(\v2).saas.accounts.v1.SolutionFrontendBindingH\x00R\bfrontend\x88\x01\x01\x12G\n" + - "\abackend\x18\x06 \x01(\v2(.saas.accounts.v1.SolutionBackendBindingH\x01R\abackend\x88\x01\x01\x129\n" + + "\bfrontend\x18\x05 \x01(\v2).saas.accounts.v1.SolutionFrontendBindingH\x00R\bfrontend\x88\x01\x01\x129\n" + "\n" + "updated_at\x18\a \x01(\v2\x1a.google.protobuf.TimestampR\tupdatedAt\x12D\n" + - "\rtombstoned_at\x18\b \x01(\v2\x1a.google.protobuf.TimestampH\x02R\ftombstonedAt\x88\x01\x01\x12J\n" + + "\rtombstoned_at\x18\b \x01(\v2\x1a.google.protobuf.TimestampH\x01R\ftombstonedAt\x88\x01\x01\x12J\n" + "\bdeclared\x18\n" + - " \x01(\v2).saas.accounts.v1.SolutionDeclaredBindingH\x03R\bdeclared\x88\x01\x01B\v\n" + - "\t_frontendB\n" + - "\n" + - "\b_backendB\x10\n" + + " \x01(\v2).saas.accounts.v1.SolutionDeclaredBindingH\x02R\bdeclared\x88\x01\x01\x12:\n" + + "\x05group\x18\v \x01(\v2\x1f.saas.accounts.v1.SolutionGroupH\x03R\x05group\x88\x01\x01B\v\n" + + "\t_frontendB\x10\n" + "\x0e_tombstoned_atB\v\n" + - "\t_declaredJ\x04\b\t\x10\n" + - "R\x10runtime_boundary\"Q\n" + + "\t_declaredB\b\n" + + "\x06_groupJ\x04\b\x06\x10\aJ\x04\b\t\x10\n" + + "R\abackendR\x10runtime_boundary\"K\n" + + "\rSolutionGroup\x12\x0e\n" + + "\x02id\x18\x01 \x01(\tR\x02id\x12\x14\n" + + "\x05title\x18\x02 \x01(\tR\x05title\x12\x14\n" + + "\x05order\x18\x03 \x01(\x05R\x05order\"Q\n" + " ListSolutionRegistrationsRequest\x12-\n" + "\x12include_tombstoned\x18\x01 \x01(\bR\x11includeTombstoned\"\x9e\x01\n" + "!ListSolutionRegistrationsResponse\x12L\n" + @@ -1019,7 +1197,7 @@ const file_saas_accounts_v1_solution_registry_proto_rawDesc = "" + "generation\x12\x16\n" + "\x06digest\x18\x02 \x01(\tR\x06digest\x12\x1a\n" + "\bdocument\x18\x03 \x01(\tR\bdocument\x12*\n" + - "\x02at\x18\x04 \x01(\v2\x1a.google.protobuf.TimestampR\x02at\"\xe4\x01\n" + + "\x02at\x18\x04 \x01(\v2\x1a.google.protobuf.TimestampR\x02at\"\x91\x02\n" + "$SolutionHostBindingAppliedGeneration\x12O\n" + "\n" + "generation\x18\x01 \x01(\v2/.saas.accounts.v1.SolutionHostBindingGenerationR\n" + @@ -1028,7 +1206,8 @@ const file_saas_accounts_v1_solution_registry_proto_rawDesc = "" + "\x06routes\x18\x03 \x03(\tR\x06routes\x12\x1f\n" + "\vsolution_id\x18\x04 \x01(\tR\n" + "solutionId\x12\x18\n" + - "\arelease\x18\x05 \x01(\tR\arelease\"\x93\x05\n" + + "\arelease\x18\x05 \x01(\tR\arelease\x12+\n" + + "\x11endpoint_delivery\x18\x06 \x01(\fR\x10endpointDelivery\"\x93\x05\n" + "\x18SolutionHostBindingState\x12\x1d\n" + "\n" + "binding_id\x18\x01 \x01(\tR\tbindingId\x12'\n" + @@ -1048,16 +1227,31 @@ const file_saas_accounts_v1_solution_registry_proto_rawDesc = "" + "\n" + "\b_appliedB\x10\n" + "\x0e_pending_sinceB\x0f\n" + - "\r_registration\"!\n" + + "\r_registration\"\xd3\x01\n" + + "\x1aSolutionFrontendGeneration\x12\x1e\n" + + "\n" + + "generation\x18\x01 \x01(\x04R\n" + + "generation\x12\x1b\n" + + "\ttarget_id\x18\x02 \x01(\tR\btargetId\x12\x1d\n" + + "\n" + + "binding_id\x18\x03 \x01(\tR\tbindingId\x12\x18\n" + + "\arelease\x18\x04 \x01(\tR\arelease\x12\x1a\n" + + "\bfrontend\x18\x05 \x01(\tR\bfrontend\x12#\n" + + "\rasset_version\x18\x06 \x01(\tR\fassetVersion\"!\n" + "\x1fListSolutionHostBindingsRequest\"j\n" + " ListSolutionHostBindingsResponse\x12F\n" + - "\bbindings\x18\x01 \x03(\v2*.saas.accounts.v1.SolutionHostBindingStateR\bbindings*\xa5\x02\n" + + "\bbindings\x18\x01 \x03(\v2*.saas.accounts.v1.SolutionHostBindingStateR\bbindings\"\x88\x01\n" + + "\"GetRetainedSolutionFrontendRequest\x12&\n" + + "\n" + + "binding_id\x18\x01 \x01(\tB\a\xbaH\x04r\x02\x10\x01R\tbindingId\x12:\n" + + "\rasset_version\x18\x02 \x01(\tB\x15\xbaH\x12r\x102\x0e^[a-f0-9]{64}$R\fassetVersion\"o\n" + + "#GetRetainedSolutionFrontendResponse\x12H\n" + + "\bfrontend\x18\x01 \x01(\v2,.saas.accounts.v1.SolutionFrontendGenerationR\bfrontend*\xa7\x02\n" + "\x1aSolutionRegistrationStatus\x12,\n" + "(SOLUTION_REGISTRATION_STATUS_UNSPECIFIED\x10\x00\x12'\n" + "#SOLUTION_REGISTRATION_STATUS_ACTIVE\x10\x01\x12(\n" + - "$SOLUTION_REGISTRATION_STATUS_PENDING\x10\x02\x12-\n" + - ")SOLUTION_REGISTRATION_STATUS_INCOMPATIBLE\x10\x04\x12+\n" + - "'SOLUTION_REGISTRATION_STATUS_TOMBSTONED\x10\x05\"\x04\b\x03\x10\x03*$SOLUTION_REGISTRATION_STATUS_EXPIRED*\x86\x01\n" + + "$SOLUTION_REGISTRATION_STATUS_PENDING\x10\x02\x12+\n" + + "'SOLUTION_REGISTRATION_STATUS_TOMBSTONED\x10\x05\"\x04\b\x03\x10\x03\"\x04\b\x04\x10\x04*$SOLUTION_REGISTRATION_STATUS_EXPIRED*)SOLUTION_REGISTRATION_STATUS_INCOMPATIBLE*\x86\x01\n" + "\x14SolutionDeclaredKind\x12&\n" + "\"SOLUTION_DECLARED_KIND_UNSPECIFIED\x10\x00\x12#\n" + "\x1fSOLUTION_DECLARED_KIND_SOLUTION\x10\x01\x12!\n" + @@ -1077,45 +1271,49 @@ func file_saas_accounts_v1_solution_registry_proto_rawDescGZIP() []byte { } var file_saas_accounts_v1_solution_registry_proto_enumTypes = make([]protoimpl.EnumInfo, 2) -var file_saas_accounts_v1_solution_registry_proto_msgTypes = make([]protoimpl.MessageInfo, 11) +var file_saas_accounts_v1_solution_registry_proto_msgTypes = make([]protoimpl.MessageInfo, 14) var file_saas_accounts_v1_solution_registry_proto_goTypes = []any{ (SolutionRegistrationStatus)(0), // 0: saas.accounts.v1.SolutionRegistrationStatus (SolutionDeclaredKind)(0), // 1: saas.accounts.v1.SolutionDeclaredKind (*SolutionFrontendBinding)(nil), // 2: saas.accounts.v1.SolutionFrontendBinding - (*SolutionBackendBinding)(nil), // 3: saas.accounts.v1.SolutionBackendBinding - (*SolutionRegistration)(nil), // 4: saas.accounts.v1.SolutionRegistration + (*SolutionRegistration)(nil), // 3: saas.accounts.v1.SolutionRegistration + (*SolutionGroup)(nil), // 4: saas.accounts.v1.SolutionGroup (*ListSolutionRegistrationsRequest)(nil), // 5: saas.accounts.v1.ListSolutionRegistrationsRequest (*ListSolutionRegistrationsResponse)(nil), // 6: saas.accounts.v1.ListSolutionRegistrationsResponse (*SolutionDeclaredBinding)(nil), // 7: saas.accounts.v1.SolutionDeclaredBinding (*SolutionHostBindingGeneration)(nil), // 8: saas.accounts.v1.SolutionHostBindingGeneration (*SolutionHostBindingAppliedGeneration)(nil), // 9: saas.accounts.v1.SolutionHostBindingAppliedGeneration (*SolutionHostBindingState)(nil), // 10: saas.accounts.v1.SolutionHostBindingState - (*ListSolutionHostBindingsRequest)(nil), // 11: saas.accounts.v1.ListSolutionHostBindingsRequest - (*ListSolutionHostBindingsResponse)(nil), // 12: saas.accounts.v1.ListSolutionHostBindingsResponse - (*timestamppb.Timestamp)(nil), // 13: google.protobuf.Timestamp + (*SolutionFrontendGeneration)(nil), // 11: saas.accounts.v1.SolutionFrontendGeneration + (*ListSolutionHostBindingsRequest)(nil), // 12: saas.accounts.v1.ListSolutionHostBindingsRequest + (*ListSolutionHostBindingsResponse)(nil), // 13: saas.accounts.v1.ListSolutionHostBindingsResponse + (*GetRetainedSolutionFrontendRequest)(nil), // 14: saas.accounts.v1.GetRetainedSolutionFrontendRequest + (*GetRetainedSolutionFrontendResponse)(nil), // 15: saas.accounts.v1.GetRetainedSolutionFrontendResponse + (*timestamppb.Timestamp)(nil), // 16: google.protobuf.Timestamp } var file_saas_accounts_v1_solution_registry_proto_depIdxs = []int32{ 0, // 0: saas.accounts.v1.SolutionRegistration.status:type_name -> saas.accounts.v1.SolutionRegistrationStatus 2, // 1: saas.accounts.v1.SolutionRegistration.frontend:type_name -> saas.accounts.v1.SolutionFrontendBinding - 3, // 2: saas.accounts.v1.SolutionRegistration.backend:type_name -> saas.accounts.v1.SolutionBackendBinding - 13, // 3: saas.accounts.v1.SolutionRegistration.updated_at:type_name -> google.protobuf.Timestamp - 13, // 4: saas.accounts.v1.SolutionRegistration.tombstoned_at:type_name -> google.protobuf.Timestamp - 7, // 5: saas.accounts.v1.SolutionRegistration.declared:type_name -> saas.accounts.v1.SolutionDeclaredBinding - 4, // 6: saas.accounts.v1.ListSolutionRegistrationsResponse.registrations:type_name -> saas.accounts.v1.SolutionRegistration + 16, // 2: saas.accounts.v1.SolutionRegistration.updated_at:type_name -> google.protobuf.Timestamp + 16, // 3: saas.accounts.v1.SolutionRegistration.tombstoned_at:type_name -> google.protobuf.Timestamp + 7, // 4: saas.accounts.v1.SolutionRegistration.declared:type_name -> saas.accounts.v1.SolutionDeclaredBinding + 4, // 5: saas.accounts.v1.SolutionRegistration.group:type_name -> saas.accounts.v1.SolutionGroup + 3, // 6: saas.accounts.v1.ListSolutionRegistrationsResponse.registrations:type_name -> saas.accounts.v1.SolutionRegistration 1, // 7: saas.accounts.v1.SolutionDeclaredBinding.kind:type_name -> saas.accounts.v1.SolutionDeclaredKind - 13, // 8: saas.accounts.v1.SolutionHostBindingGeneration.at:type_name -> google.protobuf.Timestamp + 16, // 8: saas.accounts.v1.SolutionHostBindingGeneration.at:type_name -> google.protobuf.Timestamp 8, // 9: saas.accounts.v1.SolutionHostBindingAppliedGeneration.generation:type_name -> saas.accounts.v1.SolutionHostBindingGeneration 8, // 10: saas.accounts.v1.SolutionHostBindingState.desired:type_name -> saas.accounts.v1.SolutionHostBindingGeneration 9, // 11: saas.accounts.v1.SolutionHostBindingState.applied:type_name -> saas.accounts.v1.SolutionHostBindingAppliedGeneration - 13, // 12: saas.accounts.v1.SolutionHostBindingState.pending_since:type_name -> google.protobuf.Timestamp - 4, // 13: saas.accounts.v1.SolutionHostBindingState.registration:type_name -> saas.accounts.v1.SolutionRegistration - 13, // 14: saas.accounts.v1.SolutionHostBindingState.updated_at:type_name -> google.protobuf.Timestamp + 16, // 12: saas.accounts.v1.SolutionHostBindingState.pending_since:type_name -> google.protobuf.Timestamp + 3, // 13: saas.accounts.v1.SolutionHostBindingState.registration:type_name -> saas.accounts.v1.SolutionRegistration + 16, // 14: saas.accounts.v1.SolutionHostBindingState.updated_at:type_name -> google.protobuf.Timestamp 10, // 15: saas.accounts.v1.ListSolutionHostBindingsResponse.bindings:type_name -> saas.accounts.v1.SolutionHostBindingState - 16, // [16:16] is the sub-list for method output_type - 16, // [16:16] is the sub-list for method input_type - 16, // [16:16] is the sub-list for extension type_name - 16, // [16:16] is the sub-list for extension extendee - 0, // [0:16] is the sub-list for field type_name + 11, // 16: saas.accounts.v1.GetRetainedSolutionFrontendResponse.frontend:type_name -> saas.accounts.v1.SolutionFrontendGeneration + 17, // [17:17] is the sub-list for method output_type + 17, // [17:17] is the sub-list for method input_type + 17, // [17:17] is the sub-list for extension type_name + 17, // [17:17] is the sub-list for extension extendee + 0, // [0:17] is the sub-list for field type_name } func init() { file_saas_accounts_v1_solution_registry_proto_init() } @@ -1123,7 +1321,7 @@ func file_saas_accounts_v1_solution_registry_proto_init() { if File_saas_accounts_v1_solution_registry_proto != nil { return } - file_saas_accounts_v1_solution_registry_proto_msgTypes[2].OneofWrappers = []any{} + file_saas_accounts_v1_solution_registry_proto_msgTypes[1].OneofWrappers = []any{} file_saas_accounts_v1_solution_registry_proto_msgTypes[8].OneofWrappers = []any{} type x struct{} out := protoimpl.TypeBuilder{ @@ -1131,7 +1329,7 @@ func file_saas_accounts_v1_solution_registry_proto_init() { GoPackagePath: reflect.TypeOf(x{}).PkgPath(), RawDescriptor: unsafe.Slice(unsafe.StringData(file_saas_accounts_v1_solution_registry_proto_rawDesc), len(file_saas_accounts_v1_solution_registry_proto_rawDesc)), NumEnums: 2, - NumMessages: 11, + NumMessages: 14, NumExtensions: 0, NumServices: 0, }, diff --git a/gen/saas/accounts/v1/solution_registry_service.pb.go b/gen/saas/accounts/v1/solution_registry_service.pb.go index 7363473..4acfea2 100644 --- a/gen/saas/accounts/v1/solution_registry_service.pb.go +++ b/gen/saas/accounts/v1/solution_registry_service.pb.go @@ -25,25 +25,30 @@ var File_saas_accounts_v1_solution_registry_service_proto protoreflect.FileDescr const file_saas_accounts_v1_solution_registry_service_proto_rawDesc = "" + "\n" + - "0saas/accounts/v1/solution_registry_service.proto\x12\x10saas.accounts.v1\x1a(saas/accounts/v1/solution_registry.proto\x1a\x1csaas/policy/v1/options.proto2\xd8\x02\n" + + "0saas/accounts/v1/solution_registry_service.proto\x12\x10saas.accounts.v1\x1a(saas/accounts/v1/solution_registry.proto\x1a\x1csaas/policy/v1/options.proto2\xff\x03\n" + "\x17SolutionRegistryService\x12\x9b\x01\n" + "\x18ListSolutionHostBindings\x121.saas.accounts.v1.ListSolutionHostBindingsRequest\x1a2.saas.accounts.v1.ListSolutionHostBindingsResponse\"\x18\xc2\xf3\x18\x14\b\x03\x10\x010\x01:\x02\x10\x01@\x01H\aP\x03X\x03`\x01\x12\x9e\x01\n" + - "\x19ListSolutionRegistrations\x122.saas.accounts.v1.ListSolutionRegistrationsRequest\x1a3.saas.accounts.v1.ListSolutionRegistrationsResponse\"\x18\xc2\xf3\x18\x14\b\x03\x10\x010\x01:\x02\x10\x01@\x01H\aP\x03X\x03`\x01B\xda\x01\n" + + "\x19ListSolutionRegistrations\x122.saas.accounts.v1.ListSolutionRegistrationsRequest\x1a3.saas.accounts.v1.ListSolutionRegistrationsResponse\"\x18\xc2\xf3\x18\x14\b\x03\x10\x010\x01:\x02\x10\x01@\x01H\aP\x03X\x03`\x01\x12\xa4\x01\n" + + "\x1bGetRetainedSolutionFrontend\x124.saas.accounts.v1.GetRetainedSolutionFrontendRequest\x1a5.saas.accounts.v1.GetRetainedSolutionFrontendResponse\"\x18\xc2\xf3\x18\x14\b\x03\x10\x010\x01:\x02\x10\x01@\x01H\aP\x03X\x03`\x01B\xda\x01\n" + "\x14com.saas.accounts.v1B\x1cSolutionRegistryServiceProtoP\x01ZBgithub.com/codefly-dev/saas-sdk-go/gen/saas/accounts/v1;accountsv1\xa2\x02\x03SAX\xaa\x02\x10Saas.Accounts.V1\xca\x02\x10Saas\\Accounts\\V1\xe2\x02\x1cSaas\\Accounts\\V1\\GPBMetadata\xea\x02\x12Saas::Accounts::V1b\x06proto3" var file_saas_accounts_v1_solution_registry_service_proto_goTypes = []any{ - (*ListSolutionHostBindingsRequest)(nil), // 0: saas.accounts.v1.ListSolutionHostBindingsRequest - (*ListSolutionRegistrationsRequest)(nil), // 1: saas.accounts.v1.ListSolutionRegistrationsRequest - (*ListSolutionHostBindingsResponse)(nil), // 2: saas.accounts.v1.ListSolutionHostBindingsResponse - (*ListSolutionRegistrationsResponse)(nil), // 3: saas.accounts.v1.ListSolutionRegistrationsResponse + (*ListSolutionHostBindingsRequest)(nil), // 0: saas.accounts.v1.ListSolutionHostBindingsRequest + (*ListSolutionRegistrationsRequest)(nil), // 1: saas.accounts.v1.ListSolutionRegistrationsRequest + (*GetRetainedSolutionFrontendRequest)(nil), // 2: saas.accounts.v1.GetRetainedSolutionFrontendRequest + (*ListSolutionHostBindingsResponse)(nil), // 3: saas.accounts.v1.ListSolutionHostBindingsResponse + (*ListSolutionRegistrationsResponse)(nil), // 4: saas.accounts.v1.ListSolutionRegistrationsResponse + (*GetRetainedSolutionFrontendResponse)(nil), // 5: saas.accounts.v1.GetRetainedSolutionFrontendResponse } var file_saas_accounts_v1_solution_registry_service_proto_depIdxs = []int32{ 0, // 0: saas.accounts.v1.SolutionRegistryService.ListSolutionHostBindings:input_type -> saas.accounts.v1.ListSolutionHostBindingsRequest 1, // 1: saas.accounts.v1.SolutionRegistryService.ListSolutionRegistrations:input_type -> saas.accounts.v1.ListSolutionRegistrationsRequest - 2, // 2: saas.accounts.v1.SolutionRegistryService.ListSolutionHostBindings:output_type -> saas.accounts.v1.ListSolutionHostBindingsResponse - 3, // 3: saas.accounts.v1.SolutionRegistryService.ListSolutionRegistrations:output_type -> saas.accounts.v1.ListSolutionRegistrationsResponse - 2, // [2:4] is the sub-list for method output_type - 0, // [0:2] is the sub-list for method input_type + 2, // 2: saas.accounts.v1.SolutionRegistryService.GetRetainedSolutionFrontend:input_type -> saas.accounts.v1.GetRetainedSolutionFrontendRequest + 3, // 3: saas.accounts.v1.SolutionRegistryService.ListSolutionHostBindings:output_type -> saas.accounts.v1.ListSolutionHostBindingsResponse + 4, // 4: saas.accounts.v1.SolutionRegistryService.ListSolutionRegistrations:output_type -> saas.accounts.v1.ListSolutionRegistrationsResponse + 5, // 5: saas.accounts.v1.SolutionRegistryService.GetRetainedSolutionFrontend:output_type -> saas.accounts.v1.GetRetainedSolutionFrontendResponse + 3, // [3:6] is the sub-list for method output_type + 0, // [0:3] is the sub-list for method input_type 0, // [0:0] is the sub-list for extension type_name 0, // [0:0] is the sub-list for extension extendee 0, // [0:0] is the sub-list for field type_name diff --git a/gen/saas/accounts/v1/work_contexts.pb.go b/gen/saas/accounts/v1/work_contexts.pb.go index 5f5952b..a44e74d 100644 --- a/gen/saas/accounts/v1/work_contexts.pb.go +++ b/gen/saas/accounts/v1/work_contexts.pb.go @@ -955,8 +955,20 @@ type CheckAuthorizationRevisionRequest struct { // confirmed only against that binding, re-read live; such a context checked // without it is not confirmed. Empty for a context that seals none. OperationBindingId *string `protobuf:"bytes,5,opt,name=operation_binding_id,json=operationBindingId,proto3,oneof" json:"operation_binding_id,omitempty"` - unknownFields protoimpl.UnknownFields - sizeCache protoimpl.SizeCache + // seals_no_binding ASSERTS that the context names no operation binding at + // all. A consumer must send either this or operation_binding_id, and a + // request carrying neither is refused as malformed rather than confirmed. + // + // The distinction is the whole point. The signed capability never crosses + // this boundary (see above), so the host reads the binding from fields the + // consumer copied out of it — and an OMITTED field and a context that + // genuinely seals none are indistinguishable unless one of them is stated. + // While they were, a consumer that simply forgot the binding had a narrowed + // delegation confirmed against its module's much broader installation. Now + // absence is something a consumer asserts, and forgetting is an error. + SealsNoBinding *bool `protobuf:"varint,6,opt,name=seals_no_binding,json=sealsNoBinding,proto3,oneof" json:"seals_no_binding,omitempty"` + unknownFields protoimpl.UnknownFields + sizeCache protoimpl.SizeCache } func (x *CheckAuthorizationRevisionRequest) Reset() { @@ -1024,6 +1036,13 @@ func (x *CheckAuthorizationRevisionRequest) GetOperationBindingId() string { return "" } +func (x *CheckAuthorizationRevisionRequest) GetSealsNoBinding() bool { + if x != nil && x.SealsNoBinding != nil { + return *x.SealsNoBinding + } + return false +} + // AuthorizeEvidenceReadRequest asks Accounts to authorize one filtered // Evidence read using current membership and RBAC state. Empty optional // filters describe a tenant-directory read and require unscoped evidence:read. @@ -1291,7 +1310,7 @@ const file_saas_accounts_v1_work_contexts_proto_rawDesc = "" + "\v_project_id\"\x8f\x01\n" + "\x1aWorkContextRevisionSubject\x12+\n" + "\fprincipal_id\x18\x01 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\vprincipalId\x12D\n" + - "\x06scopes\x18\x02 \x03(\v2\".saas.accounts.v1.WorkContextScopeB\b\xbaH\x05\x92\x01\x02\x10@R\x06scopes\"\xee\x02\n" + + "\x06scopes\x18\x02 \x03(\v2\".saas.accounts.v1.WorkContextScopeB\b\xbaH\x05\x92\x01\x02\x10@R\x06scopes\"\xb2\x03\n" + "!CheckAuthorizationRevisionRequest\x12\x1f\n" + "\x06org_id\x18\x01 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x05orgId\x126\n" + "\x12owner_principal_id\x18\x02 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x10ownerPrincipalId\x12>\n" + @@ -1299,8 +1318,10 @@ const file_saas_accounts_v1_work_contexts_proto_rawDesc = "" + "\bsubjects\x18\x04 \x03(\v2,.saas.accounts.v1.WorkContextRevisionSubjectB\n" + "\xbaH\a\x92\x01\x04\b\x01\x10\x11R\bsubjects\x12A\n" + "\x14operation_binding_id\x18\x05 \x01(\tB\n" + - "\xbaH\ar\x05\x10\x01\x18\x80\x04H\x00R\x12operationBindingId\x88\x01\x01B\x17\n" + - "\x15_operation_binding_id\"\xc2\x02\n" + + "\xbaH\ar\x05\x10\x01\x18\x80\x04H\x00R\x12operationBindingId\x88\x01\x01\x12-\n" + + "\x10seals_no_binding\x18\x06 \x01(\bH\x01R\x0esealsNoBinding\x88\x01\x01B\x17\n" + + "\x15_operation_binding_idB\x13\n" + + "\x11_seals_no_binding\"\xc2\x02\n" + "\x1cAuthorizeEvidenceReadRequest\x12\x1f\n" + "\x06org_id\x18\x01 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x05orgId\x128\n" + "\x13caller_principal_id\x18\x02 \x01(\tB\b\xbaH\x05r\x03\xb0\x01\x01R\x11callerPrincipalId\x12;\n" + diff --git a/go.mod b/go.mod index ee5d9aa..fa2f9ee 100644 --- a/go.mod +++ b/go.mod @@ -5,7 +5,7 @@ go 1.27.0 require ( buf.build/gen/go/bufbuild/protovalidate/protocolbuffers/go v1.36.12-20260825204119-511051f7f437.2 connectrpc.com/connect v1.21.0 - github.com/codefly-dev/core v0.19.4 + github.com/codefly-dev/core v0.19.6-0.20261018051341-b81d92e6feda github.com/google/uuid v1.6.0 golang.org/x/tools v0.52.0 google.golang.org/genproto/googleapis/api v0.0.0-20260928230214-8a89bd6388cc diff --git a/go.sum b/go.sum index a2b057d..e7fbc60 100644 --- a/go.sum +++ b/go.sum @@ -12,8 +12,8 @@ github.com/antlr4-go/antlr/v4 v4.13.1 h1:SqQKkuVZ+zWkMMNkjy5FZe5mr5WURWnlpmOuzYW github.com/antlr4-go/antlr/v4 v4.13.1/go.mod h1:GKmUxMtwp6ZgGwZSva4eWPC5mS6vUAmOABFgjdkM7Nw= github.com/brianvoe/gofakeit/v6 v6.28.0 h1:Xib46XXuQfmlLS2EXRuJpqcw8St6qSZz75OUo0tgAW4= github.com/brianvoe/gofakeit/v6 v6.28.0/go.mod h1:Xj58BMSnFqcn/fAQeSK+/PLtC5kSb7FJIq4JyGa8vEs= -github.com/codefly-dev/core v0.19.4 h1:vUvaFrWkB8B3ksQY/qlgBTVj3jMNhdEpJca8aofaals= -github.com/codefly-dev/core v0.19.4/go.mod h1:0uX/7lTBVaGV0RI2Mb3mpEr/PPdx/jZqXHym/U8FVDI= +github.com/codefly-dev/core v0.19.6-0.20261018051341-b81d92e6feda h1:ytTihtIEfVhQ7llQl+ls5swIL8JgJu89X0wlDMeqM+o= +github.com/codefly-dev/core v0.19.6-0.20261018051341-b81d92e6feda/go.mod h1:0uX/7lTBVaGV0RI2Mb3mpEr/PPdx/jZqXHym/U8FVDI= github.com/golang/protobuf v1.5.4 h1:i7eJL8qZTpSEXOPTxNKhASYpMn+8e5Q6AdndVa1dWek= github.com/golang/protobuf v1.5.4/go.mod h1:lnTiLA8Wa4RWRcIUkrtSVa5nRhsEGBg48fD6rSs7xps= github.com/google/go-cmp v0.7.0 h1:wk8382ETsv4JYUZwIsn6YpYiWiBsYLSJiTsyBybVuN8= diff --git a/moduleauthority/broker_test.go b/moduleauthority/broker_test.go index 1829a6c..9009cdb 100644 --- a/moduleauthority/broker_test.go +++ b/moduleauthority/broker_test.go @@ -149,7 +149,7 @@ func TestTheBrokerRefusesAWrongPerimeterCredential(t *testing.T) { if err != nil { t.Fatal(err) } - if _, err := client.ModuleWorkContext(t.Context()); !errors.Is(err, ErrInvalidCredentials) { + if _, err := client.MintModuleOperationContext(t.Context(), "model"); !errors.Is(err, ErrInvalidCredentials) { t.Fatalf("wrong internal token: %v", err) } wrongToken := h.client(t, Credentials{Prefix: testPrefix, Token: staticToken("another-pods-token")}) diff --git a/moduleauthority/client.go b/moduleauthority/client.go index 18663e2..0142fa1 100644 --- a/moduleauthority/client.go +++ b/moduleauthority/client.go @@ -92,8 +92,9 @@ type Gateway interface { // talks to. Every field is resolved by the consumer from its Codefly // composition; nothing has a default. type Seams struct { - // Gateway is the host auth-gateway's REST endpoint, where the module - // broker mints Work Contexts. Required. + // Gateway is the host auth-gateway's workload endpoint, where the module + // broker mints Work Contexts; its public endpoint answers 404 to a mint. + // Required. Gateway Gateway // Authority is accounts' `authority` gRPC endpoint, which serves the // exchanges and every other Work-Context-authenticated call. A module that diff --git a/moduleauthority/host_fake_test.go b/moduleauthority/host_fake_test.go index dcb962a..98cbd55 100644 --- a/moduleauthority/host_fake_test.go +++ b/moduleauthority/host_fake_test.go @@ -27,14 +27,14 @@ import ( "github.com/codefly-dev/saas-sdk-go/gen/saas/accounts/v1/accountsv1connect" ) -// This file fakes the two host seams as module-saas-starter v0.0.94 serves +// This file fakes the two host seams as module-saas-starter v0.0.103 serves // them, so the client is tested against the host's contract rather than // against itself: // // - fakeGateway is the auth-gateway's module broker // (module/services/auth-gateway/code/gateway_modules.go): the three -// POST /modules/_* paths, their perimeter (internal token + projected -// ServiceAccount bearer), body validation, status mapping, plain-text refusals and +// POST /modules/_* paths, their perimeter (projected ServiceAccount bearer, +// and the internal token on the two operation mints), body validation, status mapping, plain-text refusals and // JSON answers. Every other path answers 404 "endpoint not exposed", as the // real gateway does for every EXPOSURE_INTERNAL procedure — the old bug was // a Connect call to exactly such a path. @@ -46,8 +46,8 @@ import ( // fakeGateway is the edge-case double; the contract itself is held by // conformance/hostgateway, which mints through the host's REAL gateway // handlers at the tag in SOURCE.txt. The fake follows the real gateway's -// perimeter, prefix rule and check order (internal token, then exactly one -// Bearer, then body, prefix and binding/source validation, then accounts' +// perimeter, prefix rule and check order (the internal token on the operation +// mints, then exactly one Bearer, then body, prefix and binding/source validation, then accounts' // verdict). Where it still differs, it differs on purpose: // // - D2: it decodes the body into map[string]string and records every key, so @@ -57,7 +57,7 @@ import ( // answers 403 on the SDK's /modules/_work-context path — accounts' // PermissionDenied is a 401 there — so no test here injects one. // - D6: accounts' Unauthenticated and FailedPrecondition on the work-context -// mint (502 and 412 respectively from the real gateway) are not modelled; +// mint (401 and 412 respectively from the real gateway) are not modelled; // only injected statuses are. Conformance holds both mappings at SOURCE.txt. // - D7: it accepts one internal token; the real gateway also accepts the // previous one during rotation. @@ -199,7 +199,10 @@ func (g *fakeGateway) serve(w http.ResponseWriter, r *http.Request) { plainError(w, http.StatusMethodNotAllowed, "method not allowed") return } - if r.Header.Get("X-Codefly-Internal-Token") != testInternalToken { + // Host af5cef9a (module-saas-starter#1120) serves the mints on the workload + // endpoint alone, which is the work-context mint's whole perimeter: only + // the operation mints still hold the internal token. + if r.URL.Path != hostWorkContextPath && r.Header.Get("X-Codefly-Internal-Token") != testInternalToken { plainError(w, http.StatusUnauthorized, "unauthorized") return } @@ -617,9 +620,6 @@ type authorityState struct { principalState v1.WorkContextPrincipalState epoch uint64 principalID string - buildState v1.WorkContextApprovedBuildState - imageDigest string - incarnation uint64 bindingState v1.WorkContextOperationBindingState binding *v1.WorkContextOperationBindingAnswer revision uint64 @@ -675,19 +675,6 @@ func (a *fakeAuthority) answerAuthority( }, }, }, nil - case *v1.ModuleResolveWorkContextAuthorityRequest_ApprovedBuild: - principal := asked.ApprovedBuild.GetPrincipalId() - if state.principalID != "" { - principal = state.principalID - } - return &v1.ModuleResolveWorkContextAuthorityResponse{ - Answer: &v1.ModuleResolveWorkContextAuthorityResponse_ApprovedBuild{ - ApprovedBuild: &v1.WorkContextApprovedBuildAnswer{ - State: state.buildState, PrincipalId: principal, - ImageDigest: state.imageDigest, BuildIncarnation: state.incarnation, - }, - }, - }, nil case *v1.ModuleResolveWorkContextAuthorityRequest_OperationBinding: answer := state.binding if answer == nil { diff --git a/moduleauthority/sealed_test.go b/moduleauthority/sealed_test.go index b5f76f6..875ba41 100644 --- a/moduleauthority/sealed_test.go +++ b/moduleauthority/sealed_test.go @@ -24,17 +24,11 @@ func sealedToken(name string) string { } ctx := context.Background() _, key := corework.FixtureKeyPair() - seals := corework.FixtureSeals() - digest, incarnation, err := seals.ApprovedBuild(ctx, corework.FixturePrincipal) - if err != nil { - panic(err) - } authority := &corework.Authority{ Issuer: corework.FixtureIssuer, KeyID: corework.FixtureKeyID, Key: key, - Revisions: corework.FixtureRevisions(), Seals: seals, + Revisions: corework.FixtureRevisions(), Seals: corework.FixtureSeals(), } token, _, err := authority.Start(ctx, corework.StartInput{ - Execution: corework.Execution{ImageDigest: digest, BuildIncarnation: incarnation}, TenantID: corework.FixtureTenant, OwnerPrincipalID: corework.FixturePrincipal, OwnerPrincipalKind: "service", diff --git a/moduleauthority/verifier_sources.go b/moduleauthority/verifier_sources.go index ba539af..47ea117 100644 --- a/moduleauthority/verifier_sources.go +++ b/moduleauthority/verifier_sources.go @@ -19,9 +19,8 @@ import ( // full strength. The checks a trust root alone answers — encoding, signature, // issuer, audience, window, shape — are a forwarding hop's; the rest is the // ISSUER'S live state: the installation a capability is sealed to and its -// revision, the epoch of every principal in its chain, the build the exercising -// principal runs, the operation binding it exercises, and the authorization -// revision. A module that stops at the hop's checks accepts a capability whose +// revision, the epoch of every principal in its chain, the operation binding it +// exercises, and the authorization revision. A module that stops at the hop's checks accepts a capability whose // installation was revoked or whose principal's epoch has moved, for as long as // that capability lives. // @@ -330,41 +329,6 @@ func (s *WorkContextSources) PrincipalEpoch(ctx context.Context, principalID str } } -// ApprovedBuild answers what execution the issuer APPROVES for one principal — -// never what a workload presents, which is the caller's attestation and the -// other half of the comparison. -func (s *WorkContextSources) ApprovedBuild( - ctx context.Context, principalID string, -) (string, uint64, error) { - if principalID == "" { - return "", 0, fmt.Errorf("%w: approved build", ErrInvalidAuthorityQuestion) - } - answer, err := s.ask(ctx, "build\x00"+principalID, - func(request *v1.ModuleResolveWorkContextAuthorityRequest) { - request.Question = &v1.ModuleResolveWorkContextAuthorityRequest_ApprovedBuild{ - ApprovedBuild: &v1.WorkContextApprovedBuildQuestion{PrincipalId: principalID}, - } - }) - if err != nil { - return "", 0, err - } - build := answer.GetApprovedBuild() - if build == nil || build.GetPrincipalId() != principalID { - return "", 0, fmt.Errorf("%w: approved build", ErrUnreadableAuthorityAnswer) - } - switch build.GetState() { - case v1.WorkContextApprovedBuildState_WORK_CONTEXT_APPROVED_BUILD_STATE_APPROVED: - return build.GetImageDigest(), build.GetBuildIncarnation(), nil - case v1.WorkContextApprovedBuildState_WORK_CONTEXT_APPROVED_BUILD_STATE_BEARS_NO_EXECUTION: - // A person's session runs no approved build. This is the answer, not a - // failure — and it is NOT what an unknown principal gets, which the host - // refuses outright. - return "", 0, corework.ErrNoApprovedBuild - default: - return "", 0, fmt.Errorf("%w: approved-build state", ErrUnreadableAuthorityAnswer) - } -} - // OperationBinding resolves one binding by its opaque id, exactly. There is no // method that searches bindings for one whose scopes would admit a call: scope // containment is not binding identity, and a revoked narrow capability must not diff --git a/moduleauthority/verifier_sources_test.go b/moduleauthority/verifier_sources_test.go index f951dc8..7a5b8a4 100644 --- a/moduleauthority/verifier_sources_test.go +++ b/moduleauthority/verifier_sources_test.go @@ -112,15 +112,6 @@ func TestEveryAbsenceStateBecomesCoresSentinel(t *testing.T) { }, want: corework.ErrNoSeal, }, - { - what: "a principal that bears no execution", - state: authorityState{buildState: v1.WorkContextApprovedBuildState_WORK_CONTEXT_APPROVED_BUILD_STATE_BEARS_NO_EXECUTION}, - call: func(s *WorkContextSources) error { - _, _, err := s.ApprovedBuild(context.Background(), corework.FixturePrincipal) - return err - }, - want: corework.ErrNoApprovedBuild, - }, { what: "a binding the issuer does not hold", state: authorityState{bindingState: v1.WorkContextOperationBindingState_WORK_CONTEXT_OPERATION_BINDING_STATE_ABSENT}, @@ -176,14 +167,6 @@ func TestAnUnreadableAnswerIsRefused(t *testing.T) { return err }, }, - { - what: "no approved-build state", - state: authorityState{}, - call: func(s *WorkContextSources) error { - _, _, err := s.ApprovedBuild(context.Background(), corework.FixturePrincipal) - return err - }, - }, { what: "no binding state", state: authorityState{}, From db5a4b31066b93ea34c47a3e399b763660f3f5b1 Mon Sep 17 00:00:00 2001 From: Antoine Toussaint <312536060+antoinetoussaint-byte@users.noreply.github.com> Date: Wed, 21 Oct 2026 14:37:42 -0400 Subject: [PATCH 4/5] feat(accounts): Datasources() facade over DatasourceService accounts.Client.Datasources() wraps the generated DatasourceServiceClient beside Audit(): ListSources, GetSource, AddSource, ListSourceOperations, DeclareSourceOperations, InvokeSourceOperation, LookupInvokeSourceOperation and the three account-link RPCs, bare messages in and out. Every message, enum, enum value and oneof wrapper they reach is re-exported from accounts. It reads responses through the same client as package datasource, moved to internal/connectresponse, and documents datasource's Invoke/Lookup as the effect-safe path. internal/apiboundary now walks a oneof field's exported wrappers instead of reporting its unaliasable interface. Co-Authored-By: Claude Opus 5.5 (1M context) --- .claude/skills/api-boundary-triage/SKILL.md | 10 +- .claude/skills/refresh-generated-api/SKILL.md | 2 +- AGENTS.md | 5 +- CHANGELOG.md | 119 +++++--- README.md | 92 ++++-- accounts/datasources.go | 108 +++++++ accounts/datasources_test.go | 278 ++++++++++++++++++ accounts/types.go | 101 +++++++ datasource/client.go | 3 +- datasource/errors.go | 4 +- internal/apiboundary/boundary_test.go | 25 +- internal/apiboundary/gate_test.go | 6 + .../testdata/fixture/gen/fake/v1/fake.go | 13 + .../testdata/fixture/oneof/types.go | 13 + .../connectresponse/connectresponse.go | 27 +- .../connectresponse/connectresponse_test.go | 8 +- 16 files changed, 734 insertions(+), 80 deletions(-) create mode 100644 accounts/datasources.go create mode 100644 accounts/datasources_test.go create mode 100644 internal/apiboundary/testdata/fixture/oneof/types.go rename datasource/connect_response.go => internal/connectresponse/connectresponse.go (71%) rename datasource/connect_response_test.go => internal/connectresponse/connectresponse_test.go (89%) diff --git a/.claude/skills/api-boundary-triage/SKILL.md b/.claude/skills/api-boundary-triage/SKILL.md index f6d7d83..99ff25f 100644 --- a/.claude/skills/api-boundary-triage/SKILL.md +++ b/.claude/skills/api-boundary-triage/SKILL.md @@ -14,9 +14,13 @@ contract moves, so it cannot be. Run it alone while working: ```bash -go test ./internal/apiboundary/ -v +go test -count=1 ./internal/apiboundary/ -v ``` +`-count=1` is not optional while you edit a facade. The gate loads the module +through `go list`, whose reads Go's test cache does not track, so a cached run +reports the tree as it was before your change. + Two tests. `TestPublicAPINamesEveryTypeItExposes` runs the rule over this module. `TestGateCatchesKnownBypasses` runs it over `testdata/fixture`, a module built to break it in every way an earlier syntactic version could be @@ -36,6 +40,10 @@ puts the type in front of a consumer. type alias carries the type and *not* the package-level constants declared with it, so a consumer can hold the value and cannot write the comparison. Fix: re-export the constants too. +- **a path ending `oneof `** — a oneof field's type is an unexported + interface nothing can alias; the gate walks the exported wrappers that + implement it instead, because those are what a consumer writes + (`&accounts.AddSourceRequest_Api{...}`). Fix: alias the wrapper. - **`no public packages discovered`** — not a boundary violation. The loader found nothing, which means the module failed to load. Fix the build first. - **a `load ` error** — same: the gate refuses to report a vacuous pass. diff --git a/.claude/skills/refresh-generated-api/SKILL.md b/.claude/skills/refresh-generated-api/SKILL.md index 39daeb5..533447b 100644 --- a/.claude/skills/refresh-generated-api/SKILL.md +++ b/.claude/skills/refresh-generated-api/SKILL.md @@ -71,7 +71,7 @@ re-exports in that package's `types.go`, and generated enums need their constants too. `internal/apiboundary` decides this, not judgement: ```bash -go test ./internal/apiboundary/ -v +go test -count=1 ./internal/apiboundary/ -v ``` Use the `api-boundary-triage` skill for a failing run — in particular for which diff --git a/AGENTS.md b/AGENTS.md index 1ce682e..7e66932 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -113,14 +113,15 @@ mints through the host's *real* gateway handlers at that same ref | Path | Owns | | --- | --- | -| `accounts/` | gateway-bound facade over the accounts services; `types.go` holds its alias re-exports | -| `datasource/` | the same facade over `DatasourceService` | +| `accounts/` | gateway-bound facade over the accounts services (`Audit()`, `Datasources()`: the raw contract); `types.go` holds its alias re-exports | +| `datasource/` | the ergonomic, effect-safe facade over `DatasourceService` | | `settings/` | presence-aware `Field[M, T]` runtime; `JSONCodec` is the only typed↔ProtoJSON boundary | | `settings/catalog/` | Go / TypeScript / proto catalog renderers that `module-compose` calls | | `moduleauthority/` | a module's own authority: gateway broker mints; direct Accounts authority or explicitly selected gateway authority transport. Work Contexts are opaque `string`s, shape-checked only by `core/workcontext.Decode`. `verifier_sources.go` serves core's three live-authority sources to a callee's verifier without verifying anything itself | | `gen/` | generated output. Regenerated, never edited | | `conformance/hostgateway/` | `moduleauthority` minting through the host's real gateway at the `SOURCE.txt` ref | | `internal/apiboundary` | the public-API boundary gate, with fixtures that prove it still looks | +| `internal/connectresponse` | the one HTTP client both `DatasourceService` facades read responses through | | `internal/agentcontext` | the budget and frontmatter contract for this file and the skills | `README.md` covers what each surface does for a *consumer*, with worked diff --git a/CHANGELOG.md b/CHANGELOG.md index 1f212fe..5a4dc98 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,28 +2,97 @@ ## Unreleased +Core main and module-saas-starter v0.0.103. No Core tag carries the Core this +needs, so the floor is a pseudo-version; it moves to the first tag that does. + ### Changed -- Raise the Core dependency floor from v0.19.1 to v0.19.4, consuming Core's - Kubernetes dependency compatibility fix for stable client-go consumers. - Existing hand-written facade methods retain their signatures. -- Regenerate from released module-saas-starter v0.0.97 with the existing plugin - pins. `SOURCE.txt` now holds both generated bindings and gateway conformance - to that release: its gateway pins gRPC v1.84.0, matching Core v0.19.4's floor. - The upstream module package version remains 0.1.0; no SDK release is cut by - regeneration. -- Align conformance with host v0.0.97's work-context mint: Accounts' - `FailedPrecondition` now returns HTTP 412 (installation pending), previously - 502. The SDK preserves it as `BrokerError` without a delegation sentinel. - The source mint's 412 still maps to `ErrDelegationMissing`. +- **Core floor: `v0.19.6-0.20261018051341-b81d92e6feda`** (Core main, + 2026-10-18), from v0.19.4 on this branch and v0.19.1 in v0.1.3. Core + `22ddde98` removed the approved build from a Work Context: `SealSource` lost + `ApprovedBuild` and `ErrNoApprovedBuild` is gone, so v0.1.3 does not compile + for any consumer that requires that Core. It is also the Core the v0.0.103 + gateway requires. Core v0.19.5 still requires `SealSource.ApprovedBuild` and + cannot build this release; MVS never selects it beside this floor. +- **`gen/` moves from `9ab36e7e` to released module-saas-starter v0.0.103** + (`2cb00737`), with the existing plugin pins and buf v1.73.0. The tree + reproduces byte-for-byte from that tag, and `SOURCE.txt` records it for both + `gen-drift` and `conformance/hostgateway`. The module package version stays + 0.1.0; regeneration cuts no SDK release. +- **The module broker is the gateway's workload endpoint.** Host `af5cef9a` + (module-saas-starter#1120) serves the three mints there alone — the public + endpoint answers 404 — and `Seams.Gateway`'s documentation now says so. The + same commit dropped the internal token from the work-context mint and relays + accounts' `Unauthenticated` there as 401 (`ErrInvalidCredentials`) instead of + 502. The client is unchanged: it still sends the internal token on every + mint, which the two operation mints still require. `conformance/hostgateway` + serves the real gateway through the host's own `workloadListener`, and + `moduleauthority`'s fake gateway follows the new perimeter. +- `datasource`'s response-encoding client moves to `internal/connectresponse` + unchanged, so `accounts.Datasources()` reads responses through it too. ### Removed (breaking) -- Generated `StartTaskWorkContextRequest`, `StartInstallationTaskRequest`, and - `StartChildSessionWorkContextRequest` lose `SessionId` and `GetSessionId`. - Accounts assigns the session and returns it in `IssuedWorkContext.SessionId`; - callers must not choose one. The deleted proto names and field numbers are - reserved upstream. No hand-written facade exposes these request types. +- **`(*moduleauthority.WorkContextSources).ApprovedBuild`**. Core's verifier + no longer asks an issuer for an approved build — a change of approved builds + revokes through the principal's epoch and the installation's revision — and + its only correct "bears no execution" answer was the sentinel Core deleted. + There is no replacement; a consumer calling it directly drops the call. + `WorkContextSources` still implements Core's `SealSource`, `RevisionSource` + and `GrantSource`. +- Generated, by the v0.0.103 regeneration, against v0.1.3: + `ModuleMintWorkContextRequest.Upstream` and `.Manifest` (with their getters; + the host stopped accepting a reported upstream and manifest), and + `SolutionBackendBinding`, `SolutionRegistration.Backend`, + `SolutionFrontendBinding.ContractVersion` and + `SolutionRegistrationStatus_SOLUTION_REGISTRATION_STATUS_INCOMPATIBLE`, all + in host `af5cef9a` (module-saas-starter#1120). No + hand-written facade exposed any of them, and `moduleauthority` never sent + `Upstream` or `Manifest`. +- Generated interfaces gain methods, which breaks a consumer that implements + them: `DatasourceServiceClient`/`Handler.UpdateSource` and + `SolutionRegistryServiceClient`/`Handler.GetRetainedSolutionFrontend`. + Embedding the generated `Unimplemented…Handler` absorbs the handler half. + +### Added + +- **`accounts.Client.Datasources()`**, the `DatasourceService` facade beside + `Audit()`: `ListSources`, `GetSource`, `AddSource`, `ListSourceOperations`, + `DeclareSourceOperations`, `InvokeSourceOperation`, + `LookupInvokeSourceOperation`, `BeginDatasourceAccountLink`, + `CompleteDatasourceAccountLink` and `ListMyDatasourceAccountLinks`, bare + messages in and out, the host's Connect error returned intact. Every message, + enum, enum value and oneof wrapper they reach is re-exported from `accounts` + under its generated name (`AddSourceRequest_Api`, + `ApiOAuth2Config_GRANT_AUTHORIZATION_CODE`, …), so connecting and calling a + host-owned API source no longer needs `gen/`. It is the raw contract; + `datasource`'s `Invoke`/`Lookup` remain the effect-safe way to call an + operation. +- `moduleauthority.Client.MintModuleWorkContext(ctx)` returns + `ModuleContext{Token, ExpiresAt}` without caching, coalescing or retrying. + `ExpiresAt` is the broker's reported expiry, not a decoded token claim. + Existing `ModuleWorkContext(ctx) (string, error)` retains its cache and + shared refresh through the same mint implementation; organization binding, + bounded reads, Core-backed sealed-shape checking and safe refusals are shared. +- `BrokerTransportConnectionReset` classifies wrapped `syscall.ECONNRESET` + through error identity with a fixed diagnostic, retaining no underlying + cause. It is appended so existing transport category values remain stable; + callers can choose to retry without accessing sensitive transport errors. +- Generated, by the v0.0.103 regeneration: `UpdateSource` (a connected source + edited in place), `GetRetainedSolutionFrontend`, installation readiness + (`InstallationReadiness`, `ReadinessCondition` and their enums), carried + module access on team grants, `SolutionGroup`, `SourceFetchScope` and + `CheckAuthorizationRevisionRequest.SealsNoBinding`. These add no + hand-written facades. +- `internal/apiboundary` walks a oneof field's exported wrappers. The field's + type is an unexported interface nothing can alias; the gate used to report + that interface and stop, and now requires each wrapper a consumer writes to + be re-exported (fixture `oneof`). + +## v0.1.3 — served verifier sources + +Tagged at `14fe024` (#44) without a heading here; these are the entries it +shipped. ### Added @@ -59,22 +128,6 @@ `CodeFailedPrecondition` ("the issuer decided; mint again") from `CodeUnavailable` ("the lookup failed; retry"). -- `moduleauthority.Client.MintModuleWorkContext(ctx)` returns - `ModuleContext{Token, ExpiresAt}` without caching, coalescing or retrying. - `ExpiresAt` is the broker's reported expiry, not a decoded token claim. - Existing `ModuleWorkContext(ctx) (string, error)` retains its cache and - shared refresh through the same mint implementation; organization binding, - bounded reads, Core-backed sealed-shape checking and safe refusals are shared. -- `BrokerTransportConnectionReset` classifies wrapped `syscall.ECONNRESET` - through error identity with a fixed diagnostic, retaining no underlying - cause. It is appended so existing transport category values remain stable; - callers can choose to retry without accessing sensitive transport errors. - -- Generated source-trigger declaration, delegation, reconciliation and lookup - messages and RPCs; installation retry and pending/failed status values; - solution workload mint `Upstream` and `Manifest` fields; and authorization - revision `OperationBindingId`. These bindings add no hand-written facades. - - **`moduleauthority.WorkloadTokenFile()`**, the one answer to "where is this module's projected token": the file `CODEFLY__WORKLOAD_TOKEN_FILE` names when it is set to a non-blank value, and the pod mount diff --git a/README.md b/README.md index a2d914c..7b46a94 100644 --- a/README.md +++ b/README.md @@ -13,12 +13,46 @@ The SDK surfaces are: procedure strings, so a solution handler writes plain protos: ```go - resp, err := accounts.New(gw).Audit().QueryAuditLog(ctx, &v1.QueryAuditLogRequest{PageSize: 20}) + resp, err := accounts.New(gw).Audit().QueryAuditLog(ctx, &accounts.QueryAuditLogRequest{PageSize: 20}) ``` `gw` is any value exposing `BaseURL() string` and `HTTPClient() *http.Client` — which `github.com/codefly-dev/solution-runtime-go.Gateway` already satisfies. The runtime stays accounts-agnostic and takes **no** dependency on this SDK. + + `Datasources()` is the same facade over `DatasourceService`: the host's + source connection, operation and account-link contract, message for message. + It covers `ListSources`, `GetSource`, `AddSource`, `ListSourceOperations`, + `DeclareSourceOperations`, `InvokeSourceOperation`, + `LookupInvokeSourceOperation`, `BeginDatasourceAccountLink`, + `CompleteDatasourceAccountLink` and `ListMyDatasourceAccountLinks`, and + every message, enum, enum value and oneof wrapper they reach is re-exported + from `accounts` under its generated name: + + ```go + added, err := accounts.New(gw).Datasources().AddSource(ctx, &accounts.AddSourceRequest{ + OrgId: org, + Provider: accounts.DatasourceProvider_DATASOURCE_PROVIDER_API, + Config: &accounts.AddSourceRequest_Api{Api: &accounts.ApiDatasourceConfig{ + BaseUrl: "https://api.example.com", + CredentialKind: accounts.ApiCredentialKind_API_CREDENTIAL_KIND_OAUTH2, + Oauth2: &accounts.ApiOAuth2Config{ + Grant: accounts.ApiOAuth2Config_GRANT_AUTHORIZATION_CODE, + TokenUrl: "https://api.example.com/oauth/token", + ClientId: clientID, + }, + }}, + Boundary: &accounts.AddSourceRequest_CollectionLabel{CollectionLabel: "invoices"}, + Credential: clientSecret, + }) + ``` + + It is the raw contract: a refusal is the host's Connect error, code, + message and `ErrorInfo` intact. `datasource/` below is the ergonomic layer + over the same service, and its `Invoke` and `Lookup` are the effect-safe way + to call an operation: they mint the effect ID, keep it on every outcome and + classify an unknown one. `InvokeSourceOperation` sends exactly the request it + is given. Both facades read responses through the same client. - **`datasource/`** — the same facade over `DatasourceService`, so a solution connects a GitHub datasource collection in a few lines: @@ -219,7 +253,7 @@ The SDK surfaces are: This call surface uses the four host RPCs from [module-saas-starter#1052](https://github.com/codefly-dev/module-saas-starter/pull/1052). - `SOURCE.txt` records the released host tag `v0.0.97` used to regenerate + `SOURCE.txt` records the released host tag `v0.0.103` used to regenerate the bindings. This regeneration does not publish an SDK release. The host's runtime-scheduled `PruneSourceOperationReceipts` and `LookupPruneSourceOperationReceipts` are included in the generated bindings @@ -244,7 +278,7 @@ The SDK surfaces are: before anything is sent. **This needs a host whose accounts mints core-format Work Contexts** (module-saas-starter#1093); the former v0.0.94 source mints the pre-cutover format, which this client refuses. `SOURCE.txt` now records - v0.0.97. + v0.0.103. `Client.ModuleWorkContext(ctx)` returns a cached token, sharing refreshes between concurrent callers. Consumers that already own their expiry and @@ -334,8 +368,12 @@ The SDK surfaces are: sending. `ProjectedTokenFile` also bounds the file read to 64 KiB. Every mint sends exactly one `Authorization: Bearer ` header alongside the internal perimeter token; the removed module-secret credential has no fallback. + Since host v0.0.103 the gateway serves the three mints on its workload + endpoint alone and holds the internal token on the two operation mints only: + the work-context mint's perimeter is that endpoint, and its credential the + projected token. `Seams.Gateway` names that endpoint. - The REST bodies match [the v0.0.97 gateway](https://github.com/codefly-dev/module-saas-starter/blob/v0.0.97/module/services/auth-gateway/code/gateway_modules.go): + The REST bodies match [the v0.0.103 gateway](https://github.com/codefly-dev/module-saas-starter/blob/v0.0.103/module/services/auth-gateway/code/gateway_modules.go): | Mint path | JSON fields sent | | --- | --- | @@ -472,8 +510,8 @@ The proto source of truth is `module-saas-starter/module/services/accounts/proto To refresh from a released tag (in a checkout of that repo): ```bash -git fetch origin tag v0.0.97 -git checkout --detach v0.0.97 +git fetch origin tag v0.0.103 +git checkout --detach v0.0.103 cd module/services/accounts/proto buf generate --template /buf.gen.yaml -o ``` @@ -488,9 +526,12 @@ The template generates the complete host-owned `saas/` schema tree. Its vendored `codefly/` import closure is compiled for Runnable annotations, with imports resolved to `github.com/codefly-dev/core/generated/go`; Core owns those Go descriptors. Emitting a second copy in this SDK would conflict at -protobuf initialization. The SDK requires Core v0.19.4, which supplies the -required Runnable package and keeps the Kubernetes dependency graph compatible -with stable client-go's structured-merge-diff/v6. The SDK need not adopt the +protobuf initialization. The SDK requires Core at `b81d92e6feda` +(`v0.19.6-0.20261018051341-b81d92e6feda`), the Core the v0.0.103 gateway +requires: it supplies the Runnable package, and its `SealSource` has no +approved build. No tagged Core carries that yet; v0.19.5 still requires +`SealSource.ApprovedBuild`, so it cannot build this SDK, and the floor moves to +the first Core tag that contains `b81d92e6feda`. The SDK need not adopt the host's entire dependency generation. Verify the compatible dependency floor with SDK and consumer builds when refreshing it. The generation plugin versions remain pinned. @@ -508,12 +549,13 @@ this repository. Until release automation covers both, follow the ## Consuming ```go -import ( - "github.com/codefly-dev/saas-sdk-go/accounts" - v1 "github.com/codefly-dev/saas-sdk-go/gen/saas/accounts/v1" -) +import "github.com/codefly-dev/saas-sdk-go/accounts" ``` +Every message a facade method takes or returns, and everything reachable +through it, is re-exported by the facade package; a consumer never imports +`gen/`. + ### Exact executable artifact consent @@ -585,9 +627,10 @@ verifier, err := workcontext.NewVerifier(workcontext.VerifierSettings{ Without them a module can only run core's forwarding-hop `Inspector`, which checks the encoding, signature, issuer, audience, window and shape and nothing -live — so a capability whose installation was revoked, whose build was replaced, -whose operation binding was withdrawn or whose principal's epoch has moved stays -accepted until it expires. +live — so a capability whose installation was revoked, whose operation binding +was withdrawn or whose principal's epoch has moved stays accepted until it +expires. A change of approved builds revokes through the principal's epoch and +the installation's revision; core's verifier asks for no build. The capability is the only required setting, and it is the whole authorization: the host authenticates it, requires it to be addressed to your module (its @@ -599,8 +642,7 @@ same capability keeps one. What the answers mean: -- `corework.ErrNoSeal`, `ErrNoApprovedBuild` and `ErrNoBinding` are core's own - sentinels, which its verifier turns into a refusal of the capability. +- `corework.ErrNoSeal` and `ErrNoBinding` are core's own sentinels, which its verifier turns into a refusal of the capability. - `ErrUnreadableAuthorityAnswer` is a host answer this client will not read — a state it does not understand, another arm, or an answer about another principal, installation or binding. It is a refusal, never a permissive @@ -614,9 +656,9 @@ What the answers mean: Positive answers are cached for at most `AuthorityCacheBound` (2 seconds), which is a **ceiling**: a cached answer delays a revocation by exactly its bound, so a larger one is refused rather than clamped, and `CacheEntries: -1` turns caching -off. Refusals are never cached. One verification costs five or more round trips -(the revision, the seal, an epoch and a build for the owner and for each actor -hop, a binding), so decide the cadence for a stream deliberately rather than +off. Refusals are never cached. One verification costs four or more round trips +(the revision, the seal, an epoch for the owner and for each actor hop, a +binding), so decide the cadence for a stream deliberately rather than discovering it from a latency graph. This module verifies nothing: it holds no key, reads no signature and decides @@ -685,10 +727,10 @@ reconnect it — minting again will not help. The gateway answers 412 there only for a missing delegation, so the status alone decides it. Body-based delegation distinctions are gone: source 403s all return `ErrDelegationInvalid`, whether the delegation was revoked or is otherwise unusable. -At host v0.0.97, a module work-context mint can also answer 412 when the -workload is admitted but installed nowhere. That remains a `BrokerError` -with `StatusCode == 412` and `BrokerErrorOther`, without a delegation sentinel; -the module can serve its install endpoint while waiting for installation. +A module work-context or operation-context mint answers 412 when the module is +proven and the host holds nothing to mint against — admitted but installed +nowhere among them. That is `ErrNoHostStateToMintFor`, never a delegation +sentinel; the module can serve its install endpoint while waiting. `BrokerError.Path` and `BrokerError.Reason` have been removed. Transport and response read failures return `*moduleauthority.BrokerTransportError` diff --git a/accounts/datasources.go b/accounts/datasources.go new file mode 100644 index 0000000..6199f64 --- /dev/null +++ b/accounts/datasources.go @@ -0,0 +1,108 @@ +package accounts + +import ( + "context" + + "connectrpc.com/connect" + + "github.com/codefly-dev/saas-sdk-go/gen/saas/accounts/v1/accountsv1connect" + "github.com/codefly-dev/saas-sdk-go/internal/connectresponse" +) + +// Datasources returns the typed DatasourceService facade: the host's source +// connection, operation and account-link contract, message for message. +// +// It is the raw contract. Package datasource is the ergonomic layer over the +// same service, and its Invoke and Lookup are the effect-safe way to call a +// source operation: they mint the effect ID, keep it on every outcome and +// classify an unknown outcome. InvokeSourceOperation here sends exactly the +// request it is given and returns the host's error as Connect decoded it. +// +// Both facades read responses through the same client, so a Connect error +// arrives here exactly as it does there. +func (c *Client) Datasources() *DatasourcesClient { + return &DatasourcesClient{ + inner: accountsv1connect.NewDatasourceServiceClient( + connectresponse.Client{HTTP: c.gw.HTTPClient()}, c.gw.BaseURL(), c.opts...), + } +} + +// DatasourcesClient wraps the generated DatasourceServiceClient and hides the +// connect.Request/Response envelope. +type DatasourcesClient struct { + inner accountsv1connect.DatasourceServiceClient +} + +// unary sends one request and returns the bare response message. +func unary[Req, Res any]( + ctx context.Context, req *Req, + call func(context.Context, *connect.Request[Req]) (*connect.Response[Res], error), +) (*Res, error) { + resp, err := call(ctx, connect.NewRequest(req)) + if err != nil { + return nil, err + } + return resp.Msg, nil +} + +// ListSources returns the calling organization's connected datasources. +func (d *DatasourcesClient) ListSources(ctx context.Context, req *ListSourcesRequest) (*ListSourcesResponse, error) { + return unary(ctx, req, d.inner.ListSources) +} + +// GetSource returns one connected datasource in the calling organization. +func (d *DatasourcesClient) GetSource(ctx context.Context, req *GetSourceRequest) (*GetSourceResponse, error) { + return unary(ctx, req, d.inner.GetSource) +} + +// AddSource registers a datasource for any provider, configured by the +// request's Config oneof. The host stores the credential encrypted and returns +// the non-secret projection; no read returns the credential. +func (d *DatasourcesClient) AddSource(ctx context.Context, req *AddSourceRequest) (*AddSourceResponse, error) { + return unary(ctx, req, d.inner.AddSource) +} + +// ListSourceOperations reads a source's currently admitted operation +// declarations. +func (d *DatasourcesClient) ListSourceOperations(ctx context.Context, req *ListSourceOperationsRequest) (*ListSourceOperationsResponse, error) { + return unary(ctx, req, d.inner.ListSourceOperations) +} + +// DeclareSourceOperations atomically replaces a source's operation set, as an +// administrator. +func (d *DatasourcesClient) DeclareSourceOperations(ctx context.Context, req *DeclareSourceOperationsRequest) (*DeclareSourceOperationsResponse, error) { + return unary(ctx, req, d.inner.DeclareSourceOperations) +} + +// InvokeSourceOperation calls an admitted operation under the request's effect +// ID. A failure after dispatch does not say whether the provider acted: recover +// the same effect with LookupInvokeSourceOperation, never under a fresh ID. The +// host's refusal reasons are in the ErrorInfo of the returned Connect error. +func (d *DatasourcesClient) InvokeSourceOperation(ctx context.Context, req *InvokeSourceOperationRequest) (*InvokeSourceOperationResponse, error) { + return unary(ctx, req, d.inner.InvokeSourceOperation) +} + +// LookupInvokeSourceOperation recovers an effect's receipt without contacting +// the provider. An unknown receipt never authorizes a redispatch. +func (d *DatasourcesClient) LookupInvokeSourceOperation(ctx context.Context, req *LookupInvokeSourceOperationRequest) (*InvokeSourceOperationResponse, error) { + return unary(ctx, req, d.inner.LookupInvokeSourceOperation) +} + +// BeginDatasourceAccountLink mints a one-time state bound to the organization, +// the calling person and the connector, and returns where to sign in to the +// provider. +func (d *DatasourcesClient) BeginDatasourceAccountLink(ctx context.Context, req *BeginDatasourceAccountLinkRequest) (*BeginDatasourceAccountLinkResponse, error) { + return unary(ctx, req, d.inner.BeginDatasourceAccountLink) +} + +// CompleteDatasourceAccountLink redeems that state and the provider's +// authorization code and links the provider account to the calling person. +func (d *DatasourcesClient) CompleteDatasourceAccountLink(ctx context.Context, req *CompleteDatasourceAccountLinkRequest) (*CompleteDatasourceAccountLinkResponse, error) { + return unary(ctx, req, d.inner.CompleteDatasourceAccountLink) +} + +// ListMyDatasourceAccountLinks returns the calling person's own linked +// provider accounts. +func (d *DatasourcesClient) ListMyDatasourceAccountLinks(ctx context.Context, req *ListMyDatasourceAccountLinksRequest) (*ListMyDatasourceAccountLinksResponse, error) { + return unary(ctx, req, d.inner.ListMyDatasourceAccountLinks) +} diff --git a/accounts/datasources_test.go b/accounts/datasources_test.go new file mode 100644 index 0000000..dabfc29 --- /dev/null +++ b/accounts/datasources_test.go @@ -0,0 +1,278 @@ +package accounts_test + +import ( + "context" + "errors" + "net/http" + "net/http/httptest" + "testing" + + "connectrpc.com/connect" + "google.golang.org/genproto/googleapis/rpc/errdetails" + "google.golang.org/protobuf/proto" + + "github.com/codefly-dev/saas-sdk-go/accounts" + "github.com/codefly-dev/saas-sdk-go/gen/saas/accounts/v1/accountsv1connect" +) + +// datasourceHost answers every DatasourcesClient method with the response the +// test set, or with refusal when it is set, and records what reached it. +type datasourceHost struct { + accountsv1connect.UnimplementedDatasourceServiceHandler + response proto.Message + refusal *connect.Error + procedure string + request proto.Message +} + +func answer[Req, Res any](h *datasourceHost, req *connect.Request[Req]) (*connect.Response[Res], error) { + h.procedure = req.Spec().Procedure + h.request = any(req.Msg).(proto.Message) + if h.refusal != nil { + return nil, h.refusal + } + return connect.NewResponse(any(h.response).(*Res)), nil +} + +func (h *datasourceHost) ListSources(_ context.Context, req *connect.Request[accounts.ListSourcesRequest]) (*connect.Response[accounts.ListSourcesResponse], error) { + return answer[accounts.ListSourcesRequest, accounts.ListSourcesResponse](h, req) +} + +func (h *datasourceHost) GetSource(_ context.Context, req *connect.Request[accounts.GetSourceRequest]) (*connect.Response[accounts.GetSourceResponse], error) { + return answer[accounts.GetSourceRequest, accounts.GetSourceResponse](h, req) +} + +func (h *datasourceHost) AddSource(_ context.Context, req *connect.Request[accounts.AddSourceRequest]) (*connect.Response[accounts.AddSourceResponse], error) { + return answer[accounts.AddSourceRequest, accounts.AddSourceResponse](h, req) +} + +func (h *datasourceHost) ListSourceOperations(_ context.Context, req *connect.Request[accounts.ListSourceOperationsRequest]) (*connect.Response[accounts.ListSourceOperationsResponse], error) { + return answer[accounts.ListSourceOperationsRequest, accounts.ListSourceOperationsResponse](h, req) +} + +func (h *datasourceHost) DeclareSourceOperations(_ context.Context, req *connect.Request[accounts.DeclareSourceOperationsRequest]) (*connect.Response[accounts.DeclareSourceOperationsResponse], error) { + return answer[accounts.DeclareSourceOperationsRequest, accounts.DeclareSourceOperationsResponse](h, req) +} + +func (h *datasourceHost) InvokeSourceOperation(_ context.Context, req *connect.Request[accounts.InvokeSourceOperationRequest]) (*connect.Response[accounts.InvokeSourceOperationResponse], error) { + return answer[accounts.InvokeSourceOperationRequest, accounts.InvokeSourceOperationResponse](h, req) +} + +func (h *datasourceHost) LookupInvokeSourceOperation(_ context.Context, req *connect.Request[accounts.LookupInvokeSourceOperationRequest]) (*connect.Response[accounts.InvokeSourceOperationResponse], error) { + return answer[accounts.LookupInvokeSourceOperationRequest, accounts.InvokeSourceOperationResponse](h, req) +} + +func (h *datasourceHost) BeginDatasourceAccountLink(_ context.Context, req *connect.Request[accounts.BeginDatasourceAccountLinkRequest]) (*connect.Response[accounts.BeginDatasourceAccountLinkResponse], error) { + return answer[accounts.BeginDatasourceAccountLinkRequest, accounts.BeginDatasourceAccountLinkResponse](h, req) +} + +func (h *datasourceHost) CompleteDatasourceAccountLink(_ context.Context, req *connect.Request[accounts.CompleteDatasourceAccountLinkRequest]) (*connect.Response[accounts.CompleteDatasourceAccountLinkResponse], error) { + return answer[accounts.CompleteDatasourceAccountLinkRequest, accounts.CompleteDatasourceAccountLinkResponse](h, req) +} + +func (h *datasourceHost) ListMyDatasourceAccountLinks(_ context.Context, req *connect.Request[accounts.ListMyDatasourceAccountLinksRequest]) (*connect.Response[accounts.ListMyDatasourceAccountLinksResponse], error) { + return answer[accounts.ListMyDatasourceAccountLinksRequest, accounts.ListMyDatasourceAccountLinksResponse](h, req) +} + +type gateway struct { + base string + client *http.Client +} + +func (g gateway) BaseURL() string { return g.base } +func (g gateway) HTTPClient() *http.Client { return g.client } + +func newDatasources(t *testing.T) (*accounts.DatasourcesClient, *datasourceHost) { + t.Helper() + host := &datasourceHost{} + mux := http.NewServeMux() + mux.Handle(accountsv1connect.NewDatasourceServiceHandler(host)) + server := httptest.NewServer(mux) + t.Cleanup(server.Close) + return accounts.New(gateway{base: server.URL, client: server.Client()}).Datasources(), host +} + +// datasourceCall is one DatasourcesClient method: the procedure it must reach, +// the request a consumer builds from package accounts alone, and the response +// the host answers. +type datasourceCall struct { + procedure string + request proto.Message + response proto.Message + call func(context.Context, *accounts.DatasourcesClient, proto.Message) (proto.Message, error) +} + +func call[Req, Res any](method func(*accounts.DatasourcesClient, context.Context, *Req) (*Res, error)) func(context.Context, *accounts.DatasourcesClient, proto.Message) (proto.Message, error) { + return func(ctx context.Context, client *accounts.DatasourcesClient, request proto.Message) (proto.Message, error) { + response, err := method(client, ctx, any(request).(*Req)) + if response == nil { + return nil, err + } + return any(response).(proto.Message), err + } +} + +func datasourceCalls() map[string]datasourceCall { + source := &accounts.Datasource{Id: "ds-1", OrgId: "org-1", Provider: accounts.DatasourceProvider_DATASOURCE_PROVIDER_API} + operation := &accounts.SourceOperation{Name: "list_invoices", Effect: accounts.SourceOperation_EFFECT_READ_ONLY} + receipt := &accounts.InvokeSourceOperationResponse{ + OutputJson: `{"invoices":[]}`, + Receipt: &accounts.SourceOperationReceipt{EffectId: "effect-1"}, + } + link := &accounts.DatasourceAccountLink{Id: "link-1", OrgId: "org-1", Connector: "api"} + return map[string]datasourceCall{ + "ListSources": { + procedure: accountsv1connect.DatasourceServiceListSourcesProcedure, + request: &accounts.ListSourcesRequest{OrgId: "org-1"}, + response: &accounts.ListSourcesResponse{Datasources: []*accounts.Datasource{source}}, + call: call((*accounts.DatasourcesClient).ListSources), + }, + "GetSource": { + procedure: accountsv1connect.DatasourceServiceGetSourceProcedure, + request: &accounts.GetSourceRequest{OrgId: "org-1", Id: "ds-1"}, + response: &accounts.GetSourceResponse{Datasource: source}, + call: call((*accounts.DatasourcesClient).GetSource), + }, + "AddSource": { + procedure: accountsv1connect.DatasourceServiceAddSourceProcedure, + request: &accounts.AddSourceRequest{ + OrgId: "org-1", + Provider: accounts.DatasourceProvider_DATASOURCE_PROVIDER_API, + Config: &accounts.AddSourceRequest_Api{Api: &accounts.ApiDatasourceConfig{ + BaseUrl: "https://api.example.com", + CredentialKind: accounts.ApiCredentialKind_API_CREDENTIAL_KIND_OAUTH2, + Oauth2: &accounts.ApiOAuth2Config{ + Grant: accounts.ApiOAuth2Config_GRANT_AUTHORIZATION_CODE, + TokenUrl: "https://api.example.com/oauth/token", + ClientId: "client-1", + }, + }}, + Boundary: &accounts.AddSourceRequest_CollectionLabel{CollectionLabel: "invoices"}, + Credential: "client-secret", + }, + response: &accounts.AddSourceResponse{Datasource: source}, + call: call((*accounts.DatasourcesClient).AddSource), + }, + "ListSourceOperations": { + procedure: accountsv1connect.DatasourceServiceListSourceOperationsProcedure, + request: &accounts.ListSourceOperationsRequest{OrgId: "org-1", SourceId: "ds-1"}, + response: &accounts.ListSourceOperationsResponse{Operations: []*accounts.SourceOperation{operation}}, + call: call((*accounts.DatasourcesClient).ListSourceOperations), + }, + "DeclareSourceOperations": { + procedure: accountsv1connect.DatasourceServiceDeclareSourceOperationsProcedure, + request: &accounts.DeclareSourceOperationsRequest{OrgId: "org-1", SourceId: "ds-1", Operations: []*accounts.SourceOperation{operation}}, + response: &accounts.DeclareSourceOperationsResponse{Operations: []*accounts.SourceOperation{operation}}, + call: call((*accounts.DatasourcesClient).DeclareSourceOperations), + }, + "InvokeSourceOperation": { + procedure: accountsv1connect.DatasourceServiceInvokeSourceOperationProcedure, + request: &accounts.InvokeSourceOperationRequest{ + OrgId: "org-1", SourceId: "ds-1", Operation: "list_invoices", + InputJson: `{"limit":20}`, EffectId: "effect-1", + }, + response: receipt, + call: call((*accounts.DatasourcesClient).InvokeSourceOperation), + }, + "LookupInvokeSourceOperation": { + procedure: accountsv1connect.DatasourceServiceLookupInvokeSourceOperationProcedure, + request: &accounts.LookupInvokeSourceOperationRequest{EffectId: "effect-1"}, + response: receipt, + call: call((*accounts.DatasourcesClient).LookupInvokeSourceOperation), + }, + "BeginDatasourceAccountLink": { + procedure: accountsv1connect.DatasourceServiceBeginDatasourceAccountLinkProcedure, + request: &accounts.BeginDatasourceAccountLinkRequest{OrgId: "org-1", Connector: "api", RedirectUri: "https://app.example.com/linked", SourceId: "ds-1"}, + response: &accounts.BeginDatasourceAccountLinkResponse{AuthorizeUrl: "https://api.example.com/oauth/authorize", State: "state-1"}, + call: call((*accounts.DatasourcesClient).BeginDatasourceAccountLink), + }, + "CompleteDatasourceAccountLink": { + procedure: accountsv1connect.DatasourceServiceCompleteDatasourceAccountLinkProcedure, + request: &accounts.CompleteDatasourceAccountLinkRequest{OrgId: "org-1", State: "state-1", Code: "code-1"}, + response: &accounts.CompleteDatasourceAccountLinkResponse{Link: link}, + call: call((*accounts.DatasourcesClient).CompleteDatasourceAccountLink), + }, + "ListMyDatasourceAccountLinks": { + procedure: accountsv1connect.DatasourceServiceListMyDatasourceAccountLinksProcedure, + request: &accounts.ListMyDatasourceAccountLinksRequest{OrgId: "org-1"}, + response: &accounts.ListMyDatasourceAccountLinksResponse{Links: []*accounts.DatasourceAccountLink{link}}, + call: call((*accounts.DatasourcesClient).ListMyDatasourceAccountLinks), + }, + } +} + +// TestDatasourcesReachTheirProcedureAndUnwrap: each method sends the request it +// is given, unchanged, to its own procedure, and returns the host's response +// message as it was sent. +func TestDatasourcesReachTheirProcedureAndUnwrap(t *testing.T) { + for name, tc := range datasourceCalls() { + t.Run(name, func(t *testing.T) { + client, host := newDatasources(t) + host.response = tc.response + got, err := tc.call(t.Context(), client, tc.request) + if err != nil { + t.Fatalf("%s: %v", name, err) + } + if host.procedure != tc.procedure { + t.Errorf("procedure = %q, want %q", host.procedure, tc.procedure) + } + if !proto.Equal(host.request, tc.request) { + t.Errorf("request reaching the host = %v, want %v", host.request, tc.request) + } + if !proto.Equal(got, tc.response) { + t.Errorf("response = %v, want %v", got, tc.response) + } + }) + } +} + +// TestDatasourcesPreserveTheHostsConnectError: a refusal arrives as the host's +// own Connect error — its code, its message and its ErrorInfo — with no +// response, so a caller keys on the reason exactly as the contract documents. +func TestDatasourcesPreserveTheHostsConnectError(t *testing.T) { + for name, tc := range datasourceCalls() { + t.Run(name, func(t *testing.T) { + client, host := newDatasources(t) + refusal := connect.NewError(connect.CodeFailedPrecondition, errors.New("source operation outcome unknown")) + detail, err := connect.NewErrorDetail(&errdetails.ErrorInfo{ + Reason: "SOURCE_OPERATION_OUTCOME_UNKNOWN", Domain: "saas.accounts.v1", + }) + if err != nil { + t.Fatal(err) + } + refusal.AddDetail(detail) + host.refusal = refusal + + got, err := tc.call(t.Context(), client, tc.request) + if got != nil { + t.Errorf("a refused call returned a response: %v", got) + } + var connectErr *connect.Error + if !errors.As(err, &connectErr) { + t.Fatalf("error = %v, want a *connect.Error", err) + } + if connectErr.Code() != connect.CodeFailedPrecondition || connectErr.Message() != "source operation outcome unknown" { + t.Errorf("error = %v, want the host's code and message", connectErr) + } + var reason string + for _, detail := range connectErr.Details() { + if info, ok := must(detail.Value()).(*errdetails.ErrorInfo); ok { + reason = info.GetReason() + } + } + if reason != "SOURCE_OPERATION_OUTCOME_UNKNOWN" { + t.Errorf("ErrorInfo reason = %q, want the host's", reason) + } + if host.procedure != tc.procedure { + t.Errorf("procedure = %q, want %q", host.procedure, tc.procedure) + } + }) + } +} + +func must(value proto.Message, err error) proto.Message { + if err != nil { + panic(err) + } + return value +} diff --git a/accounts/types.go b/accounts/types.go index 83dcc04..a7a7984 100644 --- a/accounts/types.go +++ b/accounts/types.go @@ -26,3 +26,104 @@ type ( // AuditEvent is one entry of a QueryAuditLogResponse. AuditEvent = v1.AuditEvent ) + +// The DatasourcesClient messages, under their generated names: this facade is +// the raw contract, and package datasource is the ergonomic one. Package +// datasource re-exports some of the same types under idiomatic constant names; +// both name the same Go types. +type ( + ListSourcesRequest = v1.ListSourcesRequest + ListSourcesResponse = v1.ListSourcesResponse + GetSourceRequest = v1.GetSourceRequest + GetSourceResponse = v1.GetSourceResponse + AddSourceRequest = v1.AddSourceRequest + AddSourceResponse = v1.AddSourceResponse + ListSourceOperationsRequest = v1.ListSourceOperationsRequest + ListSourceOperationsResponse = v1.ListSourceOperationsResponse + DeclareSourceOperationsRequest = v1.DeclareSourceOperationsRequest + DeclareSourceOperationsResponse = v1.DeclareSourceOperationsResponse + InvokeSourceOperationRequest = v1.InvokeSourceOperationRequest + InvokeSourceOperationResponse = v1.InvokeSourceOperationResponse + LookupInvokeSourceOperationRequest = v1.LookupInvokeSourceOperationRequest + BeginDatasourceAccountLinkRequest = v1.BeginDatasourceAccountLinkRequest + BeginDatasourceAccountLinkResponse = v1.BeginDatasourceAccountLinkResponse + CompleteDatasourceAccountLinkRequest = v1.CompleteDatasourceAccountLinkRequest + CompleteDatasourceAccountLinkResponse = v1.CompleteDatasourceAccountLinkResponse + ListMyDatasourceAccountLinksRequest = v1.ListMyDatasourceAccountLinksRequest + ListMyDatasourceAccountLinksResponse = v1.ListMyDatasourceAccountLinksResponse +) + +// Every message and oneof wrapper reachable through a DatasourcesClient message, +// so a consumer can build `&AddSourceRequest{Config: &AddSourceRequest_Api{...}}`. +type ( + AddSourceRequest_Api = v1.AddSourceRequest_Api + AddSourceRequest_BoundaryNodeId = v1.AddSourceRequest_BoundaryNodeId + AddSourceRequest_CollectionLabel = v1.AddSourceRequest_CollectionLabel + AddSourceRequest_Crawler = v1.AddSourceRequest_Crawler + AddSourceRequest_Github = v1.AddSourceRequest_Github + AddSourceRequest_Upload = v1.AddSourceRequest_Upload + ApiDatasourceConfig = v1.ApiDatasourceConfig + ApiOAuth2Config = v1.ApiOAuth2Config + CrawlerDatasourceConfig = v1.CrawlerDatasourceConfig + Datasource = v1.Datasource + DatasourceAccountLink = v1.DatasourceAccountLink + GitHubDatasourceConfig = v1.GitHubDatasourceConfig + SourceOperation = v1.SourceOperation + SourceOperationReceipt = v1.SourceOperationReceipt + UploadDatasourceConfig = v1.UploadDatasourceConfig +) + +// The enums reachable through them. An alias carries the type and not its +// constants, so each value is re-exported too. +type ( + ApiCredentialKind = v1.ApiCredentialKind + ApiOAuth2Config_Grant = v1.ApiOAuth2Config_Grant + DatasourceLiveDelivery = v1.DatasourceLiveDelivery + DatasourceProvider = v1.DatasourceProvider + DatasourceStatus = v1.DatasourceStatus + SourceOperation_Effect = v1.SourceOperation_Effect +) + +const ( + ApiCredentialKind_API_CREDENTIAL_KIND_BASIC = v1.ApiCredentialKind_API_CREDENTIAL_KIND_BASIC + ApiCredentialKind_API_CREDENTIAL_KIND_BEARER = v1.ApiCredentialKind_API_CREDENTIAL_KIND_BEARER + ApiCredentialKind_API_CREDENTIAL_KIND_HEADER = v1.ApiCredentialKind_API_CREDENTIAL_KIND_HEADER + ApiCredentialKind_API_CREDENTIAL_KIND_OAUTH2 = v1.ApiCredentialKind_API_CREDENTIAL_KIND_OAUTH2 + ApiCredentialKind_API_CREDENTIAL_KIND_QUERY = v1.ApiCredentialKind_API_CREDENTIAL_KIND_QUERY + ApiCredentialKind_API_CREDENTIAL_KIND_UNSPECIFIED = v1.ApiCredentialKind_API_CREDENTIAL_KIND_UNSPECIFIED +) + +const ( + ApiOAuth2Config_GRANT_AUTHORIZATION_CODE = v1.ApiOAuth2Config_GRANT_AUTHORIZATION_CODE + ApiOAuth2Config_GRANT_CLIENT_CREDENTIALS = v1.ApiOAuth2Config_GRANT_CLIENT_CREDENTIALS + ApiOAuth2Config_GRANT_REFRESH_TOKEN = v1.ApiOAuth2Config_GRANT_REFRESH_TOKEN + ApiOAuth2Config_GRANT_UNSPECIFIED = v1.ApiOAuth2Config_GRANT_UNSPECIFIED +) + +const ( + DatasourceLiveDelivery_DATASOURCE_LIVE_DELIVERY_APP_WEBHOOK = v1.DatasourceLiveDelivery_DATASOURCE_LIVE_DELIVERY_APP_WEBHOOK + DatasourceLiveDelivery_DATASOURCE_LIVE_DELIVERY_NONE = v1.DatasourceLiveDelivery_DATASOURCE_LIVE_DELIVERY_NONE + DatasourceLiveDelivery_DATASOURCE_LIVE_DELIVERY_SOURCE_WEBHOOK = v1.DatasourceLiveDelivery_DATASOURCE_LIVE_DELIVERY_SOURCE_WEBHOOK + DatasourceLiveDelivery_DATASOURCE_LIVE_DELIVERY_UNSPECIFIED = v1.DatasourceLiveDelivery_DATASOURCE_LIVE_DELIVERY_UNSPECIFIED +) + +const ( + DatasourceProvider_DATASOURCE_PROVIDER_API = v1.DatasourceProvider_DATASOURCE_PROVIDER_API + DatasourceProvider_DATASOURCE_PROVIDER_CRAWLER = v1.DatasourceProvider_DATASOURCE_PROVIDER_CRAWLER + DatasourceProvider_DATASOURCE_PROVIDER_GITHUB = v1.DatasourceProvider_DATASOURCE_PROVIDER_GITHUB + DatasourceProvider_DATASOURCE_PROVIDER_UNSPECIFIED = v1.DatasourceProvider_DATASOURCE_PROVIDER_UNSPECIFIED + DatasourceProvider_DATASOURCE_PROVIDER_UPLOAD = v1.DatasourceProvider_DATASOURCE_PROVIDER_UPLOAD +) + +const ( + DatasourceStatus_DATASOURCE_STATUS_ACTIVE = v1.DatasourceStatus_DATASOURCE_STATUS_ACTIVE + DatasourceStatus_DATASOURCE_STATUS_DEGRADED = v1.DatasourceStatus_DATASOURCE_STATUS_DEGRADED + DatasourceStatus_DATASOURCE_STATUS_PAUSED = v1.DatasourceStatus_DATASOURCE_STATUS_PAUSED + DatasourceStatus_DATASOURCE_STATUS_UNSPECIFIED = v1.DatasourceStatus_DATASOURCE_STATUS_UNSPECIFIED +) + +const ( + SourceOperation_EFFECT_MUTATION = v1.SourceOperation_EFFECT_MUTATION + SourceOperation_EFFECT_READ_ONLY = v1.SourceOperation_EFFECT_READ_ONLY + SourceOperation_EFFECT_UNSPECIFIED = v1.SourceOperation_EFFECT_UNSPECIFIED +) diff --git a/datasource/client.go b/datasource/client.go index 178e6af..b0494ea 100644 --- a/datasource/client.go +++ b/datasource/client.go @@ -9,6 +9,7 @@ import ( v1 "github.com/codefly-dev/saas-sdk-go/gen/saas/accounts/v1" "github.com/codefly-dev/saas-sdk-go/gen/saas/accounts/v1/accountsv1connect" + "github.com/codefly-dev/saas-sdk-go/internal/connectresponse" ) var ErrInvalidBoundary = errors.New("datasource: exactly one collection label or boundary node ID is required") @@ -31,7 +32,7 @@ type Client struct { // connect.WithGRPC()) are forwarded to the underlying client. func New(gw Gateway, opts ...connect.ClientOption) *Client { return &Client{ - inner: accountsv1connect.NewDatasourceServiceClient(connectResponseClient{client: gw.HTTPClient()}, gw.BaseURL(), opts...), + inner: accountsv1connect.NewDatasourceServiceClient(connectresponse.Client{HTTP: gw.HTTPClient()}, gw.BaseURL(), opts...), } } diff --git a/datasource/errors.go b/datasource/errors.go index 2eb03cf..6a360a1 100644 --- a/datasource/errors.go +++ b/datasource/errors.go @@ -7,6 +7,8 @@ import ( "connectrpc.com/connect" "google.golang.org/genproto/googleapis/rpc/errdetails" + + "github.com/codefly-dev/saas-sdk-go/internal/connectresponse" ) var ( @@ -170,7 +172,7 @@ func mapHostError(err error, effectOutcome bool, now time.Time) error { if effectOutcome && !connect.IsWireError(err) { return &OutcomeUnknown{cause: err} } - var encodingError *unsupportedResponseEncoding + var encodingError *connectresponse.UnsupportedEncoding if errors.As(err, &encodingError) { return &DatasourceError{cause: err} } diff --git a/internal/apiboundary/boundary_test.go b/internal/apiboundary/boundary_test.go index 3c02b7f..16b77f5 100644 --- a/internal/apiboundary/boundary_test.go +++ b/internal/apiboundary/boundary_test.go @@ -20,7 +20,8 @@ // question the invariant is actually about. It loads every public package with // full type information and walks the transitive surface a consumer can reach — // exported funcs, vars, consts, struct fields, interface and named-type -// methods. A generated type anywhere in that surface must be re-exported by an +// methods, and the exported wrappers behind a oneof field's unexported +// interface. A generated type anywhere in that surface must be re-exported by an // alias in a public package, and a generated enum's constants must be // re-exported too: a type alias carries the type but *not* the package-level // constants declared with it, so aliasing `DatasourceStatus` alone still leaves @@ -201,6 +202,13 @@ func (w *walker) walk(t types.Type, path string) { return } if isUnder(obj, w.generatedPrefix) { + // A oneof field's type is an unexported interface that nothing can + // alias; what a consumer must name is each exported wrapper that + // implements it (`&accounts.AddSourceRequest_Api{...}`). + if iface, ok := t.Underlying().(*types.Interface); ok && !obj.Exported() && iface.NumMethods() > 0 { + w.walkImplementers(obj.Pkg(), iface, path) + return + } if _, ok := w.reached[obj]; !ok { w.reached[obj] = path } @@ -250,6 +258,21 @@ func (w *walker) walk(t types.Type, path string) { } } +// walkImplementers walks every exported type in pkg that implements iface, +// directly or through its pointer. +func (w *walker) walkImplementers(pkg *types.Package, iface *types.Interface, path string) { + scope := pkg.Scope() + for _, name := range scope.Names() { + obj, ok := scope.Lookup(name).(*types.TypeName) + if !ok || !obj.Exported() || obj.IsAlias() { + continue + } + if types.Implements(obj.Type(), iface) || types.Implements(types.NewPointer(obj.Type()), iface) { + w.walk(obj.Type(), path+" oneof "+name) + } + } +} + func (w *walker) walkTuple(tuple *types.Tuple, path string) { if tuple == nil { return diff --git a/internal/apiboundary/gate_test.go b/internal/apiboundary/gate_test.go index d564670..77157c9 100644 --- a/internal/apiboundary/gate_test.go +++ b/internal/apiboundary/gate_test.go @@ -41,6 +41,12 @@ func TestGateCatchesKnownBypasses(t *testing.T) { kindMissingConst + " fakev1.EnumState", kindMissingConst + " fakev1.EnumState", }, + // A oneof's unexported interface is not itself a finding; an + // unaliased wrapper is, and so is what that wrapper exposes. + "oneof": { + kindUnexported + " fakev1.OneofRightInner", + kindUnexported + " fakev1.OneofThing_Right", + }, // Control: fully re-exported, nothing to report. "clean": nil, // C5: "/gen/" in a *dependency's* path is not this module's stub tree. diff --git a/internal/apiboundary/testdata/fixture/gen/fake/v1/fake.go b/internal/apiboundary/testdata/fixture/gen/fake/v1/fake.go index 700a603..7018ba2 100644 --- a/internal/apiboundary/testdata/fixture/gen/fake/v1/fake.go +++ b/internal/apiboundary/testdata/fixture/gen/fake/v1/fake.go @@ -39,3 +39,16 @@ type TransitiveThing struct { Inner *TransitiveInner } type TransitiveInner struct{ Note string } + +// OneofThing has a oneof field, generated as an unexported interface that only +// its exported wrappers implement. +type OneofThing struct { + Choice isOneofThing_Choice +} +type isOneofThing_Choice interface{ isOneofThing_Choice() } +type OneofThing_Left struct{ Left string } +type OneofThing_Right struct{ Right *OneofRightInner } +type OneofRightInner struct{ Note string } + +func (*OneofThing_Left) isOneofThing_Choice() {} +func (*OneofThing_Right) isOneofThing_Choice() {} diff --git a/internal/apiboundary/testdata/fixture/oneof/types.go b/internal/apiboundary/testdata/fixture/oneof/types.go new file mode 100644 index 0000000..d62507d --- /dev/null +++ b/internal/apiboundary/testdata/fixture/oneof/types.go @@ -0,0 +1,13 @@ +// Package oneof aliases a message and one of its oneof wrappers but not the +// other. The field's own type is unexported and cannot be aliased; the wrappers +// are what a consumer names to set it. +package oneof + +import v1 "fixturemod/gen/fake/v1" + +type ( + OneofThing = v1.OneofThing + OneofThing_Left = v1.OneofThing_Left +) + +func Get() *OneofThing { return nil } diff --git a/datasource/connect_response.go b/internal/connectresponse/connectresponse.go similarity index 71% rename from datasource/connect_response.go rename to internal/connectresponse/connectresponse.go index 7cc8a26..74bfcb9 100644 --- a/datasource/connect_response.go +++ b/internal/connectresponse/connectresponse.go @@ -1,4 +1,7 @@ -package datasource +// Package connectresponse is the HTTP client every DatasourceService facade in +// this module binds its generated Connect client to, so the datasource and +// accounts facades read one response the same way. +package connectresponse import ( "bufio" @@ -14,19 +17,21 @@ import ( "connectrpc.com/connect" ) -type unsupportedResponseEncoding struct{ encoding string } +// UnsupportedEncoding is the cause of the CodeInternal error Do returns for a +// response whose Content-Encoding it does not read. +type UnsupportedEncoding struct{ Encoding string } -func (e *unsupportedResponseEncoding) Error() string { - return fmt.Sprintf("datasource: unsupported response encoding %q", e.encoding) +func (e *UnsupportedEncoding) Error() string { + return fmt.Sprintf("datasource: unsupported response encoding %q", e.Encoding) } -// connectResponseClient normalizes the shared SDK's accepted HTTP encodings -// before Connect decodes an error. It delegates the original request unchanged -// to the gateway client; Connect still owns envelope, detail and status decoding. -type connectResponseClient struct{ client *http.Client } +// Client normalizes the shared SDK's accepted HTTP encodings before Connect +// decodes an error. It delegates the original request unchanged to the gateway +// client; Connect still owns envelope, detail and status decoding. +type Client struct{ HTTP *http.Client } -func (c connectResponseClient) Do(request *http.Request) (*http.Response, error) { - response, err := c.client.Do(request) +func (c Client) Do(request *http.Request) (*http.Response, error) { + response, err := c.HTTP.Do(request) if err != nil || strings.HasPrefix(request.Header.Get("Content-Type"), "application/grpc") { return response, err @@ -36,7 +41,7 @@ func (c connectResponseClient) Do(request *http.Request) (*http.Response, error) // No body or HTTP status can establish an RPC outcome when its encoding // is unsupported. Close here because Connect receives an error, not a body. _ = response.Body.Close() - return nil, connect.NewError(connect.CodeInternal, &unsupportedResponseEncoding{encoding: response.Header.Get("Content-Encoding")}) + return nil, connect.NewError(connect.CodeInternal, &UnsupportedEncoding{Encoding: response.Header.Get("Content-Encoding")}) } if response.StatusCode == http.StatusOK { return response, nil diff --git a/datasource/connect_response_test.go b/internal/connectresponse/connectresponse_test.go similarity index 89% rename from datasource/connect_response_test.go rename to internal/connectresponse/connectresponse_test.go index f6d385d..328999b 100644 --- a/datasource/connect_response_test.go +++ b/internal/connectresponse/connectresponse_test.go @@ -1,4 +1,4 @@ -package datasource +package connectresponse import ( "errors" @@ -35,9 +35,9 @@ func TestUnsupportedEncodingClosesResponseWithoutReading(t *testing.T) { t.Fatal(err) } req.Header.Set("Content-Type", "application/proto") - response, err := (connectResponseClient{client: httpClient}).Do(req) - var unsupported *unsupportedResponseEncoding - if response != nil || !errors.As(err, &unsupported) || unsupported.encoding != "br" || + response, err := (Client{HTTP: httpClient}).Do(req) + var unsupported *UnsupportedEncoding + if response != nil || !errors.As(err, &unsupported) || unsupported.Encoding != "br" || connect.CodeOf(err) != connect.CodeInternal || body.reads != 0 || body.closes != 1 { t.Fatalf("unsupported response = %v, %v, reads=%d closes=%d", response, err, body.reads, body.closes) } From 2bc1b47fe17def2e5e4bbb82581637cbe40d3eed Mon Sep 17 00:00:00 2001 From: Antoine Toussaint <312536060+antoinetoussaint-byte@users.noreply.github.com> Date: Wed, 21 Oct 2026 14:42:36 -0400 Subject: [PATCH 5/5] ci(conformance): install the newer of the SDK's and the gateway's Go host-gateway-conformance installed Go from the SDK's go.mod (1.27.0) under setup-go's GOTOOLCHAIN=local, and host v0.0.103's auth-gateway module requires go 1.27.2, so the build refused before any test ran. The job builds the gateway module with this SDK required into it; it now installs the newer of the two go directives. Co-Authored-By: Claude Opus 5.5 (1M context) --- .github/workflows/ci.yml | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 3c8e8a9..ceb0439 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -102,9 +102,18 @@ jobs: uses: ./sdk/.github/actions/host-source with: gateway: "true" + # The build is the host's gateway module with this SDK required into it, + # so it needs the newer of the two modules' `go` directives; setup-go + # pins GOTOOLCHAIN=local, so neither is fetched on demand. + - id: go + run: | + set -euo pipefail + sdk=$(awk '$1 == "go" { print $2; exit }' sdk/go.mod) + host=$(awk '$1 == "go" { print $2; exit }' "source/${{ steps.source.outputs.gateway }}/go.mod") + echo "version=$(printf '%s\n%s\n' "$sdk" "$host" | sort -V | tail -n1)" >> "$GITHUB_OUTPUT" - uses: actions/setup-go@b7ad1dad31e06c5925ef5d2fc7ad053ef454303e # v7.0.0 with: - go-version-file: sdk/go.mod + go-version: ${{ steps.go.outputs.version }} cache-dependency-path: | sdk/go.sum source/${{ steps.source.outputs.gateway }}/go.sum