import { readShineUserPda } from './shine-user-pda-service.js';
import {
  defaultServerAddress,
  defaultServerHttp,
  defaultServerLogin,
  defaultServerWs,
} from '../deploy-config.js';

export const DEFAULT_SHINE_SERVER_LOGIN = defaultServerLogin;
export const DEFAULT_SHINE_SERVER_ADDRESS = defaultServerAddress;
export const DEFAULT_SHINE_SERVER_HTTP = defaultServerHttp;
export const DEFAULT_SHINE_SERVER_WS = defaultServerWs;

function normalizeHostLike(value) {
  const raw = String(value || '').trim();
  if (!raw) return '';
  try {
    const withScheme = /^[a-z]+:\/\//i.test(raw) ? raw : `https://${raw}`;
    const parsed = new URL(withScheme);
    return String(parsed.host || '').trim().toLowerCase();
  } catch {
    return raw.replace(/^https?:\/\//i, '').replace(/^wss?:\/\//i, '').replace(/\/.*$/, '').trim().toLowerCase();
  }
}

export function normalizeShineServerLogin(value) {
  return String(value || '').trim().toLowerCase();
}

export function buildShineHttpUrlFromAddress(address) {
  const host = normalizeHostLike(address);
  if (!host) return DEFAULT_SHINE_SERVER_HTTP;
  return `https://${host}`;
}

export function buildShineWsUrlFromAddress(address) {
  const host = normalizeHostLike(address);
  if (!host) return DEFAULT_SHINE_SERVER_WS;
  return `wss://${host}/ws`;
}

export async function resolveShineServerByServerLogin({ serverLogin, solanaEndpoint }) {
  const cleanServerLogin = normalizeShineServerLogin(serverLogin) || DEFAULT_SHINE_SERVER_LOGIN;
  const parsed = await readShineUserPda({
    login: cleanServerLogin,
    solanaEndpoint,
  });
  if (!parsed?.isServer) {
    throw new Error(`Логин @${cleanServerLogin} не опубликован как сервер SHiNE.`);
  }
  const serverAddress = normalizeHostLike(parsed?.serverAddress || '');
  if (!serverAddress) {
    throw new Error(`У server PDA пользователя @${cleanServerLogin} не задан server_address.`);
  }
  return {
    serverLogin: cleanServerLogin,
    serverAddress,
    httpBase: buildShineHttpUrlFromAddress(serverAddress),
    wsUrl: buildShineWsUrlFromAddress(serverAddress),
    userPda: parsed,
  };
}

export async function resolveShineServerForUserLogin({ login, solanaEndpoint, fallbackServerLogin = '' }) {
  const cleanLogin = normalizeShineServerLogin(login);
  if (!cleanLogin) throw new Error('Не указан логин пользователя для поиска сервера доступа.');
  const parsedUser = await readShineUserPda({
    login: cleanLogin,
    solanaEndpoint,
  });
  const accessServers = Array.isArray(parsedUser?.accessServers)
    ? parsedUser.accessServers.map((value) => normalizeShineServerLogin(value)).filter(Boolean)
    : [];
  const pickedServerLogin = accessServers[0] || normalizeShineServerLogin(fallbackServerLogin);
  if (!pickedServerLogin) {
    throw new Error(`У пользователя @${cleanLogin} в PDA не указан access server.`);
  }
  const resolved = await resolveShineServerByServerLogin({
    serverLogin: pickedServerLogin,
    solanaEndpoint,
  });
  return {
    ...resolved,
    accessServerLogin: pickedServerLogin,
    userPda: parsedUser,
  };
}
