Next.js 15 Server Actions 事务边界与并发一致性实践概述Server Actions 简化了表单/轻交互的服务端写入逻辑。为保障一致性与可靠性,需设计事务边界、幂等与冲突解决,并与 `revalidateTag`/PPR 协同更新缓存。幂等令牌与事务边界'use server' import { revalidateTag } from 'next/cache' import { z } from 'zod' const schema = z.object({ id: z.string().uuid(), title: z.string().min(1), idem: z.string().length(36) }) export async function savePost(formData: FormData) { const data = Object.fromEntries(formData) const parsed = schema.safeParse(data) if (!parsed.success) return { ok: false, errors: parsed.error.flatten() } // 幂等令牌(idempotency key)防重复提交 const exists = await kv.get(`idem:${parsed.data.idem}`) if (exists) return { ok: true, dedup: true } await db.transaction(async (tx) => { await tx.post.upsert({ id: parsed.data.id, title: parsed.data.title }) await kv.set(`idem:${parsed.data.idem}`, 1, { ttl: 600 }) }) revalidateTag('posts') return { ok: true } } 乐观更新与失败回滚// 客户端示例(简化) async function onSubmit(e) { e.preventDefault() const fd = new FormData(e.currentTarget) const tempId = crypto.randomUUID() setPosts((p) => [{ id: tempId, title: fd.get('title'), _optimistic: true }, ...p]) const res = await savePost(fd) if (!res.ok) { // 回滚乐观项 setPosts((p) => p.filter((x) => x.id !== tempId)) } } 冲突解决(最后写入/版本号)// 版本号策略(简化) await db.transaction(async (tx) => { const current = await tx.post.get(parsed.data.id) const nextVersion = (current?.version ?? 0) + 1 await tx.post.upsert({ id: parsed.data.id, title: parsed.data.title, version: nextVersion }) }) PPR 与标签失效协同import { unstable_cache } from 'next/cache' export const dynamic = 'force-static' const getPosts = unstable_cache(async () => { const res = await fetch(`${process.env.BASE_URL}/api/posts`, { next: { tags: ['posts'] } }) return res.json() }, ['posts'], { revalidate: 600 }) 技术参数与验证Node.js 20.x;Chrome 120+幂等防重:重复提交消除率 > 99%;PPR 命中率 > 85%回滚策略正确覆盖:失败路径下乐观项移除率 100%应用场景表单提交与设置保存;订单/内容发布等轻事务场景。注意事项幂等令牌需与用户/会话绑定;事务边界覆盖所有副作用。标签失效需与 `unstable_cache` 的 `tags` 一致。常见问题Q: 如何避免重复副作用?A: 使用幂等令牌与事务包裹持久化与外部调用,失败时回滚。参考资料Next.js Cache/Tags 文档;事务与幂等实践。---发布信息:已发布 · 技术验证 · 阅读 38 分钟 · CC BY-SA 4.0

点赞(0) 打赏

评论列表 共有 0 条评论

暂无评论
立即
投稿

微信公众账号

微信扫一扫加关注

发表
评论
返回
顶部
2.237650s