import { BOT_DESCRIPTION_MAX_LENGTH, BOT_NAME_MAX_LENGTH, BOT_TITLE_MAX_LENGTH, type ComputerMode, normalizeCreateBotProfile, } from "@rakazo/contracts"; import { Stack, useRouter } from "expo-router"; import { useState } from "react"; import { Pressable, ScrollView, Text, TextInput } from "react-native"; import { ComputerModePicker } from "../components/computer-mode-picker"; import { type MobileBot, rpc, selectLibrarySpace } from "../lib/api"; import { allowFocusPrompt, scheduleFocusPrompt } from "../lib/focus-prompt"; import { useI18n } from "../lib/i18n"; import { useMobileTokens } from "../lib/native"; export default function NewBot() { const { t } = useI18n(); const tokens = useMobileTokens(); const router = useRouter(); const [name, setName] = useState(""); const [title, setTitle] = useState(""); const [description, setDescription] = useState(""); const [computerMode, setComputerMode] = useState("team"); const [error, setError] = useState(null); const [pending, setPending] = useState(false); function close() { if (router.canDismiss()) { router.dismiss(); return; } if (router.canGoBack()) { router.back(); return; } router.replace("/"); } async function create() { if (!name.trim() || pending) return; setPending(true); setError(null); try { await selectLibrarySpace(); // Failed list is unknown — delay focus rather than treating the bot as first. const existing = await rpc("bots/list").catch(() => null); const isFirstBot = existing !== null && existing.length === 0; const bot = await rpc("bots/create", { ...normalizeCreateBotProfile({ name, title, description }), notifyOnFinish: true, computerMode, }); allowFocusPrompt(bot.id); router.replace({ pathname: "/thread", params: { botId: bot.id, name: bot.name } }); void (async () => { const started = await rpc("onboarding/start", { botId: bot.id }) .then(() => true) .catch(() => false); if (!started) return; scheduleFocusPrompt(bot.id, isFirstBot); })(); } catch (err) { setError(err instanceof Error ? err.message : t("Could not create bot")); } finally { setPending(false); } } return ( <> ( {t("Cancel")} ), }} /> {t("Name")} {t("Title")} {t("Description")} {error ? {error} : null} void create()} disabled={!name.trim() || pending} style={{ marginTop: 24, backgroundColor: tokens.primary, borderRadius: 11, padding: 16, alignItems: "center", opacity: !name.trim() || pending ? 0.4 : 1, }} > {pending ? t("Creating…") : t("Create")} ); }