function normalizeServerUrl(serverUrl) {
  return serverUrl.trim().replace(/\/+$/, "");
}

export function buildApiBaseUrl(serverUrl) {
  const normalized = normalizeServerUrl(serverUrl);
  return normalized.endsWith("/api/v1") ? normalized : `${normalized}/api/v1`;
}

export function buildHeaders(serverConfig) {
  const headers = {
    Accept: "application/json",
  };

  if (serverConfig.authMethod === "token" && serverConfig.token) {
    headers.Authorization = `token ${serverConfig.token}`;
  } else if (
    serverConfig.authMethod === "password" &&
    serverConfig.username &&
    serverConfig.password
  ) {
    headers.Authorization = `Basic ${btoa(
      `${serverConfig.username}:${serverConfig.password}`
    )}`;
  }

  return headers;
}

export async function fetchCurrentUser(serverConfig) {
  const apiBase = buildApiBaseUrl(serverConfig.serverUrl);
  const response = await fetch(`${apiBase}/user`, {
    headers: buildHeaders(serverConfig),
  });
  if (!response.ok) {
    throw new Error(`Gitea API error: ${response.status}`);
  }
  return response.json();
}

export async function fetchRepositories(serverConfig, page = 1, limit = 50) {
  const apiBase = buildApiBaseUrl(serverConfig.serverUrl);
  const url = `${apiBase}/user/repos?page=${page}&limit=${limit}&sort=updated`;
  const response = await fetch(url, {
    headers: buildHeaders(serverConfig),
  });

  if (!response.ok) {
    throw new Error(`Gitea API error: ${response.status}`);
  }
  return response.json();
}

function encodePathSegment(value = "") {
  return encodeURIComponent(value);
}

function encodeRepoPath(path = "") {
  return path
    .split("/")
    .filter(Boolean)
    .map(encodePathSegment)
    .join("/");
}

function splitRepoFullName(fullName = "") {
  const [owner, repo] = fullName.split("/");
  if (!owner || !repo) {
    throw new Error("Repository full name must be in owner/repo format.");
  }
  return { owner, repo };
}

export async function fetchRepoBranches(serverConfig, fullName) {
  const apiBase = buildApiBaseUrl(serverConfig.serverUrl);
  const { owner, repo } = splitRepoFullName(fullName);
  const url = `${apiBase}/repos/${encodePathSegment(owner)}/${encodePathSegment(repo)}/branches`;
  const response = await fetch(url, {
    headers: buildHeaders(serverConfig),
  });

  if (!response.ok) {
    throw new Error(`Gitea API error: ${response.status}`);
  }
  return response.json();
}

export async function fetchRepoContents(serverConfig, fullName, path = "", ref = "") {
  const apiBase = buildApiBaseUrl(serverConfig.serverUrl);
  const { owner, repo } = splitRepoFullName(fullName);
  const encodedPath = encodeRepoPath(path);
  const pathSuffix = encodedPath ? `/${encodedPath}` : "";
  const query = ref ? `?ref=${encodeURIComponent(ref)}` : "";
  const url = `${apiBase}/repos/${encodePathSegment(owner)}/${encodePathSegment(repo)}/contents${pathSuffix}${query}`;
  const response = await fetch(url, {
    headers: buildHeaders(serverConfig),
  });

  if (!response.ok) {
    throw new Error(`Gitea API error: ${response.status}`);
  }
  return response.json();
}
