@whooshbang/contracts 2.4.0 → 2.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +6 -0
- package/contract-manifest.json +35 -32
- package/dist/generated/artifact-index.d.ts +34 -34
- package/dist/generated/artifact-index.js +35 -32
- package/dist/generated/artifact-index.js.map +1 -1
- package/dist/generated/validators-standalone.d.ts +439 -400
- package/dist/generated/validators-standalone.js +6840 -1621
- package/dist/generated/validators-standalone.js.map +1 -1
- package/dist/generated/validators.d.ts +4 -1
- package/dist/generated/validators.js +4 -1
- package/dist/generated/validators.js.map +1 -1
- package/dist/generated/whooshbang-v1.d.ts +112 -1
- package/dist/index.d.ts +2 -2
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/fixtures/core-v1/fixture-index.json +24 -1
- package/fixtures/core-v1/requests/redeem-billing-promotion.json +3 -0
- package/fixtures/core-v1/scenarios/api-credential-invalid-indistinguishable.json +1 -1
- package/fixtures/core-v1/scenarios/api-credential-one-time-reveal.json +1 -1
- package/fixtures/core-v1/scenarios/api-credential-revocation-replay.json +1 -1
- package/fixtures/core-v1/scenarios/api-credential-rotation-overlap.json +1 -1
- package/fixtures/core-v1/scenarios/cancellation-too-late.json +1 -1
- package/fixtures/core-v1/scenarios/cross-organization-project.json +1 -1
- package/fixtures/core-v1/scenarios/cross-project-resource.json +1 -1
- package/fixtures/core-v1/scenarios/environment-mismatch.json +1 -1
- package/fixtures/core-v1/scenarios/idempotency-conflict.json +1 -1
- package/fixtures/core-v1/scenarios/idempotency-equivalent-replay.json +1 -1
- package/fixtures/core-v1/scenarios/malformed-bearer.json +1 -1
- package/fixtures/core-v1/scenarios/metadata-overrun.json +1 -1
- package/fixtures/core-v1/scenarios/missing-scope.json +1 -1
- package/fixtures/core-v1/scenarios/project-create-equivalent-replay.json +1 -1
- package/fixtures/core-v1/scenarios/project-slug-conflict.json +1 -1
- package/fixtures/core-v1/scenarios/provider-outcome-unknown.json +1 -1
- package/fixtures/core-v1/scenarios/subscription-activation-replay.json +1 -1
- package/fixtures/core-v1/scenarios/subscription-authorization-capability-opacity.json +1 -1
- package/fixtures/core-v1/scenarios/subscription-cross-connection-callback-rejected.json +1 -1
- package/fixtures/core-v1/scenarios/subscription-expired-replay.json +1 -1
- package/fixtures/core-v1/scenarios/subscription-selected-connection-replay.json +1 -1
- package/fixtures/core-v1/success/billing-promotion.json +14 -0
- package/fixtures/core-v1/success/billing-promotions.json +64 -0
- package/fixtures/core-v1/success/credit-purchase.json +2 -0
- package/fixtures/core-v1/success/subscription-change.json +7 -0
- package/fixtures/interaction-machine-v1/scenarios/ack-conflict.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/ack-cross-machine.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/ack-out-of-order.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/ack-replay.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/ambiguous-free-text.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/callback-token-opacity.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/credential-registration-conflict.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/credential-registration-replay.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/credential-revocation-replay.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/credential-rotation.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/first-credential-activates.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/interaction-duplicate.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/interaction-expired.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/interaction-mismatch.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/interaction-retired.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/interaction-stale.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/machine-admin-denied.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/machine-bound-message-create.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/machine-cancel-denied.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/machine-crash-before-ack.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/machine-notifier-mismatch.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/machine-other-message-read.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/machine-owned-message-read.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/machine-subscriber-mismatch.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/poll-uncommitted-cursor-rejected.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/project-credential-machine-endpoint-denied.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/quarantine-integrity-rejected.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/quarantine-signature-rejected.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/quarantine-valid.json +1 -1
- package/fixtures/interaction-machine-v1/scenarios/revoked-machine-credential.json +1 -1
- package/fixtures/recipient-experience-v1/scenarios/membership-broadcast-snapshot.json +1 -1
- package/fixtures/recipient-experience-v1/scenarios/preferred-binding-resolution.json +1 -1
- package/fixtures/recipient-experience-v1/scenarios/recipient-session-security.json +1 -1
- package/fixtures/recipient-experience-v1/scenarios/subscriber-initial-groups-transaction.json +1 -1
- package/openapi/generated/whooshbang-v1.bundle.json +386 -3
- package/openapi/whooshbang-v1.yaml +95 -2
- package/package.json +1 -1
- package/schemas/core-scenario.schema.json +1 -1
- package/schemas/events/agent-binding-degraded-v1.schema.json +1 -1
- package/schemas/events/interaction-expired-v1.schema.json +1 -1
- package/schemas/events/interaction-received-v1.schema.json +1 -1
- package/schemas/events/message-delivered-v1.schema.json +1 -1
- package/schemas/events/message-expired-v1.schema.json +1 -1
- package/schemas/events/message-failed-v1.schema.json +1 -1
- package/schemas/events/message-provider-accepted-v1.schema.json +1 -1
- package/schemas/events/subscription-activated-v1.schema.json +1 -1
- package/schemas/events/subscription-revoked-v1.schema.json +1 -1
- package/schemas/events/whooshbang-event-v1.schema.json +1 -1
- package/schemas/fixture-index.schema.json +1 -1
- package/schemas/interaction-machine-scenario.schema.json +1 -1
- package/schemas/interaction-v1.schema.json +1 -1
- package/schemas/machine-v1.schema.json +1 -1
- package/schemas/provider-capabilities-v1.schema.json +1 -1
- package/schemas/webhooks/webhook-delivery-case-v1.schema.json +1 -1
- package/schemas/webhooks/webhook-signing-vector-v1.schema.json +1 -1
- package/schemas/whooshbang-v1.schema.json +370 -1
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"openapi": "3.1.1",
|
|
3
3
|
"info": {
|
|
4
4
|
"title": "WhooshBang API",
|
|
5
|
-
"version": "2.
|
|
5
|
+
"version": "2.5.0",
|
|
6
6
|
"description": "The V1 contract for human organization/project administration, project-scoped\nsubscription links, and asynchronous text messages. A Clerk session selects\none organization for administration. A project credential selects one organization,\nproject, and `test` or `live` environment for product operations; request\nbodies cannot override either authenticated scope.\n\nA person's OAuth grant selects one organization and carries scopes, but no\nproject. It names the project and environment it acts in through the URL\npath, on the environment-scoped form of each operation; the service checks\nthat path against the granting person's membership on every call. The flat\nforms remain credential-only and are unchanged.\n\nResource identifiers are opaque and are not authorization. Reads outside the\ncredential scope return the same `404` shape as absent resources. Provider\ncredentials, raw Telegram identity, and protected provider responses are\nnever part of this API.\n",
|
|
7
7
|
"termsOfService": "https://flowxo.com/terms",
|
|
8
8
|
"contact": {
|
|
@@ -524,6 +524,92 @@
|
|
|
524
524
|
}
|
|
525
525
|
}
|
|
526
526
|
},
|
|
527
|
+
"/v1/billing/promotions": {
|
|
528
|
+
"get": {
|
|
529
|
+
"operationId": "getBillingPromotions",
|
|
530
|
+
"summary": "Read the organization's promotions",
|
|
531
|
+
"description": "Organization administrators can read every promotion the organization holds: rewards WhooshBang gave it\nand promotion codes it redeemed, with what remains and when each ends. Promotional value has no cash\nvalue, is never refunded and cannot move to another organization.\n",
|
|
532
|
+
"tags": ["Organization"],
|
|
533
|
+
"security": [{ "clerkSession": [] }, { "bearerGrant": [] }],
|
|
534
|
+
"x-required-scopes": ["billing:read"],
|
|
535
|
+
"x-organization-membership": "required",
|
|
536
|
+
"responses": {
|
|
537
|
+
"200": {
|
|
538
|
+
"description": "The organization's promotions, newest first.",
|
|
539
|
+
"headers": {
|
|
540
|
+
"WhooshBang-Diagnostic-Id": {
|
|
541
|
+
"$ref": "#/components/headers/DiagnosticId"
|
|
542
|
+
}
|
|
543
|
+
},
|
|
544
|
+
"content": {
|
|
545
|
+
"application/json": {
|
|
546
|
+
"schema": { "$ref": "#/components/schemas/BillingPromotions" }
|
|
547
|
+
}
|
|
548
|
+
}
|
|
549
|
+
},
|
|
550
|
+
"401": { "$ref": "#/components/responses/Unauthorized" },
|
|
551
|
+
"403": { "$ref": "#/components/responses/Forbidden" },
|
|
552
|
+
"404": { "$ref": "#/components/responses/NotFound" },
|
|
553
|
+
"429": { "$ref": "#/components/responses/RateLimited" }
|
|
554
|
+
}
|
|
555
|
+
}
|
|
556
|
+
},
|
|
557
|
+
"/v1/billing/promotions/redeem": {
|
|
558
|
+
"post": {
|
|
559
|
+
"operationId": "redeemBillingPromotion",
|
|
560
|
+
"summary": "Redeem a promotion code",
|
|
561
|
+
"description": "Organization administrators can redeem a promotion code for their own organization. Nothing is charged.\nEvery code that cannot be redeemed (mistyped, ended, fully used, not offered to this organization, or not\ncombinable with a promotion it already holds) receives the same `resource_not_found` answer. Repeated\nrefusals are rate limited per organization; wait for `Retry-After`. Reuse the same idempotency key after\nan uncertain response: it can never redeem twice.\n",
|
|
562
|
+
"tags": ["Organization"],
|
|
563
|
+
"security": [{ "clerkSession": [] }, { "bearerGrant": [] }],
|
|
564
|
+
"x-required-scopes": ["billing:write"],
|
|
565
|
+
"x-organization-membership": "required",
|
|
566
|
+
"parameters": [{ "$ref": "#/components/parameters/IdempotencyKey" }],
|
|
567
|
+
"requestBody": {
|
|
568
|
+
"required": true,
|
|
569
|
+
"content": {
|
|
570
|
+
"application/json": {
|
|
571
|
+
"schema": {
|
|
572
|
+
"$ref": "#/components/schemas/RedeemBillingPromotionRequest"
|
|
573
|
+
}
|
|
574
|
+
}
|
|
575
|
+
}
|
|
576
|
+
},
|
|
577
|
+
"responses": {
|
|
578
|
+
"200": {
|
|
579
|
+
"description": "The same promotion, replayed for a repeated idempotency key.",
|
|
580
|
+
"headers": {
|
|
581
|
+
"WhooshBang-Diagnostic-Id": {
|
|
582
|
+
"$ref": "#/components/headers/DiagnosticId"
|
|
583
|
+
}
|
|
584
|
+
},
|
|
585
|
+
"content": {
|
|
586
|
+
"application/json": {
|
|
587
|
+
"schema": { "$ref": "#/components/schemas/BillingPromotion" }
|
|
588
|
+
}
|
|
589
|
+
}
|
|
590
|
+
},
|
|
591
|
+
"201": {
|
|
592
|
+
"description": "The promotion the code gave the organization.",
|
|
593
|
+
"headers": {
|
|
594
|
+
"WhooshBang-Diagnostic-Id": {
|
|
595
|
+
"$ref": "#/components/headers/DiagnosticId"
|
|
596
|
+
}
|
|
597
|
+
},
|
|
598
|
+
"content": {
|
|
599
|
+
"application/json": {
|
|
600
|
+
"schema": { "$ref": "#/components/schemas/BillingPromotion" }
|
|
601
|
+
}
|
|
602
|
+
}
|
|
603
|
+
},
|
|
604
|
+
"400": { "$ref": "#/components/responses/BadRequest" },
|
|
605
|
+
"401": { "$ref": "#/components/responses/Unauthorized" },
|
|
606
|
+
"403": { "$ref": "#/components/responses/Forbidden" },
|
|
607
|
+
"404": { "$ref": "#/components/responses/NotFound" },
|
|
608
|
+
"409": { "$ref": "#/components/responses/Conflict" },
|
|
609
|
+
"429": { "$ref": "#/components/responses/RateLimited" }
|
|
610
|
+
}
|
|
611
|
+
}
|
|
612
|
+
},
|
|
527
613
|
"/v1/billing/auto-top-up": {
|
|
528
614
|
"get": {
|
|
529
615
|
"operationId": "getAutoTopUpSettings",
|
|
@@ -12865,6 +12951,202 @@
|
|
|
12865
12951
|
"additionalProperties": false,
|
|
12866
12952
|
"description": "Replace the requested active project selection with owned, active projects within current paid capacity. An empty selection releases all slots."
|
|
12867
12953
|
},
|
|
12954
|
+
"BillingPromotions": {
|
|
12955
|
+
"type": "object",
|
|
12956
|
+
"required": [
|
|
12957
|
+
"promotional_credit_usd",
|
|
12958
|
+
"free_shared_emails",
|
|
12959
|
+
"branding_removed_until",
|
|
12960
|
+
"promotions"
|
|
12961
|
+
],
|
|
12962
|
+
"properties": {
|
|
12963
|
+
"promotional_credit_usd": {
|
|
12964
|
+
"type": "string",
|
|
12965
|
+
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
12966
|
+
"maxLength": 40,
|
|
12967
|
+
"description": "Unexpired promotional message credit available now."
|
|
12968
|
+
},
|
|
12969
|
+
"free_shared_emails": {
|
|
12970
|
+
"type": "integer",
|
|
12971
|
+
"minimum": 0,
|
|
12972
|
+
"maximum": 2147483647,
|
|
12973
|
+
"description": "Unexpired free shared emails available now."
|
|
12974
|
+
},
|
|
12975
|
+
"branding_removed_until": {
|
|
12976
|
+
"anyOf": [
|
|
12977
|
+
{ "type": "string", "format": "date-time" },
|
|
12978
|
+
{ "type": "null" }
|
|
12979
|
+
],
|
|
12980
|
+
"description": "When the latest active branding promotion ends, if one is active."
|
|
12981
|
+
},
|
|
12982
|
+
"promotions": {
|
|
12983
|
+
"type": "array",
|
|
12984
|
+
"items": { "$ref": "#/components/schemas/BillingPromotion" },
|
|
12985
|
+
"maxItems": 200
|
|
12986
|
+
}
|
|
12987
|
+
},
|
|
12988
|
+
"additionalProperties": false,
|
|
12989
|
+
"description": "An organization's promotions: rewards WhooshBang gave it and promotion codes it redeemed, newest first."
|
|
12990
|
+
},
|
|
12991
|
+
"BillingPromotion": {
|
|
12992
|
+
"type": "object",
|
|
12993
|
+
"required": [
|
|
12994
|
+
"id",
|
|
12995
|
+
"source",
|
|
12996
|
+
"name",
|
|
12997
|
+
"status",
|
|
12998
|
+
"starts_at",
|
|
12999
|
+
"ends_at",
|
|
13000
|
+
"ended_at",
|
|
13001
|
+
"benefit"
|
|
13002
|
+
],
|
|
13003
|
+
"properties": {
|
|
13004
|
+
"id": { "type": "string", "pattern": "^grn_[0-9a-z]{26}$" },
|
|
13005
|
+
"source": {
|
|
13006
|
+
"type": "string",
|
|
13007
|
+
"enum": ["whooshbang", "code"],
|
|
13008
|
+
"description": "`whooshbang` for a reward WhooshBang gave the organization directly; `code` for a promotion code the organization redeemed."
|
|
13009
|
+
},
|
|
13010
|
+
"name": {
|
|
13011
|
+
"anyOf": [
|
|
13012
|
+
{ "type": "string", "minLength": 1, "maxLength": 120 },
|
|
13013
|
+
{ "type": "null" }
|
|
13014
|
+
],
|
|
13015
|
+
"description": "The promotion's name for a redeemed code. Null for a direct reward."
|
|
13016
|
+
},
|
|
13017
|
+
"status": {
|
|
13018
|
+
"type": "string",
|
|
13019
|
+
"enum": ["active", "pending", "expired", "used", "revoked"],
|
|
13020
|
+
"description": "`pending` is a credit pack discount carried by a payment still waiting for the customer's bank; it is not available to another purchase. `used` applies only to a discount that has been applied to a purchase or put on a plan. `revoked` means WhooshBang withdrew what remained."
|
|
13021
|
+
},
|
|
13022
|
+
"starts_at": { "type": "string", "format": "date-time" },
|
|
13023
|
+
"ends_at": {
|
|
13024
|
+
"anyOf": [
|
|
13025
|
+
{ "type": "string", "format": "date-time" },
|
|
13026
|
+
{ "type": "null" }
|
|
13027
|
+
],
|
|
13028
|
+
"description": "When the benefit stops. Null for a discount, which ends when it is used or, for a plan discount, after its months."
|
|
13029
|
+
},
|
|
13030
|
+
"ended_at": {
|
|
13031
|
+
"anyOf": [
|
|
13032
|
+
{ "type": "string", "format": "date-time" },
|
|
13033
|
+
{ "type": "null" }
|
|
13034
|
+
],
|
|
13035
|
+
"description": "When the promotion was used or withdrawn, if it was."
|
|
13036
|
+
},
|
|
13037
|
+
"benefit": {
|
|
13038
|
+
"oneOf": [
|
|
13039
|
+
{
|
|
13040
|
+
"type": "object",
|
|
13041
|
+
"required": ["kind", "credit_usd", "remaining_usd"],
|
|
13042
|
+
"properties": {
|
|
13043
|
+
"kind": { "const": "message_credit" },
|
|
13044
|
+
"credit_usd": {
|
|
13045
|
+
"type": "string",
|
|
13046
|
+
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
13047
|
+
"maxLength": 40
|
|
13048
|
+
},
|
|
13049
|
+
"remaining_usd": {
|
|
13050
|
+
"type": "string",
|
|
13051
|
+
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
13052
|
+
"maxLength": 40
|
|
13053
|
+
}
|
|
13054
|
+
},
|
|
13055
|
+
"additionalProperties": false,
|
|
13056
|
+
"description": "Promotional credit for messages. Spent before purchased, bonus and welcome credit; it never pays the shared-email charge."
|
|
13057
|
+
},
|
|
13058
|
+
{
|
|
13059
|
+
"type": "object",
|
|
13060
|
+
"required": ["kind", "shared_emails", "remaining"],
|
|
13061
|
+
"properties": {
|
|
13062
|
+
"kind": { "const": "shared_emails" },
|
|
13063
|
+
"shared_emails": {
|
|
13064
|
+
"type": "integer",
|
|
13065
|
+
"minimum": 1,
|
|
13066
|
+
"maximum": 1000000
|
|
13067
|
+
},
|
|
13068
|
+
"remaining": {
|
|
13069
|
+
"type": "integer",
|
|
13070
|
+
"minimum": 0,
|
|
13071
|
+
"maximum": 1000000
|
|
13072
|
+
}
|
|
13073
|
+
},
|
|
13074
|
+
"additionalProperties": false,
|
|
13075
|
+
"description": "Emails through WhooshBang's shared email service with no shared-email charge. The message itself is still paid for."
|
|
13076
|
+
},
|
|
13077
|
+
{
|
|
13078
|
+
"type": "object",
|
|
13079
|
+
"required": ["kind"],
|
|
13080
|
+
"properties": { "kind": { "const": "branding" } },
|
|
13081
|
+
"additionalProperties": false,
|
|
13082
|
+
"description": "WhooshBang branding can be removed from recipient messages until ends_at."
|
|
13083
|
+
},
|
|
13084
|
+
{
|
|
13085
|
+
"type": "object",
|
|
13086
|
+
"required": [
|
|
13087
|
+
"kind",
|
|
13088
|
+
"applies_to",
|
|
13089
|
+
"percent_off",
|
|
13090
|
+
"amount_off_usd",
|
|
13091
|
+
"duration",
|
|
13092
|
+
"months"
|
|
13093
|
+
],
|
|
13094
|
+
"properties": {
|
|
13095
|
+
"kind": { "const": "discount" },
|
|
13096
|
+
"applies_to": {
|
|
13097
|
+
"type": "string",
|
|
13098
|
+
"enum": ["credit_packs", "subscriptions"]
|
|
13099
|
+
},
|
|
13100
|
+
"percent_off": {
|
|
13101
|
+
"anyOf": [
|
|
13102
|
+
{ "type": "integer", "minimum": 1, "maximum": 90 },
|
|
13103
|
+
{ "type": "null" }
|
|
13104
|
+
]
|
|
13105
|
+
},
|
|
13106
|
+
"amount_off_usd": {
|
|
13107
|
+
"anyOf": [
|
|
13108
|
+
{
|
|
13109
|
+
"type": "string",
|
|
13110
|
+
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
13111
|
+
"maxLength": 40
|
|
13112
|
+
},
|
|
13113
|
+
{ "type": "null" }
|
|
13114
|
+
]
|
|
13115
|
+
},
|
|
13116
|
+
"duration": {
|
|
13117
|
+
"type": "string",
|
|
13118
|
+
"enum": ["once", "repeating"]
|
|
13119
|
+
},
|
|
13120
|
+
"months": {
|
|
13121
|
+
"anyOf": [
|
|
13122
|
+
{ "type": "integer", "minimum": 1, "maximum": 12 },
|
|
13123
|
+
{ "type": "null" }
|
|
13124
|
+
]
|
|
13125
|
+
}
|
|
13126
|
+
},
|
|
13127
|
+
"additionalProperties": false,
|
|
13128
|
+
"description": "Money off the next credit pack, or off plan and add-on charges for one charge or a number of months."
|
|
13129
|
+
}
|
|
13130
|
+
]
|
|
13131
|
+
}
|
|
13132
|
+
},
|
|
13133
|
+
"additionalProperties": false,
|
|
13134
|
+
"description": "One promotion an organization holds. Promotional value has no cash value, is never refunded and cannot move to another organization."
|
|
13135
|
+
},
|
|
13136
|
+
"RedeemBillingPromotionRequest": {
|
|
13137
|
+
"type": "object",
|
|
13138
|
+
"required": ["code"],
|
|
13139
|
+
"properties": {
|
|
13140
|
+
"code": {
|
|
13141
|
+
"type": "string",
|
|
13142
|
+
"minLength": 4,
|
|
13143
|
+
"maxLength": 64,
|
|
13144
|
+
"pattern": "^[A-Za-z0-9][A-Za-z0-9 _-]*$",
|
|
13145
|
+
"description": "The promotion code. Case, spaces, hyphens and underscores are ignored."
|
|
13146
|
+
}
|
|
13147
|
+
},
|
|
13148
|
+
"additionalProperties": false
|
|
13149
|
+
},
|
|
12868
13150
|
"BillingEntitlements": {
|
|
12869
13151
|
"type": "object",
|
|
12870
13152
|
"required": [
|
|
@@ -13029,6 +13311,8 @@
|
|
|
13029
13311
|
"monthly_price_usd",
|
|
13030
13312
|
"charge_now_usd",
|
|
13031
13313
|
"unused_time_credit_usd",
|
|
13314
|
+
"promotion",
|
|
13315
|
+
"renewal_promotion",
|
|
13032
13316
|
"effective_at",
|
|
13033
13317
|
"expires_at",
|
|
13034
13318
|
"client_secret",
|
|
@@ -13084,6 +13368,85 @@
|
|
|
13084
13368
|
],
|
|
13085
13369
|
"description": "Compatibility field: new upgrades return 0.000000; starts and boundary changes return null. Historical quotes can retain their recorded unused-time credit. No new automatic unused-time refunds or offsets."
|
|
13086
13370
|
},
|
|
13371
|
+
"promotion": {
|
|
13372
|
+
"anyOf": [
|
|
13373
|
+
{
|
|
13374
|
+
"type": "object",
|
|
13375
|
+
"required": [
|
|
13376
|
+
"percent_off",
|
|
13377
|
+
"duration",
|
|
13378
|
+
"months",
|
|
13379
|
+
"discount_usd"
|
|
13380
|
+
],
|
|
13381
|
+
"properties": {
|
|
13382
|
+
"percent_off": {
|
|
13383
|
+
"type": "integer",
|
|
13384
|
+
"minimum": 1,
|
|
13385
|
+
"maximum": 90
|
|
13386
|
+
},
|
|
13387
|
+
"duration": {
|
|
13388
|
+
"type": "string",
|
|
13389
|
+
"enum": ["once", "repeating"]
|
|
13390
|
+
},
|
|
13391
|
+
"months": {
|
|
13392
|
+
"anyOf": [
|
|
13393
|
+
{ "type": "integer", "minimum": 1, "maximum": 12 },
|
|
13394
|
+
{ "type": "null" }
|
|
13395
|
+
]
|
|
13396
|
+
},
|
|
13397
|
+
"discount_usd": {
|
|
13398
|
+
"type": "string",
|
|
13399
|
+
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
13400
|
+
"maxLength": 40,
|
|
13401
|
+
"description": "What the promotion takes off charge_now_usd."
|
|
13402
|
+
}
|
|
13403
|
+
},
|
|
13404
|
+
"additionalProperties": false
|
|
13405
|
+
},
|
|
13406
|
+
{ "type": "null" }
|
|
13407
|
+
],
|
|
13408
|
+
"description": "A promotion code's plan discount applied to this first plan or add-on purchase: charge_now_usd is already reduced by it, and the monthly charges keep it for its months. Null when no plan discount applies."
|
|
13409
|
+
},
|
|
13410
|
+
"renewal_promotion": {
|
|
13411
|
+
"anyOf": [
|
|
13412
|
+
{
|
|
13413
|
+
"type": "object",
|
|
13414
|
+
"required": [
|
|
13415
|
+
"percent_off",
|
|
13416
|
+
"duration",
|
|
13417
|
+
"renewal_price_usd",
|
|
13418
|
+
"ends_at"
|
|
13419
|
+
],
|
|
13420
|
+
"properties": {
|
|
13421
|
+
"percent_off": {
|
|
13422
|
+
"type": "integer",
|
|
13423
|
+
"minimum": 1,
|
|
13424
|
+
"maximum": 90
|
|
13425
|
+
},
|
|
13426
|
+
"duration": {
|
|
13427
|
+
"type": "string",
|
|
13428
|
+
"enum": ["once", "repeating"]
|
|
13429
|
+
},
|
|
13430
|
+
"renewal_price_usd": {
|
|
13431
|
+
"type": "string",
|
|
13432
|
+
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
13433
|
+
"maxLength": 40,
|
|
13434
|
+
"description": "What the next monthly charge for this selection comes to with the promotion: monthly_price_usd less its percentage."
|
|
13435
|
+
},
|
|
13436
|
+
"ends_at": {
|
|
13437
|
+
"anyOf": [
|
|
13438
|
+
{ "type": "string", "format": "date-time" },
|
|
13439
|
+
{ "type": "null" }
|
|
13440
|
+
],
|
|
13441
|
+
"description": "When a repeating promotion stops applying. Null for a once promotion, which applies to the next monthly charge only."
|
|
13442
|
+
}
|
|
13443
|
+
},
|
|
13444
|
+
"additionalProperties": false
|
|
13445
|
+
},
|
|
13446
|
+
{ "type": "null" }
|
|
13447
|
+
],
|
|
13448
|
+
"description": "A plan discount already running on the subscription, which keeps lowering the monthly charges after this change. It never reduces charge_now_usd. Null when none applies to the next monthly charge, and once a change is no longer a quote."
|
|
13449
|
+
},
|
|
13087
13450
|
"effective_at": {
|
|
13088
13451
|
"anyOf": [
|
|
13089
13452
|
{ "type": "string", "format": "date-time" },
|
|
@@ -13416,6 +13779,12 @@
|
|
|
13416
13779
|
"purchase_cents": {
|
|
13417
13780
|
"type": "integer",
|
|
13418
13781
|
"enum": [500, 1000, 2500, 5000, 10000]
|
|
13782
|
+
},
|
|
13783
|
+
"approved_charge_usd": {
|
|
13784
|
+
"type": "string",
|
|
13785
|
+
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
13786
|
+
"maxLength": 40,
|
|
13787
|
+
"description": "Optional. The card charge the customer approved: the pack price less any promotion shown to them. When it differs from what would be charged, the purchase is refused with credit_purchase_price_changed and nothing is charged."
|
|
13419
13788
|
}
|
|
13420
13789
|
},
|
|
13421
13790
|
"description": "Buy one credit pack now with the default card. The amount is the explicit approval of the charge."
|
|
@@ -13427,6 +13796,8 @@
|
|
|
13427
13796
|
"id",
|
|
13428
13797
|
"purchase_cents",
|
|
13429
13798
|
"credit_usd",
|
|
13799
|
+
"charged_usd",
|
|
13800
|
+
"discount_usd",
|
|
13430
13801
|
"status",
|
|
13431
13802
|
"failure",
|
|
13432
13803
|
"client_secret",
|
|
@@ -13447,6 +13818,18 @@
|
|
|
13447
13818
|
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
13448
13819
|
"maxLength": 40
|
|
13449
13820
|
},
|
|
13821
|
+
"charged_usd": {
|
|
13822
|
+
"type": "string",
|
|
13823
|
+
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
13824
|
+
"maxLength": 40,
|
|
13825
|
+
"description": "What the card is charged: the pack price less any promotional discount. The pack's credit is unchanged."
|
|
13826
|
+
},
|
|
13827
|
+
"discount_usd": {
|
|
13828
|
+
"type": "string",
|
|
13829
|
+
"pattern": "^(0|[1-9][0-9]*)\\.[0-9]{6}$",
|
|
13830
|
+
"maxLength": 40,
|
|
13831
|
+
"description": "The promotional discount taken off the pack price, or 0.000000."
|
|
13832
|
+
},
|
|
13450
13833
|
"status": {
|
|
13451
13834
|
"type": "string",
|
|
13452
13835
|
"enum": ["processing", "requires_action", "paid", "failed"]
|
|
@@ -20416,7 +20799,7 @@
|
|
|
20416
20799
|
"provider-capabilities-v1.schema": {
|
|
20417
20800
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
20418
20801
|
"$id": "https://whooshbang.flowxo.com/schemas/provider-capabilities-v1.schema.json",
|
|
20419
|
-
"x-contract-version": "2.
|
|
20802
|
+
"x-contract-version": "2.5.0",
|
|
20420
20803
|
"title": "ProviderCapabilitiesV1",
|
|
20421
20804
|
"description": "Provider-neutral, renderer-facing delivery and interaction capabilities with explicit degradation.",
|
|
20422
20805
|
"type": "object",
|
|
@@ -21197,5 +21580,5 @@
|
|
|
21197
21580
|
}
|
|
21198
21581
|
}
|
|
21199
21582
|
},
|
|
21200
|
-
"x-contract-version": "2.
|
|
21583
|
+
"x-contract-version": "2.5.0"
|
|
21201
21584
|
}
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
openapi: 3.1.1
|
|
2
2
|
jsonSchemaDialect: https://json-schema.org/draft/2020-12/schema
|
|
3
3
|
# whooshbang:public-origin production api https://api.whooshbang.com
|
|
4
|
-
x-contract-version: 2.
|
|
4
|
+
x-contract-version: 2.5.0
|
|
5
5
|
info:
|
|
6
6
|
title: WhooshBang API
|
|
7
|
-
version: 2.
|
|
7
|
+
version: 2.5.0
|
|
8
8
|
description: |
|
|
9
9
|
The V1 contract for human organization/project administration, project-scoped
|
|
10
10
|
subscription links, and asynchronous text messages. A Clerk session selects
|
|
@@ -435,6 +435,93 @@ paths:
|
|
|
435
435
|
$ref: "#/components/responses/Conflict"
|
|
436
436
|
"429":
|
|
437
437
|
$ref: "#/components/responses/RateLimited"
|
|
438
|
+
/v1/billing/promotions:
|
|
439
|
+
get:
|
|
440
|
+
operationId: getBillingPromotions
|
|
441
|
+
summary: Read the organization's promotions
|
|
442
|
+
description: |
|
|
443
|
+
Organization administrators can read every promotion the organization holds: rewards WhooshBang gave it
|
|
444
|
+
and promotion codes it redeemed, with what remains and when each ends. Promotional value has no cash
|
|
445
|
+
value, is never refunded and cannot move to another organization.
|
|
446
|
+
tags: [Organization]
|
|
447
|
+
security:
|
|
448
|
+
- clerkSession: []
|
|
449
|
+
- bearerGrant: []
|
|
450
|
+
x-required-scopes: [billing:read]
|
|
451
|
+
x-organization-membership: required
|
|
452
|
+
responses:
|
|
453
|
+
"200":
|
|
454
|
+
description: The organization's promotions, newest first.
|
|
455
|
+
headers:
|
|
456
|
+
WhooshBang-Diagnostic-Id:
|
|
457
|
+
$ref: "#/components/headers/DiagnosticId"
|
|
458
|
+
content:
|
|
459
|
+
application/json:
|
|
460
|
+
schema:
|
|
461
|
+
$ref: "#/components/schemas/BillingPromotions"
|
|
462
|
+
"401":
|
|
463
|
+
$ref: "#/components/responses/Unauthorized"
|
|
464
|
+
"403":
|
|
465
|
+
$ref: "#/components/responses/Forbidden"
|
|
466
|
+
"404":
|
|
467
|
+
$ref: "#/components/responses/NotFound"
|
|
468
|
+
"429":
|
|
469
|
+
$ref: "#/components/responses/RateLimited"
|
|
470
|
+
/v1/billing/promotions/redeem:
|
|
471
|
+
post:
|
|
472
|
+
operationId: redeemBillingPromotion
|
|
473
|
+
summary: Redeem a promotion code
|
|
474
|
+
description: |
|
|
475
|
+
Organization administrators can redeem a promotion code for their own organization. Nothing is charged.
|
|
476
|
+
Every code that cannot be redeemed (mistyped, ended, fully used, not offered to this organization, or not
|
|
477
|
+
combinable with a promotion it already holds) receives the same `resource_not_found` answer. Repeated
|
|
478
|
+
refusals are rate limited per organization; wait for `Retry-After`. Reuse the same idempotency key after
|
|
479
|
+
an uncertain response: it can never redeem twice.
|
|
480
|
+
tags: [Organization]
|
|
481
|
+
security:
|
|
482
|
+
- clerkSession: []
|
|
483
|
+
- bearerGrant: []
|
|
484
|
+
x-required-scopes: [billing:write]
|
|
485
|
+
x-organization-membership: required
|
|
486
|
+
parameters:
|
|
487
|
+
- $ref: "#/components/parameters/IdempotencyKey"
|
|
488
|
+
requestBody:
|
|
489
|
+
required: true
|
|
490
|
+
content:
|
|
491
|
+
application/json:
|
|
492
|
+
schema:
|
|
493
|
+
$ref: "#/components/schemas/RedeemBillingPromotionRequest"
|
|
494
|
+
responses:
|
|
495
|
+
"200":
|
|
496
|
+
description: The same promotion, replayed for a repeated idempotency key.
|
|
497
|
+
headers:
|
|
498
|
+
WhooshBang-Diagnostic-Id:
|
|
499
|
+
$ref: "#/components/headers/DiagnosticId"
|
|
500
|
+
content:
|
|
501
|
+
application/json:
|
|
502
|
+
schema:
|
|
503
|
+
$ref: "#/components/schemas/BillingPromotion"
|
|
504
|
+
"201":
|
|
505
|
+
description: The promotion the code gave the organization.
|
|
506
|
+
headers:
|
|
507
|
+
WhooshBang-Diagnostic-Id:
|
|
508
|
+
$ref: "#/components/headers/DiagnosticId"
|
|
509
|
+
content:
|
|
510
|
+
application/json:
|
|
511
|
+
schema:
|
|
512
|
+
$ref: "#/components/schemas/BillingPromotion"
|
|
513
|
+
"400":
|
|
514
|
+
$ref: "#/components/responses/BadRequest"
|
|
515
|
+
"401":
|
|
516
|
+
$ref: "#/components/responses/Unauthorized"
|
|
517
|
+
"403":
|
|
518
|
+
$ref: "#/components/responses/Forbidden"
|
|
519
|
+
"404":
|
|
520
|
+
$ref: "#/components/responses/NotFound"
|
|
521
|
+
"409":
|
|
522
|
+
$ref: "#/components/responses/Conflict"
|
|
523
|
+
"429":
|
|
524
|
+
$ref: "#/components/responses/RateLimited"
|
|
438
525
|
/v1/billing/auto-top-up:
|
|
439
526
|
get:
|
|
440
527
|
operationId: getAutoTopUpSettings
|
|
@@ -8754,6 +8841,12 @@ components:
|
|
|
8754
8841
|
$ref: "../schemas/whooshbang-v1.schema.json#/$defs/BillingProjectSlots"
|
|
8755
8842
|
AssignBillingProjectSlotsRequest:
|
|
8756
8843
|
$ref: "../schemas/whooshbang-v1.schema.json#/$defs/AssignBillingProjectSlotsRequest"
|
|
8844
|
+
BillingPromotions:
|
|
8845
|
+
$ref: "../schemas/whooshbang-v1.schema.json#/$defs/BillingPromotions"
|
|
8846
|
+
BillingPromotion:
|
|
8847
|
+
$ref: "../schemas/whooshbang-v1.schema.json#/$defs/BillingPromotion"
|
|
8848
|
+
RedeemBillingPromotionRequest:
|
|
8849
|
+
$ref: "../schemas/whooshbang-v1.schema.json#/$defs/RedeemBillingPromotionRequest"
|
|
8757
8850
|
BillingEntitlements:
|
|
8758
8851
|
$ref: "../schemas/whooshbang-v1.schema.json#/$defs/BillingEntitlements"
|
|
8759
8852
|
SubscriptionSelection:
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
3
|
"$id": "https://whooshbang.flowxo.com/schemas/core-scenario.schema.json",
|
|
4
|
-
"x-contract-version": "2.
|
|
4
|
+
"x-contract-version": "2.5.0",
|
|
5
5
|
"title": "CoreContractScenario",
|
|
6
6
|
"description": "A deterministic C0-02 semantic, state, idempotency, or isolation scenario.",
|
|
7
7
|
"type": "object",
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
3
|
"$id": "https://whooshbang.flowxo.com/schemas/events/agent-binding-degraded-v1.schema.json",
|
|
4
|
-
"x-contract-version": "2.
|
|
4
|
+
"x-contract-version": "2.5.0",
|
|
5
5
|
"title": "AgentBindingDegradedEventV1",
|
|
6
6
|
"description": "An agent binding entered a provider-neutral degraded state.",
|
|
7
7
|
"$ref": "whooshbang-event-v1.schema.json#/$defs/AgentBindingDegradedEvent"
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
3
|
"$id": "https://whooshbang.flowxo.com/schemas/events/interaction-expired-v1.schema.json",
|
|
4
|
-
"x-contract-version": "2.
|
|
4
|
+
"x-contract-version": "2.5.0",
|
|
5
5
|
"title": "InteractionExpiredEventV1",
|
|
6
6
|
"description": "An interaction reached its terminal expiry without a valid answer.",
|
|
7
7
|
"$ref": "whooshbang-event-v1.schema.json#/$defs/InteractionExpiredEvent"
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
3
|
"$id": "https://whooshbang.flowxo.com/schemas/events/interaction-received-v1.schema.json",
|
|
4
|
-
"x-contract-version": "2.
|
|
4
|
+
"x-contract-version": "2.5.0",
|
|
5
5
|
"title": "InteractionReceivedEventV1",
|
|
6
6
|
"description": "One authenticated, provider-neutral interaction answer was received.",
|
|
7
7
|
"$ref": "whooshbang-event-v1.schema.json#/$defs/InteractionReceivedEvent"
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
3
|
"$id": "https://whooshbang.flowxo.com/schemas/events/message-delivered-v1.schema.json",
|
|
4
|
-
"x-contract-version": "2.
|
|
4
|
+
"x-contract-version": "2.5.0",
|
|
5
5
|
"title": "MessageDeliveredEventV1",
|
|
6
6
|
"description": "A provider supplied trustworthy evidence that a message was delivered.",
|
|
7
7
|
"$ref": "whooshbang-event-v1.schema.json#/$defs/MessageDeliveredEvent"
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
3
|
"$id": "https://whooshbang.flowxo.com/schemas/events/message-expired-v1.schema.json",
|
|
4
|
-
"x-contract-version": "2.
|
|
4
|
+
"x-contract-version": "2.5.0",
|
|
5
5
|
"title": "MessageExpiredEventV1",
|
|
6
6
|
"description": "A message expired before reaching a later delivery state.",
|
|
7
7
|
"$ref": "whooshbang-event-v1.schema.json#/$defs/MessageExpiredEvent"
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
3
|
"$id": "https://whooshbang.flowxo.com/schemas/events/message-failed-v1.schema.json",
|
|
4
|
-
"x-contract-version": "2.
|
|
4
|
+
"x-contract-version": "2.5.0",
|
|
5
5
|
"title": "MessageFailedEventV1",
|
|
6
6
|
"description": "A message reached a classified terminal failure.",
|
|
7
7
|
"$ref": "whooshbang-event-v1.schema.json#/$defs/MessageFailedEvent"
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
3
3
|
"$id": "https://whooshbang.flowxo.com/schemas/events/message-provider-accepted-v1.schema.json",
|
|
4
|
-
"x-contract-version": "2.
|
|
4
|
+
"x-contract-version": "2.5.0",
|
|
5
5
|
"title": "MessageProviderAcceptedEventV1",
|
|
6
6
|
"description": "The provider accepted a message without implying delivery.",
|
|
7
7
|
"$ref": "whooshbang-event-v1.schema.json#/$defs/MessageProviderAcceptedEvent"
|