paddle-python-sdk
Paddle Billing is the developer-first merchant of record, designed for modern SaaS, AI, mobile app, and digital product businesses. We take care of payments, tax, subscriptions, and metrics with one unified API that does it all.
This is a Python SDK that you can use to integrate Paddle Billing with applications written in Python.
For working with Paddle in your frontend, use Paddle.js. You can open checkouts, securely collect payment information, build pricing pages, and integrate with Paddle Retain.
Important: This package works with Paddle Billing. It does not support Paddle Classic. To work with Paddle Classic, see: Paddle Classic dev docs
Table of contents
Requirements
Python>=3.11 (for native type hinting, StrEnum, trailing commas, f-strings)
Project dependencies (automatically installed by pip):
- requests>=2.31
- urllib3>=2.1.0
Install
Because paddle-python-sdk is available on PyPi, installation is as simple as running the following pip command:
pip install paddle-python-sdk
Usage
To authenticate, you'll need an API key. You can create and manage API keys in Paddle > Developer tools > Authentication.
Pass your API key while initializing a new Paddle client:
from paddle_billing import Client
paddle = Client('PADDLE_API_SECRET_KEY')
You can pass your Paddle API secret key into the SDK from an environment variable:
from os import getenv
from paddle_billing import Client
paddle = Client(getenv('PADDLE_API_SECRET_KEY'))
You can also pass an environment to work with Paddle's sandbox:
from paddle_billing import Client, Environment, Options
paddle = Client('PADDLE_API_SECRET_KEY', options=Options(Environment.SANDBOX))
Keep in mind that API keys are separate for your sandbox and live accounts, so you'll need to generate keys for each environment.
Examples
There are examples included in the examples folder. To prevent leaking errors we recommend encapsulating Paddle operations inside Try/Except blocks. For brevity, most of the examples below do not do this.
List entities
You can list supported entities with the list() method in the resource. It returns an iterator to help when working with multiple pages.
from paddle_billing import Client
paddle = Client('PADDLE_API_SECRET_KEY')
products = paddle.products.list()
# list() returns an iterable, so pagination is automatically handled
for product in products:
print(f"Product's id: {product.id}")
Get an entity
You can get an entity with the get() method in the resource. It accepts the id of the entity to get. The entity is returned.
from paddle_billing import Client
paddle = Client('PADDLE_API_SECRET_KEY')
product = paddle.products.get('PRODUCT_ID')
Create an entity
You can create a supported entity with the create() method in the resource. It accepts the resource's corresponding CreateOperation e.g. CreateProduct. The created entity is returned.
from paddle_billing import Client
from paddle_billing.Entities.Shared.TaxCategory import TaxCategory
from paddle_billing.Resources.Products.Operations import CreateProduct
paddle = Client('PADDLE_API_SECRET_KEY')
created_product = paddle.products.create(CreateProduct(
name = 'My Product',
tax_category = TaxCategory.Standard,
))
Update an entity
You can update a supported entity with the update() method in the resource. It accepts the id of the entity to update and the corresponding UpdateOperation e.g. UpdateProduct. The updated entity is returned.
from paddle_billing import Client
from paddle_billing.Resources.Products.Operations import UpdateProduct
paddle = Client('PADDLE_API_SECRET_KEY')
# Update the name of the product
updated_product = paddle.products.update('PRODUCT_ID', UpdateProduct(
name = 'My Improved Product'
))
Where operations require more than one id, the update() method accepts multiple arguments. For example, to update an address for a customer, pass the customerId and the addressId:
updated_address = paddle.addresses.update(
'CUSTOMER_ID',
'ADDRESS_ID',
operation_goes_here,
)
Delete an entity
You can delete an entity with the delete() method in the resource. It accepts the id of the entity to delete. The deleted entity is returned.
from paddle_billing import Client
paddle = Client('PADDLE_API_SECRET_KEY')
deleted_product = paddle.products.delete('PRODUCT_ID')
Error Handling
If a request fails, Paddle raises an ApiError that contains the same information as errors returned by the API. You can use the code attribute to search an error in the error reference and to handle the error in your app. Validation errors also return an array of errors that tell you which fields failed validation. The retry_after property will be set for too_many_requests errors.
This example shows how to handle an error with the code conflict:
from paddle_billing.Exceptions.ApiError import ApiError
try:
# Call functions from the SDK
except ApiError as error:
# error.error_code will always follow the error code defined in our documentation
if error.error_code == 'conflict':
# Handle Conflict error
Resources
Webhook signature verification
The SDK includes a helper class to verify webhook signatures sent by Notifications from Paddle.
from paddle_billing.Notifications import Secret, Verifier
integrity_check = Verifier().verify(request, Secret('WEBHOOK_SECRET_KEY'))
The verify() method currently accepts any request object matching the paddle_billing.Notifications.Requests.Request protocol, and supports popular frameworks such as Flask and Django.
Time drift max variance can be adjusted by passing seconds to Verifier() (default: 5 seconds):
integrity_check = Verifier(seconds).verify(request, Secret('WEBHOOK_SECRET_KEY'))
Learn more
Release files for paddle-python-sdk 1.15.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| paddle_python_sdk-1.15.0.tar.gz | 187.4 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| paddle_python_sdk-1.15.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 702.2 kB
Release files / paddle_python_sdk-1.15.0.tar.gz
| Download URL | paddle_python_sdk-1.15.0.tar.gz |
|---|---|
| Size | 187.4 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
2349490dd21754fab0f96b605109a38f208a1778be07121e881eacef02c87c79
|
|
BLAKE2b-256 checksum How to use checksums |
00f2b924002397c449cdcd1d0e39bbbb3791f7aed55a9df7802c3515c3d39029
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.12.9
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Jul 28, 2026.
Transparency logRelease files / paddle_python_sdk-1.15.0-py3-none-any.whl
| Download URL | paddle_python_sdk-1.15.0-py3-none-any.whl |
|---|---|
| Size | 514.8 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
3250f3bcb6a4106c03512958533d25cca6a2c572e33004013dd6131b10329f06
|
|
BLAKE2b-256 checksum How to use checksums |
a4c82d8c93128a650d7e0a3fa6e410aaf681668bc91f2e172ccb7714fb40a66c
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.12.9
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Jul 28, 2026.
Transparency log