Open16

Next.js 学んだこと

くまくま

router.refresh()とは

Next.jsの公式ドキュメント

サーバーに新しいリクエストを行い、データリクエストを再取得し、Server Componentを再レンダリングする。
クライアントは、影響を受けていないクライアント側のReact(useStateなど)やブラウザの状態(スクロール位置など)を失うことなく、更新されたReact Server Componentのペイロードをマージすることができます。

クライアントコンポーネントに影響することなくサーバコンポーネントを再レンダリングしてデータを更新してくれる
https://zenn.dev/msy/articles/f13ac46a1d3f8e

pushやreplaceと違い、サーバーからデータをfetchし直すということ。
https://zenn.dev/nishiurahiroki/articles/9275209b157345

くまくま

react-selectを使用時

Warning: Prop `id` did not match. Server: "react-select-2-live-region" Client: "react-select-3-live-region"

のエラーが発生

くまくま

JavaScriptのNumber()とparseInt()の違い

https://zenn.dev/tk4/articles/f85ef53745ff52906f57

Number()に空配列が渡された時に数値の0が返って来る事に要注意です。

https://qiita.com/gp333/items/8bfa34979da64f15035c

parseIntは、数値を含む文字列のうち、数字部分を取り出し、数値に変換する。
Numberは、数値を含む文字列の意味を解釈し、数値に変換する。文法に合わない文字列の時は、NaNを返却する。

くまくま

Auth.jsでrole(admin)を使う方法

prismaで設定するには?
https://www.prisma.io/docs/concepts/components/prisma-schema/data-model#defining-attributes
https://zenn.dev/ikekyo/scraps/f6c87fbfd3bf9d

enum Role {
  USER
  ADMIN
}

model User {
  id      Int      @id @default(autoincrement())
  role    Role     @default(USER)
}
くまくま

https://next-auth.js.org/providers/google#options

アカウントの永続化にデータベースを使用していない場合
Google アカウントの RefreshToken または AccessToken にアクセスする必要がある

app/api/auth/[...nextauth]/route.ts
app/api/auth/[...nextauth]/route.ts
const options = {
  providers: [
    GoogleProvider({
      clientId: process.env.GOOGLE_ID,
      clientSecret: process.env.GOOGLE_SECRET,
      authorization: {
        params: {
          prompt: "consent",
          access_type: "offline",
          response_type: "code"
        }
      }
    })
  ],
}
くまくま

ミドルウェア

middleware.ts
export { default } from "next-auth/middleware"; // defaultをママ使う。

export const config = {
    matcher: ["/((?!register|api|login).*)"], // ?!で否定です。
};

https://next-auth.js.org/configuration/nextjs#advanced-usage
カスタマイズしたいときは、withAuthでラップ
roleがadminの場合だけ許可

import { withAuth } from "next-auth/middleware"

export default withAuth(
  function middleware(req) {
    console.log(req.nextauth.token)
  },
  {
    callbacks: {
      authorized: ({ token }) => token?.role === "admin",
    },
  }
)

export const config = { matcher: ["/admin"] }

参考
https://zenn.dev/tfutada/articles/5557b780050574

くまくま
  // 認証情報取得
  const session = await getCurrentUser();
  // ログインしていない場合はログイン画面にリダイレクト
  if (!session || session.role !== Role.ADMIN) {
    redirect('/login');
  }
くまくま

ライブラリを使用してclsxクラス名を切り替える
https://github.com/lukeed/clsx

import clsx from 'clsx';
 
export default function InvoiceStatus({ status }: { status: string }) {
  return (
    <span
      className={clsx(
        'inline-flex items-center rounded-full px-2 py-1 text-sm',
        {
          'bg-gray-100 text-gray-500': status === 'pending',
          'bg-green-500 text-white': status === 'paid',
        },
      )}
    >
    // ...
)}