LoginSignup
3
0

Next.jsのServer ActionsをtRPCライクに使う[next-safe-action]

Last updated at Posted at 2023-12-13

こんにちは。あのちっくです。
commmune Advent Calendar 2023 13日目の記事はNext.jsのServerActionsの話です。
どうぞよろしくお願いします。

Serve rActions

Next.js 14からServer ActionsがStableになりました。

私はtRPCが大好きでよく使っているのですが、ServerActionsもtRPCのようにzodを使ってinput,outputのスキーマ定義を行ってバリデーションも効くようにしたかったので、自作の仕組みappActionを作りました。

export const sampleAction = appAction({
  input: z.object({ nickname: z.string(), title: z.string() }),
  output: z.object({
    postId: z.string(),
    title: z.string(),
    name: z.string(),
  }),
}).resolve(async (input) => {
  return {
    postId: "xxx",
    title: input.title,
    name: `${input.nickname} さん`,
  };
});

使い方は簡単で、上記のコードのようにaction定義を行うと、resolve内の関数実行時にバリデーターが実行されるというものです。型チェックも効きます。

next-safe-action

自作してから[next-safe-action]というライブラリがあることに気づいたので紹介させてください。

基本的な使い方としては、インターフェースはすこし違いますが、機能はだいたい同じです。outputの型定義も行うかどうかの違いぐらい。

"use server";

import { z } from "zod";
import { action } from "@/lib/safe-action";

const schema = z.object({ nickname: z.string(), title: z.string() });

export const sampleAction = action(schema, async ({ nickname, title }) => {
    return {
    postId: "xxx",
    title: input.title,
    name: `${input.nickname} さん`,
  };
});

いい感じですね。
さらに、next-safe-actionには追加で様々な機能があります。

非同期処理用のhooks

next-safe-actionにはuseActionというhooks関数が用意されています。


export default function Test() {
  const { execute, result } = useAction(sampleAction);
  return (
    <div>
      <button
        onClick={() => {
          execute({postId:'xx', title:'yy', name:'zz'});
        }}>
        Send
      </button>
      {result.data?.name ? <p>{result.data.name}</p> : ''}
    </div>
  );
}

というようにawaitせずにactionを実行して使うことが出来るようになります。

callback

action statusの変化に応じたコールバンク関数を定義して使うことが出来ます。

middleware

メインとなるaction関数を実行する前に、ユーザー認証処理をして、引数にユーザーデータを与えるような事をしたいことがあるとおもいます。
そういったときのためにmiddlewareの仕組みも存在します。

良さそう

next-safe-action、とてもおすすめです。
ぜひ使ってみてください。

3
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
0