Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

✨ add error #104

Merged
merged 11 commits into from
Jan 17, 2023
84 changes: 84 additions & 0 deletions examples/next-typescript/pages/error.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
import { Container, Error } from "@tonightpass/kitchen";
import { NextPage } from "next";
import React from "react";

const ErrorPage: NextPage = () => {
return (
<>
<Container
gap={10}
style={{
maxWidth: 700,
margin: "0 auto",
}}
>
<p>default</p>

<Container row>
<Error>This email address is already in use.</Error>
</Container>

<p>custom label</p>
<Container row>
<Error label="Email Error">
This email address is already in use.
</Error>
</Container>

<p>no label</p>
<Container row>
<Error label={false}>This email address is already in use. </Error>
</Container>

<p>sizes</p>
<Container gap={10}>
<Container row>
<Error>This email is in use.</Error>
</Container>
<Container row>
<Error size="large">This email is in use.</Error>
</Container>
<Container row>
<Error size="title">This email is in use.</Error>
</Container>
</Container>

<p>multiline</p>
<Container row>
<Error>
A valid email address is required so that we can verify your GitHub
installation. In the event that you cannot provide a valid email
address, please contact support.
</Error>
</Container>
<Container row>
<Error size="large">
A valid email address is required so that we can verify your GitHub
installation. In the event that you cannot provide a valid email
address, please contact support.
</Error>
</Container>
<Container row>
<Error size="title">
A valid email address is required so that we can verify your GitHub
installation. In the event that you cannot provide a valid email
address, please contact support.
</Error>
</Container>

<p>with an `error` property</p>
<Container row>
<Error
error={{
message: "The request failed.",
action: "Contact Us",
link: "https://vercel.com/contact",
}}
/>
</Container>
</Container>
</>
);
};

export default ErrorPage;
1 change: 1 addition & 0 deletions examples/next-typescript/pages/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ const IndexPage: NextPage = () => {
<Link href={"/button"}>Button</Link>
<Link href={"/checkbox"}>Checkbox</Link>
<Link href={"/drawer"}>Drawer</Link>
<Link href={"/error"}>Error</Link>
<Link href={"/icon"}>Icon</Link>
<Link href={"/link"}>Link</Link>
<Link href={"/modal"}>Modal</Link>
Expand Down
99 changes: 99 additions & 0 deletions packages/kitchen/src/components/Error/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
import React from "react";
import { RiErrorWarningLine } from "react-icons/ri";
import styled from "styled-components";
import { KitchenComponent } from "../../types";
import Icon from "../Icon";
import Text from "../Text";
import Link from "../Link";

export type ErrorProps = KitchenComponent & {
/**
* The label of the error.
* @default true
*/
label?: boolean | string;

/**
* The size of the error.
* @default "medium"
*/
size?: "medium" | "large" | "title";

error?: { message: string; action?: string; link?: string };
};

const Error = styled(
({
as: Component = "div",
label = true,
size,
error,
children,
...props
}: ErrorProps) => {
return (
<Component {...props}>
<IconContainer>
<Icon icon={RiErrorWarningLine} accent={"danger"} size={size} />
</IconContainer>
<TextContainer>
<Text size={size} accent={"danger"}>
{label && (
<Label>
{typeof label === "string" ? label : "Error"}
{label ? ": " : ""}
</Label>
)}
<Content>{error ? error.message : children}</Content>
{error && (
<Action href={error.link} variant="blend">
{error.action}
</Action>
)}
</Text>
</TextContainer>
</Component>
);
}
)<ErrorProps>`
display: inline-flex;
user-select: none;
font-weight: ${({ theme }) => theme.weight.medium};
font-size: ${(props) => {
switch (props.size) {
case "medium":
return props.theme.size.medium;
case "large":
return props.theme.size.large;
case "title":
return props.theme.size.title;
default:
return props.theme.size.medium;
}
}};
`;

const IconContainer = styled.div`
box-sizing: border-box;
`;

const TextContainer = styled.div`
box-sizing: border-box;
margin-left: 8px;
`;

const Label = styled.span`
font-size: inherit;
font-weight: ${({ theme }) => theme.weight.semiBold};
color: ${({ theme }) => theme.colors.accent.danger};
`;

const Content = styled.span`
font-size: inherit;
font-family: inherit;
color: ${({ theme }) => theme.colors.accent.danger};
`;

const Action = styled(Link)``;

export default Error;
3 changes: 3 additions & 0 deletions packages/kitchen/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,9 @@ export type { ContainerProps } from "./components/Container";
export { default as Drawer } from "./components/Drawer";
export type { DrawerProps } from "./components/Drawer";

export { default as Error } from "./components/Error";
export type { ErrorProps } from "./components/Error";

export { default as FragmentLink } from "./components/FragmentLink";
export type { FragmentLinkProps } from "./components/FragmentLink";

Expand Down