import { getDb, withTransaction } from '../utils/db.js' import { requireAuth } from '../utils/authHelpers.js' import { hashPassword } from '../utils/password.js' const ROLES = ['admin', 'leader', 'member'] export default defineEventHandler(async (event) => { requireAuth(event, { role: 'admin' }) const body = await readBody(event) const identifier = body?.identifier?.trim() const password = body?.password const role = body?.role if (!identifier || identifier.length < 1) { throw createError({ statusCode: 400, message: 'identifier required' }) } if (typeof password !== 'string' || password.length < 1) { throw createError({ statusCode: 400, message: 'password required' }) } if (!role || !ROLES.includes(role)) { throw createError({ statusCode: 400, message: 'role must be admin, leader, or member' }) } const db = await getDb() return withTransaction(db, async ({ run, get }) => { const existing = await get('SELECT id FROM users WHERE identifier = ?', [identifier]) if (existing) { throw createError({ statusCode: 409, message: 'Identifier already in use' }) } const id = crypto.randomUUID() const now = new Date().toISOString() await run( 'INSERT INTO users (id, identifier, password_hash, role, created_at, auth_provider, oidc_issuer, oidc_sub) VALUES (?, ?, ?, ?, ?, ?, ?, ?)', [id, identifier, hashPassword(password), role, now, 'local', null, null], ) const user = await get('SELECT id, identifier, role, auth_provider FROM users WHERE id = ?', [id]) return user }) })