Next.js 14中通过Server Action发送表单数据至API并展示响应
问题修复方案
1. 修正请求体格式,传递结构化数据
你当前直接将formData.get('code')的结果转成JSON字符串发送,后端/api/codelang大概率需要包含prompt的结构化数据才能正确调用OpenAI API。调整Server Action的请求体:
async function getCode(formData) { 'use server' const code = formData.get('code'); // 构造符合后端要求的请求体,包含明确的分析提示 const requestBody = { prompt: `分析以下代码的功能、所属编程语言:\n${code}` }; const res = await fetch(`${process.env.URL}/api/codelang`, { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify(requestBody), // 发送结构化对象而非纯字符串 cache: 'no-store', }); if (!res.ok) { throw new Error('请求失败'); } const data = await res.json(); // 返回提取后的有效结果 return data.choices?.[0]?.message?.content || '未获取到有效分析结果'; }
2. 在页面上展示API响应结果
Next.js 14中使用useFormState跟踪Server Action的返回结果,实现页面实时更新:
'use client'; // 引入客户端hooks需添加该指令 import { useFormState, useFormStatus } from 'react-dom'; export default function CodeLangTest() { // 初始化结果状态为空字符串 const [analysisResult, formAction] = useFormState(getCode, ''); // 处理提交加载状态 const { pending } = useFormStatus(); return ( <> <h1>代码分析工具</h1> <form action={formAction}> <input name="code" type="text" placeholder="输入代码片段" /> <button disabled={pending}>{pending ? '分析中...' : '提交'}</button> </form> {/* 渲染API响应结果 */} {analysisResult && ( <div style={{ marginTop: '20px', padding: '12px', border: '1px solid #e5e7eb' }}> <h3>分析结果:</h3> <p>{analysisResult}</p> </div> )} </> ); } // Server Action单独定义,确保'use server'指令生效 async function getCode(prevState, formData) { 'use server' const code = formData.get('code'); if (!code) return '请输入代码片段'; const requestBody = { prompt: `分析以下代码的功能、所属编程语言:\n${code}` }; try { const res = await fetch(`${process.env.URL}/api/codelang`, { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify(requestBody), cache: 'no-store', }); if (!res.ok) throw new Error('请求失败'); const data = await res.json(); return data.choices?.[0]?.message?.content || '未获取到有效分析结果'; } catch (err) { return err.message; } }
3. 后端API补充说明
确保/api/codelang正确处理请求体,将prompt传递给OpenAI API:
// app/api/codelang/route.js export async function POST(req) { const { prompt } = await req.json(); const openAiRes = await fetch('https://api.openai.com/v1/chat/completions', { method: 'POST', headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${process.env.OPENAI_API_KEY}` }, body: JSON.stringify({ model: 'gpt-3.5-turbo', messages: [{ role: 'user', content: prompt }] }) }); const data = await openAiRes.json(); return Response.json(data); }
关键问题总结
- 原代码直接发送纯字符串,后端无法构造有效OpenAI提示词,导致返回通用响应;
- 未使用
useFormState跟踪Server Action返回结果,无法在页面展示响应内容; - 添加错误处理和加载状态,提升用户交互体验。
内容的提问来源于stack exchange,提问作者StackUnderFlow
相关产品推荐
相关产品推荐

