--- title: "1.38.0 — Passkeys view fix and strict REST filter values" description: "Fixes the packaged Admin's Passkeys view, which crashed for any user holding a passkey. REST filter values are now converted to their field's type, so Boolean lists and relation-path filters work. A malformed Boolean is now a 400 instead of silently false." date: "2026-10-20" tags: ["release"] canonical: "https://django-mojo.sitesmojo.com/changelog/1-38-0/" --- Fixes the packaged Admin's Passkeys view, which crashed for any user holding a passkey. REST filter values are now converted to their field's type, so Boolean lists and relation-path filters work. A malformed Boolean is now a 400 instead of silently false. ### Breaking - A REST filter on a Boolean field with an unrecognized value (`?is_unread=maybe`) now answers 400 naming the key, on the list and on `_mode=count`. It used to mean `false` silently. Accepted: `true 1 t y yes on` / `false 0 f n no off` in any case, a JSON boolean, or `0`/`1`. `?flag=null` still means `false`. ### Fixed - Packaged Admin: the Passkeys view (user detail and My account) no longer crashes for users who hold a passkey. - Packaged Admin: **Set temporary password** is back in the user header menu and Security section. It uses the existing endpoint and needs no new permission. - `__in` / `__not_in` on a Boolean field (`?is_unread__in=true,false`) no longer answers 500. Each element is converted, and the list stays a list. - Relation-path filters (`?user__is_active=true`, `?author__last_login__gte=2026-01-01`) are converted through the field the path ends on, so a Boolean or date on a related field no longer answers 500. ### Changed - A date filter value that does not parse, including an epoch number too large for a date, is a 400. - On integer columns, a numeric string becomes an int under exact, `__in` and the comparisons. Text lookups (`__startswith`, `__icontains`, ...) take the value as sent, so `?id__startswith=026` is the pattern "026". - In a `_stats` bundle, a malformed filter value makes only that one chip `null`. The other chips and the request are unaffected. - A filter on a protected field is still dropped silently whatever its value, so a malformed value there never produces a 400. ### Upgrade notes - Clients that send loose Boolean values (anything outside the accepted list) will start getting 400s. Check the list UIs and integrations that build Boolean filters by hand. - A `normalize_rest_value` override whose only job was mapping Boolean strings is now redundant and can be removed. Note the framework answers a malformed Boolean with 400, where such a shim usually returned `False`.