Eslint changes and linting (no-mix-spaces)

This commit is contained in:
Max Leiter 2023-01-07 14:52:27 -08:00
parent 371dae25d9
commit c51ca39fa7
22 changed files with 103 additions and 87 deletions

View file

@ -7,5 +7,8 @@
"parser": "@typescript-eslint/parser", "parser": "@typescript-eslint/parser",
"plugins": ["@typescript-eslint"], "plugins": ["@typescript-eslint"],
"root": true, "root": true,
"ignorePatterns": ["node_modules/", "__tests__/"] "ignorePatterns": ["node_modules/", "__tests__/"],
"rules": {
"no-mixed-spaces-and-tabs": ["off"]
}
} }

View file

@ -6,7 +6,7 @@
"dev": "next dev --port 3000", "dev": "next dev --port 3000",
"build": "next build", "build": "next build",
"start": "next start --port 3000", "start": "next start --port 3000",
"lint": "next lint && prettier --list-different --config .prettierrc '{components,lib,app,pages}/**/*.{ts,tsx}' --write", "lint": "next lint && prettier --list-different --config .prettierrc 'src/{components,lib,app,pages}/**/*.{ts,tsx}' --write",
"analyze": "cross-env ANALYZE=true next build", "analyze": "cross-env ANALYZE=true next build",
"find:unused": "next-unused", "find:unused": "next-unused",
"prisma": "prisma", "prisma": "prisma",

View file

@ -1,5 +1,5 @@
import Input from "@components/input" import Input from "@components/input"
import { ChangeEvent, memo } from "react" import { ChangeEvent } from "react"
import styles from "../post.module.css" import styles from "../post.module.css"

View file

@ -55,7 +55,6 @@ const Post = ({
title: doc.title, title: doc.title,
content: doc.content, content: doc.content,
id: doc.id id: doc.id
// eslint-disable-next-line no-mixed-spaces-and-tabs
})) }))
: [emptyDoc] : [emptyDoc]
@ -285,7 +284,6 @@ const Post = ({
} }
]) ])
}} }}
type="default"
style={{ style={{
flex: 1 flex: 1
}} }}

View file

@ -13,7 +13,7 @@ export const PostButtons = ({
files, files,
loading, loading,
postId, postId,
parentId, parentId
}: { }: {
title: string title: string
files?: Pick<PostWithFiles, "files">["files"] files?: Pick<PostWithFiles, "files">["files"]

View file

@ -21,9 +21,9 @@ export const PostTitle = ({
visibility, visibility,
createdAt, createdAt,
expiresAt, expiresAt,
loading, loading
// authorId }: // authorId
}: TitleProps) => { TitleProps) => {
return ( return (
<span className={styles.title}> <span className={styles.title}>
<h1 <h1

View file

@ -22,35 +22,38 @@ const PasswordModalPage = ({ setPost, postId, authorId }: Props) => {
? undefined ? undefined
: session?.user && session?.user?.id === authorId : session?.user && session?.user?.id === authorId
const [isPasswordModalOpen, setIsPasswordModalOpen] = useState(false) const [isPasswordModalOpen, setIsPasswordModalOpen] = useState(false)
const onSubmit = useCallback(async (password: string) => { const onSubmit = useCallback(
const res = await fetch(`/api/post/${postId}?password=${password}`, { async (password: string) => {
method: "GET", const res = await fetch(`/api/post/${postId}?password=${password}`, {
headers: { method: "GET",
"Content-Type": "application/json" headers: {
} "Content-Type": "application/json"
}) }
if (!res.ok) {
setToast({
type: "error",
message: "Wrong password"
}) })
return
}
const data = await res.json() if (!res.ok) {
if (data) {
if (data.error) {
setToast({ setToast({
message: data.error, type: "error",
type: "error" message: "Wrong password"
}) })
} else { return
setIsPasswordModalOpen(false)
setPost(data.post)
} }
}
}, [postId, setPost, setToast]) const data = await res.json()
if (data) {
if (data.error) {
setToast({
message: data.error,
type: "error"
})
} else {
setIsPasswordModalOpen(false)
setPost(data.post)
}
}
},
[postId, setPost, setToast]
)
const onClose = () => { const onClose = () => {
setIsPasswordModalOpen(false) setIsPasswordModalOpen(false)

View file

@ -21,11 +21,9 @@ type SharedProps = {
type Props = ( type Props = (
| { | {
skeleton?: true skeleton?: true
// eslint-disable-next-line no-mixed-spaces-and-tabs
} }
| { | {
skeleton?: false skeleton?: false
// eslint-disable-next-line no-mixed-spaces-and-tabs
} }
) & ) &
SharedProps SharedProps

View file

@ -6,7 +6,7 @@ type BadgeProps = {
} & React.HTMLAttributes<HTMLDivElement> } & React.HTMLAttributes<HTMLDivElement>
const Badge = React.forwardRef<HTMLDivElement, BadgeProps>( const Badge = React.forwardRef<HTMLDivElement, BadgeProps>(
({ type, children, ...rest}: BadgeProps, ref) => { ({ type, children, ...rest }: BadgeProps, ref) => {
return ( return (
<div className={styles.container} {...rest}> <div className={styles.container} {...rest}>
<div className={`${styles.badge} ${styles[type]}`} ref={ref}> <div className={`${styles.badge} ${styles[type]}`} ref={ref}>

View file

@ -15,7 +15,11 @@ type Props = {
visibility: string visibility: string
} }
const VisibilityControl = ({ authorId, postId, visibility: postVisibility }: Props) => { const VisibilityControl = ({
authorId,
postId,
visibility: postVisibility
}: Props) => {
const { data: session } = useSession() const { data: session } = useSession()
const isAuthor = session?.user && session?.user?.id === authorId const isAuthor = session?.user && session?.user?.id === authorId
const [visibility, setVisibility] = useState<string>(postVisibility) const [visibility, setVisibility] = useState<string>(postVisibility)
@ -23,7 +27,7 @@ const VisibilityControl = ({ authorId, postId, visibility: postVisibility }: Pro
const [isSubmitting, setSubmitting] = useState<string | null>() const [isSubmitting, setSubmitting] = useState<string | null>()
const [passwordModalVisible, setPasswordModalVisible] = useState(false) const [passwordModalVisible, setPasswordModalVisible] = useState(false)
const { setToast } = useToasts() const { setToast } = useToasts()
const router = useRouter(); const router = useRouter()
const sendRequest = useCallback( const sendRequest = useCallback(
async (visibility: string, password?: string) => { async (visibility: string, password?: string) => {
@ -43,7 +47,6 @@ const VisibilityControl = ({ authorId, postId, visibility: postVisibility }: Pro
message: "Visibility updated", message: "Visibility updated",
type: "success" type: "success"
}) })
} else { } else {
setToast({ setToast({
message: "An error occurred", message: "An error occurred",
@ -84,10 +87,12 @@ const VisibilityControl = ({ authorId, postId, visibility: postVisibility }: Pro
return ( return (
<> <>
<ButtonGroup style={{ <ButtonGroup
maxWidth: 600, style={{
margin: "var(--gap) auto", maxWidth: 600,
}}> margin: "var(--gap) auto"
}}
>
<Button <Button
disabled={visibility === "private"} disabled={visibility === "private"}
onClick={() => onSubmit("private")} onClick={() => onSubmit("private")}

View file

@ -1,9 +1,12 @@
import styles from "./button.module.css" import styles from "./button.module.css"
import { forwardRef, Ref } from "react" import { forwardRef } from "react"
import clsx from "clsx" import clsx from "clsx"
import { Spinner } from "@components/spinner" import { Spinner } from "@components/spinner"
type Props = React.HTMLProps<HTMLButtonElement> & { type Props = React.DetailedHTMLProps<
React.ButtonHTMLAttributes<HTMLButtonElement>,
HTMLButtonElement
> & {
children?: React.ReactNode children?: React.ReactNode
buttonType?: "primary" | "secondary" buttonType?: "primary" | "secondary"
className?: string className?: string
@ -25,7 +28,6 @@ const Button = forwardRef<HTMLButtonElement, Props>(
onClick, onClick,
className, className,
buttonType = "primary", buttonType = "primary",
type = "button",
disabled = false, disabled = false,
iconRight, iconRight,
iconLeft, iconLeft,
@ -41,11 +43,10 @@ const Button = forwardRef<HTMLButtonElement, Props>(
return ( return (
<button <button
ref={ref} ref={ref}
className={clsx( className={clsx(styles.button, className, {
styles.button, [styles.primary]: buttonType === "primary",
type === "primary" || (type === "secondary" && styles[type]), [styles.secondary]: buttonType === "secondary"
className })}
)}
disabled={disabled || loading} disabled={disabled || loading}
onClick={onClick} onClick={onClick}
style={{ height, width, margin, padding }} style={{ height, width, margin, padding }}

View file

@ -17,7 +17,7 @@ type InputProps = Omit<Props, "onChange" | "value" | "label" | "aria-label"> &
| { | {
onChange: Props["onChange"] onChange: Props["onChange"]
value: Props["value"] value: Props["value"]
} // if onChange or value is passed, we require both }
| { | {
onChange?: never onChange?: never
value?: never value?: never
@ -64,6 +64,7 @@ const Input = React.forwardRef<HTMLInputElement, InputProps>(
ref={ref} ref={ref}
id={labelId} id={labelId}
className={clsx(styles.input, label && styles.withLabel, className)} className={clsx(styles.input, label && styles.withLabel, className)}
required={required}
{...props} {...props}
style={{ style={{
width, width,

View file

@ -92,33 +92,35 @@ const ListItem = ({
<ExpirationBadge postExpirationDate={post.expiresAt} /> <ExpirationBadge postExpirationDate={post.expiresAt} />
</div> </div>
</span> </span>
{!hideActions ? <span className={styles.buttons}> {!hideActions ? (
{post.parentId && ( <span className={styles.buttons}>
<Tooltip content={"View parent"}> {post.parentId && (
<Tooltip content={"View parent"}>
<Button
iconRight={<ArrowUpCircle />}
onClick={viewParentClick}
height={38}
/>
</Tooltip>
)}
<Tooltip content={"Make a copy"}>
<Button <Button
iconRight={<ArrowUpCircle />} iconRight={<Edit />}
onClick={viewParentClick} onClick={editACopy}
height={38} height={38}
/> />
</Tooltip> </Tooltip>
)} {isOwner && (
<Tooltip content={"Make a copy"}> <Tooltip content={"Delete"}>
<Button <Button
iconRight={<Edit />} iconRight={<Trash />}
onClick={editACopy} onClick={deletePost}
height={38} height={38}
/> />
</Tooltip> </Tooltip>
{isOwner && ( )}
<Tooltip content={"Delete"}> </span>
<Button ) : null}
iconRight={<Trash />}
onClick={deletePost}
height={38}
/>
</Tooltip>
)}
</span> : null}
</div> </div>
{post.description && ( {post.description && (

View file

@ -53,7 +53,7 @@ export function useApiTokens({ userId, initialTokens }: UseApiTokens) {
mutate([...(data || []), response]) mutate([...(data || []), response])
return response as SerializedApiToken return response as SerializedApiToken
} }
const expireToken = async (id: string) => { const expireToken = async (id: string) => {

View file

@ -1,3 +1,3 @@
export async function copyToClipboard(text: string ) { export async function copyToClipboard(text: string) {
await navigator.clipboard.writeText(text) await navigator.clipboard.writeText(text)
} }

View file

@ -24,4 +24,4 @@ export default async function Mine() {
) )
} }
export const revalidate = 0; export const revalidate = 0

View file

@ -68,7 +68,9 @@ export default async function Page() {
<div> <div>
<h2>Recent public posts</h2> <h2>Recent public posts</h2>
<Suspense <Suspense
fallback={<PostList skeleton hideSearch initialPosts={JSON.stringify({})} />} fallback={
<PostList skeleton hideSearch initialPosts={JSON.stringify({})} />
}
> >
{/* @ts-expect-error because of async RSC */} {/* @ts-expect-error because of async RSC */}
<PublicPostList getPostsPromise={getPostsPromise} /> <PublicPostList getPostsPromise={getPostsPromise} />

View file

@ -5,7 +5,10 @@ import Input from "@components/input"
import Note from "@components/note" import Note from "@components/note"
import { Spinner } from "@components/spinner" import { Spinner } from "@components/spinner"
import { useToasts } from "@components/toasts" import { useToasts } from "@components/toasts"
import { SerializedApiToken, useApiTokens } from "src/app/hooks/swr/use-api-tokens" import {
SerializedApiToken,
useApiTokens
} from "src/app/hooks/swr/use-api-tokens"
import { copyToClipboard } from "src/app/lib/copy-to-clipboard" import { copyToClipboard } from "src/app/lib/copy-to-clipboard"
import { useSession } from "next-auth/react" import { useSession } from "next-auth/react"
import { useState } from "react" import { useState } from "react"

View file

@ -146,7 +146,7 @@ export const authOptions: NextAuthOptions = {
if (config.enable_admin && totalUsers === 1) { if (config.enable_admin && totalUsers === 1) {
await prisma.user.update({ await prisma.user.update({
where: { where: {
id: user.id, id: user.id
}, },
data: { data: {
role: "admin" role: "admin"
@ -161,7 +161,7 @@ export const authOptions: NextAuthOptions = {
}, },
data: { data: {
username: user.name, username: user.name,
displayName: user.name, displayName: user.name
} }
}) })
} }

View file

@ -68,7 +68,7 @@ async function handleGet(req: NextApiRequest, res: NextApiResponse<unknown>) {
post: { post: {
id: post.id, id: post.id,
visibility: post.visibility, visibility: post.visibility,
authorId: post.authorId, authorId: post.authorId
} }
}) })
} }

View file

@ -25,7 +25,7 @@ export default async function handle(
expiresAt: true, expiresAt: true,
name: true name: true
} }
}); })
console.log(tokens) console.log(tokens)