PyPI & TestPyPI Accounts & Tokens

This content was generated with the assistance of AI and should be verified against the official documentation before being relied on in production.

The reference material consulted while preparing these pages is listed in the Python Reference bibliography.

Uploading needs an identity: a PyPI account with two-factor authentication, and either an API token or, better, a trusted publisher (see Trusted Publishing & Attestations). This page describes the account side as documented by PyPI on 2026-10-22; nothing here was run against PyPI or TestPyPI, and the tokens shown are placeholders (pypi-AgEI…). The short version is on Virtual Environments & Packaging.

Accounts

  • Register on pypi.org and, separately, on test.pypi.org: the two have separate databases, accounts, tokens and projects. TestPyPI is pruned now and then, accounts included.

  • Verify your email address. Registering a project and uploading a file require a verified address. Disposable addresses are rejected.

  • Two-factor authentication is mandatory for every account since 2024-01-01. Before adding a method, PyPI makes you generate recovery codes and "burn" one to prove you stored them. Then add at least two methods:

    • a security device (WebAuthn: a FIDO key or a phone), preferred because it resists phishing;

    • an authentication application (TOTP), which shares a secret with PyPI and shows six-digit codes.

  • Sensitive actions (adding collaborators, deleting files, creating tokens, setting up 2FA) ask for your password again after 30 minutes. PyPI checks passwords against breach databases (through Have I Been Pwned’s k-anonymity API) and refuses known ones.

API tokens

An API token replaces your password for uploads (the web login is not usable by tools):

  • create it under Account settings → API tokens (after verifying your email);

  • scope it to one project whenever possible; an account-wide token can upload to every project you maintain. The scope list only offers existing projects, so the very first upload of a new project needs an account-wide token, or a pending trusted publisher, which avoids tokens entirely;

  • use it with the username __token__ and the whole token as the password, including its pypi- prefix;

  • tokens can be decoded with base64 to compare their identifier with the one PyPI shows;

  • a token found on a public website (a commit, a log) is revoked automatically and you get an email: investigate the exposure, check the account’s security history, then create a new one.

Since twine 5.0.0 (2024-02-10) only __token__ is accepted as the username for PyPI and TestPyPI, and since 6.0.0 (2024-11-29) it is the default, so TWINE_PASSWORD alone is enough.

.pypirc

twine (and flit) read upload targets and credentials from ~/.pypirc, an INI file. twine’s built-in defaults are a [pypi] and a [testpypi] section; a private index needs index-servers:

[distutils]
index-servers =
    pypi
    testpypi
    birdwatch

[pypi]
username = __token__

[testpypi]
username = __token__

[birdwatch]
repository = http://localhost:8082/
username = birdwatch

Keep passwords out of it: store them in the system keyring, which twine queries by repository URL and username,

keyring set https://upload.pypi.org/legacy/ __token__
keyring set https://test.pypi.org/legacy/ __token__
keyring set http://localhost:8082/ birdwatch

or pass them through TWINE_PASSWORD in CI. If a password = line is unavoidable, make the file private (chmod 600 ~/.pypirc). Since twine 7.0.0 the file is read as UTF-8. Poetry does not read .pypirc; it has its own repositories and credentials (see Publishing with Poetry).

Collaborators and organizations

  • A project has owners (full control: releases, collaborators, deletion) and maintainers (can upload releases, nothing else). Owners invite by PyPI username; the invitee must accept. An owner can remove themselves only if another owner remains.

  • Transferring ownership means adding the new owner, who can then remove you. Granting ownership gives away the project: the new owner can remove you.

  • Organization accounts group users into teams with project permissions. They are paid for companies and free for community projects, with the same features.

"Invalid or non-existent authentication information"

The upload error PyPI returns for bad credentials. Its documented causes:

  1. the token was revoked (by you, or automatically after a leak);

  2. the token is malformed, typically with a trailing newline from a file or a secret store;

  3. the username is not __token__;

  4. the token belongs to the other index (a TestPyPI token used for PyPI or the reverse);

  5. on Windows, pasting into a getpass prompt with Ctrl-V or Shift+Insert silently pastes nothing; use the window menu’s Edit → Paste.