kratos icon indicating copy to clipboard operation
kratos copied to clipboard

Passkey strategy/method for API flows

Open Saancreed opened this issue 7 months ago • 1 comments

Preflight checklist

Ory Network Project

No response

Context and scope

Currently, Kratos does not expose any Passkey-related features to API clients and restricts access to them to browser clients only. However, API clients such as mobile applications could take advantage of platform-specific credential managers to give users the ability to use passkeys outside of web browsers, most likely via a custom integration that would connect WebAuthn challenges and responses to platform APIs. The idea is to relax some flow type checks to expose passkey strategy to API clients that would like to implement such custom integration.

Goals and non-goals

Goals:

  • Allowing sufficiently aware clients to take advantage of passkey strategy in API flows
  • Avoiding confusing simpler clients with strategies that require custom, possibly platform-specific handling

Non-goals:

  • Defining how clients are supposed to handle passkey strategy

The design

The simplest way to achieve this is to remove various checks that skip the passkey strategy for non-browser flows, and optionally re-add them a bit deeper to skip sending the WebAuthn script (and possibly the trigger button), which is useless for API clients. Registration, Login and Settings flows would then contain additional nodes like passkey_challenge and passkey_create_data. Mobile applications could then read attached challenge JSON, pass it to native credential manager, get the response, and send it to Kratos in fields such as passkey_login or passkey_register with method set to passkey.

Finally, there is a possibllity to make it configurable whether the passkey strategy should be exposed to API clients as a separate knob, but ideally we would implement this in a way that won't be a breaking change and thus, the knob would be of little value.

APIs

We simply reuse some of the nodes already exposed to browser clients.

Data storage

No response

Code and pseudo-code

A prototype that implements the first goal but does not yet take the second one into consideration is here: https://github.com/leancodepl/kratos/commit/5b649de7f7958de0ef18cebb90e5eb0a5c71c285

This is sufficient for our mobile Flutter applications (targeting Android and iOS) to expose passkeys to their users. What remains to be done is making sure we don't send any new node that wouldn't be hidden, so existing clients unaware of passkey method can keep working as they are.

Degree of constraint

No response

Alternatives considered

No response

Saancreed avatar May 06 '25 16:05 Saancreed

I personally looking for this solution in native apps as well. But sadly it isn't available yet. I tried looking the codebase but I'm not go expert so I can't really figure it out how to make this work by opening some of nodes to the API so we can reuse them. Maybe some other devs can check if this is feasible with the current implementation we have right now.

jcbriones avatar Jul 15 '25 02:07 jcbriones