import apiService from './apiService';
import API_CONFIG from '../config/api';

export interface CommentData {
  name: string;
  owner: string;
  creation: string;
  modified: string;
  modified_by: string;
  comment_type: string;
  comment_email: string;
  comment_by: string;
  content: string;
  reference_doctype: string;
  reference_name: string;
  published: number;
  seen: number;
}

export interface MentionUser {
  name: string;
  full_name: string;
  user_image?: string;
}

async function getCsrfToken(): Promise<string | null> {
  if (typeof window !== 'undefined' && (window as Window & { csrf_token?: string }).csrf_token) {
    return (window as Window & { csrf_token?: string }).csrf_token || null;
  }
  try {
    const data = await apiService.apiCall<string>('/api/method/frappe.sessions.get_csrf_token');
    return data || null;
  } catch {
    return null;
  }
}

const commentService = {
  async getComments(
    referenceDoctype: string,
    referenceName: string
  ): Promise<CommentData[]> {
    const filters = JSON.stringify([
      ['reference_doctype', '=', referenceDoctype],
      ['reference_name', '=', referenceName],
      ['comment_type', 'in', ['Comment', 'Info', 'Edit', 'Attachment', 'Like']],
    ]);
    const fields = JSON.stringify([
      'name', 'owner', 'creation', 'modified', 'modified_by',
      'comment_type', 'comment_email', 'comment_by',
      'content', 'reference_doctype', 'reference_name',
      'published', 'seen',
    ]);

    const res = await apiService.apiCall<any>(
      `/api/resource/Comment?filters=${encodeURIComponent(filters)}&fields=${encodeURIComponent(fields)}&order_by=creation asc&limit_page_length=100`
    );
    return res?.data ?? [];
  },

  async postComment(
    referenceDoctype: string,
    referenceName: string,
    content: string
  ): Promise<CommentData> {
    const baseUrl = API_CONFIG.BASE_URL || '';
    const csrf = await getCsrfToken();
    const headers: Record<string, string> = { 'Content-Type': 'application/json' };
    if (csrf) headers['X-Frappe-CSRF-Token'] = csrf;

    const res = await fetch(`${baseUrl}/api/resource/Comment`, {
      method: 'POST',
      credentials: 'include',
      headers,
      body: JSON.stringify({
        comment_type: 'Comment',
        reference_doctype: referenceDoctype,
        reference_name: referenceName,
        content,
      }),
    });

    if (!res.ok) {
      const err = await res.json().catch(() => ({}));
      throw new Error(err?.exc || err?._server_messages || 'Failed to post comment');
    }

    const json = await res.json();
    return json.data;
  },

  async deleteComment(commentName: string): Promise<void> {
    const baseUrl = API_CONFIG.BASE_URL || '';
    const csrf = await getCsrfToken();
    const headers: Record<string, string> = {};
    if (csrf) headers['X-Frappe-CSRF-Token'] = csrf;

    const res = await fetch(`${baseUrl}/api/resource/Comment/${encodeURIComponent(commentName)}`, {
      method: 'DELETE',
      credentials: 'include',
      headers,
    });

    if (!res.ok) {
      const err = await res.json().catch(() => ({}));
      throw new Error(err?.exc || 'Failed to delete comment');
    }
  },

  async searchUsers(query: string): Promise<MentionUser[]> {
    const baseUrl = API_CONFIG.BASE_URL || '';
    const filters = query
      ? JSON.stringify([
          ['enabled', '=', 1],
          ['user_type', '=', 'System User'],
          ['name', 'like', `%${query}%`],
        ])
      : JSON.stringify([
          ['enabled', '=', 1],
          ['user_type', '=', 'System User'],
        ]);

    const fields = JSON.stringify(['name', 'full_name', 'user_image']);

    const res = await fetch(
      `${baseUrl}/api/resource/User?filters=${encodeURIComponent(filters)}&fields=${encodeURIComponent(fields)}&limit_page_length=20&order_by=full_name asc`,
      { credentials: 'include' }
    );

    if (!res.ok) return [];

    const json = await res.json();
    return (json.data ?? []).filter(
      (u: MentionUser) => u.name !== 'Administrator' && u.name !== 'Guest'
    );
  },

  async getCurrentUser(): Promise<string> {
    const baseUrl = API_CONFIG.BASE_URL || '';
    const res = await fetch(`${baseUrl}/api/method/frappe.auth.get_logged_user`, {
      credentials: 'include',
    });
    const json = await res.json();
    return json.message || '';
  },
};

export default commentService;
