http://open-source-security-software.net/project/py_webauthn/releases.atomRecent releases for py_webauthn2025-07-03T15:10:39.988884+00:00python-feedgenpy_webauthn v0.4.7py_webauthn v0.4.72020-03-13T23:02:29+00:00v0.4.72020-03-13T23:02:29+00:00py_webauthn v1.0.0-beta1py_webauthn v1.0.0-beta12021-10-15T16:15:13+00:00Preview release of the revitalized py_webauthn library. See PR #95 2021-10-15T16:15:13+00:00py_webauthn v1.0.0-beta2py_webauthn v1.0.0-beta22021-10-15T16:49:25+00:002021-10-15T16:49:25+00:00py_webauthn v1.0.0py_webauthn v1.0.02021-10-15T17:20:05+00:00This preview release of the revitalized py_webauthn library features an entirely new API, as well as support for all attestation statement formats included in L2 of the WebAuthn spec:
- **Packed**
- **TPM**
- **Android Key**
- **Android SafetyNet**
- **FIDO U2F**
- **Apple**
- **None**
Practical examples are included in the **examples/** directory to serve as a primary reference for now on how to use the new library functionality.2021-10-15T17:20:05+00:00py_webauthn v1.0.1py_webauthn v1.0.12021-10-18T15:48:11+00:00**Changes:**
- Fixed SafetyNet unit test failing due to expired x5c certs (see PR #99)2021-10-18T15:48:11+00:00py_webauthn v1.1.0py_webauthn v1.1.02021-11-11T00:54:49+00:00**Changes:**
- Fixed SafetyNet attestation statement verification failing due to server time drift
- Added py.typed file to indicate type information is present (PEP-561)2021-11-11T00:54:49+00:00py_webauthn v1.2.0py_webauthn v1.2.02021-12-10T19:00:11+00:00**Changes:**
- Switched from Pydantic to the combination of **attrs + cattrs**. This achieves more-Pythonic library behavior when used in a project alongside other third-party packages that use subclasses of `bytes` to represent such values as credential IDs and public keys.2021-12-10T19:00:11+00:00py_webauthn v1.2.1py_webauthn v1.2.12022-01-06T20:24:19+00:00**Changes:**
- Clarify `credential` docstring for `verify_authentication_response()`2022-01-06T20:24:19+00:00py_webauthn v1.3.0py_webauthn v1.3.02022-02-14T19:50:26+00:00**Changes:**
- Switch back from attrs + cattrs to **Pydantic** while preserving support for `bytes`-like values in subclasses of `WebAuthnBaseModel`.
- See issue #113 for more context2022-02-14T19:50:26+00:00py_webauthn v1.4.0py_webauthn v1.4.02022-02-17T23:16:04+00:00**Changes:**
- Add support for `memoryviews` for `BytesLike` properties including `credential_public_key`, `authenticator_data`, etc...2022-02-17T23:16:04+00:00py_webauthn v1.5.0py_webauthn v1.5.02022-04-06T19:18:48+00:00**Changes:**
- Fix authenticator data parsing to correctly parse extension data when present ([#125](https://github.com/duo-labs/py_webauthn/pull/125))
- Add support for the new `"cable"` transport ([#129](https://github.com/duo-labs/py_webauthn/pull/129))2022-04-06T19:18:48+00:00py_webauthn v1.5.1py_webauthn v1.5.12022-04-28T17:58:21+00:00**Changes:**
- Refine support for bytes-like inputs to comply with stricter mypy configurations ([#130](https://github.com/duo-labs/py_webauthn/pull/130))2022-04-28T17:58:21+00:00py_webauthn v1.5.2py_webauthn v1.5.22022-04-28T19:29:54+00:00**Changes:**
- Restore the ability to pass more common bytes-like values for `bytes` fields, such as `str` values ([#132](https://github.com/duo-labs/py_webauthn/pull/132))2022-04-28T19:29:54+00:00py_webauthn v1.6.0py_webauthn v1.6.02022-07-13T20:09:47+00:00**Changes:**
- Add new `credential_device_type` and `credential_backed_up` values to output from `verify_registration_response()` and `verify_authentication_response()` ([#136](https://github.com/duo-labs/py_webauthn/pull/136))
- Add support for the new `"hybrid"` transport (the generalized, eventual successor to `"cable"`) ([#137](https://github.com/duo-labs/py_webauthn/pull/137))2022-07-13T20:09:47+00:00py_webauthn v1.7.0py_webauthn v1.7.02023-01-30T22:45:39+00:00**Changes:**
- Add new `authenticator_attachment` value to `RegistrationCredential` and `AuthenticationCredential`, defining the attachment of the authenticator that completed a corresponding ceremony, as it may be returned by the WebAuthn API ([#141](https://github.com/duo-labs/py_webauthn/pull/141))2023-01-30T22:45:39+00:00py_webauthn v1.7.1py_webauthn v1.7.12023-02-17T20:27:17+00:00**Changes:**
- Add support for `from webauthn import *` syntax with proper use of `__all__` ([#146](https://github.com/duo-labs/py_webauthn/pull/146))2023-02-17T20:27:17+00:00py_webauthn v1.7.2py_webauthn v1.7.22023-02-17T21:15:09+00:00**Changes:**
- Update `cryptography` to 39.0.1 (and its dependency `pyOpenSSL` to 23.0.0) ([#148](https://github.com/duo-labs/py_webauthn/pull/148))
- See ["39.0.1 - 2023-02-07" in cryptography's CHANGELOG](https://github.com/pyca/cryptography/blob/main/CHANGELOG.rst#3901---2023-02-07) for more info2023-02-17T21:15:09+00:00py_webauthn v1.8.0py_webauthn v1.8.02023-03-15T22:04:58+00:00**Changes:**
- Move the `RegistrationCredential.transports` property into `RegistrationCredential.response.transports` to better conform to upcoming WebAuthn JSON serialization method output ([#150](https://github.com/duo-labs/py_webauthn/pull/150))2023-03-15T22:04:58+00:00py_webauthn v1.8.1py_webauthn v1.8.12023-05-04T18:56:22+00:00**Changes:**
- Update dependency versions in **setup.py** ([#151](https://github.com/duo-labs/py_webauthn/pull/151))2023-05-04T18:56:22+00:00py_webauthn v1.9.0py_webauthn v1.9.02023-07-05T20:25:03+00:00**Changes:**
- Keep using Pydantic v1.x for now ([#157](https://github.com/duo-labs/py_webauthn/pull/157))
- Update cryptography and pyOpenSSL dependencies ([#154](https://github.com/duo-labs/py_webauthn/pull/154), [#158](https://github.com/duo-labs/py_webauthn/pull/158))2023-07-05T20:25:03+00:00py_webauthn v1.10.0py_webauthn v1.10.02023-08-15T04:11:07+00:00**Changes:**
- Support use in projects using either Pydantic v1 or v2 ([#166](https://github.com/duo-labs/py_webauthn/pull/166))2023-08-15T04:11:07+00:00py_webauthn v1.10.1py_webauthn v1.10.12023-08-15T05:25:24+00:00**Changes:**
- Fix parsing error caused by registration responses from certain models of authenticators that incorrectly CBOR-encode their `authData` after creating an Ed25519 public keys ([#167](https://github.com/duo-labs/py_webauthn/pull/167))2023-08-15T05:25:24+00:00py_webauthn v1.11.0py_webauthn v1.11.02023-09-29T21:11:09+00:00**Changes:**
- The `credential` argument in `verify_registration_response()` and `verify_authentication_response()` can now also be a stringified JSON `str` or a plain JSON `dict` version of a WebAuthn response ([#172](https://github.com/duo-labs/py_webauthn/pull/172), [#178](https://github.com/duo-labs/py_webauthn/pull/178))
- Various methods will now raise `webauthn.helpers.exceptions.InvalidCBORData` when there is a problem parsing CBOR-encoded data ([#179](https://github.com/duo-labs/py_webauthn/pull/179))
- Updated dependencies to `cbor2==5.4.6` and `cryptography==41.0.4` ([#178](https://github.com/duo-labs/py_webauthn/pull/178))
2023-09-29T21:11:09+00:00py_webauthn v1.11.1py_webauthn v1.11.12023-10-31T21:23:18+00:00**Changes:**
- Deprecation warnings related to `cbor2` in projects using `cbor2>=5.5.0` will no longer appear during registration and authentication response verification ([#181](https://github.com/duo-labs/py_webauthn/pull/181))2023-10-31T21:23:18+00:00py_webauthn v2.0.0py_webauthn v2.0.02024-01-11T16:18:23+00:00**Changes:**
- See **Breaking Changes** below
**Breaking Changes:**
- [Pydantic](https://docs.pydantic.dev/latest/) is no longer used by py_webauthn. If your project
calls any Pydantic-specific methods on classes provided by py_webauthn then you will need to
refactor those calls accordingly. Typical use of py_webauthn should not need any major refactor
related to this change, but please see **Breaking Changes** below ([#195](https://github.com/duo-labs/py_webauthn/pull/195))
- `webauthn.helpers.generate_challenge()` now always generates 64 random bytes and no longer accepts any arguments. Refactor your existing calls to remove any arguments ([#198](https://github.com/duo-labs/py_webauthn/pull/198))
- `webauthn.helpers.exceptions.InvalidClientDataJSONStructure` has been replaced by `webauthn.helpers.exceptions.InvalidJSONStructure` ([#195](https://github.com/duo-labs/py_webauthn/pull/195))
- `webauthn.helpers.json_loads_base64url_to_bytes()` has been removed ([#195](https://github.com/duo-labs/py_webauthn/pull/195))
- The `user_id` argument passed into `generate_registration_options()` is now `Optional[bytes]`
instead of a required `str` value. A random sequence of 64 bytes will be generated for `user_id`
if it is `None` ([#197](https://github.com/duo-labs/py_webauthn/pull/197))
- There are a few options available to refactor existing calls:
### Option 1: Use the `base64url_to_bytes()` helper
If you already store your WebAuthn user ID bytes as base64url-encoded strings then you can simply decode these strings to bytes using an included helper:
**Before:**
```py
options = generate_registration_options(
# ...
user_id: "3ZPk1HGhX_cul7z5UydfZE_vgnUYkOVshDNcvI1ILyQ",
)
```
**After:**
```py
from webauthn.helpers import bytes_to_base64url
options = generate_registration_options(
# ...
user_id: bytes_to_base64url("3ZPk1HGhX_cul7z5UydfZE_vgnUYkOVshDNcvI1ILyQ"),
)
```
### Option 2: Generate unique WebAuthn-specific identifiers for existing and new users
WebAuthn **strongly** encourages Relying Parties to use 64 randomized bytes for **every** user ID you pass into `navigator.credentials.create()`. This would be a second identifier used exclusively for WebAuthn that you associate along with your typical internal user ID.
py_webauthn includes a `generate_user_handle()` helper that can simplify the task of creating this special user identifier for your existing users in one go:
```py
from webauthn.helpers import generate_user_handle
# Pseudocode (imagine this is in some kind of migration script)
for user in get_all_users_in_db():
add_webauthn_user_id_to_db_for_user(
current_user=user.id,
webauthn_user_id=generate_user_handle(), # Generates 64 random bytes
)
```
You can also use this method when creating new users to ensure that all subsequent users have a WebAuthn-specific identifier as well:
```py
from webauthn.helpers import generate_user_handle
# ...existing user onboarding logic...
# Pseudocode
create_new_user_in_db(
# ...
webauthn_user_id=generate_user_handle(),
)
```
Once your users are assigned their second WebAuthn-specific ID you can then pass those bytes into `generate_registration_options()` on subsequent calls:
```py
# Pseudocode
webauthn_user_id: bytes = get_webauthn_user_id_bytes_from_db(current_user.id)
options = generate_registration_options(
# ...
user_id=webauthn_user_id,
)
```
### Option 3: Let `generate_registration_options()` generate a user ID for you
When the `user_id` argument is omitted then a random 64-byte identifier will be generated for you:
**Before:**
```py
options = generate_registration_options(
# ...
user_id: "USERIDGOESHERE",
)
```
**After:**
```py
# Pseudocode
webauthn_user_id: bytes | None = get_webauthn_user_id_bytes_from_db(
current_user=current_user.id,
)
options = generate_registration_options(
# ...
user_id=webauthn_user_id,
)
if webauthn_user_id is None:
# Pseudocode
store_webauthn_user_id_bytes_in_your_db(
current_user=current_user.id,
webauthn_user_id=options.user.id, # Randomly generated 64-bytes
)
```
### Option 4: Encode existing `str` argument to UTF-8 bytes
This technique is a quick win, but can be prone to base64url-related encoding and decoding quirks between browsers. **It is recommended you quickly follow this up with Option 2 or Option 3 above:**
**Before:**
```py
options = generate_registration_options(
# ...
user_id: "USERIDGOESHERE",
)
```
**After:**
```py
options = generate_registration_options(
# ...
user_id: "USERIDGOESHERE".encode('utf-8'),
)
```2024-01-11T16:18:23+00:00