The U2F Javascript API consists of two calls - one to register a U2F token with a relying party (i.e., cause the U2F token to generate a new key pair, and to introduce the new public key to the relying party), and one to sign an identity assertion (i.e., exercise a previously-registered key pair).

Notation

Type names, attribute names and element names are written as code.

String literals are enclosed in “”, e.g. “UAF-TLV”.

In formulas we use “|” to denote byte wise concatenation operations.

DOM APIs are described using the ECMAScript [[!ECMA-262]] bindings for WebIDL [[!WebIDL]].

U2F specific terminology used in this document is defined in [[!FIDOGlossary]].

Key Words

The key words “MUST”, “MUST NOT”, “REQUIRED”, “SHALL”, “SHALL NOT”, “SHOULD”, “SHOULD NOT”, “RECOMMENDED”, “MAY”, and “OPTIONAL” in this document are to be interpreted as described in [[!RFC2119]].

Below we explain some of the terms used in this document:

TermDefinition

websafe-base64 encoding

This is the "Base 64 Encoding with URL and Filename Safe Alphabet" from Section 5 in [[!RFC4648]] without padding.

stringified javascript object

This is the JSON object (i.e., a string starting with "{" and ending with "}") whose keys are the property names of the javascript object, and whose values are the corresponding property values. Only "data objects" can be stringified, i.e., only objects whose property names and values are supported in JSON.

Introduction

Note: Reading the 'FIDO U2F Overview' (see [[U2FOverview]] in bibliography) is recommended as a background for this document.

A Relying Party (RP) consumes identity assertions from U2F tokens. The RP's web pages communicate with the U2F tokens on the client through a Javascript API. The RP also needs to perform some verification steps on the server side (see below). How the data obtained by the RP's Javascript is transferred to the RP's server is out of scope of this document. We instead describe the Javascript API used by the RP.

API Levels

The U2F API MAY be exposed to web pages on two levels. On the required lower level, RPs interact with the FIDO client through a MessagePort [[!WEBMESSAGING]] object. The low-level MessagePort API defines the message formats for messages sent and received on the port, for the two operations supported by the API. This specification does not describe how such a port is made available to RP web pages, as this is (for now) implementation and browser dependent.

For convenience, the FIDO client MAY also expose a high-level Javascript API built on top of the MessagePort API. This API consists of functions corresponding to the different requests that can be made to the FIDO client. These functions respond to the RP asynchronously by invoking a callback.

Why two API levels? The messaging API requires only that pages obtain a MessagePort instance to the FIDO client, i.e. no code needs to be injected to JavaScript context of the RP's pages. This allows RPs to keep full control over the JS running in their pages. The JS API is offered as a convenient abstraction of the messaging API, and is useful for RP developers to quickly integrate U2F into their websites.

Low-level MessagePort API

RP web pages communicate with the FIDO client over an instance of the HTML5 MessagePort interface. Client implementations may choose how this instance is made available to web pages.

Messages sent to the FIDO client SHOULD be Request dictionaries:

DOMString type
The type of request, either "u2f_register_request" or "u2f_sign_request".
SignRequest[] signRequests
A list of SignRequest dictionaries, one for each token already registered with this RP.
RegisterRequest[]? registerRequests
A list of RegisterRequest dictionaries, one for each protocol version that the RP is willing to register.
int? timeoutSeconds
A timeout for the FIDO Client's processing, in seconds.
optional int? requestId
An integer identifying this request from concurrent requests.

SignRequest and RegisterRequest are defined below. If timeoutSeconds is omitted, timeout behavior is unspecified. If requestId is present, the FIDO client MUST include its value the corresponding Response dictionary under the same key.

Responses from the FIDO client to the RP webpage SHOULD be Response dictionaries:

DOMString type
The response type, either "u2f_register_response" or "u2f_sign_response"
(Error or RegisterResponse or SignResponse) responseData
The response data, see
int? requestId
The requestId value of the corresponding request, if present. Otherwise omitted.

Errors are indicated by an Error dictionary sent as the response data. An error dictionary can be identified by checking for its non-zero integer errorCode key. RegisterResponse and SignResponse do not define this key. An error object may optionally contain a string errorMessage with further description of the error.

ErrorCode errorCode
An error code from the ErrorCode enumeration.
DOMString? errorMessage
A description of the error.

High-level Javascript API

A FIDO client MAY provide a JavaScript convenience API that abstracts the lower-level MessagePort API. Implementations may choose how to make such an API available to RP web pages. If such an API is provided, it SHOULD provide a namespace object u2f of the following interface.

void register(...)
RegisterRequest[] registerRequests
Register requests, one for each U2F protocol version accepted by RP
SignRequest[] signRequests
Sign requests for already registered tokens
function(RegisterResponse or Error) callback
Response handler
optional int? opt_timeoutSeconds
Timeout in seconds, for the FIDO client's handling of the request.
void sign(...)
SignRequest[] signRequests
Sign requests, one for each registered token
function(SignResponse or Error) callback
Response handler
optional int? opt_timeoutSeconds
Timeout in seconds, for the FIDO client's handling of the request.

The JavaScript API MUST invoke the provided callbacks with either response objects, or an error object. An error can be detected by testing for a non-zero errorCode key.

  u2f.sign(reqs, function(response) {
                  if (response.errorCode) {
                    // response is an Error
                    ...
                  } else {
                    // response is a SignResponse
                    ...
                  }
                });
          

U2F operations

Regardless of the API level used, the U2F client MUST support the two operations of registering a token, and generating a signed assertion. This section describes the interface to each operation, their corresponding request and response dictionaries and possible error codes.

Registration

To register a U2F token for a user account at the RP, the RP MUST:

For each version it is willing to register, it then prepares a RegisterRequest dictionary as follows:

DOMString version
The version of the protocol that the to-be-registered token must speak. E.g. "U2F_V2".
DOMString challenge
The websafe-base64-encoded challenge.
DOMString appId
The application id that the RP asserts. The new key pair that the U2F token generates will be associated with this application id. (For application id details see [[!FIDOAppIDAndFacets]] in bibliography).
Additionally, the RP SHOULD prepare a SignRequest for each U2F token that is already registered for the current user. See the following section for the specification of sign requests.

The RP delivers a registration request to the FIDO client either via the low-level MessagePort API, or by invoking the high-level JavaScript API.

// Low-level API
var port = <obtain U2F MessagePort in a browser specific manner>;
port.addEventListener(‘message’, responseHandler);
port.postMessage({
 ‘type’: ‘u2f_register_request’,
 ‘registerRequests’: [<RegisterRequest instance>, ...],
 ‘signRequests’: [<SignRequest for known token 1>, ...],
 ‘timeoutSeconds’: 30,
 ‘requestId’: <unique integer>  // optional
});
          
// High-level API
u2f.register([<RegisterRequest instance>, ...], 
             [<SignRequest for known token 1>, ...],
             registerResponseHandler);
          

The FIDO client SHOULD treat the order of RegisterRequest dictionaries in the first parameter as a prioritized list. That is, if multiple tokens are present that support more than one version provided by the RP, the version that appears first should be selected. Note that this means multiple RegisterRequests with the same version are redundant, since the first one will always be selected.

Note also that the responseHandler in the low-level API receives a Response object, while the registerResponseHandler in the high-level API receives the Error or RegisterResponse objects directly.

The FIDO client will create the raw registration and sign request messages from this data (see [[!U2FRawMsgs]] in bibliography), and attempt to perform a registration operation with a U2F token. The sign request messages will have the (internal) checkOnly boolean of the control state set to true, and are used to identity such U2F tokens that are already registered with the relying party. The registration request message is then used to register a U2F token that is not already registered (if such a token is present).

Note that as part of creating the registration request message, the FIDO client will create a Client Data object (see [[!U2FRawMsgs]]). This Client Data object will be returned to the caller as part of the registration response (see below).

If the registration is successful, the FIDO client returns (via the message port, or the JS API callback) a RegisterResponse dictionary as follows.

DOMString registrationData
The raw registration response websafe-base64
DOMString clientData
The client data created by the FIDO client, websafe-base64 encoded.
For the contents of these fields, refer to [[!U2FRawMsgs]] (see bibliography).

Generating signed identity assertions

To obtain an identity assertion from a locally-attached U2F token, the RP must

DOMString version
Version of the protocol that the to-be-registered U2F token must speak. E.g. "U2F_V2"
DOMString challenge
The websafe-base64-encoded challenge.
DOMString keyHandle
The registered keyHandle to use for signing, as returned by the U2F token during registration.
DOMString appId
The application id that the RP would like to assert.

In response to a sign request, the FIDO client should perform the following steps:

Eventually the FIDO client must respond (via the MessageChannel or the provided callback). In the case of an error, an Error dictionary is returned. In case of success, a SignResponse is returned.

DOMString keyHandle
The keyHandle of the SignRequest that was processed.
DOMString signatureData
The raw response from U2F device, websafe-base64 encoded.
DOMString clientData
The client data created by the FIDO client, websafe-base64 encoded.

If there are multiple U2F tokens that responded to the authentication request, the FIDO client will pick one of the responses and pass it to the caller.

Error codes

When an Error object is returned, its errorCode field is set to a non-negative integer indicating the general error that occurred, from the following enumeration.

const int OK = 0
Success. Not used in errors but reserved
const int OTHER_ERROR = 1
An error otherwise not enumerated here
const int BAD_REQUEST = 2
The request cannot be processed
const int CONFIGURATION_UNSUPPORTED = 3
Client configuration is not supported
const int DEVICE_INELIGIBLE = 4
The presented device is not eligible for this request. For a registration request this may mean that the token is already registered, and for a sign request it may mean the token does not know the presented key handle.
const int TIMEOUT = 5
Timeout reached before request could be satisfied