feat: add email notification for new leave requests

- mailer.ts: nodemailer transport via local sendmail
- leave-notification.ts: HTML email matching PHP template
- Sends notification to LEAVE_NOTIFY_EMAIL on new leave request
- Non-blocking: errors logged but don't fail the request
- Added LEAVE_NOTIFY_EMAIL and APP_URL env vars

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
BOHA
2026-03-23 11:54:29 +01:00
parent 0baa604ade
commit 8a453deaac
5 changed files with 145 additions and 0 deletions

View File

@@ -7,6 +7,7 @@ import { success, error, parseId } from '../../utils/response';
import { parsePagination, buildPaginationMeta } from '../../utils/pagination';
import { parseBody } from '../../schemas/common';
import { CreateLeaveRequestSchema, ReviewLeaveRequestSchema } from '../../schemas/leave-requests.schema';
import { notifyNewLeaveRequest } from '../../services/leave-notification';
const VALID_LEAVE_TYPES = ['vacation', 'sick', 'unpaid'] as const;
const VALID_REVIEW_STATUSES = ['approved', 'rejected'] as const;
@@ -85,6 +86,22 @@ export default async function leaveRequestsRoutes(fastify: FastifyInstance): Pro
});
await logAudit({ request, authData, action: 'create', entityType: 'leave_request', entityId: leaveRequest.id, description: `Vytvořena žádost o nepřítomnost` });
// Send email notification (non-blocking)
try {
const employeeName = `${authData.firstName} ${authData.lastName}`.trim() || authData.username;
notifyNewLeaveRequest({
leave_type: leaveType,
date_from: body.date_from,
date_to: body.date_to,
total_days: businessDays,
total_hours: businessDays * 8,
notes: body.notes,
}, employeeName).catch(err => request.log.error(err, 'Leave notification error'));
} catch (err) {
request.log.error(err, 'Leave notification error');
}
return success(reply, { id: leaveRequest.id }, 201, 'Žádost byla odeslána ke schválení');
});