import { ApolloClient, InMemoryCache, createHttpLink, ApolloLink } from '@apollo/client/core';
import { setContext } from '@apollo/client/link/context';
import { API_CONFIG, REQUEST_HEADERS, TEST_CREDENTIALS } from '../config/constants';
import { authManager } from './auth';

// UUID generator that works in non-secure contexts (HTTP)
function generateUUID(): string {
  if (typeof crypto !== 'undefined' && crypto.randomUUID) {
    return crypto.randomUUID();
  }
  // Fallback for non-secure contexts
  return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, (c) => {
    const r = (Math.random() * 16) | 0;
    const v = c === 'x' ? r : (r & 0x3) | 0x8;
    return v.toString(16);
  });
}

const httpLink = createHttpLink({
  uri: API_CONFIG.GRAPHQL_ENDPOINT,
});

// Auth link that adds exact headers from Proxyman capture
const authLink = setContext(async (operation, { headers }) => {
  console.log('GraphQL operation:', operation.operationName);

  let token: string;
  try {
    token = await authManager.getToken();
    console.log('Got auth token, length:', token?.length);
  } catch (err) {
    console.error('Failed to get auth token:', err);
    throw err;
  }

  // Exact headers from Proxyman capture
  const newHeaders = {
    ...headers,
    // From Proxyman: Host header (handled by browser)
    'Accept': REQUEST_HEADERS['Accept'],
    'Accept-Language': REQUEST_HEADERS['Accept-Language'],
    'Accept-Encoding': REQUEST_HEADERS['Accept-Encoding'],
    'Content-Type': REQUEST_HEADERS['Content-Type'],
    'Connection': REQUEST_HEADERS['Connection'],
    'User-Agent': REQUEST_HEADERS['User-Agent'],
    // Auth headers
    'Authorization': `Bearer ${token}`,
    'x-profile-id': TEST_CREDENTIALS.PROFILE_ID,
    // App identification headers - exact from Proxyman
    'x-device-os': REQUEST_HEADERS['x-device-os'],
    'x-app-version': REQUEST_HEADERS['x-app-version'],
    'x-os-version': REQUEST_HEADERS['x-os-version'],
    // Transaction headers
    'x-transaction-id': generateUUID(),
    'x-event-analytics-id': TEST_CREDENTIALS.EVENT_ANALYTICS_ID,
  };

  console.log('Request headers:', Object.keys(newHeaders));
  return { headers: newHeaders };
});

export const apolloClient = new ApolloClient({
  link: ApolloLink.from([authLink, httpLink]),
  cache: new InMemoryCache({
    typePolicies: {
      Profile: {
        keyFields: ['id'],
      },
      Chat: {
        keyFields: ['id'],
      },
      ChatSummary: {
        keyFields: ['id'],
      },
    },
  }),
  defaultOptions: {
    watchQuery: {
      fetchPolicy: 'cache-and-network',
    },
  },
});
