mirror of https://github.com/coder/coder.git
refactor: Redesign auth cli page and add workspaces link (#3737)
This commit is contained in:
parent
779c446a6e
commit
3cf17d34e7
|
@ -1,15 +0,0 @@
|
|||
import { Story } from "@storybook/react"
|
||||
import { CliAuthToken, CliAuthTokenProps } from "./CliAuthToken"
|
||||
|
||||
export default {
|
||||
title: "components/CliAuthToken",
|
||||
component: CliAuthToken,
|
||||
argTypes: {
|
||||
sessionToken: { control: "text", defaultValue: "some-session-token" },
|
||||
},
|
||||
}
|
||||
|
||||
const Template: Story<CliAuthTokenProps> = (args) => <CliAuthToken {...args} />
|
||||
|
||||
export const Example = Template.bind({})
|
||||
Example.args = {}
|
|
@ -1,14 +0,0 @@
|
|||
import { screen } from "@testing-library/react"
|
||||
import { render } from "../../testHelpers/renderHelpers"
|
||||
import { CliAuthToken } from "./CliAuthToken"
|
||||
|
||||
describe("CliAuthToken", () => {
|
||||
it("renders content", async () => {
|
||||
// When
|
||||
render(<CliAuthToken sessionToken="test-token" />)
|
||||
|
||||
// Then
|
||||
await screen.findByText("Session Token")
|
||||
await screen.findByText("test-token")
|
||||
})
|
||||
})
|
|
@ -1,29 +0,0 @@
|
|||
import Paper from "@material-ui/core/Paper"
|
||||
import { makeStyles } from "@material-ui/core/styles"
|
||||
import Typography from "@material-ui/core/Typography"
|
||||
import { FC } from "react"
|
||||
import { CodeExample } from "../CodeExample/CodeExample"
|
||||
|
||||
export interface CliAuthTokenProps {
|
||||
sessionToken: string
|
||||
}
|
||||
|
||||
export const CliAuthToken: FC<React.PropsWithChildren<CliAuthTokenProps>> = ({ sessionToken }) => {
|
||||
const styles = useStyles()
|
||||
return (
|
||||
<Paper className={styles.container}>
|
||||
<Typography className={styles.title}>Session Token</Typography>
|
||||
<CodeExample code={sessionToken} />
|
||||
</Paper>
|
||||
)
|
||||
}
|
||||
|
||||
const useStyles = makeStyles((theme) => ({
|
||||
title: {
|
||||
marginBottom: theme.spacing(2),
|
||||
},
|
||||
container: {
|
||||
maxWidth: "680px",
|
||||
padding: theme.spacing(2),
|
||||
},
|
||||
}))
|
|
@ -3,13 +3,14 @@ import { makeStyles } from "@material-ui/core/styles"
|
|||
import AccountTreeIcon from "@material-ui/icons/AccountTree"
|
||||
import AssistantIcon from "@material-ui/icons/Assistant"
|
||||
import ChatIcon from "@material-ui/icons/Chat"
|
||||
import { colors } from "theme/colors"
|
||||
import * as TypesGen from "../../api/typesGenerated"
|
||||
|
||||
export const Language = {
|
||||
buildInfoText: (buildInfo: TypesGen.BuildInfoResponse): string => {
|
||||
return `Coder ${buildInfo.version}`
|
||||
},
|
||||
copyrightText: `Copyright \u00a9 ${new Date().getFullYear()} Coder Technologies, Inc. All rights reserved.`,
|
||||
copyrightText: `Copyright \u00a9 ${new Date().getFullYear()} Coder Technologies, Inc.`,
|
||||
reportBugLink: "Report an issue or share feedback",
|
||||
discordLink: "Join Coder on Discord",
|
||||
}
|
||||
|
@ -55,12 +56,12 @@ export const Footer: React.FC<React.PropsWithChildren<FooterProps>> = ({ buildIn
|
|||
|
||||
const useFooterStyles = makeStyles((theme) => ({
|
||||
root: {
|
||||
opacity: 0.6,
|
||||
color: colors.gray[7],
|
||||
textAlign: "center",
|
||||
flex: "0",
|
||||
paddingTop: theme.spacing(2),
|
||||
paddingBottom: theme.spacing(2),
|
||||
marginTop: theme.spacing(3),
|
||||
marginTop: theme.spacing(8),
|
||||
},
|
||||
copyRight: {
|
||||
margin: theme.spacing(0.25),
|
||||
|
|
|
@ -11,7 +11,7 @@ const Language = {
|
|||
),
|
||||
}
|
||||
|
||||
export const Welcome: FC<PropsWithChildren<{ message?: JSX.Element }>> = ({
|
||||
export const Welcome: FC<PropsWithChildren<{ message?: JSX.Element | string }>> = ({
|
||||
message = Language.defaultMessage,
|
||||
}) => {
|
||||
const styles = useStyles()
|
||||
|
|
|
@ -1,20 +1,15 @@
|
|||
import { makeStyles } from "@material-ui/core/styles"
|
||||
import { useActor } from "@xstate/react"
|
||||
import React, { useContext, useEffect, useState } from "react"
|
||||
import { Helmet } from "react-helmet-async"
|
||||
import { getApiKey } from "../../api/api"
|
||||
import { CliAuthToken } from "../../components/CliAuthToken/CliAuthToken"
|
||||
import { FullScreenLoader } from "../../components/Loader/FullScreenLoader"
|
||||
import { pageTitle } from "../../util/page"
|
||||
import { XServiceContext } from "../../xServices/StateContext"
|
||||
import { CliAuthPageView } from "./CliAuthPageView"
|
||||
|
||||
export const CliAuthenticationPage: React.FC<React.PropsWithChildren<unknown>> = () => {
|
||||
const xServices = useContext(XServiceContext)
|
||||
const [authState] = useActor(xServices.authXService)
|
||||
const { me } = authState.context
|
||||
|
||||
const styles = useStyles()
|
||||
|
||||
const [apiKey, setApiKey] = useState<string | null>(null)
|
||||
|
||||
useEffect(() => {
|
||||
|
@ -25,26 +20,12 @@ export const CliAuthenticationPage: React.FC<React.PropsWithChildren<unknown>> =
|
|||
}
|
||||
}, [me?.id])
|
||||
|
||||
if (!apiKey) {
|
||||
return <FullScreenLoader />
|
||||
}
|
||||
|
||||
return (
|
||||
<div className={styles.root}>
|
||||
<>
|
||||
<Helmet>
|
||||
<title>{pageTitle("CLI Auth")}</title>
|
||||
</Helmet>
|
||||
<CliAuthToken sessionToken={apiKey} />
|
||||
</div>
|
||||
<CliAuthPageView sessionToken={apiKey} />
|
||||
</>
|
||||
)
|
||||
}
|
||||
|
||||
const useStyles = makeStyles(() => ({
|
||||
root: {
|
||||
width: "100vw",
|
||||
height: "100vh",
|
||||
display: "flex",
|
||||
justifyContent: "center",
|
||||
alignItems: "center",
|
||||
},
|
||||
}))
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
import { Story } from "@storybook/react"
|
||||
import { CliAuthPageView, CliAuthPageViewProps } from "./CliAuthPageView"
|
||||
|
||||
export default {
|
||||
title: "pages/CliAuthPageView",
|
||||
component: CliAuthPageView,
|
||||
argTypes: {
|
||||
sessionToken: { control: "text", defaultValue: "some-session-token" },
|
||||
},
|
||||
}
|
||||
|
||||
const Template: Story<CliAuthPageViewProps> = (args) => <CliAuthPageView {...args} />
|
||||
|
||||
export const Example = Template.bind({})
|
||||
Example.args = {}
|
|
@ -0,0 +1,65 @@
|
|||
import Button from "@material-ui/core/Button"
|
||||
import { makeStyles } from "@material-ui/core/styles"
|
||||
import { CodeExample } from "components/CodeExample/CodeExample"
|
||||
import { SignInLayout } from "components/SignInLayout/SignInLayout"
|
||||
import { Welcome } from "components/Welcome/Welcome"
|
||||
import React from "react"
|
||||
import { Link as RouterLink } from "react-router-dom"
|
||||
import { FullScreenLoader } from "../../components/Loader/FullScreenLoader"
|
||||
|
||||
export interface CliAuthPageViewProps {
|
||||
sessionToken: string | null
|
||||
}
|
||||
|
||||
export const CliAuthPageView: React.FC<CliAuthPageViewProps> = ({ sessionToken }) => {
|
||||
const styles = useStyles()
|
||||
|
||||
if (!sessionToken) {
|
||||
return <FullScreenLoader />
|
||||
}
|
||||
|
||||
return (
|
||||
<SignInLayout>
|
||||
<Welcome message="Session token" />
|
||||
<p className={styles.text}>
|
||||
Copy the session token below and{" "}
|
||||
<strong className={styles.lineBreak}>paste it in your terminal</strong>.
|
||||
</p>
|
||||
|
||||
<CodeExample code={sessionToken} />
|
||||
|
||||
<div className={styles.links}>
|
||||
<Button component={RouterLink} size="large" to="/workspaces" fullWidth variant="outlined">
|
||||
Go to workspaces
|
||||
</Button>
|
||||
</div>
|
||||
</SignInLayout>
|
||||
)
|
||||
}
|
||||
|
||||
const useStyles = makeStyles((theme) => ({
|
||||
title: {
|
||||
fontSize: theme.spacing(4),
|
||||
fontWeight: 400,
|
||||
lineHeight: "140%",
|
||||
margin: 0,
|
||||
},
|
||||
|
||||
text: {
|
||||
fontSize: 16,
|
||||
color: theme.palette.text.secondary,
|
||||
marginBottom: theme.spacing(4),
|
||||
textAlign: "center",
|
||||
lineHeight: "160%",
|
||||
},
|
||||
|
||||
lineBreak: {
|
||||
whiteSpace: "nowrap",
|
||||
},
|
||||
|
||||
links: {
|
||||
display: "flex",
|
||||
justifyContent: "flex-end",
|
||||
paddingTop: theme.spacing(1),
|
||||
},
|
||||
}))
|
Loading…
Reference in New Issue