Skip to main content

Paravane

Paravane Python SDK

The official Python SDK for accessing Paravane APIs.

The first supported product is smtpRS, Paravane's email validation and email risk scoring API. smtpRS validates email addresses and evaluates domain, mail, authentication, disposable-email, and related risk signals for onboarding, trust, fraud-prevention, review, and operational workflows.

This SDK provides a stable client entry point, request serialization, typed response helpers, structured errors, examples, tests, and packaging conventions that can grow as Paravane adds additional product APIs.

PyPI Python

Documentation · Installation · Quickstart · Examples · Development

Contents

Documentation

This README documents the Python SDK. The hosted documentation is the canonical reference for the smtpRS HTTP API, response contract, analysis profiles, and limits.

Installation

Install the latest release from PyPI:

python -m pip install --upgrade paravane

To install the current development version directly from GitHub:

python -m pip install "git+https://github.com/paravaneai/paravane-python.git"

For local development:

git clone git@github.com:paravaneai/paravane-python.git
cd paravane-python
python -m pip install -e ".[dev]"

Requirements

Python 3.10 or newer.

Runtime dependency:

  • requests>=2.33.0

Development dependencies are installed with:

python -m pip install -e ".[dev]"

Quickstart

Create an API key from the Paravane API keys page, copy it when it is shown, and store it in your server-side environment. The production client already defaults to https://api.paravane.io; do not append /v1 to the base URL.

Set your API key:

export PARAVANE_API_KEY="pvn_live_..."

On Windows PowerShell:

$env:PARAVANE_API_KEY = "pvn_live_..."

Validate and assess an email address with smtpRS:

from paravane import ParavaneClient

client = ParavaneClient()

result = client.smtprs.analyze("alice@example.com")

print(result.decision)
print(result.overall_risk)
print(result.credits_charged)

The SDK method is named analyze(...) for Python readability. The HTTP API endpoint remains:

POST /v1/analyse

Usage

Create a client with an API key:

from paravane import ParavaneClient

client = ParavaneClient(api_key="pvn_live_...")

Or use PARAVANE_API_KEY:

from paravane import ParavaneClient

client = ParavaneClient()

Run an email validation and risk analysis:

result = client.smtprs.analyze("person@example.com")

if result.decision == "allow":
    print("Continue")
else:
    print("Review or block")

Inspect the normalized response:

print(result.email)
print(result.decision)
print(result.overall_risk)
print(result.analysis_profile)
print(result.credit_cost)
print(result.usage)

Access the original API response:

raw = result.to_dict()
print(raw)

smtpRS

smtpRS is Paravane's email validation and email risk scoring API. It combines directly observable email and domain validation signals with Paravane's proprietary machine-learning model for risk analysis.

The API returns a structured result containing a risk score, decision, supporting reasons, analysis-profile context, and available domain evidence. Applications should use these fields together rather than interpreting the score as a standalone probability.

smtpRS is available through:

client.smtprs

Analysis profiles

smtpRS provides named profiles so applications can choose the appropriate balance of coverage, latency, and credit usage without configuring individual checks.

Profile Credits Availability Intended use
quick 1 All plans Lightweight screening; this is the default.
standard 3 Basic and above Broader passive analysis.
adaptive 5 Pro and above Adds checks when the initial result needs more context.
deep 5 Pro and above Comprehensive analysis without catch-all probing.
catch_all 20 Enterprise or entitled accounts Deep analysis with catch-all probing.

Use the default quick profile:

result = client.smtprs.analyze("person@example.com")

Or request another profile available to your account:

result = client.smtprs.analyze(
    "person@example.com",
    profile="standard",
)

Profile availability is enforced by the API. Requesting a profile that is not included with the current plan raises PermissionDeniedError.

Legacy mode flags

The older disposable_only, strict_disposable, guess, and run_catch_all arguments remain available for compatibility. New integrations should use profile instead. Do not combine profile with an enabled legacy mode flag.

For example, replace:

result = client.smtprs.analyze(
    "person@example.com",
    strict_disposable=True,
)

with:

result = client.smtprs.analyze(
    "person@example.com",
    profile="deep",
)

Low-latency posture

Use the fast flag when your workflow favors lower latency:

result = client.smtprs.analyze(
    "person@example.com",
    fast=True,
)

Company Validity Beta

Paid smtpRS callers can explicitly request the optional Company Validity Beta:

result = client.smtprs.analyze(
    "person@example.com",
    profile="standard",
    company_validity_beta=True,
)

beta = result.company_validity_beta
if beta is not None:
    print(beta.status)  # "beta"
    print(beta.requested)  # True
    print(beta.enabled)  # True when the feature was active for this request
    print(beta.notes)

signal = result.domain_signal
if signal is not None:
    print(signal.domain_status)
    print(signal.mail_status)
    print(signal.company_valid)

The option is omitted by default, so existing calls retain their current behavior. It is available only to paid smtpRS plans and provides additive company-domain context rather than an allowlist. It currently adds no credits beyond the selected profile. Free-plan requests that explicitly enable it receive PermissionDeniedError. Because the response contract is beta, applications can use result.to_dict() to retain access to newly added fields.

Configuration

from paravane import ParavaneClient

client = ParavaneClient(
    api_key="pvn_live_...",
    base_url="https://api.paravane.io",
    timeout=20.0,
    max_network_retries=1,
)

Environment variables:

Name Purpose Default
PARAVANE_API_KEY API key used for requests. None
PARAVANE_BASE_URL API base URL. https://api.paravane.io

Most applications should leave PARAVANE_BASE_URL unset. If an approved alternate endpoint is required, provide only its scheme and host; the SDK adds /v1/analyse itself.

Per-request options

You can set a timeout for one request:

result = client.smtprs.analyze(
    "person@example.com",
    timeout=5.0,
)

You can pass an idempotency key:

result = client.smtprs.analyze(
    "person@example.com",
    idempotency_key="signup-check-123",
)

You can pass future or preview query parameters without waiting for a new SDK release:

result = client.smtprs.analyze(
    "person@example.com",
    extra_params={"preview_flag": "enabled"},
)

Custom HTTP sessions

The SDK uses requests by default. If your environment needs custom connection pooling, proxies, certificates, or adapters, pass a configured requests.Session:

import requests
from paravane import ParavaneClient

session = requests.Session()
session.proxies.update(
    {
        "https": "https://proxy.example.com:8443",
    }
)

client = ParavaneClient(
    api_key="pvn_live_...",
    session=session,
)

Retries

By default, the SDK does not retry network calls:

client = ParavaneClient(max_network_retries=0)

Enable limited retries for transient network failures, 429 rate limits, and 5xx API responses:

client = ParavaneClient(max_network_retries=2)

Billable POST requests are retried only when you supply an idempotency key. Without one, analyze makes one attempt even when max_network_retries is greater than zero:

result = client.smtprs.analyze(
    "person@example.com",
    idempotency_key="customer-signup-456",
)

Idempotency

The SDK accepts an idempotency_key and sends it as:

Idempotency-Key: your-key

Use stable keys for requests that your application may retry after timeouts or transient failures.

Errors

Unsuccessful requests raise structured exceptions from paravane.errors.

from paravane import (
    AuthenticationError,
    ParavaneClient,
    QuotaExceededError,
    RateLimitError,
    ValidationError,
)

client = ParavaneClient()

try:
    result = client.smtprs.analyze("person@example.com")
except AuthenticationError:
    print("Check your API key.")
except QuotaExceededError:
    print("The workspace has exhausted its available credits.")
except RateLimitError:
    print("Slow down and retry later.")
except ValidationError as exc:
    print("Request was invalid:", exc)

Exception classes:

Class Typical cause
ConfigurationError Missing API key or invalid client setup.
APIConnectionError Network failure, timeout, DNS failure, or connection error.
APIError Generic non-success API response.
AuthenticationError Missing, invalid, or revoked API key.
PermissionDeniedError API key lacks access to the requested resource.
ValidationError Invalid request payload or parameters.
QuotaExceededError Plan or credit quota has been exhausted.
RateLimitError Too many requests.

API errors include useful details when available:

try:
    client.smtprs.analyze("not-an-email")
except ValidationError as exc:
    print(exc.status_code)
    print(exc.code)
    print(exc.request_id)
    print(exc.response)

Responses and raw data

The SDK returns SmtpRsAnalysis for smtpRS analysis requests.

result = client.smtprs.analyze("person@example.com")

Common fields:

Field Description
email Email address represented by the response, when returned by the API.
decision Customer-facing recommendation such as allow, manual_review, or reject, when returned by the API.
overall_risk Normalized email risk score returned by smtpRS. It is not a probability.
tier Workspace/API-key tier reflected by the response.
analysis_profile Analysis path used by the API.
response_profile Response shape, such as summary/full.
credit_cost Planned credit cost for the selected profile.
credits_charged Credits recorded for the request, when returned.
company_validity_beta Typed beta status, opt-in state, availability, credit cost, and API notes.
domain_signal Typed domain, mail, and company-context facts when returned.
reasons Human-readable reason strings, when returned.
usage Usage/quota snapshot, when returned.
raw Original API payload.

To avoid losing fields added by the API before the SDK is updated, the full payload is always preserved:

raw = result.to_dict()
print(raw["usage"])

Types

This package includes inline type hints and ships a py.typed marker.

The response helper is a dataclass:

from paravane import SmtpRsAnalysis


def handle_result(result: SmtpRsAnalysis) -> None:
    print(result.decision)
    signal = result.domain_signal
    if signal is not None:
        print(signal.mail_capable)

Type hints are intended to describe stable SDK behavior. The raw API response may include additional fields that are not represented as first-class dataclass attributes yet.

Logging

The SDK does not install or configure logging handlers. Applications should configure logging at the application boundary.

For now, request failures are surfaced through exceptions. If you need detailed HTTP logging during development, configure your own requests.Session or enable logging in your HTTP stack.

Examples

This repository includes small examples:

examples/basic_analyze.py
examples/strict_analyze.py
examples/batch_csv.py

Run one with:

PARAVANE_API_KEY="pvn_live_..." python examples/basic_analyze.py

Windows PowerShell:

$env:PARAVANE_API_KEY = "pvn_live_..."
python examples/basic_analyze.py

Development

Create an environment:

python -m venv .venv
source .venv/bin/activate
python -m pip install -e ".[dev]"

Windows PowerShell:

python -m venv .venv
.\.venv\Scripts\Activate.ps1
python -m pip install -e ".[dev]"

Run tests:

pytest

Run lint:

ruff check .

Build the package:

python -m build

Recommended pre-commit check:

pytest && ruff check . && python -m build

Repository layout

paravane-python/
  .github/workflows/   GitHub Actions checks
  examples/            Small runnable examples
  src/paravane/        SDK package source
  tests/               Unit tests
  pyproject.toml       Packaging metadata and tool config
  RELEASING.md         Maintainer release process

Versioning

Current package version:

1.0.3

Security

Do not put API keys in source code, client-side apps, mobile apps, screenshots, or public repositories.

Recommended handling:

  • load API keys from environment variables or a secret manager
  • rotate keys if they are exposed
  • create separate keys for development, staging, and production
  • revoke keys that are no longer needed

Report suspected vulnerabilities privately:

security@paravane.io

Support

For product or account support:

contact@paravane.io

For security reports:

security@paravane.io

Release files for paravane 1.0.3

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

Source distribution (sdist)

Source distribution for paravane 1.0.3
File Size Uploaded
paravane-1.0.3.tar.gz 22.9 kB Details

Built distribution (wheel)

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

Total release size: 39.3 kB

Release files / paravane-1.0.3.tar.gz

Download URL paravane-1.0.3.tar.gz
Size 22.9 kB
Tags Source
SHA-256 checksum
How to use checksums
5a6ab1199796a364b0bf7b74fcf0f0120857c106af073bc28e282336d408f349
BLAKE2b-256 checksum
How to use checksums
0092933e175f7388bb06a04c81f72d87f79f82408fd9f39dbb79fecd54cefa37
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/6.1.0 CPython/3.13.13

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 Sep 10, 2026.

Transparency log

Release files / paravane-1.0.3-py3-none-any.whl

Download URL paravane-1.0.3-py3-none-any.whl
Size 16.4 kB
Tags Python 3
SHA-256 checksum
How to use checksums
1489db9127fdd36aaa699047eadf9d29c8a775867a4d04349ef96ae0c520f168
BLAKE2b-256 checksum
How to use checksums
71a308fb0d3673cddf7ca9aa5b9bf81e13d146e4c8043605713aa75934676486
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/6.1.0 CPython/3.13.13

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 Sep 10, 2026.

Transparency log

Release history Release notifications | RSS feed

This release

1.0.3 This release

2 release files

1.0.2

2 release files

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