// app/api/internal/foreign-student/update-appointment-status/[id]/route.js
import pool from '../../../../../../lib/db/db';
import { NextRequest, NextResponse } from 'next/server';
import { RowDataPacket } from 'mysql2';
import jwt from 'jsonwebtoken';
import { z } from 'zod';

type PageProps = {
  params: Promise<{
    id: string;
  }>;
};

// Validation schema
const statusSchema = z.object({
  status: z.enum(['pending', 'confirmed', 'scheduled', 'completed', 'cancelled', 'no_show']),
  notes: z.string().max(1000).optional()
});

export async function POST(
  req: NextRequest,
  { params }: PageProps
) {
  const connection = await pool.getConnection();
  
  try {
    const {id} = await params;
    const appointmentId = id;
    
    if (!appointmentId) {
      connection.release();
      return NextResponse.json(
        { success: false, message: 'Invalid appointment ID' },
        { status: 400 }
      );
    }

    // Get token from cookie
    const token = req.cookies.get('university-token')?.value;
    
    if (!token) {
      connection.release();
      return NextResponse.json(
        { success: false, message: 'Authentication required' },
        { status: 401 }
      );
    }

    // Verify token
    let decoded;
    try {
      decoded = jwt.verify(token, process.env.JWT_SECRET as string);
    } catch (err) {
      connection.release();
      return NextResponse.json(
        { success: false, message: 'Invalid or expired token' },
        { status: 401 }
      );
    }

    // Check if user is authorized (foreign student)
    if (decoded.role !== 'foreign-student') {
      connection.release();
      return NextResponse.json(
        { success: false, message: 'Access denied' },
        { status: 403 }
      );
    }

    const foreignStudentId = decoded.id;
    const body = await req.json();
    
    // Validate input
    const validatedData = statusSchema.parse(body);

    // Start transaction
    await connection.beginTransaction();

    // 1. Check if appointment exists and belongs to this foreign student
    const [appointment] = await connection.query<RowDataPacket[]>(
      `SELECT fsbs.id, fsbs.session_date, fsbs.end_time, fsbs.status,
              s.first_name as student_name, s.email as student_email
       FROM foreign_student_booked_sessions fsbs
       INNER JOIN users s ON fsbs.student_id = s.id
       WHERE fsbs.id = ? AND fsbs.foreign_student_id = ?`,
      [appointmentId, foreignStudentId]
    );

    if (appointment.length === 0) {
      await connection.rollback();
      connection.release();
      return NextResponse.json(
        { success: false, message: 'Appointment not found or access denied' },
        { status: 404 }
      );
    }

    const currentAppointment = appointment[0];

    // 2. Check if confirming appointment - only allow after 1 minute of end time
    if (validatedData.status === 'completed') {
      const now = new Date();
      const appointmentDate = new Date(currentAppointment.session_date);
      const [hours, minutes] = currentAppointment.end_time.split(':');
      appointmentDate.setHours(parseInt(hours), parseInt(minutes), 0, 0);
      
      // Add 1 minute to the end time
      const oneMinuteAfterEnd = new Date(appointmentDate.getTime() + 60000);
      
      if (now < oneMinuteAfterEnd) {
        await connection.rollback();
        connection.release();
        return NextResponse.json(
          { 
            success: false, 
            message: 'Cannot confirm appointment yet. Please wait 1 minute after the session end time.' 
          },
          { status: 400 }
        );
      }
    }

    // 3. Format notes for completed status with feedback
    let notesToStore = validatedData.notes || '';
    if (validatedData.status === 'completed' && validatedData.notes) {
      // Add timestamp and label for feedback
      const now = new Date();
      const timestamp = now.toLocaleString('en-US', {
        year: 'numeric',
        month: 'short',
        day: 'numeric',
        hour: '2-digit',
        minute: '2-digit'
      });
      
      // Check if there are existing notes
      const existingNotes = currentAppointment.notes || '';
      
      if (existingNotes) {
        // Append feedback to existing notes
        notesToStore = `${existingNotes}\n\n--- Feedback (${timestamp}) ---\n${validatedData.notes}`;
      } else {
        // Create new feedback entry
        notesToStore = `--- Feedback (${timestamp}) ---\n${validatedData.notes}`;
      }
    }

    // 4. Update appointment status and notes
    await connection.query(
      `UPDATE foreign_student_booked_sessions 
       SET status = ?, notes = ?, updated_at = NOW()
       WHERE id = ? AND foreign_student_id = ?`,
      [validatedData.status, notesToStore, appointmentId, foreignStudentId]
    );

    // Commit transaction
    await connection.commit();
    connection.release();

    return NextResponse.json({
      success: true,
      message: `Appointment ${validatedData.status} successfully`
    }, { status: 200 });

  } catch (err: any) {
    // Rollback on any error
    if (connection) {
      await connection.rollback();
      connection.release();
    }
    
    console.error('Update appointment status error:', err);
    
    // Zod validation errors
    if (err instanceof z.ZodError) {
      const errors = {};
      err.errors.forEach(error => {
        const path = error.path.join('.');
        errors[path] = error.message;
      });
      
      return NextResponse.json(
        { 
          success: false, 
          message: 'Validation failed', 
          errors 
        },
        { status: 400 }
      );
    }
    
    // Database or other errors
    return NextResponse.json(
      { 
        success: false, 
        message: 'Failed to update appointment status' 
      },
      { status: 500 }
    );
  }
}