This commit is contained in:
poipiii
2022-12-27 16:42:01 +08:00
82 changed files with 1184 additions and 316 deletions
+45
View File
@@ -0,0 +1,45 @@
import { useSession } from "next-auth/react";
import { Footer } from "../components/Footer";
import { Header } from "../components/Header";
import Head from "next/head";
import Link from "next/link";
export default function Error() {
const { data: session } = useSession();
if (!session) {
return (
<>
<Head>
<title>Open Assistant</title>
<meta name="404" content="Sorry, this page doesn't exist." />
</Head>
<Header />
<main className="flex h-3/4 items-center justify-center overflow-hidden subpixel-antialiased text-xl">
{"Sorry, the page you're looking for does not exist."}
</main>
<Footer />
</>
);
}
return (
<>
<Head>
<title>Open Assistant</title>
<meta
name="description"
content="Conversational AI for everyone. An open source project to create a chat enabled GPT LLM run by LAION and contributors around the world."
/>
</Head>
<Header />
<main>
<h2>Open Chat Gpt</h2>
<p>You are logged in</p>
<Link href="/grading/grade-output">~Rate a prompt and output now~</Link>
</main>
<Footer />
</>
);
}
+24 -1
View File
@@ -1,12 +1,35 @@
import { ChakraProvider } from "@chakra-ui/react";
import { SessionProvider } from "next-auth/react";
import { Inter } from "@next/font/google";
import { extendTheme } from "@chakra-ui/react";
import "../styles/globals.css";
import "focus-visible";
const inter = Inter({
subsets: ["latin"],
variable: "--font-inter",
});
const theme = extendTheme({
styles: {
global: {
body: {
bg: "white",
},
main: {
fontFamily: "Inter",
},
header: {
fontFamily: "Inter",
},
},
},
});
function MyApp({ Component, pageProps: { session, ...pageProps } }) {
return (
<ChakraProvider>
<ChakraProvider theme={theme}>
<SessionProvider session={session}>
<Component {...pageProps} />
</SessionProvider>
+3 -1
View File
@@ -37,7 +37,9 @@ export const authOptions: AuthOptions = {
adapter: PrismaAdapter(prisma),
providers,
pages: {
signIn: "/auth/signin",
signIn: "/auth/signup",
verifyRequest: "/auth/verify",
// error: "/auth/error", -Will be used later
},
session: {
strategy: "jwt",
-62
View File
@@ -1,62 +0,0 @@
import { Button, Input } from "@chakra-ui/react";
import Head from "next/head";
import { FaDiscord, FaGithub, FaMagic } from "react-icons/fa";
import { getCsrfToken, getProviders, signIn } from "next-auth/react";
import { useRef } from "react";
import { AuthLayout } from "src/components/AuthLayout";
export default function Signin({ csrfToken, providers }) {
const { discord, email } = providers;
const emailEl = useRef(null);
const signinWithEmail = () => {
signIn(email.id, { callbackUrl: "/", email: emailEl.current.value });
};
return (
<>
<Head>
<title>Log in</title>
</Head>
<AuthLayout title="Log In" subtitle={<></>}>
<div className="space-y-6 w-100 flex flex-col justify-center items-center ">
{discord && (
<Button
leftIcon={<FaDiscord />}
colorScheme="blue"
size="lg"
w="36"
onClick={() => signIn(discord.id, { callbackUrl: "/" })}
>
Discord
</Button>
)}
<Button w="36" leftIcon={<FaGithub />} colorScheme="blue" size="lg">
Github
</Button>
{email && (
<div>
<Input variant="outline" placeholder="Email Address" ref={emailEl} />
<Button w="36" leftIcon={<FaMagic />} colorScheme="blue" size="lg" onClick={signinWithEmail}>
Email
</Button>
</div>
)}
</div>
</AuthLayout>
</>
);
}
export async function getServerSideProps(context) {
const csrfToken = await getCsrfToken();
const providers = await getProviders();
return {
props: {
csrfToken,
providers,
},
};
}
+103
View File
@@ -0,0 +1,103 @@
import { Button, Input, Stack } from "@chakra-ui/react";
import Head from "next/head";
import { FaDiscord, FaEnvelope, FaGithub } from "react-icons/fa";
import { getCsrfToken, getProviders, signIn } from "next-auth/react";
import { useRef } from "react";
import Link from "next/link";
import { AuthLayout } from "src/components/AuthLayout";
export default function Signin({ csrfToken, providers }) {
const { discord, email, github } = providers;
const emailEl = useRef(null);
const signinWithEmail = () => {
signIn(email.id, { callbackUrl: "/", email: emailEl.current.value });
};
return (
<>
<Head>
<title>Sign Up - Open Assistant</title>
<meta name="Sign Up" content="Sign up to access Open Assistant" />
</Head>
<AuthLayout>
<Stack spacing="2">
{email && (
<Stack>
<Input variant="outline" size="lg" placeholder="Email Address" ref={emailEl} />
<Button
size={"lg"}
leftIcon={<FaEnvelope />}
colorScheme="gray"
onClick={signinWithEmail}
// isDisabled="false"
>
Continue with Email
</Button>
</Stack>
)}
{discord && (
<Button
bg="#5865F2"
_hover={{ bg: "#4A57E3" }}
_active={{
bg: "#454FBF",
}}
size="lg"
leftIcon={<FaDiscord />}
color="white"
onClick={() => signIn(discord, { callbackUrl: "/" })}
// isDisabled="false"
>
Continue with Discord
</Button>
)}
{github && (
<Button
bg="#333333"
_hover={{ bg: "#181818" }}
_active={{
bg: "#101010",
}}
size={"lg"}
leftIcon={<FaGithub />}
colorScheme="blue"
// isDisabled="false"
>
Continue with Github
</Button>
)}
</Stack>
<div className="pt-10 text-center">
By signing up you agree to our <br></br>
<Link href="#" aria-label="Terms of Service" className="hover:underline underline-offset-4">
<b>Terms of Service</b>
</Link>{" "}
and{" "}
<Link href="#" aria-label="Terms of Use" className="hover:underline underline-offset-4">
<b>Privacy Policy</b>
</Link>
.
</div>
<hr className="mt-14 mb-4 h-px bg-gray-200 border-0" />
<div className="text-center">
Already have an account?{" "}
<Link href="#" aria-label="Log In" className="hover:underline underline-offset-4">
<b>Log In</b>
</Link>
</div>
</AuthLayout>
</>
);
}
export async function getServerSideProps(context) {
const csrfToken = await getCsrfToken();
const providers = await getProviders();
return {
props: {
csrfToken,
providers,
},
};
}
+38
View File
@@ -0,0 +1,38 @@
import Head from "next/head";
import { getCsrfToken, getProviders, signIn } from "next-auth/react";
import Link from "next/link";
import { AuthLayout } from "src/components/AuthLayout";
export default function Verify() {
return (
<>
<Head>
<title>Sign Up - Open Assistant</title>
<meta name="Sign Up" content="Sign up to access Open Assistant" />
</Head>
<AuthLayout>
<h1 className="text-lg">A sign-in link has been sent to your email address.</h1>
<hr className="mt-14 mb-4 h-px bg-gray-200 border-0" />
<Link
href="#"
aria-label="Log In"
className="flex justify-center font-medium text-black hover:underline underline-offset-4"
>
Already have an account? Log In
</Link>
</AuthLayout>
</>
);
}
export async function getServerSideProps(context) {
const csrfToken = await getCsrfToken();
const providers = await getProviders();
return {
props: {
csrfToken,
providers,
},
};
}
+9 -8
View File
@@ -2,6 +2,7 @@ import { useSession } from "next-auth/react";
import Head from "next/head";
import Link from "next/link";
import { Button, Input, Stack } from "@chakra-ui/react";
import { CallToAction } from "../components/CallToAction";
import { Faq } from "../components/Faq";
@@ -25,7 +26,7 @@ export default function Home() {
/>
</Head>
<Header />
<main>
<main className="z-0">
<Hero />
<CallToAction />
@@ -45,13 +46,13 @@ export default function Home() {
/>
</Head>
<Header />
<main>
<h2>Open Chat Gpt</h2>
<p>You are logged in</p>
<Link href="/grading/grade-output">~Rate a prompt and output now~</Link>
<Link href="/leaderboard/score-leaderboard">~view the score leaderboard~</Link>
<main className="h-3/4 z-0 bg-white flex flex-col items-center justify-center gap-2">
<Button size="lg" colorScheme="blue" className="drop-shadow">
<Link href="/grading/grade-output">Rate a prompt and output now</Link>
</Button>
<Button size="lg" colorScheme="blue" className="drop-shadow">
<Link href="/summarize/story">Summarize a story</Link>
</Button>
</main>
<Footer />
</>
+118
View File
@@ -0,0 +1,118 @@
// TODO(#65): Unify and simplify the task paths
import { Textarea } from "@chakra-ui/react";
import { useRef, useState } from "react";
import useSWRMutation from "swr/mutation";
import useSWRImmutable from "swr/immutable";
import fetcher from "src/lib/fetcher";
import poster from "src/lib/poster";
const SummarizeStory = () => {
// Use an array of tasks that record the sequence of steps until a task is
// deemed complete.
const [tasks, setTasks] = useState([]);
const inputRef = useRef<HTMLTextAreaElement>(null);
// Fetch the very fist task. We can ignore everything except isLoading
// because the onSuccess handler will update `tasks` when ready.
const { isLoading } = useSWRImmutable("/api/new_task/summarize_story", fetcher, {
onSuccess: (data) => {
console.log(data);
setTasks([data]);
},
});
// Every time we submit an answer to the latest task, let the backend handle
// all the interactions then add the resulting task to the queue. This ends
// when we hit the done task.
const { trigger, isMutating } = useSWRMutation("/api/update_task", poster, {
onSuccess: async (data) => {
const newTask = await data.json();
// This is the more efficient way to update a react state array.
setTasks((oldTasks) => [...oldTasks, newTask]);
},
});
// Trigger a mutation that updates the current task. We should probably
// signal somewhere that this interaction is being processed.
const submitResponse = (task: { id: string }) => {
const text = inputRef.current.value.trim();
trigger({
id: task.id,
content: {
update_type: "text_reply_to_post",
text,
},
});
};
/**
* TODO: Make this a nicer loading screen.
*/
if (tasks.length == 0) {
return <div className=" p-6 h-full mx-auto bg-slate-100 text-gray-800">Loading...</div>;
}
return (
<div className=" p-6 h-full mx-auto bg-slate-100 text-gray-800">
{/* Instrunction and Output panels */}
<section className="mb-8 lt-lg:mb-12 ">
<div className="grid lg:gap-x-12 lg:grid-cols-2">
{/* Instruction panel */}
<div className="rounded-lg shadow-lg h-full block bg-white">
<div className="p-6">
<h5 className="text-lg font-semibold">Instruction</h5>
<p className="text-lg py-1">Summarize the following story</p>
<div className="bg-slate-800 p-6 rounded-xl text-white whitespace-pre-wrap">{tasks[0].task.story}</div>
</div>
</div>
{/* Output panel */}
<div className="mt-6 lg:mt-0 rounded-lg shadow-lg h-full block bg-white">
<div className="flex justify-center p-6">
<Textarea name="summary" placeholder="Summary" ref={inputRef} />
</div>
</div>
</div>
</section>
{/* Info & controls */}
<section className="mb-8 p-4 rounded-lg shadow-lg bg-white flex flex-row justify-items-stretch ">
<div className="flex flex-col justify-self-start text-gray-700">
<div>
<span>
<b>Prompt</b>
</span>
<span className="ml-2">{tasks[0].id}</span>
</div>
<div>
<span>
<b>Output</b>
</span>
<span className="ml-2">Submit your answer</span>
</div>
</div>
{/* Skip / Submit controls */}
<div className="flex justify-center ml-auto">
<button
type="button"
className="mr-2 inline-flex items-center rounded-md border border-transparent bg-indigo-100 px-4 py-2 text-sm font-medium text-indigo-700 hover:bg-indigo-200 focus:outline-none focus:ring-2 focus:ring-indigo-500 focus:ring-offset-2"
>
Skip
</button>
<button
type="button"
onClick={() => submitResponse(tasks[0])}
className="inline-flex items-center rounded-md border border-transparent bg-indigo-600 px-4 py-2 text-sm font-medium text-white shadow-sm hover:bg-indigo-700 focus:outline-none focus:ring-2 focus:ring-indigo-500 focus:ring-offset-2"
>
Submit
</button>
</div>
</section>
</div>
);
};
export default SummarizeStory;