Bulk migration pbkdf2 can't login after successfull migration

I think I’m running into the same issue as this topic, which sadly don’t have a solution yet.

This doesn’t let me paste links but here’s the path of the similar post

/t/cant-log-in-using-imported-pbkdf2-hashed-passwords/61815

Here’s the code that originally created the salt and hash

async hashPassword(password: string) {
         const salt = crypto.randomBytes(16).toString('hex')
         const hash = crypto.pbkdf2Sync(password, salt, 100000, 64, 'sha256').toString('hex')
         return `${salt}:${hash}`
       }

This is the code I’m using to migrate

  const [saltHex, hashHex] = user.password.split(':')
  const saltBytes = Buffer.from(saltHex, 'hex')
  const hashBytes = Buffer.from(hashHex, 'hex')

  const saltB64 = saltBytes.toString('base64')
  const hashB64 = hashBytes.toString('base64')
    const hash2 = phc.serialize({
    id: 'pbkdf2-sha256',
    params: {
      i: 100000,
      l: 64
    },
    salt: Buffer.from(saltB64, 'base64'),
    hash: Buffer.from(hashB64, 'base64')
  })

  return {
    email: user.email,
    email_verified: true,
    given_name: user.additionalDetails?.firstName,
    family_name: user.additionalDetails?.lastName,
    picture: user.avatar,

    custom_password_hash: {
      algorithm: 'pbkdf2',
      hash: {
        encoding: 'utf8',
        value: hash2
      }
    }
  }

Also tried doing it manually but gets me the same result

  const hash = `$pbkdf2-sha256$i=100000,l=64$${saltB64.replaceAll('=', '')}$${hashB64.replaceAll('=', '')}`

Everything looks ok during the migration but when I try to login I see this in the dashboard’s logs

  "details": {
    "error": {
      "message": "Password change required.",
      "reason": "Verification failed for the provided custom_password_hash: {'algorithm':'pbkdf2','hash':{'encoding':'utf8','value':'$pbkdf2-sha256$QqblTgpBqA3jvDRl...'},'salt':{'value':''}}"
    }
  },

Figured it out.

Since originally the salt passed to crypto.pbkdf2Sync came from

         const salt = crypto.randomBytes(16).toString('hex')

I had to create the buffer from ascii instead of hex

  const saltBytes = Buffer.from(saltHex, 'ascii')

With this change the passwords started matching

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.