From 39d53819b47d402ed1b03dd21e8242e5468e20bd Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Wed, 8 Apr 2026 21:13:26 +0000 Subject: [PATCH 1/7] codegen metadata --- .stats.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.stats.yml b/.stats.yml index e601ebaa..3efdf4ae 100644 --- a/.stats.yml +++ b/.stats.yml @@ -1,4 +1,4 @@ configured_endpoints: 193 -openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/frostedinc%2Fwhopsdk-e284f164f530a4ebe56001acedd17b184c1886a923699ab4084c7a41ebb73d5a.yml -openapi_spec_hash: 20f5bb8d4625bd9695845a77279926ea +openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/frostedinc%2Fwhopsdk-2132c11b688fd9f9a5237d808f19e9acb2dafe2f3c6e159e93b65465718ae4be.yml +openapi_spec_hash: 53bc06afa2f9f32cc863f8300038b001 config_hash: fee5c8b2e5f00cef705ad48c3f3b5b5a From 9a3a5ebc9eea6d29bbb4ff08ca1b67ec869d875c Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Thu, 9 Apr 2026 04:13:45 +0000 Subject: [PATCH 2/7] codegen metadata --- .stats.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.stats.yml b/.stats.yml index 3efdf4ae..66cac6a9 100644 --- a/.stats.yml +++ b/.stats.yml @@ -1,4 +1,4 @@ configured_endpoints: 193 -openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/frostedinc%2Fwhopsdk-2132c11b688fd9f9a5237d808f19e9acb2dafe2f3c6e159e93b65465718ae4be.yml -openapi_spec_hash: 53bc06afa2f9f32cc863f8300038b001 +openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/frostedinc%2Fwhopsdk-705412f3f0007209701ba39dbdf18a040585fc44d17faa7bf90885e9688cb4a7.yml +openapi_spec_hash: 2d7cf217dfb8f6d9a272c0643b30d013 config_hash: fee5c8b2e5f00cef705ad48c3f3b5b5a From 8a21bdbf1781f0648dab879d60525264a14cb1f2 Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Thu, 9 Apr 2026 06:13:30 +0000 Subject: [PATCH 3/7] feat(api): api update --- .stats.yml | 4 ++-- src/resources/payments.ts | 6 ++++++ src/resources/refunds.ts | 3 ++- 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/.stats.yml b/.stats.yml index 66cac6a9..c9f22c57 100644 --- a/.stats.yml +++ b/.stats.yml @@ -1,4 +1,4 @@ configured_endpoints: 193 -openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/frostedinc%2Fwhopsdk-705412f3f0007209701ba39dbdf18a040585fc44d17faa7bf90885e9688cb4a7.yml -openapi_spec_hash: 2d7cf217dfb8f6d9a272c0643b30d013 +openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/frostedinc%2Fwhopsdk-d0bafad1dd96b7430affd043c4f997985ab34c6c6b42a9839e0e9edc4f9c59b1.yml +openapi_spec_hash: 0867d34f6d45f6d9e3b95139ef7139bd config_hash: fee5c8b2e5f00cef705ad48c3f3b5b5a diff --git a/src/resources/payments.ts b/src/resources/payments.ts index 58c43433..11b8c6b9 100644 --- a/src/resources/payments.ts +++ b/src/resources/payments.ts @@ -292,6 +292,7 @@ export type PaymentMethodTypes = | 'apple_pay' | 'au_becs_debit' | 'bacs_debit' + | 'bancolombia' | 'bancontact' | 'billie' | 'bizum' @@ -306,6 +307,7 @@ export type PaymentMethodTypes = | 'custom' | 'customer_balance' | 'demo_pay' + | 'efecty' | 'eps' | 'eu_bank_transfer' | 'fpx' @@ -324,10 +326,12 @@ export type PaymentMethodTypes = | 'kriya' | 'link' | 'mb_way' + | 'mercado_pago' | 'mobilepay' | 'mondu' | 'multibanco' | 'naver_pay' + | 'nequi' | 'netbanking' | 'ng_bank' | 'ng_bank_transfer' @@ -338,6 +342,7 @@ export type PaymentMethodTypes = | 'nz_bank_account' | 'oxxo' | 'p24' + | 'pse' | 'pay_by_bank' | 'payco' | 'paynow' @@ -360,6 +365,7 @@ export type PaymentMethodTypes = | 'shopeepay' | 'sofort' | 'south_korea_market' + | 'spei' | 'splitit' | 'sunbit' | 'swish' diff --git a/src/resources/refunds.ts b/src/resources/refunds.ts index 0f832556..216d14fa 100644 --- a/src/resources/refunds.ts +++ b/src/resources/refunds.ts @@ -61,7 +61,8 @@ export type PaymentProvider = | 'checkout_dot_com' | 'airwallex' | 'coinflow' - | 'sequra'; + | 'sequra' + | 'dlocal'; /** * The status of the refund reference. From c54d2a001185928de49909552c6e142b0a73fd7a Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Thu, 9 Apr 2026 09:13:41 +0000 Subject: [PATCH 4/7] codegen metadata --- .stats.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.stats.yml b/.stats.yml index c9f22c57..9c7e46d5 100644 --- a/.stats.yml +++ b/.stats.yml @@ -1,4 +1,4 @@ configured_endpoints: 193 -openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/frostedinc%2Fwhopsdk-d0bafad1dd96b7430affd043c4f997985ab34c6c6b42a9839e0e9edc4f9c59b1.yml -openapi_spec_hash: 0867d34f6d45f6d9e3b95139ef7139bd +openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/frostedinc%2Fwhopsdk-58749e1928f402cc3e236d38b53bce3b10530bfaccbe426181bba9b1bfc42498.yml +openapi_spec_hash: ecea6e6c4b93665aee5554839a26ded8 config_hash: fee5c8b2e5f00cef705ad48c3f3b5b5a From b6e0e4d1ab23a07baed3f8c738871f29c844836d Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Thu, 9 Apr 2026 20:10:51 +0000 Subject: [PATCH 5/7] chore(internal): show error causes in MCP servers when running in local mode --- packages/mcp-server/src/code-tool-worker.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/packages/mcp-server/src/code-tool-worker.ts b/packages/mcp-server/src/code-tool-worker.ts index 9f188419..95448a7f 100644 --- a/packages/mcp-server/src/code-tool-worker.ts +++ b/packages/mcp-server/src/code-tool-worker.ts @@ -378,7 +378,8 @@ function makeSdkProxy(obj: T, { path, isBelievedBad = false }: function parseError(code: string, error: unknown): string | undefined { if (!(error instanceof Error)) return; - const message = error.name ? `${error.name}: ${error.message}` : error.message; + const cause = error.cause instanceof Error ? `: ${error.cause.message}` : ''; + const message = error.name ? `${error.name}: ${error.message}${cause}` : `${error.message}${cause}`; try { // Deno uses V8; the first ":LINE:COLUMN" is the top of stack. const lineNumber = error.stack?.match(/:([0-9]+):[0-9]+/)?.[1]; From 415a34513f334fb848a16c306d48c5806b8ef80e Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Fri, 10 Apr 2026 01:55:37 +0000 Subject: [PATCH 6/7] feat(api): manual updates --- .stats.yml | 4 +- api.md | 5 + packages/mcp-server/src/code-tool-worker.ts | 2 + packages/mcp-server/src/local-docs-search.ts | 83 +++++ packages/mcp-server/src/methods.ts | 12 + src/client.ts | 8 + src/resources/checkout-configurations.ts | 13 +- src/resources/index.ts | 4 + src/resources/invoices.ts | 371 +++++++++++++++++++ src/resources/plans.ts | 21 +- tests/api-resources/invoices.test.ts | 95 +++++ 11 files changed, 606 insertions(+), 12 deletions(-) diff --git a/.stats.yml b/.stats.yml index 9c7e46d5..fc1b6001 100644 --- a/.stats.yml +++ b/.stats.yml @@ -1,4 +1,4 @@ -configured_endpoints: 193 +configured_endpoints: 195 openapi_spec_url: https://storage.googleapis.com/stainless-sdk-openapi-specs/frostedinc%2Fwhopsdk-58749e1928f402cc3e236d38b53bce3b10530bfaccbe426181bba9b1bfc42498.yml openapi_spec_hash: ecea6e6c4b93665aee5554839a26ded8 -config_hash: fee5c8b2e5f00cef705ad48c3f3b5b5a +config_hash: 2ceaf6cd488db626c181a1ca9460ace6 diff --git a/api.md b/api.md index 13ccd6a5..feba6690 100644 --- a/api.md +++ b/api.md @@ -80,6 +80,7 @@ Methods: Types: - TaxIdentifierType +- InvoiceDeleteResponse - InvoiceMarkPaidResponse - InvoiceMarkUncollectibleResponse - InvoiceVoidResponse @@ -88,7 +89,9 @@ Methods: - client.invoices.create({ ...params }) -> Invoice - client.invoices.retrieve(id) -> Invoice +- client.invoices.update(id, { ...params }) -> Invoice - client.invoices.list({ ...params }) -> InvoiceListItemsCursorPage +- client.invoices.delete(id) -> InvoiceDeleteResponse - client.invoices.markPaid(id) -> InvoiceMarkPaidResponse - client.invoices.markUncollectible(id) -> InvoiceMarkUncollectibleResponse - client.invoices.void(id) -> InvoiceVoidResponse @@ -186,6 +189,8 @@ Methods: Types: +- CheckoutFont +- CheckoutShape - PlanListResponse - PlanDeleteResponse diff --git a/packages/mcp-server/src/code-tool-worker.ts b/packages/mcp-server/src/code-tool-worker.ts index 95448a7f..f3e483a7 100644 --- a/packages/mcp-server/src/code-tool-worker.ts +++ b/packages/mcp-server/src/code-tool-worker.ts @@ -113,10 +113,12 @@ const fuse = new Fuse( 'client.apps.retrieve', 'client.apps.update', 'client.invoices.create', + 'client.invoices.delete', 'client.invoices.list', 'client.invoices.markPaid', 'client.invoices.markUncollectible', 'client.invoices.retrieve', + 'client.invoices.update', 'client.invoices.void', 'client.courseLessonInteractions.list', 'client.courseLessonInteractions.retrieve', diff --git a/packages/mcp-server/src/local-docs-search.ts b/packages/mcp-server/src/local-docs-search.ts index 4350347e..1332b26e 100644 --- a/packages/mcp-server/src/local-docs-search.ts +++ b/packages/mcp-server/src/local-docs-search.ts @@ -452,6 +452,89 @@ const EMBEDDED_METHODS: MethodEntry[] = [ }, }, }, + { + name: 'update', + endpoint: '/invoices/{id}', + httpMethod: 'patch', + summary: 'Update invoice', + description: "Update a draft invoice's details.\n\nRequired permissions:\n - `invoice:update`", + stainlessPath: '(resource) invoices > (method) update', + qualified: 'client.invoices.update', + params: [ + 'id: string;', + 'automatically_finalizes_at?: string;', + 'billing_address?: { city?: string; country?: string; line1?: string; line2?: string; name?: string; phone?: string; postal_code?: string; state?: string; tax_id_type?: string; tax_id_value?: string; };', + 'charge_buyer_fee?: boolean;', + "collection_method?: 'send_invoice' | 'charge_automatically';", + 'customer_name?: string;', + 'due_date?: string;', + 'email_address?: string;', + 'line_items?: { label: string; unit_price: number; quantity?: number; }[];', + 'mailing_address_id?: string;', + 'member_id?: string;', + 'payment_method_id?: string;', + "plan?: { billing_period?: number; custom_fields?: { field_type: 'text'; name: string; id?: string; order?: number; placeholder?: string; required?: boolean; }[]; description?: string; expiration_days?: number; initial_price?: number; internal_notes?: string; legacy_payment_method_controls?: boolean; payment_method_configuration?: { disabled: string[]; enabled: string[]; include_platform_defaults: boolean; }; plan_type?: 'renewal' | 'one_time'; release_method?: 'buy_now' | 'waitlist'; renewal_price?: number; stock?: number; trial_period_days?: number; unlimited_stock?: boolean; visibility?: 'visible' | 'hidden' | 'archived' | 'quick_link'; };", + ], + response: + "{ id: string; created_at: string; current_plan: { id: string; currency: string; formatted_price: string; }; due_date: string; email_address: string; fetch_invoice_token: string; number: string; status: 'draft' | 'open' | 'paid' | 'past_due' | 'uncollectible' | 'void'; user: { id: string; name: string; username: string; }; }", + markdown: + "## update\n\n`client.invoices.update(id: string, automatically_finalizes_at?: string, billing_address?: { city?: string; country?: string; line1?: string; line2?: string; name?: string; phone?: string; postal_code?: string; state?: string; tax_id_type?: string; tax_id_value?: string; }, charge_buyer_fee?: boolean, collection_method?: 'send_invoice' | 'charge_automatically', customer_name?: string, due_date?: string, email_address?: string, line_items?: { label: string; unit_price: number; quantity?: number; }[], mailing_address_id?: string, member_id?: string, payment_method_id?: string, plan?: { billing_period?: number; custom_fields?: { field_type: 'text'; name: string; id?: string; order?: number; placeholder?: string; required?: boolean; }[]; description?: string; expiration_days?: number; initial_price?: number; internal_notes?: string; legacy_payment_method_controls?: boolean; payment_method_configuration?: { disabled: payment_method_types[]; enabled: payment_method_types[]; include_platform_defaults: boolean; }; plan_type?: 'renewal' | 'one_time'; release_method?: 'buy_now' | 'waitlist'; renewal_price?: number; stock?: number; trial_period_days?: number; unlimited_stock?: boolean; visibility?: 'visible' | 'hidden' | 'archived' | 'quick_link'; }): { id: string; created_at: string; current_plan: object; due_date: string; email_address: string; fetch_invoice_token: string; number: string; status: invoice_status; user: object; }`\n\n**patch** `/invoices/{id}`\n\nUpdate a draft invoice's details.\n\nRequired permissions:\n - `invoice:update`\n\n### Parameters\n\n- `id: string`\n\n- `automatically_finalizes_at?: string`\n The date and time when the invoice will be automatically finalized and charged.\n\n- `billing_address?: { city?: string; country?: string; line1?: string; line2?: string; name?: string; phone?: string; postal_code?: string; state?: string; tax_id_type?: string; tax_id_value?: string; }`\n Inline billing address to create or update a mailing address for this invoice.\n - `city?: string`\n The city of the address.\n - `country?: string`\n The country of the address.\n - `line1?: string`\n The line 1 of the address.\n - `line2?: string`\n The line 2 of the address.\n - `name?: string`\n The name of the customer.\n - `phone?: string`\n The phone number of the customer.\n - `postal_code?: string`\n The postal code of the address.\n - `state?: string`\n The state of the address.\n - `tax_id_type?: string`\n The type of tax identifier\n - `tax_id_value?: string`\n The value of the tax identifier.\n\n- `charge_buyer_fee?: boolean`\n Whether to charge the customer a buyer fee on this invoice.\n\n- `collection_method?: 'send_invoice' | 'charge_automatically'`\n The method of collection for an invoice.\n\n- `customer_name?: string`\n The name of the customer.\n\n- `due_date?: string`\n The date by which the invoice must be paid.\n\n- `email_address?: string`\n The email address of the customer.\n\n- `line_items?: { label: string; unit_price: number; quantity?: number; }[]`\n Line items that break down the invoice total.\n\n- `mailing_address_id?: string`\n The unique identifier of an existing mailing address to attach.\n\n- `member_id?: string`\n The unique identifier of a member to assign as the customer.\n\n- `payment_method_id?: string`\n The unique identifier of the payment method to charge.\n\n- `plan?: { billing_period?: number; custom_fields?: { field_type: 'text'; name: string; id?: string; order?: number; placeholder?: string; required?: boolean; }[]; description?: string; expiration_days?: number; initial_price?: number; internal_notes?: string; legacy_payment_method_controls?: boolean; payment_method_configuration?: { disabled: string[]; enabled: string[]; include_platform_defaults: boolean; }; plan_type?: 'renewal' | 'one_time'; release_method?: 'buy_now' | 'waitlist'; renewal_price?: number; stock?: number; trial_period_days?: number; unlimited_stock?: boolean; visibility?: 'visible' | 'hidden' | 'archived' | 'quick_link'; }`\n Updated plan attributes.\n - `billing_period?: number`\n The interval in days at which the plan charges (renewal plans).\n - `custom_fields?: { field_type: 'text'; name: string; id?: string; order?: number; placeholder?: string; required?: boolean; }[]`\n An array of custom field objects.\n - `description?: string`\n The description of the plan.\n - `expiration_days?: number`\n The number of days until the membership expires and revokes access (expiration plans). For example, 365 for a one-year access period.\n - `initial_price?: number`\n An additional amount charged upon first purchase. Use only if a one time payment OR you want to charge an additional amount on top of the renewal price. Provided as a number in the specified currency. Eg: 10.43 for $10.43\n - `internal_notes?: string`\n A personal description or notes section for the business.\n - `legacy_payment_method_controls?: boolean`\n Whether this plan uses legacy payment method controls\n - `payment_method_configuration?: { disabled: string[]; enabled: string[]; include_platform_defaults: boolean; }`\n The explicit payment method configuration for the plan. If not provided, the platform or company's defaults will apply.\n - `plan_type?: 'renewal' | 'one_time'`\n The type of plan that can be attached to a product\n - `release_method?: 'buy_now' | 'waitlist'`\n The methods of how a plan can be released.\n - `renewal_price?: number`\n The amount the customer is charged every billing period. Use only if a recurring payment. Provided as a number in the specified currency. Eg: 10.43 for $10.43\n - `stock?: number`\n The number of units available for purchase.\n - `trial_period_days?: number`\n The number of free trial days added before a renewal plan.\n - `unlimited_stock?: boolean`\n When true, the plan has unlimited stock (stock field is ignored). When false, purchases are limited by the stock field.\n - `visibility?: 'visible' | 'hidden' | 'archived' | 'quick_link'`\n Visibility of a resource\n\n### Returns\n\n- `{ id: string; created_at: string; current_plan: { id: string; currency: string; formatted_price: string; }; due_date: string; email_address: string; fetch_invoice_token: string; number: string; status: 'draft' | 'open' | 'paid' | 'past_due' | 'uncollectible' | 'void'; user: { id: string; name: string; username: string; }; }`\n An invoice represents an itemized bill sent by a company to a customer for a specific product and plan, tracking the amount owed, due date, and payment status.\n\n - `id: string`\n - `created_at: string`\n - `current_plan: { id: string; currency: string; formatted_price: string; }`\n - `due_date: string`\n - `email_address: string`\n - `fetch_invoice_token: string`\n - `number: string`\n - `status: 'draft' | 'open' | 'paid' | 'past_due' | 'uncollectible' | 'void'`\n - `user: { id: string; name: string; username: string; }`\n\n### Example\n\n```typescript\nimport Whop from '@whop/sdk';\n\nconst client = new Whop();\n\nconst invoice = await client.invoices.update('inv_xxxxxxxxxxxxxx');\n\nconsole.log(invoice);\n```", + perLanguage: { + http: { + example: + 'curl https://api.whop.com/api/v1/invoices/$ID \\\n -X PATCH \\\n -H "Authorization: Bearer $WHOP_API_KEY"', + }, + python: { + method: 'invoices.update', + example: + 'import os\nfrom whop_sdk import Whop\n\nclient = Whop(\n api_key=os.environ.get("WHOP_API_KEY"), # This is the default and can be omitted\n)\ninvoice = client.invoices.update(\n id="inv_xxxxxxxxxxxxxx",\n)\nprint(invoice.id)', + }, + ruby: { + method: 'invoices.update', + example: + 'require "whop_sdk"\n\nwhop = WhopSDK::Client.new(api_key: "My API Key")\n\ninvoice = whop.invoices.update("inv_xxxxxxxxxxxxxx")\n\nputs(invoice)', + }, + typescript: { + method: 'client.invoices.update', + example: + "import Whop from '@whop/sdk';\n\nconst client = new Whop({\n apiKey: process.env['WHOP_API_KEY'], // This is the default and can be omitted\n});\n\nconst invoice = await client.invoices.update('inv_xxxxxxxxxxxxxx');\n\nconsole.log(invoice.id);", + }, + }, + }, + { + name: 'delete', + endpoint: '/invoices/{id}', + httpMethod: 'delete', + summary: 'Delete invoice', + description: 'Delete a draft invoice.\n\nRequired permissions:\n - `invoice:update`', + stainlessPath: '(resource) invoices > (method) delete', + qualified: 'client.invoices.delete', + params: ['id: string;'], + response: 'boolean', + markdown: + "## delete\n\n`client.invoices.delete(id: string): boolean`\n\n**delete** `/invoices/{id}`\n\nDelete a draft invoice.\n\nRequired permissions:\n - `invoice:update`\n\n### Parameters\n\n- `id: string`\n\n### Returns\n\n- `boolean`\n Represents `true` or `false` values.\n\n### Example\n\n```typescript\nimport Whop from '@whop/sdk';\n\nconst client = new Whop();\n\nconst invoice = await client.invoices.delete('inv_xxxxxxxxxxxxxx');\n\nconsole.log(invoice);\n```", + perLanguage: { + http: { + example: + 'curl https://api.whop.com/api/v1/invoices/$ID \\\n -X DELETE \\\n -H "Authorization: Bearer $WHOP_API_KEY"', + }, + python: { + method: 'invoices.delete', + example: + 'import os\nfrom whop_sdk import Whop\n\nclient = Whop(\n api_key=os.environ.get("WHOP_API_KEY"), # This is the default and can be omitted\n)\ninvoice = client.invoices.delete(\n "inv_xxxxxxxxxxxxxx",\n)\nprint(invoice)', + }, + ruby: { + method: 'invoices.delete', + example: + 'require "whop_sdk"\n\nwhop = WhopSDK::Client.new(api_key: "My API Key")\n\ninvoice = whop.invoices.delete("inv_xxxxxxxxxxxxxx")\n\nputs(invoice)', + }, + typescript: { + method: 'client.invoices.delete', + example: + "import Whop from '@whop/sdk';\n\nconst client = new Whop({\n apiKey: process.env['WHOP_API_KEY'], // This is the default and can be omitted\n});\n\nconst invoice = await client.invoices.delete('inv_xxxxxxxxxxxxxx');\n\nconsole.log(invoice);", + }, + }, + }, { name: 'list', endpoint: '/course_lesson_interactions', diff --git a/packages/mcp-server/src/methods.ts b/packages/mcp-server/src/methods.ts index 3c84176e..0114ae65 100644 --- a/packages/mcp-server/src/methods.ts +++ b/packages/mcp-server/src/methods.ts @@ -46,12 +46,24 @@ export const sdkMethods: SdkMethod[] = [ httpMethod: 'get', httpPath: '/invoices/{id}', }, + { + clientCallName: 'client.invoices.update', + fullyQualifiedName: 'invoices.update', + httpMethod: 'patch', + httpPath: '/invoices/{id}', + }, { clientCallName: 'client.invoices.list', fullyQualifiedName: 'invoices.list', httpMethod: 'get', httpPath: '/invoices', }, + { + clientCallName: 'client.invoices.delete', + fullyQualifiedName: 'invoices.delete', + httpMethod: 'delete', + httpPath: '/invoices/{id}', + }, { clientCallName: 'client.invoices.markPaid', fullyQualifiedName: 'invoices.markPaid', diff --git a/src/client.ts b/src/client.ts index 82ddb2e3..6779e5a1 100644 --- a/src/client.ts +++ b/src/client.ts @@ -235,9 +235,11 @@ import { } from './resources/forums'; import { InvoiceCreateParams, + InvoiceDeleteResponse, InvoiceListParams, InvoiceMarkPaidResponse, InvoiceMarkUncollectibleResponse, + InvoiceUpdateParams, InvoiceVoidResponse, Invoices, TaxIdentifierType, @@ -321,6 +323,8 @@ import { PayoutMethods, } from './resources/payout-methods'; import { + CheckoutFont, + CheckoutShape, PlanCreateParams, PlanDeleteResponse, PlanListParams, @@ -1538,10 +1542,12 @@ export declare namespace Whop { export { Invoices as Invoices, type TaxIdentifierType as TaxIdentifierType, + type InvoiceDeleteResponse as InvoiceDeleteResponse, type InvoiceMarkPaidResponse as InvoiceMarkPaidResponse, type InvoiceMarkUncollectibleResponse as InvoiceMarkUncollectibleResponse, type InvoiceVoidResponse as InvoiceVoidResponse, type InvoiceCreateParams as InvoiceCreateParams, + type InvoiceUpdateParams as InvoiceUpdateParams, type InvoiceListParams as InvoiceListParams, }; @@ -1618,6 +1624,8 @@ export declare namespace Whop { export { Plans as Plans, + type CheckoutFont as CheckoutFont, + type CheckoutShape as CheckoutShape, type PlanListResponse as PlanListResponse, type PlanDeleteResponse as PlanDeleteResponse, type PlanListResponsesCursorPage as PlanListResponsesCursorPage, diff --git a/src/resources/checkout-configurations.ts b/src/resources/checkout-configurations.ts index d97b074a..2e043def 100644 --- a/src/resources/checkout-configurations.ts +++ b/src/resources/checkout-configurations.ts @@ -2,6 +2,7 @@ import { APIResource } from '../core/resource'; import * as PaymentsAPI from './payments'; +import * as PlansAPI from './plans'; import * as Shared from './shared'; import { APIPromise } from '../core/api-promise'; import { CursorPage, type CursorPageParams, PagePromise } from '../core/pagination'; @@ -565,7 +566,7 @@ export declare namespace CheckoutConfigurationCreateParams { /** * The different border-radius styles available for checkout pages. */ - border_style?: 'rounded' | 'pill' | 'rectangular' | null; + border_style?: PlansAPI.CheckoutShape | null; /** * A hex color code for the button color (e.g. #FF5733). @@ -575,7 +576,7 @@ export declare namespace CheckoutConfigurationCreateParams { /** * The different font families available for checkout pages. */ - font_family?: 'system' | 'roboto' | 'open_sans' | null; + font_family?: PlansAPI.CheckoutFont | null; } /** @@ -662,7 +663,7 @@ export declare namespace CheckoutConfigurationCreateParams { /** * The different border-radius styles available for checkout pages. */ - border_style?: 'rounded' | 'pill' | 'rectangular' | null; + border_style?: PlansAPI.CheckoutShape | null; /** * A hex color code for the button color (e.g. #FF5733). @@ -672,7 +673,7 @@ export declare namespace CheckoutConfigurationCreateParams { /** * The different font families available for checkout pages. */ - font_family?: 'system' | 'roboto' | 'open_sans' | null; + font_family?: PlansAPI.CheckoutFont | null; } /** @@ -754,7 +755,7 @@ export declare namespace CheckoutConfigurationCreateParams { /** * The different border-radius styles available for checkout pages. */ - border_style?: 'rounded' | 'pill' | 'rectangular' | null; + border_style?: PlansAPI.CheckoutShape | null; /** * A hex color code for the button color (e.g. #FF5733). @@ -764,7 +765,7 @@ export declare namespace CheckoutConfigurationCreateParams { /** * The different font families available for checkout pages. */ - font_family?: 'system' | 'roboto' | 'open_sans' | null; + font_family?: PlansAPI.CheckoutFont | null; } /** diff --git a/src/resources/index.ts b/src/resources/index.ts index fae5299e..f548b9af 100644 --- a/src/resources/index.ts +++ b/src/resources/index.ts @@ -229,10 +229,12 @@ export { export { Invoices, type TaxIdentifierType, + type InvoiceDeleteResponse, type InvoiceMarkPaidResponse, type InvoiceMarkUncollectibleResponse, type InvoiceVoidResponse, type InvoiceCreateParams, + type InvoiceUpdateParams, type InvoiceListParams, } from './invoices'; export { @@ -315,6 +317,8 @@ export { } from './payout-methods'; export { Plans, + type CheckoutFont, + type CheckoutShape, type PlanListResponse, type PlanDeleteResponse, type PlanCreateParams, diff --git a/src/resources/invoices.ts b/src/resources/invoices.ts index a981b745..04add940 100644 --- a/src/resources/invoices.ts +++ b/src/resources/invoices.ts @@ -42,11 +42,40 @@ export class Invoices extends APIResource { * Required permissions: * * - `invoice:basic:read` + * + * @example + * ```ts + * const invoice = await client.invoices.retrieve( + * 'inv_xxxxxxxxxxxxxx', + * ); + * ``` */ retrieve(id: string, options?: RequestOptions): APIPromise { return this._client.get(path`/invoices/${id}`, options); } + /** + * Update a draft invoice's details. + * + * Required permissions: + * + * - `invoice:update` + * + * @example + * ```ts + * const invoice = await client.invoices.update( + * 'inv_xxxxxxxxxxxxxx', + * ); + * ``` + */ + update( + id: string, + body: InvoiceUpdateParams | null | undefined = {}, + options?: RequestOptions, + ): APIPromise { + return this._client.patch(path`/invoices/${id}`, { body, ...options }); + } + /** * Returns a paginated list of invoices for a company, with optional filtering by * product, status, collection method, and creation date. @@ -54,6 +83,14 @@ export class Invoices extends APIResource { * Required permissions: * * - `invoice:basic:read` + * + * @example + * ```ts + * // Automatically fetches more pages as needed. + * for await (const invoiceListItem of client.invoices.list()) { + * // ... + * } + * ``` */ list( query: InvoiceListParams | null | undefined = {}, @@ -62,12 +99,37 @@ export class Invoices extends APIResource { return this._client.getAPIList('/invoices', CursorPage, { query, ...options }); } + /** + * Delete a draft invoice. + * + * Required permissions: + * + * - `invoice:update` + * + * @example + * ```ts + * const invoice = await client.invoices.delete( + * 'inv_xxxxxxxxxxxxxx', + * ); + * ``` + */ + delete(id: string, options?: RequestOptions): APIPromise { + return this._client.delete(path`/invoices/${id}`, options); + } + /** * Mark an open invoice as paid when payment was collected outside of Whop. * * Required permissions: * * - `invoice:update` + * + * @example + * ```ts + * const response = await client.invoices.markPaid( + * 'inv_xxxxxxxxxxxxxx', + * ); + * ``` */ markPaid(id: string, options?: RequestOptions): APIPromise { return this._client.post(path`/invoices/${id}/mark_paid`, options); @@ -79,6 +141,13 @@ export class Invoices extends APIResource { * Required permissions: * * - `invoice:update` + * + * @example + * ```ts + * const response = await client.invoices.markUncollectible( + * 'inv_xxxxxxxxxxxxxx', + * ); + * ``` */ markUncollectible(id: string, options?: RequestOptions): APIPromise { return this._client.post(path`/invoices/${id}/mark_uncollectible`, options); @@ -91,6 +160,13 @@ export class Invoices extends APIResource { * Required permissions: * * - `invoice:update` + * + * @example + * ```ts + * const response = await client.invoices.void( + * 'inv_xxxxxxxxxxxxxx', + * ); + * ``` */ void(id: string, options?: RequestOptions): APIPromise { return this._client.post(path`/invoices/${id}/void`, options); @@ -213,6 +289,11 @@ export type TaxIdentifierType = | 'sr_fin' | 'xi_vat'; +/** + * Represents `true` or `false` values. + */ +export type InvoiceDeleteResponse = boolean; + /** * Represents `true` or `false` values. */ @@ -899,6 +980,294 @@ export declare namespace InvoiceCreateParams { } } +export interface InvoiceUpdateParams { + /** + * The date and time when the invoice will be automatically finalized and charged. + */ + automatically_finalizes_at?: string | null; + + /** + * Inline billing address to create or update a mailing address for this invoice. + */ + billing_address?: InvoiceUpdateParams.BillingAddress | null; + + /** + * Whether to charge the customer a buyer fee on this invoice. + */ + charge_buyer_fee?: boolean | null; + + /** + * The method of collection for an invoice. + */ + collection_method?: Shared.CollectionMethod | null; + + /** + * The name of the customer. + */ + customer_name?: string | null; + + /** + * The date by which the invoice must be paid. + */ + due_date?: string | null; + + /** + * The email address of the customer. + */ + email_address?: string | null; + + /** + * Line items that break down the invoice total. + */ + line_items?: Array | null; + + /** + * The unique identifier of an existing mailing address to attach. + */ + mailing_address_id?: string | null; + + /** + * The unique identifier of a member to assign as the customer. + */ + member_id?: string | null; + + /** + * The unique identifier of the payment method to charge. + */ + payment_method_id?: string | null; + + /** + * Updated plan attributes. + */ + plan?: InvoiceUpdateParams.Plan | null; +} + +export namespace InvoiceUpdateParams { + /** + * Inline billing address to create or update a mailing address for this invoice. + */ + export interface BillingAddress { + /** + * The city of the address. + */ + city?: string | null; + + /** + * The country of the address. + */ + country?: string | null; + + /** + * The line 1 of the address. + */ + line1?: string | null; + + /** + * The line 2 of the address. + */ + line2?: string | null; + + /** + * The name of the customer. + */ + name?: string | null; + + /** + * The phone number of the customer. + */ + phone?: string | null; + + /** + * The postal code of the address. + */ + postal_code?: string | null; + + /** + * The state of the address. + */ + state?: string | null; + + /** + * The type of tax identifier + */ + tax_id_type?: InvoicesAPI.TaxIdentifierType | null; + + /** + * The value of the tax identifier. + */ + tax_id_value?: string | null; + } + + /** + * A single line item to include on the invoice, with a label, quantity, and unit + * price. + */ + export interface LineItem { + /** + * The label or description for this line item. + */ + label: string; + + /** + * The unit price for this line item. Provided as a number in the specified + * currency. Eg: 10.43 for $10.43 + */ + unit_price: number; + + /** + * The quantity of this line item. Defaults to 1. + */ + quantity?: number | null; + } + + /** + * Updated plan attributes. + */ + export interface Plan { + /** + * The interval in days at which the plan charges (renewal plans). + */ + billing_period?: number | null; + + /** + * An array of custom field objects. + */ + custom_fields?: Array | null; + + /** + * The description of the plan. + */ + description?: string | null; + + /** + * The number of days until the membership expires and revokes access (expiration + * plans). For example, 365 for a one-year access period. + */ + expiration_days?: number | null; + + /** + * An additional amount charged upon first purchase. Use only if a one time payment + * OR you want to charge an additional amount on top of the renewal price. Provided + * as a number in the specified currency. Eg: 10.43 for $10.43 + */ + initial_price?: number | null; + + /** + * A personal description or notes section for the business. + */ + internal_notes?: string | null; + + /** + * Whether this plan uses legacy payment method controls + */ + legacy_payment_method_controls?: boolean | null; + + /** + * The explicit payment method configuration for the plan. If not provided, the + * platform or company's defaults will apply. + */ + payment_method_configuration?: Plan.PaymentMethodConfiguration | null; + + /** + * The type of plan that can be attached to a product + */ + plan_type?: Shared.PlanType | null; + + /** + * The methods of how a plan can be released. + */ + release_method?: Shared.ReleaseMethod | null; + + /** + * The amount the customer is charged every billing period. Use only if a recurring + * payment. Provided as a number in the specified currency. Eg: 10.43 for $10.43 + */ + renewal_price?: number | null; + + /** + * The number of units available for purchase. + */ + stock?: number | null; + + /** + * The number of free trial days added before a renewal plan. + */ + trial_period_days?: number | null; + + /** + * When true, the plan has unlimited stock (stock field is ignored). When false, + * purchases are limited by the stock field. + */ + unlimited_stock?: boolean | null; + + /** + * Visibility of a resource + */ + visibility?: Shared.Visibility | null; + } + + export namespace Plan { + export interface CustomField { + /** + * The type of the custom field. + */ + field_type: 'text'; + + /** + * The name of the custom field. + */ + name: string; + + /** + * The ID of the custom field (if being updated) + */ + id?: string | null; + + /** + * The order of the field. + */ + order?: number | null; + + /** + * The placeholder value of the field. + */ + placeholder?: string | null; + + /** + * Whether or not the field is required. + */ + required?: boolean | null; + } + + /** + * The explicit payment method configuration for the plan. If not provided, the + * platform or company's defaults will apply. + */ + export interface PaymentMethodConfiguration { + /** + * An array of payment method identifiers that are explicitly disabled. Only + * applies if the include_platform_defaults is true. + */ + disabled: Array; + + /** + * An array of payment method identifiers that are explicitly enabled. This means + * these payment methods will be shown on checkout. Example use case is to only + * enable a specific payment method like cashapp, or extending the platform + * defaults with additional methods. + */ + enabled: Array; + + /** + * Whether Whop's platform default payment method enablement settings are included + * in this configuration. The full list of default payment methods can be found in + * the documentation at docs.whop.com/payments. + */ + include_platform_defaults: boolean; + } + } +} + export interface InvoiceListParams extends CursorPageParams { /** * Returns the elements in the list that come before the specified cursor. @@ -960,10 +1329,12 @@ export interface InvoiceListParams extends CursorPageParams { export declare namespace Invoices { export { type TaxIdentifierType as TaxIdentifierType, + type InvoiceDeleteResponse as InvoiceDeleteResponse, type InvoiceMarkPaidResponse as InvoiceMarkPaidResponse, type InvoiceMarkUncollectibleResponse as InvoiceMarkUncollectibleResponse, type InvoiceVoidResponse as InvoiceVoidResponse, type InvoiceCreateParams as InvoiceCreateParams, + type InvoiceUpdateParams as InvoiceUpdateParams, type InvoiceListParams as InvoiceListParams, }; } diff --git a/src/resources/plans.ts b/src/resources/plans.ts index abf24aa3..43749207 100644 --- a/src/resources/plans.ts +++ b/src/resources/plans.ts @@ -1,6 +1,7 @@ // File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details. import { APIResource } from '../core/resource'; +import * as PlansAPI from './plans'; import * as PaymentsAPI from './payments'; import * as Shared from './shared'; import { APIPromise } from '../core/api-promise'; @@ -124,6 +125,16 @@ export class Plans extends APIResource { export type PlanListResponsesCursorPage = CursorPage; +/** + * The different font families available for checkout pages. + */ +export type CheckoutFont = 'system' | 'roboto' | 'open_sans'; + +/** + * The different border-radius styles available for checkout pages. + */ +export type CheckoutShape = 'rounded' | 'pill' | 'rectangular'; + /** * A plan defines pricing and billing terms for a checkout. Plans can optionally * belong to a product, where they represent different pricing options such as @@ -488,7 +499,7 @@ export namespace PlanCreateParams { /** * The different border-radius styles available for checkout pages. */ - border_style?: 'rounded' | 'pill' | 'rectangular' | null; + border_style?: PlansAPI.CheckoutShape | null; /** * A hex color code for the button color (e.g. #FF5733). @@ -498,7 +509,7 @@ export namespace PlanCreateParams { /** * The different font families available for checkout pages. */ - font_family?: 'system' | 'roboto' | 'open_sans' | null; + font_family?: PlansAPI.CheckoutFont | null; } export interface CustomField { @@ -697,7 +708,7 @@ export namespace PlanUpdateParams { /** * The different border-radius styles available for checkout pages. */ - border_style?: 'rounded' | 'pill' | 'rectangular' | null; + border_style?: PlansAPI.CheckoutShape | null; /** * A hex color code for the button color (e.g. #FF5733). @@ -707,7 +718,7 @@ export namespace PlanUpdateParams { /** * The different font families available for checkout pages. */ - font_family?: 'system' | 'roboto' | 'open_sans' | null; + font_family?: PlansAPI.CheckoutFont | null; } export interface CustomField { @@ -844,6 +855,8 @@ export interface PlanListParams extends CursorPageParams { export declare namespace Plans { export { + type CheckoutFont as CheckoutFont, + type CheckoutShape as CheckoutShape, type PlanListResponse as PlanListResponse, type PlanDeleteResponse as PlanDeleteResponse, type PlanListResponsesCursorPage as PlanListResponsesCursorPage, diff --git a/tests/api-resources/invoices.test.ts b/tests/api-resources/invoices.test.ts index a15bd83a..23ec6f81 100644 --- a/tests/api-resources/invoices.test.ts +++ b/tests/api-resources/invoices.test.ts @@ -105,6 +105,89 @@ describe('resource invoices', () => { expect(dataAndResponse.response).toBe(rawResponse); }); + // Mock server tests are disabled + test.skip('update', async () => { + const responsePromise = client.invoices.update('inv_xxxxxxxxxxxxxx'); + const rawResponse = await responsePromise.asResponse(); + expect(rawResponse).toBeInstanceOf(Response); + const response = await responsePromise; + expect(response).not.toBeInstanceOf(Response); + const dataAndResponse = await responsePromise.withResponse(); + expect(dataAndResponse.data).toBe(response); + expect(dataAndResponse.response).toBe(rawResponse); + }); + + // Mock server tests are disabled + test.skip('update: request options and params are passed correctly', async () => { + // ensure the request options are being passed correctly by passing an invalid HTTP method in order to cause an error + await expect( + client.invoices.update( + 'inv_xxxxxxxxxxxxxx', + { + automatically_finalizes_at: '2023-12-01T05:00:00.401Z', + billing_address: { + city: 'city', + country: 'country', + line1: 'line1', + line2: 'line2', + name: 'name', + phone: 'phone', + postal_code: 'postal_code', + state: 'state', + tax_id_type: 'ad_nrt', + tax_id_value: 'tax_id_value', + }, + charge_buyer_fee: true, + collection_method: 'send_invoice', + customer_name: 'customer_name', + due_date: '2023-12-01T05:00:00.401Z', + email_address: 'email_address', + line_items: [ + { + label: 'label', + unit_price: 6.9, + quantity: 6.9, + }, + ], + mailing_address_id: 'ma_xxxxxxxxxxxxxxx', + member_id: 'mber_xxxxxxxxxxxxx', + payment_method_id: 'pmt_xxxxxxxxxxxxxx', + plan: { + billing_period: 42, + custom_fields: [ + { + field_type: 'text', + name: 'name', + id: 'id', + order: 42, + placeholder: 'placeholder', + required: true, + }, + ], + description: 'description', + expiration_days: 42, + initial_price: 6.9, + internal_notes: 'internal_notes', + legacy_payment_method_controls: true, + payment_method_configuration: { + disabled: ['acss_debit'], + enabled: ['acss_debit'], + include_platform_defaults: true, + }, + plan_type: 'renewal', + release_method: 'buy_now', + renewal_price: 6.9, + stock: 42, + trial_period_days: 42, + unlimited_stock: true, + visibility: 'visible', + }, + }, + { path: '/_stainless_unknown_path' }, + ), + ).rejects.toThrow(Whop.NotFoundError); + }); + // Mock server tests are disabled test.skip('list', async () => { const responsePromise = client.invoices.list(); @@ -141,6 +224,18 @@ describe('resource invoices', () => { ).rejects.toThrow(Whop.NotFoundError); }); + // Mock server tests are disabled + test.skip('delete', async () => { + const responsePromise = client.invoices.delete('inv_xxxxxxxxxxxxxx'); + const rawResponse = await responsePromise.asResponse(); + expect(rawResponse).toBeInstanceOf(Response); + const response = await responsePromise; + expect(response).not.toBeInstanceOf(Response); + const dataAndResponse = await responsePromise.withResponse(); + expect(dataAndResponse.data).toBe(response); + expect(dataAndResponse.response).toBe(rawResponse); + }); + // Mock server tests are disabled test.skip('markPaid', async () => { const responsePromise = client.invoices.markPaid('inv_xxxxxxxxxxxxxx'); From 5a0b2862d1c1f90451f4362d85b086d22b25aa6f Mon Sep 17 00:00:00 2001 From: "stainless-app[bot]" <142633134+stainless-app[bot]@users.noreply.github.com> Date: Fri, 10 Apr 2026 01:55:55 +0000 Subject: [PATCH 7/7] release: 0.0.37 --- .release-please-manifest.json | 2 +- CHANGELOG.md | 14 ++++++++++++++ package.json | 2 +- packages/mcp-server/manifest.json | 2 +- packages/mcp-server/package.json | 2 +- packages/mcp-server/src/server.ts | 2 +- src/version.ts | 2 +- 7 files changed, 20 insertions(+), 6 deletions(-) diff --git a/.release-please-manifest.json b/.release-please-manifest.json index d1b9552f..b7d91ce7 100644 --- a/.release-please-manifest.json +++ b/.release-please-manifest.json @@ -1,3 +1,3 @@ { - ".": "0.0.36" + ".": "0.0.37" } diff --git a/CHANGELOG.md b/CHANGELOG.md index e811c6e5..e453989a 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,19 @@ # Changelog +## 0.0.37 (2026-04-10) + +Full Changelog: [v0.0.36...v0.0.37](https://github.com/whopio/whopsdk-typescript/compare/v0.0.36...v0.0.37) + +### Features + +* **api:** api update ([8a21bdb](https://github.com/whopio/whopsdk-typescript/commit/8a21bdbf1781f0648dab879d60525264a14cb1f2)) +* **api:** manual updates ([415a345](https://github.com/whopio/whopsdk-typescript/commit/415a34513f334fb848a16c306d48c5806b8ef80e)) + + +### Chores + +* **internal:** show error causes in MCP servers when running in local mode ([b6e0e4d](https://github.com/whopio/whopsdk-typescript/commit/b6e0e4d1ab23a07baed3f8c738871f29c844836d)) + ## 0.0.36 (2026-04-08) Full Changelog: [v0.0.35...v0.0.36](https://github.com/whopio/whopsdk-typescript/compare/v0.0.35...v0.0.36) diff --git a/package.json b/package.json index 13ec4600..8c2d0116 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@whop/sdk", - "version": "0.0.36", + "version": "0.0.37", "description": "The official TypeScript library for the Whop API", "author": "Whop <>", "types": "dist/index.d.ts", diff --git a/packages/mcp-server/manifest.json b/packages/mcp-server/manifest.json index d4818134..c1fe5e92 100644 --- a/packages/mcp-server/manifest.json +++ b/packages/mcp-server/manifest.json @@ -1,7 +1,7 @@ { "dxt_version": "0.2", "name": "@whop/mcp", - "version": "0.0.36", + "version": "0.0.37", "description": "The official MCP Server for the Whop API", "author": { "name": "Whop" diff --git a/packages/mcp-server/package.json b/packages/mcp-server/package.json index f7280845..16ed5343 100644 --- a/packages/mcp-server/package.json +++ b/packages/mcp-server/package.json @@ -1,6 +1,6 @@ { "name": "@whop/mcp", - "version": "0.0.36", + "version": "0.0.37", "description": "The official MCP Server for the Whop API", "author": "Whop <>", "types": "dist/index.d.ts", diff --git a/packages/mcp-server/src/server.ts b/packages/mcp-server/src/server.ts index 39c2cd29..4ac4a582 100644 --- a/packages/mcp-server/src/server.ts +++ b/packages/mcp-server/src/server.ts @@ -28,7 +28,7 @@ export const newMcpServer = async ({ new McpServer( { name: 'whop_sdk_api', - version: '0.0.36', + version: '0.0.37', }, { instructions: await getInstructions({ stainlessApiKey, customInstructionsPath }), diff --git a/src/version.ts b/src/version.ts index 435aa19e..66fe2303 100644 --- a/src/version.ts +++ b/src/version.ts @@ -1 +1 @@ -export const VERSION = '0.0.36'; // x-release-please-version +export const VERSION = '0.0.37'; // x-release-please-version