tokportal
TokPortal is the managed social infrastructure API: real TikTok, Instagram and YouTube accounts created, warmed and operated by human account managers in 16+ countries — exposed as a REST API and an MCP server. No OAuth per account, no 25-posts/day cap, no app review.
Docs https://developers.tokportal.com · API base https://app.tokportal.com/api/ext · OpenAPI https://developers.tokportal.com/openapi.json · MCP remote https://app.tokportal.com/api/ext/mcp · Get an API key https://app.tokportal.com/developer/api-keys · llms.txt https://developers.tokportal.com/llms.txt
tokportal is the official Python SDK for the TokPortal API (Python 3.9+, typed, standard library only). Every public operation is available as a resource method or through the generated request_operation map.
Install
pip install tokportal
30-second quickstart
import os
from tokportal import TokPortal
client = TokPortal(api_key=os.environ["TOKPORTAL_API_KEY"])
# 1. Create a bundle: a fresh managed TikTok account in the USA + 1 video slot.
# Credits are debited now; the account manager is assigned at publish time.
bundle = client.bundles.create({
"bundle_type": "account_and_videos",
"platform": "tiktok",
"country": "USA",
"title": "US launch",
"videos_quantity": 1,
})
bundle_id = bundle["data"]["id"]
# 2. Upload the video straight from disk -> public_url
upload = client.uploads.video_direct("./launch.mp4", bundle_id, content_type="video/mp4")
# 3. Configure the account profile and video slot 1, then publish
client.bundles.configure_account(bundle_id, {
"username": "mybrand.us",
"visible_name": "My Brand",
"biography": "Official account",
})
client.bundles.configure_video(bundle_id, 1, {
"video_type": "video",
"video_url": upload["data"]["public_url"],
"description": "Day 1 - launching in the US #launch",
"target_publish_date": "2026-09-01",
})
client.bundles.publish(bundle_id)
# 4. Later (webhook `account.in_review` / `account.finalized`, or polling):
# saved_account_id is the real delivered account -> read it back
current = client.bundles.get(bundle_id)["data"]
if current.get("saved_account_id"):
account = client.accounts.get(current["saved_account_id"])["data"]
print(account["username"], account["profile_url"])
Method names follow the generated resource map (
bundles,uploads,accounts,analytics,webhooks). If a helper does not exist for an operation, useclient.request_operation("<operationId>", path=..., query=..., body=...).
Full example
import os
from tokportal import TokPortal, TokPortalApiError
client = TokPortal(api_key=os.environ["TOKPORTAL_API_KEY"])
me = client.me()
bundle = client.bundles.create({
"bundle_type": "account_and_videos",
"country": "USA",
"videos_quantity": 5,
})
csv = client.analytics.export_videos(account=["saved-account-id"])
image = client.uploads.image_from_url({
"url": "https://cdn.example.com/photo.jpg",
"bundle_id": bundle["data"]["id"],
})
print(me["data"]["email"], bundle["data"], csv, image["data"])
Direct multipart uploads use the same structured errors and idempotency support:
uploaded = client.uploads.video_direct(
"./video.mp4",
bundle["data"]["id"],
content_type="video/mp4",
idempotency_key="video-upload-123",
)
Manage TokPortal Coverage from the latest atomic quote. A zero-credit quote is valid and still requires an explicit reactivation call:
coverage = client.accounts.coverage("saved-account-id")
quote = coverage["data"]["reactivation_quote"]
if quote:
client.accounts.reactivate_coverage(
"saved-account-id",
{
"expected_credits": quote["credits"],
"expected_current_period_end": quote["current_period_end"],
"expected_lock_version": quote["lock_version"],
},
idempotency_key="coverage-reactivate-saved-account-id-v4",
)
client.accounts.pause_coverage(
"saved-account-id",
idempotency_key="coverage-pause-saved-account-id-v4",
)
Credential reveal and verification-code access use the same irreversible
two-step policy flow. First call without acceptance to receive HTTP 428 and
error.details.policy_version; then show those terms to the account owner and
retry with that exact version. The accepted request may debit credits and
permanently detach the account. These secret-bearing responses are never stored
for replay, so these helpers intentionally do not accept idempotency_key.
After an uncertain transport result, reconcile the safe account state before
deciding whether to call the endpoint again without a key:
If an accepted call returns HTTP 409 with
CREDENTIAL_REVEAL_QUOTE_CHANGED, no charge or reveal occurred. Read the
current policy and expected_credit_cost from error.details, show the new
terms to the owner, obtain fresh consent, and retry with the new version. Never
retry a 409 automatically.
try:
client.accounts.reveal_credentials("saved-account-id")
except TokPortalApiError as error:
if error.status_code != 428:
raise
policy_version = str(error.details["policy_version"])
credentials = client.accounts.reveal_credentials(
"saved-account-id",
acceptance={
"acknowledge_support_forfeit": True,
"policy_version": policy_version,
},
)
The same no-replay rule applies to webhooks.create, uploads.image,
uploads.video, and analytics.create_report because they return a signing
secret, signed upload capability, or report access token. These helpers do not
accept idempotency_key, and request_operation rejects one locally for all
six sensitive operation IDs.
Discover and operate webhooks without dropping to raw HTTP:
catalog = client.webhooks.events()
endpoints = client.webhooks.list(event="bundle.published")
retry = client.webhooks.retry_delivery(endpoints["data"][0]["id"], "delivery-id")
Every OpenAPI operation is also reachable through the generated operation map:
same_retry = client.request_operation(
"retryWebhookDelivery",
path={"id": endpoints["data"][0]["id"], "delivery_id": "delivery-id"},
)
csv_again = client.request_operation(
"exportAnalyticsVideos",
query={"account": ["saved-account-id"]},
)
The SDK sends X-TokPortal-Client: tokportal-python/0.1.0 on API requests for observability and support diagnostics.
Verify signed webhook deliveries with the exact raw request body:
from tokportal import verify_webhook_signature
valid = verify_webhook_signature(
raw_body,
request.headers["TokPortal-Signature"],
os.environ["TOKPORTAL_WEBHOOK_SECRET"],
)
from tokportal import TokPortalApiError
try:
client.bundles.create({
"bundle_type": "account_and_videos",
"country": "USA",
"videos_quantity": 5,
})
except TokPortalApiError as error:
print(error.status_code, error.code, error.details, error.request_id)
if error.retryable:
wait_seconds = error.retry_after_seconds or 1
# Retry with backoff.
pass
print(error.rate_limit)
API keys use the format sk_ followed by 64 lowercase hex characters. TokPortal stores only a SHA-256 hash of the key and shows the raw key once at creation.
Source of truth
This package is generated from the TokPortal public OpenAPI schema
(https://developers.tokportal.com/openapi.json) in the private TokPortal
monorepo. Generated files (tokportal/_generated.py) are overwritten on every release — do not edit
them by hand. See CONTRIBUTING.md for what we accept as PRs
and SECURITY.md for vulnerability reporting.
Links
- Documentation: https://developers.tokportal.com
- SDKs & CLI guide: https://developers.tokportal.com/sdks-cli
- MCP server: https://developers.tokportal.com/mcp ·
tokportal-mcp - API reference (OpenAPI): https://developers.tokportal.com/openapi.json
- Other packages:
@tokportal/node·@tokportal/cli·tokportal(PyPI) ·github.com/tokportal/tokportal-go
MIT © TokPortal
Metadata
Release files for tokportal 0.1.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 | |
|---|---|---|---|
| tokportal-0.1.0.tar.gz | 16.1 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| tokportal-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 32.0 kB
Release files / tokportal-0.1.0.tar.gz
| Download URL | tokportal-0.1.0.tar.gz |
|---|---|
| Size | 16.1 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
c50a8fa18e54ff515a8fb0e8b919b2f7fc7cfb09316a2e4ab9983a06329df8ce
|
|
BLAKE2b-256 checksum How to use checksums |
1ffc367dc5d93a1711aa898bf7944e13b105594d2d383f80c6858f9a11d2501e
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.14.3
|
Release files / tokportal-0.1.0-py3-none-any.whl
| Download URL | tokportal-0.1.0-py3-none-any.whl |
|---|---|
| Size | 15.9 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
453491e47f57ea509d9bffd1f6f118707c3df8d553aa178ae41ec7ec2b76cd51
|
|
BLAKE2b-256 checksum How to use checksums |
badd0c5d9ee440a76296640bd3db8bc567137f3d97f85b80a89b636d49207707
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.14.3
|