import { GROUP_MEMBER_MAX, GROUP_MEMBER_MIN } from "@rakazo/contracts"; import { Stack, useLocalSearchParams, useRouter } from "expo-router"; import { useEffect, useState } from "react"; import { Alert, Pressable, ScrollView, Text, TextInput } from "react-native"; import { BotMemberPicker } from "../components/bot-member-picker"; import { type MobileBot, type MobileGroup, rpc } from "../lib/api"; import { useI18n } from "../lib/i18n"; import { useMobileTokens } from "../lib/native"; export default function GroupSettingsScreen() { const { t } = useI18n(); const tokens = useMobileTokens(); const router = useRouter(); const { groupId } = useLocalSearchParams<{ groupId: string }>(); const [group, setGroup] = useState(null); const [bots, setBots] = useState([]); const [name, setName] = useState(""); const [selected, setSelected] = useState([]); const [error, setError] = useState(null); const [pending, setPending] = useState(false); useEffect(() => { if (!groupId) return; void Promise.all([ rpc("groups/list").then( (groups) => groups.find((row) => row.id === groupId) ?? null, ), rpc("bots/list"), ]) .then(([nextGroup, nextBots]) => { if (!nextGroup) throw new Error(t("Group not found")); setGroup(nextGroup); setName(nextGroup.name); setSelected(nextGroup.members.map((member) => member.botId)); setBots(nextBots.filter((bot) => !bot.archivedAt)); }) .catch((err) => setError(err instanceof Error ? err.message : t("Could not load group"))); }, [groupId]); async function save() { if (!groupId || !group || pending) return; setPending(true); setError(null); try { const input: { groupId: string; name?: string; botIds?: string[] } = { groupId }; if (name.trim() !== group.name) input.name = name.trim(); const memberIds = group.members.map((member) => member.botId).join(","); if (selected.join(",") !== memberIds) input.botIds = selected; if (input.name || input.botIds) await rpc("groups/update", input); router.back(); } catch (err) { setError(err instanceof Error ? err.message : t("Could not save group")); } finally { setPending(false); } } function remove() { if (!groupId || !group) return; Alert.alert(group.name, t("Delete this group? Bots and their solo threads are kept."), [ { text: t("Cancel"), style: "cancel" }, { text: t("Delete"), style: "destructive", onPress: () => void rpc("groups/remove", { groupId }) .then(() => router.replace("/")) .catch((err) => Alert.alert( t("Could not delete group"), err instanceof Error ? err.message : t("Try again."), ), ), }, ]); } return ( <> {t("Name")} {t("Members")} {error ? {error} : null} void save()} disabled={ !name.trim() || selected.length < GROUP_MEMBER_MIN || selected.length > GROUP_MEMBER_MAX || pending } style={{ marginTop: 24, backgroundColor: tokens.primary, opacity: !name.trim() || selected.length < GROUP_MEMBER_MIN || selected.length > GROUP_MEMBER_MAX || pending ? 0.5 : 1, borderRadius: 11, padding: 14, alignItems: "center", }} > {pending ? t("Saving…") : t("Save")} {t("Delete group")} ); }