import { initI18n, onLangChange, t, getLang } from "./i18n";
import { initSidebar } from "./sidebar";
import { projectIndent } from "./project-indent";

interface ChecklistItem {
  labelDE: string;
  labelEN: string;
  noteDE?: string;
  noteEN?: string;
  rule?: string;
}

interface ChecklistGroup {
  titleDE: string;
  titleEN: string;
  items: ChecklistItem[];
}

interface Checklist {
  slug: string;
  titleDE: string;
  titleEN: string;
  descriptionDE: string;
  descriptionEN: string;
  regime: string;
  courtDE: string;
  courtEN: string;
  deadlineDE?: string;
  deadlineEN?: string;
  referenceDE?: string;
  referenceEN?: string;
  groups: ChecklistGroup[];
  // Slice B fields — present on authored entries via the merged
  // catalog response. 'static' templates don't carry these.
  origin?: "static" | "authored";
  visibility?: string;
  owner_email?: string;
  owner_display_name?: string;
}

interface Me {
  id: string;
  email: string;
  display_name: string;
  global_role?: string;
}

interface UserSummary {
  id: string;
  email: string;
  display_name: string;
}

interface PartnerUnit {
  id: string;
  name: string;
}

interface Share {
  id: string;
  checklist_id: string;
  recipient_kind: "user" | "office" | "partner_unit" | "project";
  recipient_label: string;
}

interface ChecklistInstance {
  id: string;
  template_slug: string;
  name: string;
  project_id?: string | null;
  state: Record<string, boolean>;
  created_by: string;
  created_at: string;
  updated_at: string;
  project_reference?: string | null;
  project_title?: string | null;
}

interface AkteSummary {
  id: string;
  reference?: string | null;
  title: string;
  path: string;
}

let template: Checklist | null = null;
let instances: ChecklistInstance[] = [];
let projects: AkteSummary[] = [];
let totalItems = 0;

function esc(s: string): string {
  const d = document.createElement("div");
  d.textContent = s;
  return d.innerHTML;
}

function templateSlug(): string {
  // /checklisten/{slug}
  const parts = window.location.pathname.split("/").filter(Boolean);
  return parts[1] ?? "";
}

async function loadTemplate() {
  const slug = templateSlug();
  const resp = await fetch(`/api/checklists/${encodeURIComponent(slug)}`);
  if (!resp.ok) {
    document.title = "404 — Paliad";
    document.getElementById("checklist-title")!.textContent = t("checklisten.notfound");
    return;
  }
  template = await resp.json();
  if (template) {
    totalItems = template.groups.reduce((n, g) => n + g.items.length, 0);
  }
  renderHeader();
}

async function loadInstances() {
  const slug = templateSlug();
  try {
    const resp = await fetch(`/api/checklists/${encodeURIComponent(slug)}/instances`);
    if (!resp.ok) {
      instances = [];
    } else {
      instances = await resp.json();
    }
  } catch {
    instances = [];
  }
  renderInstances();
}

async function loadAkten() {
  try {
    const resp = await fetch("/api/projects");
    if (resp.ok) projects = await resp.json();
  } catch {
    projects = [];
  }
  renderAkteOptions();
}

function renderHeader() {
  if (!template) return;
  const isEN = getLang() === "en";
  const title = isEN ? template.titleEN : template.titleDE;
  const desc = isEN ? template.descriptionEN : template.descriptionDE;
  const court = isEN ? template.courtEN : template.courtDE;
  const deadline = isEN ? template.deadlineEN : template.deadlineDE;
  const reference = isEN ? template.referenceEN : template.referenceDE;

  document.title = `${title} — Paliad`;
  document.getElementById("checklist-title")!.textContent = title;
  document.getElementById("checklist-subtitle")!.textContent = desc;

  const courtLabel = isEN ? "Court / Authority" : "Gericht / Behörde";
  const deadlineLabel = isEN ? "Deadline" : "Deadline";
  const refLabel = isEN ? "Reference" : "Rechtsgrundlage";
  const regimeLabel = isEN ? "Regime" : "Bereich";
  const itemsLabel = isEN ? "Items" : "Punkte";

  const parts: string[] = [];
  parts.push(`<div class="checklist-meta-item"><dt>${regimeLabel}</dt><dd><span class="checklist-regime checklist-regime-${esc(template.regime)}">${esc(template.regime)}</span></dd></div>`);
  parts.push(`<div class="checklist-meta-item"><dt>${courtLabel}</dt><dd>${esc(court)}</dd></div>`);
  if (deadline) {
    parts.push(`<div class="checklist-meta-item"><dt>${deadlineLabel}</dt><dd>${esc(deadline)}</dd></div>`);
  }
  if (reference) {
    parts.push(`<div class="checklist-meta-item"><dt>${refLabel}</dt><dd>${esc(reference)}</dd></div>`);
  }
  parts.push(`<div class="checklist-meta-item"><dt>${itemsLabel}</dt><dd>${totalItems}</dd></div>`);
  document.getElementById("checklist-meta")!.innerHTML = parts.join("");
}

function progress(inst: ChecklistInstance): { done: number; pct: number } {
  const done = Object.values(inst.state || {}).filter(Boolean).length;
  const pct = totalItems === 0 ? 0 : Math.round((done / totalItems) * 100);
  return { done, pct };
}

function formatDate(iso: string): string {
  const d = new Date(iso);
  if (isNaN(d.getTime())) return "";
  const lang = getLang();
  return d.toLocaleDateString(lang === "en" ? "en-GB" : "de-DE", {
    year: "numeric", month: "2-digit", day: "2-digit",
  });
}

function renderInstances() {
  const loading = document.getElementById("instances-loading")!;
  const empty = document.getElementById("instances-empty")!;
  const wrap = document.getElementById("instances-tablewrap")!;
  const body = document.getElementById("instances-body")!;

  loading.style.display = "none";

  if (instances.length === 0) {
    empty.style.display = "";
    wrap.style.display = "none";
    return;
  }
  empty.style.display = "none";
  wrap.style.display = "";

  const isEN = getLang() === "en";
  const deleteLabel = isEN ? "Delete" : "Löschen";
  const openLabel = isEN ? "Öffnen" : "Öffnen";
  const personalLabel = isEN ? "personal" : "persönlich";

  body.innerHTML = instances.map((inst) => {
    const { done, pct } = progress(inst);
    const akteCell = inst.project_id && inst.project_reference
      ? `<a href="/projects/${esc(inst.project_id)}" class="checklist-instance-project-link">${esc(inst.project_reference)}</a>`
      : `<span class="entity-muted">${personalLabel}</span>`;
    return `<tr data-id="${esc(inst.id)}" class="checklist-instance-row">
      <td><a href="/checklists/instances/${esc(inst.id)}" class="checklist-instance-name">${esc(inst.name)}</a></td>
      <td>
        <div class="checklist-progress-inline">
          <div class="checklist-progress-bar">
            <div class="checklist-progress-fill" style="width:${pct}%"></div>
          </div>
          <span class="checklist-progress-label">${done} / ${totalItems}</span>
        </div>
      </td>
      <td>${akteCell}</td>
      <td>${esc(formatDate(inst.created_at))}</td>
      <td class="checklist-instance-actions">
        <a class="btn-small btn-ghost" href="/checklists/instances/${esc(inst.id)}">${esc(openLabel)}</a>
        <button type="button" class="btn-small btn-ghost btn-delete-instance" data-id="${esc(inst.id)}" data-name="${esc(inst.name)}">${esc(deleteLabel)}</button>
      </td>
    </tr>`;
  }).join("");

  body.querySelectorAll<HTMLButtonElement>(".btn-delete-instance").forEach((btn) => {
    btn.addEventListener("click", (e) => {
      e.preventDefault();
      e.stopPropagation();
      const id = btn.dataset.id!;
      const name = btn.dataset.name ?? "";
      const msg = (t("checklisten.instances.delete.confirm") || "").replace("{name}", name);
      if (!confirm(msg)) return;
      void deleteInstance(id);
    });
  });

  body.querySelectorAll<HTMLTableRowElement>(".checklist-instance-row").forEach((row) => {
    const id = row.dataset.id!;
    row.addEventListener("click", (e) => {
      const target = e.target as HTMLElement;
      if (target.closest("a") || target.closest("button")) return;
      window.location.href = `/checklists/instances/${id}`;
    });
  });
}

function renderAkteOptions() {
  const sel = document.getElementById("new-instance-project") as HTMLSelectElement;
  if (!sel) return;
  const none = sel.querySelector('option[value=""]');
  sel.innerHTML = "";
  if (none) sel.appendChild(none);
  projects.forEach((a) => {
    const opt = document.createElement("option");
    opt.value = a.id;
    opt.textContent = `${projectIndent(a.path)}${a.reference || ""} — ${a.title}`;
    sel.appendChild(opt);
  });
}

function initNewInstance() {
  const modal = document.getElementById("new-instance-modal")!;
  const form = document.getElementById("new-instance-form")! as HTMLFormElement;
  const msg = document.getElementById("new-instance-msg")!;
  const nameInput = document.getElementById("new-instance-name") as HTMLInputElement;
  const akteSel = document.getElementById("new-instance-project") as HTMLSelectElement;

  const open = () => {
    msg.textContent = "";
    msg.className = "form-msg";
    nameInput.value = "";
    akteSel.value = "";
    modal.style.display = "flex";
    nameInput.focus();
  };
  const close = () => { modal.style.display = "none"; };

  document.getElementById("btn-new-instance")!.addEventListener("click", open);
  document.getElementById("new-instance-close")!.addEventListener("click", close);
  document.getElementById("new-instance-cancel")!.addEventListener("click", close);
  modal.addEventListener("click", (e) => { if (e.target === e.currentTarget) close(); });

  form.addEventListener("submit", async (e) => {
    e.preventDefault();
    const name = nameInput.value.trim();
    if (!name) {
      msg.textContent = t("checklisten.newInstance.error.name");
      msg.className = "form-msg form-msg-error";
      return;
    }
    const akteID = akteSel.value || null;
    const payload: { name: string; project_id?: string } = { name };
    if (akteID) payload.project_id = akteID;

    const slug = templateSlug();
    const submitBtn = form.querySelector(".btn-primary") as HTMLButtonElement;
    submitBtn.disabled = true;
    try {
      const resp = await fetch(`/api/checklists/${encodeURIComponent(slug)}/instances`, {
        method: "POST",
        headers: { "Content-Type": "application/json" },
        body: JSON.stringify(payload),
      });
      if (!resp.ok) {
        msg.textContent = t("checklisten.newInstance.error.generic");
        msg.className = "form-msg form-msg-error";
        return;
      }
      const created = await resp.json() as ChecklistInstance;
      window.location.href = `/checklists/instances/${encodeURIComponent(created.id)}`;
    } catch {
      msg.textContent = t("checklisten.newInstance.error.generic");
      msg.className = "form-msg form-msg-error";
    } finally {
      submitBtn.disabled = false;
    }
  });
}

async function deleteInstance(id: string) {
  try {
    const resp = await fetch(`/api/checklist-instances/${encodeURIComponent(id)}`, { method: "DELETE" });
    if (!resp.ok && resp.status !== 204) {
      alert(t("checklisten.instances.delete.error"));
      return;
    }
    instances = instances.filter((i) => i.id !== id);
    renderInstances();
  } catch {
    alert(t("checklisten.instances.delete.error"));
  }
}

function initFeedback() {
  const modal = document.getElementById("feedback-modal")!;
  const form = document.getElementById("feedback-form")!;
  const msg = document.getElementById("feedback-msg")!;

  document.getElementById("btn-feedback")!.addEventListener("click", () => {
    msg.textContent = "";
    msg.className = "form-msg";
    modal.style.display = "flex";
  });

  document.getElementById("modal-close")!.addEventListener("click", () => { modal.style.display = "none"; });
  document.getElementById("modal-cancel")!.addEventListener("click", () => { modal.style.display = "none"; });
  modal.addEventListener("click", (e) => { if (e.target === e.currentTarget) modal.style.display = "none"; });

  form.addEventListener("submit", async (e) => {
    e.preventDefault();
    if (!template) return;
    const submitBtn = form.querySelector(".btn-submit") as HTMLButtonElement;
    const payload = {
      feedback_type: (document.getElementById("feedback-type") as HTMLSelectElement).value,
      checklist: template.slug,
      message: (document.getElementById("feedback-message") as HTMLTextAreaElement).value.trim(),
    };

    if (!payload.message) {
      msg.textContent = t("checklisten.feedback.error.required");
      msg.className = "form-msg form-msg-error";
      return;
    }

    submitBtn.disabled = true;
    try {
      const resp = await fetch("/api/checklists/feedback", {
        method: "POST",
        headers: { "Content-Type": "application/json" },
        body: JSON.stringify(payload),
      });
      if (!resp.ok) {
        msg.textContent = t("checklisten.feedback.error.generic");
        msg.className = "form-msg form-msg-error";
        return;
      }
      msg.textContent = t("checklisten.feedback.success");
      msg.className = "form-msg form-msg-success";
      (document.getElementById("feedback-message") as HTMLTextAreaElement).value = "";
      setTimeout(() => { modal.style.display = "none"; }, 1500);
    } catch {
      msg.textContent = t("checklisten.feedback.error.generic");
      msg.className = "form-msg form-msg-error";
    } finally {
      submitBtn.disabled = false;
    }
  });
}

function rerenderAll() {
  renderHeader();
  renderInstances();
}

// --- Slice B: owner actions + admin promote + share modal ----------------

let me: Me | null = null;
let isOwner = false;
let isAdmin = false;
let shareUsers: UserSummary[] = [];
let sharePartnerUnits: PartnerUnit[] = [];
let shareProjects: AkteSummary[] = [];
let activeShareKind: "user" | "office" | "partner_unit" | "project" = "user";

async function loadMe(): Promise<Me | null> {
  try {
    const resp = await fetch("/api/me");
    if (!resp.ok) return null;
    return await resp.json();
  } catch {
    return null;
  }
}

function templateOriginInfo() {
  return template as unknown as {
    origin?: string;
    visibility?: string;
    owner_email?: string;
    owner_display_name?: string;
  } | null;
}

function applyOwnerControls() {
  const info = templateOriginInfo();
  const isAuthored = info?.origin === "authored";
  const provenance = document.getElementById("checklist-provenance")!;
  if (isAuthored && info?.owner_display_name) {
    provenance.style.display = "";
    provenance.textContent = t("checklisten.detail.authored.by").replace("{author}", info.owner_display_name);
  } else {
    provenance.style.display = "none";
  }

  isOwner = !!(isAuthored && me && info?.owner_email && me.email.toLowerCase() === info.owner_email.toLowerCase());
  isAdmin = !!(me && me.global_role === "global_admin");
  const ownerOnly = (id: string, show: boolean) => {
    const el = document.getElementById(id);
    if (el) (el as HTMLElement).style.display = show ? "" : "none";
  };
  if (template) {
    (document.getElementById("btn-edit-template") as HTMLAnchorElement | null)?.setAttribute(
      "href",
      `/checklists/templates/${encodeURIComponent(template.slug)}/edit`,
    );
  }
  ownerOnly("btn-edit-template", isOwner);
  ownerOnly("btn-share-template", isOwner);
  ownerOnly("btn-delete-template", isOwner);

  // Admin promote/demote — only when an authored template is visible to
  // an admin, and only the appropriate one for the current visibility.
  if (isAuthored && isAdmin) {
    const isGlobal = info?.visibility === "global";
    ownerOnly("btn-promote-template", !isGlobal);
    ownerOnly("btn-demote-template", isGlobal);
  } else {
    ownerOnly("btn-promote-template", false);
    ownerOnly("btn-demote-template", false);
  }
}

function initOwnerActions() {
  document.getElementById("btn-delete-template")?.addEventListener("click", async () => {
    if (!template) return;
    const isEN = getLang() === "en";
    const title = isEN ? template.titleEN : template.titleDE;
    const msg = t("checklisten.detail.delete.confirm").replace("{title}", title);
    if (!window.confirm(msg)) return;
    const resp = await fetch(`/api/checklists/templates/${encodeURIComponent(template.slug)}`, { method: "DELETE" });
    if (!resp.ok) {
      window.alert(t("checklisten.detail.delete.error"));
      return;
    }
    window.location.href = "/checklists?tab=mine";
  });

  document.getElementById("btn-promote-template")?.addEventListener("click", async () => {
    if (!template) return;
    if (!window.confirm(t("checklisten.detail.promote.confirm"))) return;
    const resp = await fetch(`/api/admin/checklists/${encodeURIComponent(template.slug)}/promote`, { method: "POST" });
    if (!resp.ok) {
      window.alert(t("checklisten.detail.promote.error"));
      return;
    }
    window.location.reload();
  });

  document.getElementById("btn-demote-template")?.addEventListener("click", async () => {
    if (!template) return;
    if (!window.confirm(t("checklisten.detail.demote.confirm"))) return;
    const resp = await fetch(`/api/admin/checklists/${encodeURIComponent(template.slug)}/demote`, {
      method: "POST",
      headers: { "Content-Type": "application/json" },
      body: JSON.stringify({ target: "firm" }),
    });
    if (!resp.ok) {
      window.alert(t("checklisten.detail.promote.error"));
      return;
    }
    window.location.reload();
  });
}

async function loadSharePickerData() {
  // Fire all three lookups in parallel — the share modal needs all of
  // them but doesn't depend on their order.
  try {
    const [usersResp, unitsResp, projectsResp] = await Promise.all([
      fetch("/api/users"),
      fetch("/api/partner-units"),
      fetch("/api/projects"),
    ]);
    shareUsers = usersResp.ok ? await usersResp.json() : [];
    sharePartnerUnits = unitsResp.ok ? await unitsResp.json() : [];
    shareProjects = projectsResp.ok ? await projectsResp.json() : [];
  } catch {
    /* leave whatever loaded */
  }
  populateSharePickerOptions();
}

function populateSharePickerOptions() {
  const userSel = document.getElementById("share-user") as HTMLSelectElement;
  if (userSel) {
    userSel.innerHTML = `<option value="">${esc(t("checklisten.share.pick"))}</option>`;
    shareUsers
      .slice()
      .sort((a, b) => a.display_name.localeCompare(b.display_name))
      .forEach((u) => {
        if (me && u.id === me.id) return; // can't share with self
        const opt = document.createElement("option");
        opt.value = u.id;
        opt.textContent = `${u.display_name} (${u.email})`;
        userSel.appendChild(opt);
      });
  }
  const officeSel = document.getElementById("share-office") as HTMLSelectElement;
  if (officeSel) {
    const officeKeys = ["munich", "duesseldorf", "hamburg", "amsterdam", "london", "paris", "milan", "madrid"];
    officeSel.innerHTML = `<option value="">${esc(t("checklisten.share.pick"))}</option>`;
    officeKeys.forEach((k) => {
      const opt = document.createElement("option");
      opt.value = k;
      opt.textContent = k.charAt(0).toUpperCase() + k.slice(1);
      officeSel.appendChild(opt);
    });
  }
  const puSel = document.getElementById("share-partner-unit") as HTMLSelectElement;
  if (puSel) {
    puSel.innerHTML = `<option value="">${esc(t("checklisten.share.pick"))}</option>`;
    sharePartnerUnits
      .slice()
      .sort((a, b) => a.name.localeCompare(b.name))
      .forEach((u) => {
        const opt = document.createElement("option");
        opt.value = u.id;
        opt.textContent = u.name;
        puSel.appendChild(opt);
      });
  }
  const prSel = document.getElementById("share-project") as HTMLSelectElement;
  if (prSel) {
    prSel.innerHTML = `<option value="">${esc(t("checklisten.share.pick"))}</option>`;
    shareProjects
      .slice()
      .sort((a, b) => (a.reference || a.title).localeCompare(b.reference || b.title))
      .forEach((p) => {
        const opt = document.createElement("option");
        opt.value = p.id;
        opt.textContent = `${p.reference || ""} — ${p.title}`;
        prSel.appendChild(opt);
      });
  }
}

function switchShareKind(kind: "user" | "office" | "partner_unit" | "project") {
  activeShareKind = kind;
  document.querySelectorAll<HTMLButtonElement>("#share-kind-pills .filter-pill").forEach((p) => {
    p.classList.toggle("active", p.dataset.kind === kind);
  });
  document.querySelectorAll<HTMLElement>(".share-kind-section").forEach((s) => {
    s.style.display = s.dataset.kind === kind ? "" : "none";
  });
}

function initShareModal() {
  const modal = document.getElementById("share-modal")!;
  const msg = document.getElementById("share-msg")!;
  const close = () => { modal.style.display = "none"; };

  document.getElementById("btn-share-template")?.addEventListener("click", async () => {
    if (!template) return;
    msg.textContent = "";
    msg.className = "form-msg";
    switchShareKind("user");
    modal.style.display = "flex";
    await loadSharePickerData();
    await renderGrants();
  });

  document.getElementById("share-close")?.addEventListener("click", close);
  document.getElementById("share-cancel")?.addEventListener("click", close);
  modal.addEventListener("click", (e) => { if (e.target === e.currentTarget) close(); });

  document.getElementById("share-kind-pills")?.addEventListener("click", (e) => {
    const btn = (e.target as HTMLElement).closest<HTMLButtonElement>(".filter-pill[data-kind]");
    if (!btn) return;
    switchShareKind(btn.dataset.kind as typeof activeShareKind);
  });

  document.getElementById("share-submit")?.addEventListener("click", async () => {
    if (!template) return;
    const input: Record<string, unknown> = { recipient_kind: activeShareKind };
    switch (activeShareKind) {
      case "user": {
        const v = (document.getElementById("share-user") as HTMLSelectElement).value;
        if (!v) { msg.textContent = t("checklisten.share.error.pick"); msg.className = "form-msg form-msg-error"; return; }
        input["recipient_user_id"] = v;
        break;
      }
      case "office": {
        const v = (document.getElementById("share-office") as HTMLSelectElement).value;
        if (!v) { msg.textContent = t("checklisten.share.error.pick"); msg.className = "form-msg form-msg-error"; return; }
        input["recipient_office"] = v;
        break;
      }
      case "partner_unit": {
        const v = (document.getElementById("share-partner-unit") as HTMLSelectElement).value;
        if (!v) { msg.textContent = t("checklisten.share.error.pick"); msg.className = "form-msg form-msg-error"; return; }
        input["recipient_partner_unit_id"] = v;
        break;
      }
      case "project": {
        const v = (document.getElementById("share-project") as HTMLSelectElement).value;
        if (!v) { msg.textContent = t("checklisten.share.error.pick"); msg.className = "form-msg form-msg-error"; return; }
        input["recipient_project_id"] = v;
        break;
      }
    }
    const resp = await fetch(`/api/checklists/templates/${encodeURIComponent(template.slug)}/shares`, {
      method: "POST",
      headers: { "Content-Type": "application/json" },
      body: JSON.stringify(input),
    });
    if (!resp.ok) {
      let errMsg = t("checklisten.share.error.generic");
      try {
        const j = await resp.json();
        if (j?.error) errMsg = j.error;
      } catch { /* keep generic */ }
      msg.textContent = errMsg;
      msg.className = "form-msg form-msg-error";
      return;
    }
    msg.textContent = t("checklisten.share.success");
    msg.className = "form-msg form-msg-success";
    await renderGrants();
  });
}

async function renderGrants() {
  if (!template) return;
  const list = document.getElementById("share-grants-list")!;
  const empty = document.getElementById("share-grants-empty")!;
  const resp = await fetch(`/api/checklists/templates/${encodeURIComponent(template.slug)}/shares`);
  const rows: Share[] = resp.ok ? await resp.json() : [];
  if (rows.length === 0) {
    list.innerHTML = "";
    list.appendChild(empty);
    empty.style.display = "";
    return;
  }
  empty.style.display = "none";
  list.innerHTML = rows.map((s) => {
    const kindLabel = esc(t(("checklisten.share.grants.recipient." + s.recipient_kind) as never) || s.recipient_kind);
    return `<li class="share-grant-row" data-id="${esc(s.id)}">
      <span class="share-grant-kind">${kindLabel}</span>
      <span class="share-grant-label">${esc(s.recipient_label || "")}</span>
      <button type="button" class="btn-small btn-ghost" data-action="revoke" data-id="${esc(s.id)}">${esc(t("checklisten.share.grants.revoke"))}</button>
    </li>`;
  }).join("");
  list.querySelectorAll<HTMLButtonElement>("button[data-action=revoke]").forEach((btn) => {
    btn.addEventListener("click", async () => {
      if (!window.confirm(t("checklisten.share.grants.revoke.confirm"))) return;
      const resp = await fetch(`/api/checklists/shares/${encodeURIComponent(btn.dataset.id!)}`, { method: "DELETE" });
      if (!resp.ok && resp.status !== 204) {
        window.alert(t("checklisten.share.grants.revoke.error"));
        return;
      }
      await renderGrants();
    });
  });
}

document.addEventListener("DOMContentLoaded", () => {
  initI18n();
  initSidebar();
  initNewInstance();
  initFeedback();
  initOwnerActions();
  initShareModal();
  onLangChange(rerenderAll);
  void (async () => {
    me = await loadMe();
    await loadTemplate();
    applyOwnerControls();
  })();
  void loadInstances();
  void loadAkten();
});
