(function (global) {
  "use strict";

  function escapeHtml(s) {
    return String(s ?? "")
      .replace(/&/g, "&amp;")
      .replace(/</g, "&lt;")
      .replace(/>/g, "&gt;")
      .replace(/"/g, "&quot;");
  }

  function createLabMasterPanel() {
    let root = null;
    let recipeId = null;
    let state = null;
    let components = [];
    let profiles = [];
    async function api(path, opts) {
      const resp = await fetch(path, opts);
      const data = await resp.json().catch(() => ({}));
      if (!resp.ok) throw new Error(data.message || "Ошибка API");
      return data;
    }

    async function ensureCatalogs(rationType) {
      const [compResp, profData] = await Promise.all([
        components.length ? Promise.resolve(components) : fetch("/api/components").then((r) => r.json()),
        api(`/api/lab/animal-profiles${rationType ? `?ration_type=${encodeURIComponent(rationType)}` : ""}`),
      ]);
      if (Array.isArray(compResp)) components = compResp;
      profiles = profData.profiles || [];
    }

    async function loadRecipes() {
      const data = await api("/api/lab/recipes");
      return data.recipes || [];
    }

    async function loadRation(id) {
      return api(`/api/lab/rations/${encodeURIComponent(id)}`);
    }

    function componentOptionsHtml(selectedId) {
      const opts = ['<option value="">— компонент —</option>'];
      components.forEach((c) => {
        const sel = String(c.id) === String(selectedId) ? " selected" : "";
        opts.push(`<option value="${escapeHtml(c.id)}"${sel}>${escapeHtml(c.name)}</option>`);
      });
      return opts.join("");
    }

    function profileOptionsHtml(selectedId) {
      const opts = ['<option value="">— профиль норм —</option>'];
      profiles.forEach((p) => {
        const sel = String(p.id) === String(selectedId) ? " selected" : "";
        opts.push(
          `<option value="${escapeHtml(p.id)}"${sel}>${escapeHtml(p.label)} (${escapeHtml(p.rationType)})</option>`
        );
      });
      return opts.join("");
    }

    function render() {
      if (!root) return;
      const indicators = (state?.rationResults?.indicators || []).slice(0, 8);
      const lines = state?.lines || [];
      root.innerHTML =
        `<div class="zt-k-hub-lab">` +
        `<div class="zt-k-hub-lab__toolbar">` +
        `<label class="zt-k-hub-lab__field">Рецепт <select data-lab-recipe-select class="form-select form-select-sm"></select></label>` +
        `<label class="zt-k-hub-lab__field">Профиль <select data-lab-profile-select class="form-select form-select-sm">${profileOptionsHtml(state?.animalProfileId)}</select></label>` +
        `<label class="zt-k-hub-lab__field">Тип <select data-lab-ration-type class="form-select form-select-sm">` +
        `<option value="BEEF" ${state?.rationType === "BEEF" ? "selected" : ""}>Мясное</option>` +
        `<option value="DAIRY" ${state?.rationType === "DAIRY" ? "selected" : ""}>Дойное</option>` +
        `</select></label>` +
        `<button type="button" class="btn btn-sm btn-primary" data-action="lab-recalculate">Пересчёт</button>` +
        `<button type="button" class="btn btn-sm btn-outline-primary" data-action="lab-save">Сохранить</button>` +
        `<button type="button" class="btn btn-sm btn-outline-secondary" data-action="lab-add-line">+ Строка</button>` +
        `<button type="button" class="btn btn-sm btn-outline-secondary" data-action="lab-print-ration" title="Печать рациона">Печать</button>` +
        `<button type="button" class="btn btn-sm btn-outline-secondary" data-action="lab-print-compound" title="Печать комбикорма">Комб.</button>` +
        `</div>` +
        `<div class="zt-k-hub-lab__subtitle">Зоотехнический мастер · ${escapeHtml(state?.recipeName || "")}</div>` +
        `<table class="table table-sm zt-k-hub-lab__table"><thead><tr>` +
        `<th>Компонент WESP</th><th>кг/день</th><th>В рац.</th><th>Комб.</th><th></th></tr></thead><tbody>` +
        (lines.length
          ? lines
              .map(
                (l, i) =>
                  `<tr data-line-idx="${i}">` +
                  `<td><select class="form-select form-select-sm" data-field="componentId">${componentOptionsHtml(l.componentId)}</select></td>` +
                  `<td><input class="form-control form-control-sm" data-field="dailyKg" type="number" step="0.01" value="${l.dailyKg ?? ""}"></td>` +
                  `<td class="text-center"><input type="checkbox" data-field="inRation" ${l.inRation ? "checked" : ""}></td>` +
                  `<td class="text-center"><input type="checkbox" data-field="inCompound" ${l.inCompound ? "checked" : ""}></td>` +
                  `<td><button type="button" class="btn btn-sm btn-link text-danger p-0" data-action="lab-remove-line" data-line-idx="${i}" title="Удалить">&times;</button></td>` +
                  `</tr>`
              )
              .join("")
          : `<tr><td colspan="5" class="text-muted text-center">Нет строк — добавьте или создайте из рецепта</td></tr>`) +
        `</tbody></table>` +
        `<div class="zt-k-hub-lab__indicators">` +
        indicators
          .map(
            (ind) =>
              `<span class="badge bg-light text-dark me-1 mb-1">${escapeHtml(ind.label)}: ${escapeHtml(ind.content)} ${escapeHtml(ind.unit)}</span>`
          )
          .join("") +
        `</div></div>`;

      const sel = root.querySelector("[data-lab-recipe-select]");
      if (sel && sel.options.length === 0) {
        loadRecipes().then((recipes) => {
          sel.innerHTML =
            '<option value="">—</option>' +
            recipes
              .map(
                (r) =>
                  `<option value="${escapeHtml(r.id)}" ${r.id === recipeId ? "selected" : ""}>${escapeHtml(r.name)}</option>`
              )
              .join("");
        });
      }
    }

    async function reload() {
      if (!recipeId) return;
      try {
        state = await loadRation(recipeId);
        await ensureCatalogs(state.rationType);
        if (!state.exists) {
          const ok = await global.WespDialog?.confirm?.(
            "Создать мастер из текущего рецепта?",
            { title: "Мастер рациона" }
          );
          if (ok) {
            await api(`/api/lab/rations/${encodeURIComponent(recipeId)}/seed-from-execution`, {
              method: "POST",
            });
            state = await loadRation(recipeId);
            await ensureCatalogs(state.rationType);
          } else {
            await api(`/api/lab/rations/${encodeURIComponent(recipeId)}/ensure-empty`, {
              method: "POST",
            });
            state = await loadRation(recipeId);
            await ensureCatalogs(state.rationType);
          }
        }
        render();
      } catch (e) {
        global.WespZootechNotify?.createAdapter?.()?.error?.(e.message, { fallback: "Не удалось выполнить операцию" });
      }
    }

    function collectLines() {
      if (!root || !state) return [];
      return (state.lines || []).map((line, i) => {
        const row = root.querySelector(`tr[data-line-idx="${i}"]`);
        if (!row) return line;
        const componentId = row.querySelector('[data-field="componentId"]')?.value || null;
        const comp = components.find((c) => String(c.id) === String(componentId));
        return {
          ...line,
          componentId,
          ingredientName: comp?.name || line.ingredientName,
          dailyKg: parseFloat(row.querySelector('[data-field="dailyKg"]')?.value) || null,
          inRation: row.querySelector('[data-field="inRation"]')?.checked,
          inCompound: row.querySelector('[data-field="inCompound"]')?.checked,
        };
      });
    }

    function collectPayload() {
      const rationType = root.querySelector("[data-lab-ration-type]")?.value || state?.rationType;
      return {
        lines: collectLines(),
        rationType,
        animalProfileId: root.querySelector("[data-lab-profile-select]")?.value || null,
      };
    }

    return {
      mount(el) {
        root = el;
        root.addEventListener("click", async (ev) => {
          const btn = ev.target.closest("[data-action]");
          if (!btn || !recipeId) return;
          const action = btn.getAttribute("data-action");
          try {
            if (action === "lab-add-line") {
              state.lines = [...(state?.lines || []), {
                componentId: "",
                ingredientName: "",
                dailyKg: 0,
                inRation: true,
                inCompound: false,
              }];
              render();
              return;
            }
            if (action === "lab-remove-line") {
              const idx = parseInt(btn.getAttribute("data-line-idx"), 10);
              if (!Number.isNaN(idx)) {
                state.lines = (state.lines || []).filter((_, i) => i !== idx);
                render();
              }
              return;
            }
            if (action === "lab-recalculate") {
              await api(`/api/lab/rations/${encodeURIComponent(recipeId)}/recalculate`, {
                method: "POST",
              });
              await reload();
            }
            if (action === "lab-save") {
              await api(`/api/lab/rations/${encodeURIComponent(recipeId)}`, {
                method: "PUT",
                headers: { "Content-Type": "application/json" },
                body: JSON.stringify(collectPayload()),
              });
              await reload();
              global.WespZootechNotify?.createAdapter?.()?.success?.("Мастер сохранён");
            }
            if (action === "lab-print-ration" || action === "lab-print-compound") {
              const mode = action === "lab-print-compound" ? "compound" : "ration";
              global.open?.(
                `/api/lab/rations/${encodeURIComponent(recipeId)}/print?mode=${mode}`,
                "_blank",
                "noopener"
              );
            }
          } catch (e) {
            global.WespZootechNotify?.createAdapter?.()?.error?.(e.message, { fallback: "Не удалось выполнить операцию" });
          }
        });
        root.addEventListener("change", async (ev) => {
          if (ev.target.matches("[data-lab-recipe-select]")) {
            recipeId = ev.target.value;
            reload();
            return;
          }
          if (ev.target.matches("[data-lab-ration-type]")) {
            const rt = ev.target.value;
            state = { ...state, rationType: rt };
            profiles = [];
            await ensureCatalogs(rt);
            render();
            return;
          }
          if (ev.target.matches("[data-lab-profile-select]")) {
            const profile = profiles.find((p) => String(p.id) === String(ev.target.value));
            if (profile?.rationType) {
              state = { ...state, rationType: profile.rationType, animalProfileId: profile.id };
              const typeSel = root.querySelector("[data-lab-ration-type]");
              if (typeSel) typeSel.value = profile.rationType;
            }
          }
        });
      },
      destroy() {
        root = null;
        state = null;
      },
      reload,
      setRecipeId(id) {
        recipeId = id;
        reload();
      },
    };
  }

  global.WespLabMasterPanel = { createLabMasterPanel };
})(window);
