From 34ce9b43be1f2445a8c0f67716c91e43a709cbc7 Mon Sep 17 00:00:00 2001 From: Lukas Bindreiter Date: Wed, 22 Jul 2026 10:15:17 +0200 Subject: [PATCH 1/2] Update checkout action --- .github/workflows/buf.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/buf.yaml b/.github/workflows/buf.yaml index ae9ec12..5e49978 100644 --- a/.github/workflows/buf.yaml +++ b/.github/workflows/buf.yaml @@ -20,7 +20,7 @@ jobs: steps: - name: Checkout code - uses: actions/checkout@v6 + uses: actions/checkout@v7 - name: Buf build/lint/format/breaking/push uses: bufbuild/buf-action@v1 with: From 3b19be6568f8bd9a60374553b857414dbae5ea09 Mon Sep 17 00:00:00 2001 From: Lukas Bindreiter Date: Wed, 22 Jul 2026 17:00:44 +0200 Subject: [PATCH 2/2] Accounts service --- .pre-commit-config.yaml | 2 +- apis/accounts/v1alpha1/account.proto | 76 +++++++++++++ apis/accounts/v1alpha1/billing.proto | 103 ++++++++++++++++++ .../v1alpha1/authentication.proto | 60 ---------- buf.lock | 4 +- 5 files changed, 182 insertions(+), 63 deletions(-) create mode 100644 apis/accounts/v1alpha1/account.proto create mode 100644 apis/accounts/v1alpha1/billing.proto delete mode 100644 apis/authentication/v1alpha1/authentication.proto diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 1a2bf0f..38de3d0 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -1,6 +1,6 @@ repos: - repo: https://github.com/bufbuild/buf - rev: v1.71.0 + rev: v1.72.0 hooks: - id: buf-lint - id: buf-format diff --git a/apis/accounts/v1alpha1/account.proto b/apis/accounts/v1alpha1/account.proto new file mode 100644 index 0000000..509b42f --- /dev/null +++ b/apis/accounts/v1alpha1/account.proto @@ -0,0 +1,76 @@ +// Public API for resolving account details associated with an authenticated request. + +edition = "2023"; + +package accounts.v1alpha1; + +import "buf/validate/validate.proto"; + +option features.field_presence = IMPLICIT; + +// GetAccountDetailsRequest requests details about the account associated with the calling credential. +message GetAccountDetailsRequest {} + +// AccountDetails is a minimal view of the account associated with an authenticated request. +message AccountDetails { + string user_name = 1; + string email = 2; + string organization_name = 3; + string organization_slug = 4; + // The authentication method used to authenticate the request. + AuthenticationMethod active_authentication_method = 5; +} + +// AuthenticationMethod describes the credential used to authenticate the request. +message AuthenticationMethod { + option (buf.validate.message).oneof = { + fields: [ + "api_key", + "jwt" + ] + required: true + }; + option (buf.validate.message).cel = { + id: "authentication_method.type_matches_details" + message: "authentication method type must match its details" + expression: "(this.type == 1 && has(this.api_key)) || (this.type == 2 && has(this.jwt))" + }; + + // Type identifies the kind of credential used to authenticate the request. + enum Type { + TYPE_UNSPECIFIED = 0; + TYPE_API_KEY = 1; + TYPE_JWT = 2; + } + + Type type = 1 [(buf.validate.field).enum = { + defined_only: true + not_in: [0] + }]; + APIKeyDetails api_key = 2; + JWTDetails jwt = 3; +} + +// APIKeyDetails describes the API key used for the request without exposing its secret or internal identifier. +message APIKeyDetails { + string name = 1; + string description = 2; + // The non-secret identifier embedded in the API key. + string public_identifier = 3; +} + +// JWTDetails describes the verified JWT without exposing the token or subject and session identifiers. +message JWTDetails { + // The verified issuer. For Clerk-authenticated requests, this is the Clerk issuer URL. + string issuer = 1 [(buf.validate.field).string = { + min_len: 1 + uri: true + }]; +} + +// AccountService exposes information about the account associated with an authenticated request. +service AccountService { + // GetAccountDetails resolves the calling credential to its effective account details. + // Requests without valid authentication fail with UNAUTHENTICATED. + rpc GetAccountDetails(GetAccountDetailsRequest) returns (AccountDetails) {} +} diff --git a/apis/accounts/v1alpha1/billing.proto b/apis/accounts/v1alpha1/billing.proto new file mode 100644 index 0000000..0974e36 --- /dev/null +++ b/apis/accounts/v1alpha1/billing.proto @@ -0,0 +1,103 @@ +// Public API for reading subscription plan and usage information. + +edition = "2023"; + +package accounts.v1alpha1; + +import "buf/validate/validate.proto"; +import "google/protobuf/timestamp.proto"; + +option features.field_presence = IMPLICIT; + +// SubscriptionTier identifies the type of subscription an organization has. +enum SubscriptionTier { + SUBSCRIPTION_TIER_UNSPECIFIED = 0; + SUBSCRIPTION_TIER_FREE = 1; + SUBSCRIPTION_TIER_PAID = 2; + SUBSCRIPTION_TIER_CUSTOM = 3; +} + +// BillingCadence is the period in which the base subscription and add-ons are billed. +enum BillingCadence { + BILLING_CADENCE_UNSPECIFIED = 0; + BILLING_CADENCE_MONTHLY = 1; + BILLING_CADENCE_YEARLY = 2; +} + +// Unit identifies the unit in which a usage metric is measured. +enum Unit { + UNIT_UNSPECIFIED = 0; + UNIT_NO_UNIT = 1; + UNIT_BYTES = 2; + UNIT_SECONDS = 3; +} + +// MetricAggregation describes how the current value of a metric was aggregated. +enum MetricAggregation { + METRIC_AGGREGATION_UNSPECIFIED = 0; + METRIC_AGGREGATION_TOTAL = 1; + METRIC_AGGREGATION_USAGE_PERIOD = 2; +} + +// BillingPeriod describes the time range and anchor of a billing period. +message BillingPeriod { + google.protobuf.Timestamp start = 1; + google.protobuf.Timestamp end = 2; + google.protobuf.Timestamp anchor = 3; +} + +// Plan describes the active subscription plan of an organization. +message Plan { + SubscriptionTier tier = 1; + repeated string add_ons = 2; + BillingCadence billing_cadence = 3; + BillingPeriod subscription_billing_period = 4; + BillingPeriod usage_billing_period = 5; + // Set when a canceled subscription remains valid until the given time. + google.protobuf.Timestamp valid_until = 6; +} + +// UsageRecord is the value of a metric at a specific time. +message UsageRecord { + google.protobuf.Timestamp timestamp = 1; + int64 value = 2; + int64 cumulative_value = 3; +} + +// UsageHistory contains the historical values and billing periods of a metric. +message UsageHistory { + repeated BillingPeriod usage_periods = 1; + repeated UsageRecord records = 2; +} + +// UsageMetric describes the current and historical consumption of an organization metric. +message UsageMetric { + string key = 1; + Unit unit = 2; + // Unset when the metric is unlimited. + int64 limit = 3 [features.field_presence = EXPLICIT]; + int64 value = 4; + MetricAggregation aggregation = 5; + UsageHistory history = 6; +} + +// GetActivePlanRequest requests the active plan of the calling organization. +message GetActivePlanRequest {} + +// GetUsageReportRequest requests current usage and, optionally, historical values. +message GetUsageReportRequest { + // The number of history days to return. Zero omits history. + uint64 history_days = 1 [(buf.validate.field).uint64.lte = 365]; +} + +// UsageReport contains the usage metrics tracked for an organization. +message UsageReport { + repeated UsageMetric metrics = 1; + BillingPeriod usage_period = 2; +} + +// BillingService exposes subscription plan and usage information. +service BillingService { + rpc GetActivePlan(GetActivePlanRequest) returns (Plan) {} + rpc GetUsageReport(GetUsageReportRequest) returns (UsageReport) {} +} diff --git a/apis/authentication/v1alpha1/authentication.proto b/apis/authentication/v1alpha1/authentication.proto deleted file mode 100644 index 3b2e146..0000000 --- a/apis/authentication/v1alpha1/authentication.proto +++ /dev/null @@ -1,60 +0,0 @@ -// Public API for resolving the identity associated with an authenticated request. - -edition = "2023"; - -package authentication.v1alpha1; - -import "buf/validate/validate.proto"; -import "tilebox/v1/id.proto"; - -option features.field_presence = IMPLICIT; - -// User is the Tilebox user associated with an authenticated request. -message User { - // The user's Tilebox ID. - tilebox.v1.ID id = 1 [(buf.validate.field).required = true]; - // The user's display name. - string name = 2; - // The user's email address. - string email = 3; -} - -// Organization is the Tilebox organization associated with an authenticated request. -message Organization { - // The organization's Tilebox ID. - tilebox.v1.ID id = 1 [(buf.validate.field).required = true]; - // The organization's display name. - string name = 2; - // The organization's unique slug. - string slug = 3; -} - -// APIKey identifies an API key without exposing its secret. -message APIKey { - // The API key's Tilebox ID. - tilebox.v1.ID id = 1 [(buf.validate.field).required = true]; - // The non-secret identifier embedded in the API key. - string identifier = 2; - // The API key's user-provided description. - string description = 3; -} - -// GetAuthenticationStatusRequest requests the identity associated with the calling credential. -message GetAuthenticationStatusRequest {} - -// AuthenticationStatus describes the identity associated with the calling credential. -message AuthenticationStatus { - // The authenticated user. - User user = 1 [(buf.validate.field).required = true]; - // The organization the request acts within. - Organization organization = 2 [(buf.validate.field).required = true]; - // The API key used to authenticate the request. Unset for JWT or session authentication. - APIKey api_key = 3; -} - -// AuthenticationService exposes information about the effective authentication of a request. -service AuthenticationService { - // GetAuthenticationStatus resolves the calling credential to its effective user and organization. - // Requests without valid authentication fail with UNAUTHENTICATED. - rpc GetAuthenticationStatus(GetAuthenticationStatusRequest) returns (AuthenticationStatus) {} -} diff --git a/buf.lock b/buf.lock index dba1a87..8291b8c 100644 --- a/buf.lock +++ b/buf.lock @@ -2,8 +2,8 @@ version: v2 deps: - name: buf.build/bufbuild/protovalidate - commit: 50325440f8f24053b047484a6bf60b76 - digest: b5:74cb6f5c0853c3c10aafc701614194bbd63326bdb8ef4068214454b8894b03ba4113e04b3a33a8321cdf05336e37db4dc14a5e2495db8462566914f36086ba31 + commit: 435963d1631043e694e56e6bcc3c79c3 + digest: b5:f4ea07ad2dd94bd7243562f9908b9fb104feef8076040c89d9f7c1dedc074de4d4ce2b997686ef4400f3eccb765a7cfc20ed4acdd70b9a3699351245c61dba97 - name: buf.build/googleapis/googleapis commit: c17df5b2beca46928cc87d5656bd5343 digest: b5:648a01e0170d4512dea7d564016165decd1ed6e34bef79fe54753e51ad7e27545709ad9157d7551270147d551155c595a2fb0bf5bb33b1c83040ddbce915c604