Skip to main content

Cru World Wine

Cru Trading API for Python

CI PyPI Python versions License

The Python SDK for the Cru Trading API, Cru World Wine's partner REST API. Read Cru's live bid and offer books for every wine, manage your own bids and offers, see your portfolio, purchases and sales, and trade: buy an offer or sell into a bid. It has a synchronous client, Cru, and an asyncio one, AsyncCru, with typed models for every answer, automatic retries and OAuth token refresh, and nothing to install beyond httpx.

Installation

pip install cruworldwine

Python 3.9 or later.

Connecting

With a partner credential, whose writes run at once:

from cruworldwine import Cru

with Cru(client_key='cru_live_...', client_secret='...', market='uk') as cru:
    client = cru.ping().client
    print(client.organisation, client.market, client.currency, client.scopes)

Or with asyncio, here as a connected app acting for a customer, whose writes wait for the customer to confirm them:

import asyncio

from cruworldwine import AsyncCru


async def main() -> None:
    async with AsyncCru(access_token='...', refresh_token='...', oauth_client_id='...') as cru:
        page = await cru.bids.list(status=['live'])
        async for bid in page:
            print(bid.code, bid.price, bid.quantity)


asyncio.run(main())

Cru() alone reads CRU_CLIENT_KEY and CRU_CLIENT_SECRET (or CRU_ACCESS_TOKEN), CRU_MARKET and CRU_ENVIRONMENT from the environment. Authentication covers both ways in.

Sandbox

To build and test where no real money or wine changes hands, use the sandbox, with credentials issued for it: environment='sandbox' (or CRU_ENVIRONMENT=sandbox) calls https://{market}.crusandbox.com/api/v1 in place of https://{market}.cruworldwine.com/api/v1.

cru = Cru(client_key='...', client_secret='...', environment='sandbox', market='hk')
print(cru.market_info.currency)  # HKD

MARKETS and lookup_market() list each market's name, currency, symbol and URLs; Configuration has the details.

Typed models

Every endpoint is a typed method, and every answer a typed model with an attribute per API field and the API's descriptions as docstrings, so an editor completes and checks them. Fields this version does not know are kept in .raw.

for wine in cru.portfolio.list(is_listed=True).auto_paging_iter():  # PortfolioWine
    for line in wine.portfolio:  # PortfolioLine
        print(wine.wine_name, line.quantity, line.pricing.listing_price, line.pricing.net_proceeds)

Import any model from cruworldwine.models.

Documentation

  • Authentication: partner credentials, connected apps and OAuth refresh, the environment.
  • Configuration: constructor and per-call options, the sandbox and the markets, with_options(), timeouts, retries, logging, app_info.
  • Async: AsyncCru, async paging and concurrency.
  • Pagination: pages, and walking every item.
  • Writes and confirmations: idempotency references, staged writes and confirming them.
  • Errors: the error classes, what they hold, and request ids.
  • Compatibility: tolerant models, values that may grow, and the versioning policy.
  • Architecture: how the SDK is built, the life of a request, and the code generation.
  • The API itself: developers.cruworldwine.com.

Examples

examples/ has scripts to run with credentials in the environment: portfolio.py prints your portfolio, market.py the bids and offers on a wine, place_bid.py places a bid and, as a connected app, confirms it, and async_market.py asks for several wines at once with AsyncCru.

Versioning and support

The SDK follows semantic versioning. While it is 0.x, a minor release may change the public API, and every such change is in the changelog; patch releases never do. It supports Python 3.9 to 3.15 on Linux, macOS and Windows, and only the latest minor release gets fixes. Compatibility has the whole policy.

Every method

Generated from the spec; each method's docstring has the full description. AsyncCru has the same methods: await them, and a Page is an AsyncPage.

Method Endpoint Returns
cru.ping() GET /ping Ping
cru.portfolio.list(...) GET /portfolio Page[PortfolioWine]
cru.offers.list(...) GET /offers Page[PortfolioWine]
cru.offers.create(...) POST /offers Write[OfferResult]
cru.offers.get(code) GET /offers/{code} PortfolioWine
cru.offers.update(code, ...) PATCH /offers/{code} Write[OfferResult]
cru.offers.remove(code, ...) DELETE /offers/{code} Write[OfferRemoveResult]
cru.bids.list(...) GET /bids Page[OwnBid]
cru.bids.place(...) POST /bids Write[BidResult]
cru.bids.get(code) GET /bids/{code} OwnBid
cru.bids.update(code, ...) PATCH /bids/{code} Write[BidResult]
cru.bids.cancel(code, ...) DELETE /bids/{code} Write[BidResult]
cru.bids.renew(code, ...) POST /bids/{code}/renew Write[BidResult]
cru.market.list(...) GET /market Page[MarketWine]
cru.market.get_wine(lwin18, ...) GET /market/wines/{lwin18} MarketWine
cru.market.list_bids(...) GET /market/bids Page[MarketWine]
cru.market.get_bid(code) GET /market/bids/{code} MarketBidDetail
cru.market.get_wine_bids(lwin18, ...) GET /market/wines/{lwin18}/bids MarketWine
cru.market.list_offers(...) GET /market/offers Page[MarketWine]
cru.market.get_offer(code) GET /market/offers/{code} MarketOfferDetail
cru.market.get_wine_offers(lwin18, ...) GET /market/wines/{lwin18}/offers MarketWine
cru.market.buy_offer(code, ...) POST /market/offers/{code}/buy Write[BuyResult]
cru.market.sell_to_bid(code, ...) POST /market/bids/{code}/sell Write[SellResult]
cru.wines.search(...) GET /wines Page[Wine]
cru.wines.get(lwin18) GET /wines/{lwin18} WineDetail
cru.trades.list_purchases(...) GET /trades/purchases Page[Purchase]
cru.trades.list_sales(...) GET /trades/sales Page[Sale]
cru.warehouses.list() GET /warehouses list[Warehouse]
cru.warehouses.get(code) GET /warehouses/{code} Warehouse
cru.inbond_warehouses.list() GET /warehouses/inbond list[InbondWarehouse]
cru.inbond_warehouses.suggest(...) POST /warehouses/inbond Write[InbondWarehouseResult]
cru.inbond_warehouses.get(id) GET /warehouses/inbond/{id} InbondWarehouse
cru.inbond_addresses.list() GET /addresses/inbond list[InbondAddress]
cru.inbond_addresses.add(...) POST /addresses/inbond Write[InbondAddressResult]
cru.inbond_addresses.remove(id, ...) DELETE /addresses/inbond/{id} Write[InbondAddressResult]
cru.confirmations.get(code) GET /confirmations/{code} Confirmation
cru.confirmations.confirm(code) POST /confirmations/{code} Write[Any]
cru.confirmations.cancel(code) DELETE /confirmations/{code} None
cru.photos.get(id) GET /photos/{id} bytes

Contributing, security and licence

CONTRIBUTING.md explains the layout, the Makefile and how releases are cut. Report a vulnerability privately, as SECURITY.md explains, never in a public issue. Apache License 2.0; see LICENSE.

Metadata

Release files for cruworldwine 0.2.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for cruworldwine 0.2.0
File Size Uploaded Provenance Actions
cruworldwine-0.2.0.tar.gz 97.5 kB With provenance Details for cruworldwine-0.2.0.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for cruworldwine 0.2.0
File Interpreter ABI Platform Actions
cruworldwine-0.2.0-py3-none-any.whl Python 3 none any Details for cruworldwine-0.2.0-py3-none-any.whl

Total release size: 186.9 kB

Release files / cruworldwine-0.2.0.tar.gz

Download URL cruworldwine-0.2.0.tar.gz
Size 97.5 kB
Tags Source
SHA-256 checksum
How to use checksums
290a687a0461d2208d74a9ef19f2662f005561b17fb1dc8b61c96a70d7e2dbc8
BLAKE2b-256 checksum
How to use checksums
27f6b82e503a10cb77fb8bc72790069a383e9e0cbfbb87c4f52c4ca4c659ddb9
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

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 Oct 26, 2026.

Transparency log

Release files / cruworldwine-0.2.0-py3-none-any.whl

Download URL cruworldwine-0.2.0-py3-none-any.whl
Size 89.4 kB
Tags Python 3
SHA-256 checksum
How to use checksums
8622e8c28ae4a926ba53db3224bce8fa363d31591466aaa2793964448f76bde5
BLAKE2b-256 checksum
How to use checksums
208b1e15d1d21bc219ed3ce0ecab5fcb6d580be46a0fcaad9415f110e9ca46a5
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

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 Oct 26, 2026.

Transparency log

Security for cruworldwine 0.2.0

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.

Full provenance

Both files in this release have been uploaded with provenance metadata.

Select from 2 files

Attestation for cruworldwine-0.2.0.tar.gz

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 Oct 26, 2026.

Transparency log

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.2.0 This release

2 release files Full provenance

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page