Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Unexpected RpIdHash #45

Closed
raynirola opened this issue Apr 14, 2024 · 15 comments
Closed

Unexpected RpIdHash #45

raynirola opened this issue Apr 14, 2024 · 15 comments

Comments

@raynirola
Copy link

I am implementing webauthn in chrome extension, registration works, authentication fails with Unexpected RpIdHash: foo vs bar

client:

async function authenticate() {
    const challenge = await ky
        .create({ prefixUrl: process.env.API_URL, credentials: 'include' })
        .post('auth/challenge', { json: { username: 'testuser' } })
        .json<{ challenge: string; id?: string }>();

    const authentication = await client.authenticate(challenge.id ? [challenge.id] : [], challenge.challenge, {
        authenticatorType: 'auto',
        userVerification: 'required',
        mediation: 'required',
        timeout: 60000,
        debug: false,
    });

    await ky
        .create({ prefixUrl: process.env.API_URL, credentials: 'include' })
        .post('auth/login', { json: { authentication } })
        .json<{ message: string }>();
}

server:

  const authentication = req.body.authentication as AuthenticationEncoded

  const credential = await db.credential.findUniqueOrThrow({ where: { credentialId: authentication.credentialId } })

  await server.verifyAuthentication(
    authentication,
    {
      id: credential.credentialId,
      algorithm: credential.algorithm,
      publicKey: credential.publicKey,
    },
    {
      challenge: req.signedCookies.challenge,
      origin: 'chrome-extension:https://id',
      userVerified: false,
      verbose: true,
    },
  )
@dagnelies
Copy link
Collaborator

I suspect the origin will not be chrome-extension:https://id but rather the domain name of the website being visited.

@raynirola
Copy link
Author

raynirola commented Apr 14, 2024

No, this is all in context of popup panel, there's no website being visited. @dagnelies
image

@dagnelies
Copy link
Collaborator

Hmmm... I never tried it with browser extensions so far, so I'm not familiar with it.
The lib uses window.location.hostname as default RP ID. Perhaps that's an issue in the extension's context.
You can also enable the register(..., {debug: true}) flag to have the RP ID printed out in the console (in debug level).

@raynirola
Copy link
Author

raynirola commented Apr 14, 2024

window.location.hostname

Is there a way to override this? For chrome extension this needs to be set to empty. This will also prevent authentication from iframes I guess.

@raynirola
Copy link
Author

@dagnelies I found the issue, can I pr for extension support?

@dagnelies
Copy link
Collaborator

Sure, you're welcome! Ideally with a note in the readme too.

@dagnelies
Copy link
Collaborator

Solved in v1.6.0
You can now override rp:{id:..., name:...} in the registration options

@raynirola
Copy link
Author

@dagnelies Thanks.

@dagnelies
Copy link
Collaborator

@raynirola ...wait a second ...it's incomplete ...further fix coming

@dagnelies dagnelies reopened this Apr 18, 2024
@raynirola
Copy link
Author

raynirola commented Apr 18, 2024

Still 1 issue, rp.id is optional by default (on browsers), and with chrome extension it needs to be set to undefined.

@dagnelies
Copy link
Collaborator

dagnelies commented Apr 18, 2024

Well, according to the specs it is required: https://w3c.github.io/webauthn/#dom-publickeycredentialrpentity-id

EDIT: Nevermind... the name is required but not the id

@raynirola
Copy link
Author

Well, according to the specs it is required: https://w3c.github.io/webauthn/#dom-publickeycredentialrpentity-id

EDIT: Nevermind... the name is required but not the id

https://developer.mozilla.org/en-US/docs/Web/API/CredentialsContainer/create#id_4

@raynirola
Copy link
Author

raynirola commented Apr 18, 2024

I guess there's confusion between entity id and relying party id, or browsers not following specs

@dagnelies
Copy link
Collaborator

dagnelies commented Apr 18, 2024

I guess there's confusion between entity id and relying party id, or browsers not following specs

In the specs too, the RP ID is always a domain and never ever anything else. Regarding "browsers not following specs" it's kind of commonplace with webauthn sadly 😓 ...and is still feels like a "moving target". I would be warry of seeing behavior changes regarding webauthn and chrome extensions.

Regarding your initial post, could you please try out the latest version and simply set domain to your "chrome-extension id"?
Since you had origin: 'chrome-extension:https://id', as origin in the authentication result, it may just work out. ...otherwise, yeah, it would need a flag to disable it ...but I wonder what value it would receive in practice. After all, verifying the rpId hash is part of the verification procedure.

@dagnelies
Copy link
Collaborator

So, in register(... {domain:id}) authenticate(... {domain:id}) and verifyAuthentication(... {domain:id})

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants