// @bun
import {
  select
} from "./chunk-seyt2a5p.js";
import {
  open_default
} from "./chunk-fr1k79kd.js";
import {
  adkLogo
} from "./chunk-5agyx08n.js";
import {
  userInput
} from "./chunk-tefbm840.js";
import {
  getLoginUrl,
  startCallbackServer
} from "./chunk-4cgz94zj.js";
import {
  identifyUser
} from "./chunk-w4a48hxy.js";
import {
  telemetry_default
} from "./chunk-c18d2qwm.js";
import {
  bind,
  box,
  fg,
  getActiveTheme,
  mount,
  onKey,
  router,
  signal,
  t,
  text,
  timeout
} from "./chunk-m2h26j5f.js";
import {
  createCliLogger
} from "./chunk-t993tmz7.js";
import {
  auth
} from "./chunk-7krp2mgz.js";

// src/components/loading-box.ts
function loadingBox(ctx, props = {}, children = []) {
  const {
    width = 80,
    borderColor = getActiveTheme().ui.border,
    borderStyle = "rounded",
    paddingX = 1,
    paddingY,
    marginBottom,
    minHeight
  } = props;
  return box(ctx, {
    border: true,
    borderStyle,
    borderColor,
    width,
    paddingX,
    paddingY,
    marginBottom,
    minHeight
  }, children);
}

// src/commands/adk-login.ts
import { spawn } from "child_process";
var flushTelemetry = () => Promise.race([telemetry_default.shutdown(), new Promise((resolve) => setTimeout(resolve, 2000))]).catch(() => {});
function loginView(renderer, scope, deps) {
  const { options, onSuccess, onCancel } = deps;
  const theme = getActiveTheme();
  const view = signal(options.profile ? "select-method" : "loading-profiles");
  const loginUrl = signal(undefined);
  let existingProfiles = [];
  let chosenProfile = options.profile;
  let errorMsg = "";
  let callbackCancel = null;
  const eff = () => ({ ...options, profile: chosenProfile });
  if (!options.profile) {
    (async () => {
      const profiles = await auth.listProfiles();
      if (profiles.length === 0) {
        chosenProfile = "default";
        view.set("select-method");
      } else {
        existingProfiles = profiles;
        view.set("select-profile");
      }
    })();
  }
  const handleProfileSelected = (profileName) => {
    chosenProfile = profileName;
    view.set("select-method");
  };
  const handleBrowserLogin = async () => {
    errorMsg = "";
    view.set("browser-waiting");
    try {
      const { url: callbackUrl, waitForToken, cancel } = await startCallbackServer({ timeout: 300000 });
      callbackCancel = cancel;
      const url = getLoginUrl(callbackUrl, eff().apiUrl);
      loginUrl.set(url);
      if (process.platform === "win32") {
        const cp = spawn("cmd", ["/c", "start", "", url], { detached: true, stdio: "ignore" });
        cp.unref();
      } else {
        await open_default(url);
      }
      const result = await waitForToken();
      callbackCancel = null;
      if (!result.success || !result.token) {
        if (view() !== "browser-waiting")
          return;
        errorMsg = "Login timed out. Please try again.";
        view.set("select-method");
        return;
      }
      view.set("authenticating");
      await auth.login(result.token, { profile: chosenProfile, apiUrl: eff().apiUrl });
      await identifyUser().catch(() => {});
      view.set("success");
    } catch (error) {
      callbackCancel = null;
      errorMsg = error instanceof Error ? error.message : "Browser login failed";
      view.set("select-method");
    }
  };
  const handleTokenSubmit = async (token) => {
    view.set("authenticating");
    errorMsg = "";
    try {
      await auth.login(token, { profile: chosenProfile, apiUrl: eff().apiUrl });
      await identifyUser().catch(() => {});
      view.set("success");
    } catch (error) {
      errorMsg = error instanceof Error ? error.message : "Login failed";
      view.set("manual-entry");
    }
  };
  const logo = () => adkLogo(renderer, {
    subtitle: "Login",
    logoColor: theme.accent.purple,
    titleColor: theme.text.primary,
    subtitleColor: theme.text.dim
  });
  const body = router(renderer, scope, view, (v, viewScope) => {
    if (v === "loading-profiles") {
      return box(renderer, { flexDirection: "column" }, [
        loadingBox(renderer, {}, [text(renderer, t`${fg(theme.text.dim)("Loading profiles\u2026")}`)])
      ]);
    }
    if (v === "select-profile") {
      const profileOptions = [
        ...existingProfiles.map((p) => ({
          id: p.name,
          label: p.name,
          value: p.name,
          description: p.apiUrl.replace("https://", "")
        })),
        {
          id: "__new__",
          label: "Create new profile",
          value: "__new__",
          description: "Save login under a new profile name"
        }
      ];
      return box(renderer, { flexDirection: "column" }, [
        logo(),
        text(renderer, t`${fg(theme.text.dim)("Which profile should these credentials be saved to?")}`),
        select(renderer, viewScope, {
          options: profileOptions,
          onSubmit: (value) => {
            if (value === "__new__")
              view.set("new-profile");
            else
              handleProfileSelected(value);
          },
          onCancel
        })
      ]);
    }
    if (v === "new-profile") {
      return box(renderer, { flexDirection: "column" }, [
        logo(),
        text(renderer, t`${fg(theme.text.dim)("Enter a name for the new profile")}`),
        box(renderer, { marginTop: 1 }, [
          userInput(renderer, viewScope, {
            prompt: "Profile name:",
            placeholder: "e.g. staging, production",
            validate: (value) => value.trim() ? null : "Profile name is required",
            onSubmit: (value) => handleProfileSelected(value.trim()),
            onCancel: () => view.set("select-profile")
          })
        ])
      ]);
    }
    if (v === "browser-waiting") {
      const urlLine = text(renderer, "");
      viewScope.add(bind(() => {
        const url = loginUrl();
        urlLine.content = url ? t`${fg(theme.text.dim)("If the browser didn't open, visit:")}\n${fg(theme.text.link)(url)}` : t``;
      }, [loginUrl]));
      viewScope.add(onKey(renderer, (key) => {
        if (key.name === "escape") {
          callbackCancel?.();
          callbackCancel = null;
          view.set("select-method");
        }
      }));
      return box(renderer, { flexDirection: "column" }, [
        logo(),
        text(renderer, t`${fg(theme.text.dim)("Waiting for browser authentication...")}`),
        box(renderer, { marginTop: 1 }, [
          loadingBox(renderer, {}, [text(renderer, t`${fg(theme.text.dim)("Opening browser\u2026")}`)])
        ]),
        box(renderer, { marginTop: 1, flexDirection: "column" }, [urlLine]),
        box(renderer, { marginTop: 1 }, [
          text(renderer, t`${fg(theme.text.dim)("Press Esc to cancel \u2022 Ctrl-C to quit")}`)
        ])
      ]);
    }
    if (v === "manual-entry") {
      const children2 = [
        logo(),
        text(renderer, t`${fg(theme.text.dim)("Enter your Botpress Personal Access Token")}`),
        box(renderer, { marginTop: 1, flexDirection: "column" }, [
          userInput(renderer, viewScope, {
            prompt: "Enter your Botpress API token:",
            placeholder: "bp_xxx...",
            type: "password",
            validate: (value) => value.trim() ? null : "Token is required",
            onSubmit: (value) => handleTokenSubmit(value),
            onCancel: () => view.set("select-method")
          })
        ])
      ];
      if (errorMsg)
        children2.push(text(renderer, t`${fg(theme.status.error)(errorMsg)}`));
      return box(renderer, { flexDirection: "column" }, children2);
    }
    if (v === "authenticating") {
      return box(renderer, { flexDirection: "column" }, [
        loadingBox(renderer, {}, [text(renderer, t`${fg(theme.text.dim)("Authenticating\u2026")}`)])
      ]);
    }
    if (v === "success") {
      const userLine = text(renderer, t`${fg(theme.text.primary)("Logged in as Loading...")}`);
      auth.getCurrentProfileDetails().then((details) => {
        const userDisplay = details?.displayName ? `${details.displayName} (${details.email})` : details?.email || "Unknown user";
        userLine.content = t`${fg(theme.text.primary)(`Logged in as ${userDisplay}`)}`;
      });
      timeout(viewScope, 1500, onSuccess);
      return box(renderer, { flexDirection: "column" }, [
        text(renderer, t`${fg(theme.status.success)(`${theme.symbols.checkmark} Successfully logged in to Botpress`)}`),
        userLine,
        text(renderer, t`${fg(theme.text.dim)(`Profile: ${eff().profile || "default"}`)}`),
        text(renderer, t`${fg(theme.text.dim)(`API URL: ${eff().apiUrl || "https://api.botpress.cloud"}`)}`)
      ]);
    }
    const children = [
      logo(),
      text(renderer, t`${fg(theme.text.dim)("Log in to Botpress")}`),
      select(renderer, viewScope, {
        options: [
          { id: "browser", label: "Continue with Browser", value: "browser" },
          { id: "pat", label: "Continue with Personal Access Token (PAT)", value: "pat" }
        ],
        onSubmit: (value) => {
          if (value === "browser")
            handleBrowserLogin();
          else
            view.set("manual-entry");
        },
        onCancel: () => {
          if (existingProfiles.length > 0)
            view.set("select-profile");
          else
            onCancel();
        }
      })
    ];
    if (errorMsg) {
      children.push(box(renderer, { marginTop: 1 }, [text(renderer, t`${fg(theme.status.error)(errorMsg)}`)]));
    }
    return box(renderer, { flexDirection: "column" }, children);
  });
  return body;
}
var adkLogin = async (options = {}) => {
  const logger = createCliLogger();
  const token = options.token || process.env.BOTPRESS_TOKEN;
  const nonInteractiveProfile = options.profile || "default";
  if (token && (!process.stdout.isTTY || options.token)) {
    try {
      await auth.login(token, { ...options, profile: nonInteractiveProfile });
      await identifyUser().catch(() => {});
      logger.info("\u2713 Successfully logged in to Botpress", "green");
      const profileDetails = await auth.getCurrentProfileDetails();
      const userDisplay = profileDetails?.displayName ? `${profileDetails.displayName} (${profileDetails.email})` : profileDetails?.email || "Unknown user";
      logger.info(`Logged in as ${userDisplay}`);
      logger.info(`Profile: ${nonInteractiveProfile}`, "gray");
      logger.info(`API URL: ${options.apiUrl || "https://api.botpress.cloud"}`, "gray");
      return;
    } catch (error) {
      logger.fatal(error);
    }
  }
  return new Promise((resolve, reject) => {
    let appRef = null;
    const onSuccess = () => {
      appRef?.unmount();
      if (options.exitAfterLogin === false) {
        resolve();
      } else {
        flushTelemetry().finally(() => process.exit(0));
      }
    };
    const onCancel = () => {
      appRef?.unmount();
      logger.info("Login cancelled.", "yellow");
      flushTelemetry().finally(() => {
        if (options.exitAfterLogin === false)
          reject(new Error("Login cancelled"));
        else
          process.exit(0);
      });
    };
    mount((renderer, scope) => loginView(renderer, scope, { options, onSuccess, onCancel }), {
      exitOnCtrlC: true
    }).then((app) => {
      appRef = app;
    }, reject);
  });
};

export { adkLogin };
