import crypto from 'node:crypto'

const configuredKey = process.env.MEMBERSHIP_ENCRYPTION_KEY
const fallbackKey = '0000000000000000000000000000000000000000000000000000000000000000'

if (!configuredKey) {
  console.warn('MEMBERSHIP_ENCRYPTION_KEY is not set. Using a development fallback key.')
}

const getKey = () => {
  const key = Buffer.from(configuredKey || fallbackKey, 'hex')
  if (key.length !== 32) {
    throw new Error('MEMBERSHIP_ENCRYPTION_KEY must be 64 hex characters.')
  }
  return key
}

export const encryptField = (value = '') => {
  if (!value) return ''
  const iv = crypto.randomBytes(16)
  const cipher = crypto.createCipheriv('aes-256-gcm', getKey(), iv)
  const encrypted = Buffer.concat([cipher.update(String(value), 'utf8'), cipher.final()])
  const tag = cipher.getAuthTag()
  return `${iv.toString('hex')}:${tag.toString('hex')}:${encrypted.toString('hex')}`
}

export const decryptField = (value = '') => {
  if (!value || !String(value).includes(':')) return value || ''
  const parts = String(value).split(':')
  if (parts.length !== 3 || parts[0].length !== 32 || parts[1].length !== 32) return value

  const [ivHex, tagHex, encryptedHex] = parts
  const decipher = crypto.createDecipheriv('aes-256-gcm', getKey(), Buffer.from(ivHex, 'hex'))
  decipher.setAuthTag(Buffer.from(tagHex, 'hex'))
  return Buffer.concat([
    decipher.update(Buffer.from(encryptedHex, 'hex')),
    decipher.final(),
  ]).toString('utf8')
}

export const encryptMembership = (member) => ({
  ...member,
  fullName: encryptField(member.fullName),
  email: encryptField(member.email || ''),
  phone: encryptField(member.phone || ''),
  signature: encryptField(member.signature || ''),
})

export const decryptMembership = (member) => ({
  ...member,
  fullName: decryptField(member.fullName),
  email: decryptField(member.email || ''),
  phone: decryptField(member.phone || ''),
  signature: decryptField(member.signature || ''),
})
