import type { ErrorRequestHandler, RequestHandler } from 'express';
import { AppError } from '../utils/errors.js';
import { logger } from '../utils/logger.js';
import { describeError } from '../utils/describeError.js';
import { env } from '../config/env.js';

export const notFoundHandler: RequestHandler = (req, res) => {
  res.status(404).json({ error: 'not_found', message: `No route for ${req.method} ${req.path}` });
};

/** Converts thrown errors into a consistent JSON shape; hides internals in prod. */
export const errorHandler: ErrorRequestHandler = (err, _req, res, _next) => {
  if (err instanceof AppError) {
    res.status(err.status).json({ error: err.code, message: err.message, details: err.details });
    return;
  }

  // Body-parser / multer size errors arrive with their own status.
  const status = Number((err as any)?.status ?? (err as any)?.statusCode ?? 500);
  if (status >= 400 && status < 500) {
    res.status(status).json({ error: 'bad_request', message: (err as Error).message });
    return;
  }

  logger.error('unhandled error', { err: describeError(err), stack: (err as Error).stack });
  res.status(500).json({
    error: 'internal_error',
    message: env.isProd ? 'Something went wrong' : describeError(err),
  });
};
