test(e2e): seed hashed user tokens in TokenFactory (GHSA-r6w9-259g-gwrv)

Reset/confirm/deletion tokens (kinds 1-3) are now stored as a SHA-256 hash and
looked up by hash, so the e2e factory must seed the hash while returning the
plaintext to the test. Kind 4 (caldav/bcrypt) is seeded verbatim.
This commit is contained in:
kolaente
2026-07-19 18:59:34 +02:00
parent 6895a7765e
commit e31ea2de50
2 changed files with 23 additions and 2 deletions
+15 -1
View File
@@ -1,3 +1,4 @@
import {createHash} from 'node:crypto'
import {faker} from '@faker-js/faker'
import {Factory} from '../support/factory'
@@ -26,4 +27,17 @@ export class TokenFactory extends Factory {
...(attrs ?? {}),
}
}
}
// The API stores reset/confirm/deletion tokens (kinds 1-3) as a SHA-256 hash
// and looks them up by that hash; caldav tokens (kind 4) use bcrypt and are
// seeded verbatim. Seed the hash so the plaintext token the test uses still
// resolves server-side (matches pkg/user/token.go hashUserToken).
static transformForSeed(item: Record<string, unknown>): Record<string, unknown> {
const kind = item.kind as number
if (typeof item.token === 'string' && kind >= 1 && kind <= 3) {
return {...item, token: createHash('sha256').update(item.token).digest('hex')}
}
return item
}
}
+8 -1
View File
@@ -15,6 +15,13 @@ export class Factory {
return {}
}
// Hook to transform a row just before it is seeded to the DB. The returned
// data (from create()) keeps the original values; only what is written to the
// database is transformed. Default: identity.
static transformForSeed(item: Record<string, unknown>): Record<string, unknown> {
return item
}
/**
* Seeds a bunch of fake data into the database.
*
@@ -61,7 +68,7 @@ export class Factory {
}
// Skip arrays, objects, and other complex types
}
return flatItem
return this.transformForSeed(flatItem)
})
await this.seed(this.table, flatData, truncate)