You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

NextJS Server Actions结合Resend无法发送邮件排查求助

NextJS 13.5.1 Server Actions + Resend 发送邮件报错401(缺失API Key)

问题场景

使用NextJS 13.5.1并启用Server Actions,通过表单提交调用Server Actions结合Resend发送邮件。已通过curl验证Resend API Key可正常发送邮件,但在项目中执行时始终返回以下401错误:

{
statusCode: 401,
message: "Missing API Key",
name: "missing_api_key"
}


相关代码

表单组件文件(packages/landing/src/containers/AgencyFormal/ContactUs/index.js)

import React, { useState } from 'react';
import {
  Container,
  FormWrapper,
  Heading,
  Form,
  Row,
  FormField,
  RequiredLabel,
  Input,
  Button,
  Label,
  Textarea,
} from "./contactUs.style";
import { sendEmail } from '@/../actions/sendEmail';

const ContactUs = () => {
  const [name, setName] = useState('');
  const [email, setEmail] = useState('');
  const [message, setMessage] = useState('');
  const [isLoading, setIsLoading] = useState(false);
  const [status, setStatus] = useState(null);

  const onSubmit = async (e) => {
    e.preventDefault();
    setIsLoading(true);
    const result = await sendEmail({ name, email, message });
    console.log("Sending...")

    if (result.success) {
      console.log("Success")
      setStatus('Email sent successfully!');
      setName('');
      setEmail('');
      setMessage('');
    } else {
      setStatus(result.error);
    }
    setIsLoading(false);
  };

  return (
    <Container>
      <Heading>Connect with Our Team of Experts</Heading>
      <FormWrapper>
        <Form onSubmit={onSubmit}>
          <Row>
            <FormField>
              <RequiredLabel htmlFor="name">Full Name</RequiredLabel>
              <Input
                type="text"
                id="name"
                name="name"
                placeholder="John Doe"
                onChange={(e) => setName(e.target.value)}
                value={name}
                required
              />
            </FormField>
            <FormField>
              <RequiredLabel htmlFor="email">Email</RequiredLabel>
              <Input
                type="email"
                id="email"
                name="email"
                placeholder="doe@email.com"
                onChange={(e) => setEmail(e.target.value)}
                value={email}
                required
              />
            </FormField>
          </Row>
          <Row>
            <FormField>
              <RequiredLabel htmlFor="phone">Phone</RequiredLabel>
              <Input
                type="tel"
                id="phone"
                name="phone"
                placeholder="+1 555 123 4567"
                required
              />
            </FormField>
            <FormField>
              <Label htmlFor="website">Website</Label>
              <Input
                type="text"
                id="website"
                name="website"
                placeholder="yourwebsite.com"
              />
            </FormField>
          </Row>
          <FormField>
            <RequiredLabel htmlFor="message">Message</RequiredLabel>
            <Textarea
              id="message"
              name="message"
              placeholder="How can I help you?"
              onChange={(e) => setMessage(e.target.value)}
              value={message}
              required
            />
          </FormField>
          <Button type="submit" disabled={isLoading}>
            {isLoading ? 'Sending...' : 'Submit'}
          </Button>
          {status && <p>{status}</p>}
        </Form>
      </FormWrapper>
    </Container>
  );
};

export default ContactUs;

Server Action文件(packages/landing/src/actions/sendEmail.js)

import { Resend } from 'resend';


export async function sendEmail(data) {
  'use server';
  const { name, email, message } = data;
  const resend = new Resend(process.env.RESEND_KEY);

  try {
    await resend.emails.send({
      from: "anitadd@gmail.com",
      to: ['bobby@gmail.com'],
      subject: 'Contact form submission',
      text: "This is website",
    });
    console.log("try")
    return { success: true };
  } catch (error) {
    console.error('Error sending email:', error);
    return { error: 'Failed to send email' };
  }
}

解决方案

1. 修正环境变量文件位置

在monorepo结构下,环境变量文件必须放在**packages/landing目录下**,而非项目根目录。创建packages/landing/.env.local并配置:

RESEND_KEY=你的实际Resend API密钥

NextJS默认从当前应用目录加载.env.local,根目录的环境变量子包无法读取。

2. 验证环境变量读取

在sendEmail.js中添加临时日志,确认变量是否加载成功:

export async function sendEmail(data) {
  'use server';
  console.log('RESEND_KEY:', process.env.RESEND_KEY); // 检查控制台输出
  // ... 原有代码
}

如果输出为undefined,检查文件名是否为.env.local(.env仅在生产构建时生效,开发环境需用.env.local)。

3. 重启开发服务器

修改环境变量后,必须重启NextJS开发服务器,否则新变量不会生效。

4. 确认Server Actions配置

检查next.config.js中是否启用Server Actions(NextJS 13.4+默认启用,但自定义配置时需确保未禁用):

/** @type {import('next').NextConfig} */
const nextConfig = {
  experimental: {
    serverActions: true,
  },
};

module.exports = nextConfig;

5. 核对API密钥一致性

确保项目中使用的API密钥和curl测试时完全一致,避免复制错误或使用了无效的测试密钥。


内容的提问来源于stack exchange,提问作者Dr4ke the b4dass

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 18:40:20