Skip to main content

Python SDK for Shopify Partners API - Comprehensive GraphQL client with type safety

Project description

Shopify Partners SDK

PyPI version Python Support License: MIT Code style: black

Modern Python SDK for Shopify Partners API - Comprehensive GraphQL client with type safety, automatic pagination, and dual query approaches (raw GraphQL + dynamic FieldSelector). Built for developers who want powerful functionality without complex abstractions.

🚀 Key Features

🎯 Dual Query Approaches

  • Raw GraphQL - Execute queries directly with full control
  • Dynamic FieldSelector - Build queries programmatically with type safety

🛡️ Production-Ready

  • Type Safety - Full type hints throughout the codebase
  • Automatic Pagination - Built-in cursor-based pagination support
  • Intelligent Rate Limiting - Exponential backoff with retry logic
  • Comprehensive Error Handling - Detailed GraphQL and HTTP error messages

🚀 Developer Experience

  • Zero Complex Abstractions - Direct GraphQL access with minimal overhead
  • Synchronous API - Simple, intuitive Python interface
  • Extensible Architecture - Easy to extend with custom field selections
  • Rich Documentation - Comprehensive examples and API reference

📦 Installation

Using pip

pip install shopify-partners-sdk

Using Poetry

poetry add shopify-partners-sdk

Development Installation

# Clone the repository
git clone https://github.com/amitray007/shopify-partners-sdk.git
cd shopify-partners-sdk

# Install with Poetry
poetry install

# Or with pip in development mode
pip install -e .

⚡ Quick Start

1. Get Your Credentials

Get your credentials from the Shopify Partners Dashboard:

  1. SettingsAPI credentials
  2. Create or select an API credential
  3. Copy your Organization ID and Access Token (starts with prtapi_)

2. Choose Your Approach

The SDK provides two ways to interact with the Shopify Partners API:

🎯 Option 1: FieldSelector (Recommended)

from shopify_partners_sdk import ShopifyPartnersClient, FieldSelector

# Initialize the client
client = ShopifyPartnersClient(
    organization_id="your-org-id",
    access_token="prtapi_your-access-token",
    api_version="2025-04"
)

# Build and execute query with FieldSelector
fields = FieldSelector().add_fields('id', 'title', 'handle')
result = client.query('app', fields, id='your-app-id')
print(f"App: {result['app']['title']}")

client.close()

🔧 Option 2: Raw GraphQL

from shopify_partners_sdk import ShopifyPartnersClient

# Initialize the client
client = ShopifyPartnersClient(
    organization_id="your-org-id",
    access_token="prtapi_your-access-token",
    api_version="2025-04"
)

# Execute raw GraphQL
query = """
query GetApp($id: ID!) {
  app(id: $id) {
    id
    title
    handle
  }
}
"""
response = client.execute_raw(query, {"id": "your-app-id"})
result = response["data"]
print(f"App: {result['app']['title']}")

client.close()

3. Environment Variables

You can also configure the client using environment variables:

export SHOPIFY_PARTNERS_ORGANIZATION_ID="your-org-id"
export SHOPIFY_PARTNERS_ACCESS_TOKEN="prtapi_your-access-token"
export SHOPIFY_PARTNERS_API_VERSION="2025-04"
from shopify_partners_sdk import ShopifyPartnersClient

# Client will automatically use environment variables
client = ShopifyPartnersClient()

📚 Usage Examples

FieldSelector Approach (Recommended)

from shopify_partners_sdk import FieldSelector, CommonFields

# Simple query
fields = FieldSelector().add_fields('id', 'title', 'handle', 'apiKey')
result = client.query('app', fields, id='app-id')

# Query with nested fields
app_fields = (FieldSelector()
    .add_fields('id', 'title', 'handle')
    .add_nested_field('shop', FieldSelector().add_fields('name', 'myshopifyDomain')))
result = client.query('app', app_fields, id='app-id')

# Paginated connection query
app_fields = CommonFields.basic_app()  # Predefined common fields
result = client.connection_query('apps', app_fields, first=25)

# Complex nested query with money fields
transaction_fields = (FieldSelector()
    .add_fields('id', 'createdAt', 'type')
    .add_money_field('netAmount')  # Automatically adds amount and currencyCode
    .add_nested_field('app', CommonFields.basic_app())
    .add_nested_field('shop', CommonFields.basic_shop()))

result = client.connection_query('transactions', transaction_fields, first=50)

# Complex query with nested connections
event_fields = FieldSelector().add_field('type')
app_fields = (FieldSelector()
    .add_field('name')
    .add_connection_field('events', event_fields, first=10))  # Connection with args
result = client.query('app', app_fields, id='app-id')

Raw GraphQL Approach

# Get a single app
query = """
query GetApp($id: ID!) {
  app(id: $id) {
    id
    title
    handle
    apiKey
  }
}
"""
response = client.execute_raw(query, {"id": "app-id"})
app = response["data"]["app"]

# Get API versions
query = """
query GetApiVersions {
  publicApiVersions {
    handle
    displayName
    supported
  }
}
"""
response = client.execute_raw(query)
versions = response["data"]["publicApiVersions"]

# Get paginated apps
query = """
query GetApps($first: Int!, $after: String) {
  apps(first: $first, after: $after) {
    edges {
      cursor
      node {
        id
        title
        handle
      }
    }
    pageInfo {
      hasNextPage
      hasPreviousPage
    }
  }
}
"""
response = client.execute_raw(query, {"first": 25})
apps = response["data"]["apps"]

Mutations

FieldSelector Mutations (Recommended)

# Create an app credit with FieldSelector
result_fields = (FieldSelector()
    .add_nested_field('appCredit', FieldSelector()
        .add_fields('id', 'description')
        .add_money_field('amount'))
    .add_nested_field('userErrors', FieldSelector()
        .add_fields('field', 'message')))

input_data = {
    "appId": "your-app-id",
    "amount": {"amount": "10.00", "currencyCode": "USD"},
    "description": "Refund for billing issue"
}

result = client.mutation('appCreditCreate', result_fields, input=input_data)

if result.get("userErrors"):
    print("Errors:", result["userErrors"])
else:
    print("Credit created:", result["appCredit"])

Raw GraphQL Mutations

# Create an app credit
mutation = """
mutation CreateAppCredit($input: AppCreditCreateInput!) {
  appCreditCreate(input: $input) {
    appCredit {
      id
      description
      amount {
        amount
        currencyCode
      }
    }
    userErrors {
      field
      message
    }
  }
}
"""

input_data = {
    "appId": "your-app-id",
    "amount": {"amount": "10.00", "currencyCode": "USD"},
    "description": "Refund for billing issue"
}

response = client.execute_raw(mutation, {"input": input_data})
result = response["data"]

🏗️ Advanced Usage

Custom HTTP Client

import requests
from shopify_partners_sdk import ShopifyPartnersClient

# Custom HTTP client with specific settings
session = requests.Session()
session.timeout = 60.0

client = ShopifyPartnersClient(
    organization_id="your-org-id",
    access_token="your-token",
    http_client=session
)

Error Handling

from shopify_partners_sdk.exceptions import (
    AuthenticationError,
    RateLimitError,
    GraphQLError
)

try:
    # FieldSelector approach
    fields = FieldSelector().add_fields('id', 'title')
    result = client.query('app', fields, id='invalid-id')
except AuthenticationError:
    print("Invalid credentials")
except RateLimitError as e:
    print(f"Rate limited. Retry after: {e.retry_after} seconds")
except GraphQLError as e:
    print(f"GraphQL error: {e.message}")

try:
    # Raw GraphQL approach
    query = """
    query GetApp($id: ID!) {
      app(id: $id) { id title }
    }
    """
    response = client.execute_raw(query, {"id": "invalid-id"})
    if response.get("errors"):
        print("GraphQL errors:", response["errors"])
    else:
        result = response["data"]
except AuthenticationError:
    print("Invalid credentials")
except RateLimitError as e:
    print(f"Rate limited. Retry after: {e.retry_after} seconds")

Configuration

from shopify_partners_sdk.config import ShopifyPartnersSDKSettings

# Custom configuration
settings = ShopifyPartnersSDKSettings(
    organization_id="your-org-id",
    access_token="your-token",
    api_version="2025-04",
    base_url="https://partners.shopify.com",
    timeout_seconds=30.0,
    max_retries=3,
    log_level="INFO"
)

client = ShopifyPartnersClient.from_settings(settings)

🔍 Available Types and Fields

Core Types

  • App: id, name, apiKey, events
  • Shop: id, name, myshopifyDomain, avatarUrl
  • Organization: id, name, avatarUrl
  • Transaction: id, createdAt (interface)
  • Money: amount, currencyCode
  • AppEvent: type, occurredAt, app, shop (interface)

Billing Types

  • AppCharge: id, amount, name, test (interface)
  • AppCredit: id, amount, name, test
  • AppSubscription: id, amount, name, test, billingOn
  • AppPurchaseOneTime: id, amount, name, test

Enums

  • Currency: USD, EUR, GBP, CAD, AUD, etc.
  • AppEventTypes: RELATIONSHIP_INSTALLED, CREDIT_APPLIED, SUBSCRIPTION_CHARGE_ACCEPTED, etc.
  • TransactionType: APP_ONE_TIME_SALE, APP_SUBSCRIPTION_SALE, SERVICE_SALE, etc.
  • AppPricingInterval: EVERY_30_DAYS, ANNUAL

🛠️ Development

Setup Development Environment

# Clone the repository
git clone https://github.com/amitray007/shopify-partners-sdk.git
cd shopify-partners-sdk

# Install Poetry (if not already installed)
curl -sSL https://install.python-poetry.org | python3 -

# Install dependencies
poetry install

# Install pre-commit hooks
poetry run pre-commit install

🤝 Contributing

Contributions are welcome! Please read our Contributing Guide for details on our code of conduct and the process for submitting pull requests.

Development Workflow

  1. Fork the repository
  2. Create a feature branch (git checkout -b feature/amazing-feature)
  3. Make your changes
  4. Add tests for your changes
  5. Ensure all tests pass (poetry run pytest)
  6. Commit your changes (git commit -m 'Add amazing feature')
  7. Push to the branch (git push origin feature/amazing-feature)
  8. Open a Pull Request

📄 License

This project is licensed under the MIT License - see the LICENSE file for details.

🔗 Links

📋 Changelog

See CHANGELOG.md for a list of changes and version history.

💬 Community & Support

🙏 Acknowledgments

  • Built with Requests for reliable HTTP client functionality
  • Uses Pydantic for data validation and settings management
  • Inspired by the official Shopify GraphQL APIs and developer feedback

Made with ❤️ for the Shopify developer community

⭐ Star this repo🐛 Report Bug💡 Request Feature

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

shopify_partners_sdk-0.1.1.tar.gz (42.6 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

shopify_partners_sdk-0.1.1-py3-none-any.whl (56.5 kB view details)

Uploaded Python 3

File details

Details for the file shopify_partners_sdk-0.1.1.tar.gz.

File metadata

  • Download URL: shopify_partners_sdk-0.1.1.tar.gz
  • Upload date:
  • Size: 42.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for shopify_partners_sdk-0.1.1.tar.gz
Algorithm Hash digest
SHA256 3fdd910afe758887c1e1d0db42ba7cf38ea5039413dc2ff7571b57510ed0a1aa
MD5 7bcd25c5e729abed96e7847c30dee28f
BLAKE2b-256 d44f0a86121d25b37ddfb60ac85c0b04cbe4439e017171829c4e61c735dcd77b

See more details on using hashes here.

Provenance

The following attestation bundles were made for shopify_partners_sdk-0.1.1.tar.gz:

Publisher: release.yml on amitray007/shopify-partners-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file shopify_partners_sdk-0.1.1-py3-none-any.whl.

File metadata

File hashes

Hashes for shopify_partners_sdk-0.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 c7f479a0b5592f87d91ec09313daac1a987c47b69fe301fca4645d85c3a8ec31
MD5 dd00ffcb7736228fd7e3255a88ef8d51
BLAKE2b-256 71b0460a977838d6d30a907c219c7983c68904e7770162e484441c2b79bcafb2

See more details on using hashes here.

Provenance

The following attestation bundles were made for shopify_partners_sdk-0.1.1-py3-none-any.whl:

Publisher: release.yml on amitray007/shopify-partners-sdk

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page