| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189 |
- import styles from "./auth.module.scss";
- import { IconButton } from "./button";
- import { useState, useEffect } from "react";
- import { useNavigate } from "react-router-dom";
- import { Path, SAAS_CHAT_URL } from "../constant";
- import { useAccessStore } from "../store";
- import Locale from "../locales";
- import Delete from "../icons/close.svg";
- import Arrow from "../icons/arrow.svg";
- import Logo from "../icons/logo.svg";
- import { useMobileScreen } from "@/app/utils";
- import BotIcon from "../icons/bot.svg";
- import { getClientConfig } from "../config/client";
- import { PasswordInput } from "./ui-lib";
- import LeftIcon from "@/app/icons/left.svg";
- import { safeLocalStorage } from "@/app/utils";
- import {
- trackSettingsPageGuideToCPaymentClick,
- trackAuthorizationPageButtonToCPaymentClick,
- } from "../utils/auth-settings-events";
- import clsx from "clsx";
- const storage = safeLocalStorage();
- export function AuthPage() {
- const navigate = useNavigate();
- const accessStore = useAccessStore();
- const goHome = () => navigate(Path.Home);
- const goChat = () => navigate(Path.Chat);
- const goSaas = () => {
- trackAuthorizationPageButtonToCPaymentClick();
- window.location.href = SAAS_CHAT_URL;
- };
- const resetAccessCode = () => {
- accessStore.update((access) => {
- access.openaiApiKey = "";
- access.accessCode = "";
- });
- }; // Reset access code to empty string
- useEffect(() => {
- if (getClientConfig()?.isApp) {
- navigate(Path.Settings);
- }
- // eslint-disable-next-line react-hooks/exhaustive-deps
- }, []);
- return (
- <div className={styles["auth-page"]}>
- <TopBanner></TopBanner>
- <div className={styles["auth-header"]}>
- <IconButton
- icon={<LeftIcon />}
- text={Locale.Auth.Return}
- onClick={() => navigate(Path.Home)}
- ></IconButton>
- </div>
- <div className={clsx("no-dark", styles["auth-logo"])}>
- <BotIcon />
- </div>
- <div className={styles["auth-title"]}>{Locale.Auth.Title}</div>
- <div className={styles["auth-tips"]}>{Locale.Auth.Tips}</div>
- <PasswordInput
- style={{ marginTop: "3vh", marginBottom: "3vh" }}
- aria={Locale.Settings.ShowPassword}
- aria-label={Locale.Auth.Input}
- value={accessStore.accessCode}
- type="text"
- placeholder={Locale.Auth.Input}
- onChange={(e) => {
- accessStore.update(
- (access) => (access.accessCode = e.currentTarget.value),
- );
- }}
- />
- {!accessStore.hideUserApiKey ? (
- <>
- <div className={styles["auth-tips"]}>{Locale.Auth.SubTips}</div>
- <PasswordInput
- style={{ marginTop: "3vh", marginBottom: "3vh" }}
- aria={Locale.Settings.ShowPassword}
- aria-label={Locale.Settings.Access.OpenAI.ApiKey.Placeholder}
- value={accessStore.openaiApiKey}
- type="text"
- placeholder={Locale.Settings.Access.OpenAI.ApiKey.Placeholder}
- onChange={(e) => {
- accessStore.update(
- (access) => (access.openaiApiKey = e.currentTarget.value),
- );
- }}
- />
- <PasswordInput
- style={{ marginTop: "3vh", marginBottom: "3vh" }}
- aria={Locale.Settings.ShowPassword}
- aria-label={Locale.Settings.Access.Google.ApiKey.Placeholder}
- value={accessStore.googleApiKey}
- type="text"
- placeholder={Locale.Settings.Access.Google.ApiKey.Placeholder}
- onChange={(e) => {
- accessStore.update(
- (access) => (access.googleApiKey = e.currentTarget.value),
- );
- }}
- />
- </>
- ) : null}
- <div className={styles["auth-actions"]}>
- <IconButton
- text={Locale.Auth.Confirm}
- type="primary"
- onClick={goChat}
- />
- <IconButton
- text={Locale.Auth.SaasTips}
- onClick={() => {
- goSaas();
- }}
- />
- </div>
- </div>
- );
- }
- function TopBanner() {
- const [isHovered, setIsHovered] = useState(false);
- const [isVisible, setIsVisible] = useState(true);
- const isMobile = useMobileScreen();
- useEffect(() => {
- // 检查 localStorage 中是否有标记
- const bannerDismissed = storage.getItem("bannerDismissed");
- // 如果标记不存在,存储默认值并显示横幅
- if (!bannerDismissed) {
- storage.setItem("bannerDismissed", "false");
- setIsVisible(true); // 显示横幅
- } else if (bannerDismissed === "true") {
- // 如果标记为 "true",则隐藏横幅
- setIsVisible(false);
- }
- }, []);
- const handleMouseEnter = () => {
- setIsHovered(true);
- };
- const handleMouseLeave = () => {
- setIsHovered(false);
- };
- const handleClose = () => {
- setIsVisible(false);
- storage.setItem("bannerDismissed", "true");
- };
- if (!isVisible) {
- return null;
- }
- return (
- <div
- className={styles["top-banner"]}
- onMouseEnter={handleMouseEnter}
- onMouseLeave={handleMouseLeave}
- >
- <div className={clsx(styles["top-banner-inner"], "no-dark")}>
- <Logo className={styles["top-banner-logo"]}></Logo>
- <span>
- {Locale.Auth.TopTips}
- <a
- href={SAAS_CHAT_URL}
- rel="stylesheet"
- onClick={() => {
- trackSettingsPageGuideToCPaymentClick();
- }}
- >
- {Locale.Settings.Access.SaasStart.ChatNow}
- <Arrow style={{ marginLeft: "4px" }} />
- </a>
- </span>
- </div>
- {(isHovered || isMobile) && (
- <Delete className={styles["top-banner-close"]} onClick={handleClose} />
- )}
- </div>
- );
- }
|