繁体   English   中英

Nodemailer 不适用于 Heroku 部署

[英]Nodemailer not working on Heroku deployment

因此,我使用 Heroku 部署了我的网站组合,但我的联系表格(使用 nodemailer)不起作用。 这很奇怪,因为当我从我的电脑上尝试它时,我收到一个 email 但我从其他人那里听说它不能正常工作。 这是我的 index.js 的代码:

var express = require('express');
var router = express.Router();
var nodemailer = require('nodemailer');
var cors = require('cors');
const creds = require('./config');

var transport = {
    host: 'smtp.gmail.com', 
    port: 465,
    auth: {
    user: creds.USER,
    pass: creds.PASS
  }
}

var transporter = nodemailer.createTransport(transport)

transporter.verify((error, success) => {
  if (error) {
    console.log(error);
  } else {
    console.log('Server is ready to take messages');
  }
});

router.post('/send', (req, res, next) => {
  var name = req.body.name
  var email = req.body.email
  var message = req.body.message
  var content = ` name: ${name} \n email: ${email} \n message: ${message} `

  var mail = {
    from: name,
    to: 'js5360@columbia.edu', 
    subject: 'New Message from Contact Form',
    text: content
  }

  transporter.sendMail(mail, (err, data) => {
    if (err) {
      res.json({
        status: 'fail'
      })
    } else {
      res.json({
       status: 'success'
      })
    }
  })
})

const app = express()
app.use(cors())
app.use(express.json())
app.use('/', router)
app.listen(3002)

这是我使用的处理程序 function:

constructor(props) {
    super(props);                     
       this.state = {                      
          name: "",                                    
          email: "",                     
          message: "",                   
        }              
  }

  handleSubmit(e){
    e.preventDefault();
    axios({
      method: "POST", 
      url:"http://localhost:3002/send", 
      data:  this.state
    }).then((response)=>{
      if (response.data.status === 'success'){
        alert("Message Sent."); 
        this.resetForm()
      }else if(response.data.status === 'fail'){
        alert("Message failed to send.")
      }
    })
  }

  resetForm(){

     this.setState({name: "", email: "", message: ""})
  }

以前当我在 localhost 上工作时,我已经启用了对安全性较低的应用程序的访问,因此它在本地运行良好。

诚然,我对 express 或 nodemailer 了解不多,并按照此处概述的说明进行操作: https://blog.mailtrap.io/react-contact-form/ 我有一种感觉,我发送的 get/post 请求的 url 是本地的,这使得它无法在我自己的计算机上运行。

任何人都可以提供一些我必须解决的问题吗? 任何帮助将不胜感激:)

我现在实际上遇到了同样的问题,但是在达到这一点之前您可能需要解决一些问题,最重要的是环境变量。

尽管在端口 3002 上提供服务,您的页面是否仍在部署到 heroku? 就像您的内容在 Heroku 构建之后出现? 我有这个错误,如果你遇到它,你可以通过用 process.env.PORT 替换服务器端口来解决它,heroku 会在生产期间自动在内部分配。 请参阅我在下面粘贴的服务器文件。

const port = process.env.PORT || 3000;
...
app.listen(port, () => {
  console.log(`Server is up on port ${port}!`);
});

会处理的。

其次,部署 URL 时将不再是 localhost。 它必须指向以 api 路由 axios.post('www.example.com/send', object) 为后缀的域...

您可以在构建期间使用 dotenv 环境变量来处理这些问题,例如:

let URI = process.env.NODE_ENV === 'development' ? process.env.REACT_APP_DEV_URI : process.env.REACT_APP_PROD_URI;

并在你的根目录中有一个 .env 文件

REACT_APP_DEV_URI=http://www.localhost:3000
REACT_APP_PROD_URI=https://www.example.com

然后在你的反应客户端

axios.post(`${URI}/send-email`, data)

查找 dotenv npm 模块并使用它来根据应用程序是处于开发模式还是生产模式来提取不同的环境变量。 通过 process.env.NODE_ENV

最佳实践是 to.gitignore 这个文件,因为它在 github 上公开公开凭据。 Heroku 无论如何都会忽略它,环境变量必须通过 CLI 设置,您可以一次复制并粘贴一个并使用这些命令进行设置,或者 heroku 上有一个页面用于添加此配置。 https://devcenter.heroku.com/articles/config-vars

在服务器端同样的事情。

/**
 * express.router() option? : https://stackoverflow.com/questions/61852261/nodemailer-not-working-on-heroku-deployment
 */
const express = 
  require('express'), 
  bodyParser = require('body-parser'), 
  nodemailer = require('nodemailer'), 
  cors = require('cors'), path = require('path'), 
  port = process.env.PORT || 3000;

require('dotenv').config();

let directory = process.env.NODE_ENV === 'development' ? 'public' : 'build',
publicPath = path.join(__dirname, '..', directory);

const app = express();

console.log(process.env.NODE_ENV)

app.use(cors());
app.use(express.static(publicPath));

app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));


app.get('*', (req, res) => {
  res.sendFile(path.join(publicPath, 'index.html'));
});

app.post('/send-email', (req, res) => {
  console.log('request: ', req.body)
  let data = req.body;
  let transporter = nodemailer.createTransport({
    service: 'gmail',
    port: 465,
    auth: {
      user: process.env.EMAIL,
      pass: process.env.PASSWORD
    }
  });

  let mailOptions = {
    from: data.email,
    to: process.env.EMAIL,
    subject: `${data.subject}`,
    html: `<p>${data.name}</p>
            <p>${data.email}</p> 
            <p>${data.message}</p>`
  };

  // console.log('mailOptions are', mailOptions)

  transporter.sendMail(mailOptions,[
  (err, info) => {
    if(err) {
      res.send(err)
    } else {
      res.send(info.messageId)
    }
    transporter.close();
  }]);
})

app.listen(port, () => {
  console.log(`Server is up on port ${port}!`);
});

我会及时通知您我正在做什么以使我的工作也能正常工作。

尝试这个,

https://accounts.google.com/b/0/DisplayUnlockCaptcha

我收到了 Google 发送的 email,说明我的帐户正在从服务器位置访问,如果您告诉 Google 不要阻止它。

这将允许机器远程访问您的 Gmail。

我正在搜索类似的问题。 当我从本地后端服务器端口 3000 发送联系邮件时,它工作正常。 但是在推送到 Heroku 之后它没有用。 该问题与 .env 文件有关。

因此,通过将“.env”代码直接添加到 Heroku 仪表板的设置面板中的“Config Vars”中,我能够成功发送 email。

EMAIL_ID=your@email.com
PASSWORD=yourpassword

即密钥:EMAIL-ID 值:your@email.com 等。

一切顺利

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM