I'm trying few days to composing mail sending with node.js to gmail with no success :-(
at the beginning of tries I try to send form submittion to my gmail but first I need to understand how do I sent simple mail from body to gmail,
perhaps I wrong with syntax or missing something?
actually I uses "heroku" as storage and domain for my site
I tried several plugins (such as mailgun, send grid and more) but the process was too complicated integrate their API's into my site.
actually,
I find this article in stack overflow that describe how to send the via nodemailer in relation to my error - URL: node.js nodemailer gmail error
when i copy the answer1 to my code i still receiving error.
I' also pass trough all gmail setup how to turn off security block for less secured apps but i'm still receiving error.
all the requires installed over my npm
npm install --save
** code **
var nodemailer = require('nodemailer');
var smtpTransport = require('nodemailer-smtp-transport');
function handleSayHello(req, res) {
var transport = nodemailer.createTransport(smtpTransport({
service: 'gmail',
auth: {
user: 'myGmail#gmail.com', // my mail
pass: 'myPassword'
}
}));
var mailOptions = {
from: 'myGmail#gmail.com', // sender address
to: 'myGmail#gmail.com', // list of receivers
subject: 'Email Example' // Subject line
//text: text //, // plaintext body
//html: '<b>Hello world ?</b>' // You can choose to send an HTML body instead
};
transport.sendMail(mailOptions, function (error, info) {
if (error) {
console.log(error);
res.json({
yo: 'error',
err: error
});
} else {
console.log('Message sent: ' + info.response);
res.json({
yo: info.response,
info: info
});
};
});
}
router.get('/', function (req, res, next) {
handleSayHello(req, res);
});
then i receive this error:
{
"yo": "error",
"err": {
"code": "EAUTH",
"response": "534-5.7.14 <https://accounts.google.com/signin/continue?sarp=1&scc=1&plt=AKgnsbtx\n534-5.7.14 e8jnXXDaDg-dpFfc3H5ljeaBdmnxbXBDXMh-aXS-mmV4gQsXMSZLiiJHDXuOr3wy-IR2Zp\n534-5.7.14 xnznWLf5y5e3xTbJNlZBNcxBMajM9-SFQGy1MQM2XZRpHgtywuDtEj5iPiP0b2T6Wjbsxg\n534-5.7.14 hgehfzufG6h13qhjQK5IgRPNQsSICRQBtRCl3E1J62wFo8bnvZv4peY5aK55JMpwhSavJb\n534-5.7.14 ho-b9ExGGsXFmw_Er6lc8m3vCmO_Q> Please log in via your web browser and\n534-5.7.14 then try again.\n534-5.7.14 Learn more at\n534 5.7.14 https://support.google.com/mail/answer/78754 t35sm887733qtc.40 - gsmtp",
"responseCode": 534,
"command": "AUTH PLAIN"
}
}
if someone can take my code and fix it (if needed) and explain simply what do i need to modify in my google account I'll be great-full so much!
to allow from google/gmail, you should follow these links and allow to less secure apps access:
unlock account
and
Less secure apps
Let me know if still have issue, I'll check/debug your code.
Related
im trying to make a login endpoint/api, and i am sending the user login data through the authentication headers, is that okay for the security?
the authorization headers is actually contains an object, it is encoded to a Base64, it contains user data like hashed password (not hashed yet in this code), username, and some sort of a serverkey (to authorize if it is the right client that sending an api request), just wanna make sure if it is secure or not..
const aFunction = (req, res) => {
require('crypto').randomBytes(48, function(err, buffer) {
const token = buffer.toString('hex');
const auth = JSON.parse(Buffer.from(req.headers.authorization, 'base64').toString('ascii'))
if(auth.serverkey == version["serverkey"]){
loginUser(auth.username,token).then(data =>{
if (data.rows.length < 1 || data.rows[0].password != auth.password) {
res.send({
status: "failed",
message: "Username/Password is wrong",
status_code: 400
})
}else{
res.send({
status: "success",
message: "successfully logged in",
status_code: 200, token: token
})
}
})
}else{
res.send({
status: "failed",
message: "Unauthorized Client",
status_code: 401
})
}
});
}
I would add a check for if (req.secure) to your code, and reject any non-https request coming your way. (Don't do this if your nodejs program is behind a reverse proxy.)
Users with browsers can see everything you send back and forth to your server, whether via https or http. (devtools) So, if by reading your headers they can figure out how to send you malicious headers, then somebody will. And base64 encoding has exactly the same security as no encoding at all. So salt and hash your passwords. Use the bcrypt package or jwts.
I would handle errors this way, by calling next() with an error parameter rather than by using .send() to deliver a failure message. Use this sort of code.
const createError = require('http-errors')
...
const myfunction (req, res, next) {
...
if (!req.secure) return next(createError(403, 'https required'))
...
});
I am trying to make a contact page with react and I'm struggling with sending the e-mail part.
I'm trying to use nodemailer, and my code for that is:
var nodemailer = require('nodemailer');
var xoauth2=require('xoauth2');
var transporter = nodemailer.createTransport({
service: 'gmail',
auth: {
xoauth2:xoauth2.createXOAuth2Generator({
user: 'mymail#gmail.com',
clientId: '',
clientSecret: '',
refreshToken:''
})
}
});
var mailOptions = {
from: 'Name <mymail#gmail.com>',
to: 'mymail#gmail.com',
subject: 'Sending Email to test Node.js nodemailer',
text: 'That was easy to test!'
};
transporter.sendMail(mailOptions, function(error, info){
if (error) {
console.log(error);
} else {
console.log('Email sent');
}
});
I have put the clientId, clientSecret and refreshToken from google API and oauth2 playground and enabled the non secure apps thing. But when I'm trying to send the e-mail I get
TypeError: net.isIP is not a function
EDIT: I have tried adding after service: 'gmail'
type: 'SMTP',
host: 'smtp.gmail.com',
Still not working
I was facing the same issue when trying to implement the nodemailer code client side. The reason was because nodemailer doesn't seem to work in the browser (only in node). Moving it serverside (into an express app) solved the issue.
This post regarding the same error (but affecting a different library) also suggests that running the files in the browser is the problem: http://www.ganzhoupress.com/github_/cypress-io/cypress/issues/1981
Hope this helps.
replace ==>
var nodemailer = require('nodemailer');
with this ==>
var nodemailer = window.require('nodemailer');
this will solve your problem.
I'm a very beginner backend developer, so my apologies if this question is rather novice. For a certain javascript file, the script performs perfectly when I execute it using
$ node hello.js
However, I wish to execute this javascript code through a button click on my form. Encapsulating this code into a function and calling the function seems to result in an error every single time.
tls.connect is not a function
Is there a way to manually reproduce the terminal command $ node hello.js from javascript? Any solutions or helpful links would be greatly appreciated.
For some context, the code in question is meant to forward an email with a message to a single recipient when activated. I am using nodemailer to achieve this alongside a server hosted on DigitalOcean. The webapp is built using React.
sendMyMail(event) {
var nodemailer = require('nodemailer');
var smtpTransport = require('nodemailer-smtp-transport');
let transporter = nodemailer.createTransport(smtpTransport({
service: 'gmail',
secure: false,
port: 25,
auth: {
user: 'myemail#gmail.com',
pass: 'mypass'
},
tls: {
rejectUnauthorized: false
}
}));
let HelperOptions = {
from: '"Contact Form" <myemail#gmail.com',
to: 'myforward#gmail.com',
subject: 'Hello World',
text: 'Hello World 2.0'
};
transporter.sendMail(HelperOptions, (error, info) => {
if (error) {
console.log("Unable to send mail!");
return console.log(error);
}
console.log("The message was sent!");
console.log(info);
});
}
You will need a node server in order to send an email via the script you wrote. The script must be invoked in order to send the mail. In order to invoke that particular script, you'll need a server that will serve that script when route (which handles the script invocation) is encountered.
For details, see: https://appdividend.com/2017/08/11/send-email-in-node-js/#
I have spent couple of days implementing my own mail server using node.js. I used modules like "smtp-server" for creating smtp server and also "smtp-connection" to connect and send mail to it. But I'm getting confused because I don't know how to send mails from my smtp server to providers smtp servers like google or yahoo.
Can anyone help me?
Here is my code for more information:
My index.js file:
var SMTPServer = require('smtp-server').SMTPServer;
var port = 9025;
var serverOptions = {
name: "smtp-interceptor",
onConnect: onConnect,
onAuth: onAuth,
onData: onData
};
var server = new SMTPServer(serverOptions);
server.listen(port, 'localhost', function () {
console.log('SMTP server is listening on port ' + port);
});
function onConnect(session, callback) {
console.log('Connected');
return callback(); // Accept the connection
}
function onData(stream, session, callback) {
stream.pipe(process.stdout); // print message to console
console.log('Session \n', session.envelope);
stream.on('end', callback);
}
function onAuth(auth, session, callback){
if(auth.username !== 'Mahan' || auth.password !== 'Tafreshi') {
return callback(new Error('Invalid username or password'));
}
callback(null, {user: 123}); // where 123 is the user id or similar property
}
And my connection.js file:
var SMTPConnection = require('smtp-connection');
process.env.NODE_TLS_REJECT_UNAUTHORIZED = "0";
var connection = new SMTPConnection({
host: 'localhost',
port: 9025,
secure: false
});
connection.connect(function (){
console.log('Connceted to SMTP server');
var auth = {
user: 'Mahan',
pass: 'Tafreshi'
};
connection.login(auth, function (err) {
if(err)
return console.log('Login Failed \n', err);
console.log('Login Successful');
var envelope = {
from: "testapp#testapplocal.com",
to: "mahantp19#gmail.com"
};
var message = 'Test message1';
connection.send(envelope, message, function (err, info) {
if(err)
return console.log('Error : ' + err);
console.log('Message sent');
console.log('Accepted : ' + info.accepted);
console.log('Rejected : ' + info.rejected);
console.log(info.response);
connection.quit();
console.log('Quit connection');
connection.close();
});
});
});
There are many checks an email must pass before it's accepted by most mail providers. These checks attempt to validate the server sending the message is authorized to send on behalf of the sender.
IE: My server can send an email saying it's from "someone-special#somewhere-important.com"... That doesn't mean I'm "anywhere important" by any means.
While you may have had success sending mail from an SMTP server in the past using another technology such as PHP or an Exchange Server, the rules have changed significantly. Gmail has just began full enforcement this year.
I would assume your current issue has nothing to do with node as much as recent changes by the big providers.
Some of the checks that are needed include:
DKIM Keys (DNS Record)
SPF Record (DNS Record)
DMARK has been setup.
Dedicated IP Address for the server is required.
Your servers IP not being blacklisted.
The content of your email passes their filters.
Attempt to have an email sent from your server appear to be from a visitor or customer.
Among many others.
Any domain you want to "Act as Sender" must have these in place for most of the major providers to accept you message.
Google has a great set of tools and walkthroughs on getting an IP/Domain setup.
Visit the Google MX Record Checker and enter in the domain/subdomain you want to use as sender and it will tell you everything that is failing as well as passing.
Alternative Solutions
I use sendgrid.com. They have A node library that makes sending mail very easy. They also provide me the ability to proxy messages via SMTP. This means you can utilize the standard methods to deliver messages. You will just change out "localhost" with an hostname they provide. However, if this is for a new setup, go for the API.
Whomever is hosting your email should offer the ability for you send messages via SMTP or an API
An endless supply of other providers are out their, most of which allow low volume senders to send for FREE.
Word of warning
I tried for a few years keeping up with all the changes and inevitably, I continued to hit barriers of blocked messages with no ability to know until someone did not get an email. If your sending low volume, you should be able to use third parties without paying paying for it. If you are sending high volume, the cost of their service is cheap compared to the endless issues you will encounter even once you get it initially rolling.
PS. I have no affiliation with any email provider or sender. I pay them too.
Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
We don’t allow questions seeking recommendations for books, tools, software libraries, and more. You can edit the question so it can be answered with facts and citations.
Closed 8 months ago.
Improve this question
I have sent confirmation e-mails to users by using nodemailer for my project. It is working fine.
Now I am looking to send verification codes to mobile numbers from node.js, but I don’t know how to do that.
Is there any module to send verification codes to mobile numbers, like nodemailer does with e-mail addresses? Or if not, how can I do this myself?
I developing my project using node.js and mongodb, JavaScript and jQuery.
Most carriers provide a SMS gateway to which you can send an email and have it arrive as SMS. If you want a free way of sending SMS that works with your current nodemailer implementation, this is probably your best option. Otherwise, you might want to search for paid SMS services that you can integrate with.
Here is a list of SMS gateways: http://en.wikipedia.org/wiki/List_of_SMS_gateways
From the linked Wikipedia page:
For instance, to send to a number typically expressed in the USA as 987-555-0100, one would email 9875550100#SMS-gateway.
NodeJS package https://www.npmjs.com/package/springedge will be easy to send sms. You can install as
npm install springedge
Code example of sending sms:
// send sms
var springedge = require('springedge');
var params = {
'apikey': '', // API Key
'sender': 'SEDEMO', // Sender Name
'to': [
'919019xxxxxxxx' //Moblie Number
],
'message': 'test+message'
};
springedge.messages.send(params, 5000, function (err, response) {
if (err) {
return console.log(err);
}
console.log(response);
});
To ensure you can reach a users mobile no matter their location and network it's likely you're going to have to look at a paid service such as Nexmo (who I work for) or Twilio.
With these services you can either build your own verification (2FA - Two Factor Authentication) workflow:
User enters their phone number in a form and submits to your app
Your app receives the phone number
You send the user an SMS with an auth code
User receives the auth code
User enters auth code into a form and submits to your app
Your app receives the auth code and checks that auth code against the phone number (maybe using the current session phone number)
If the auth code is the one you are expected then the user is validated
Or you can use their 2FA authentication products (Nexmo - Verify or Twilio - Authy that should help simplify this workflow.
Using Nexmo verify the code would be:
Send Verification Request
var Nexmo = require('nexmo');
var nexmo = new Nexmo({apiKey: API_KEY, apiSecret: API_SECRET});
var verifyRequestId = null; // use in the check process
nexmo.verify.request({number: TO_NUMBER, brand: APP_NAME}, function(err, result) {
if(err) { console.error(err); }
else {
verifyRequestId = result. request_id;
}
});
Check Authentication Code
nexmo.verify.control({request_id: verifyRequestId, cmd: 'cancel'}, function(err, result) {
if(err) { console.error(err); }
else {
console.log(result);
}
});
You can use MSG 91 service. It provides OTP verification service as well.
One easiest way to send message to any number from node js is to use a library called fast-two-sms.
This library is easy to integrate in your project and it is also very cheap and provide free credit after signup.
Here's how you can integrate this library.
First install it:
npm install fast-two-sms
or
yarn add fast-two-sms
Then in js file:
const fast2sms = require('fast-two-sms')
var options = {authorization : YOUR_API_KEY , message : 'YOUR_MESSAGE_HERE' , numbers : ['9999999999','8888888888']}
fast2sms.sendMessage(options)
And don't forget to generate an api key from their website.
OR
You can use firebase authentication also.
For a testing you should use this API https://www.fast2sms.com however you can use it as a business too. Before running the below code make sure you have generated valid API Authorization Key and for that you should register for free.
Now place receiver's mobile number for bulk message to and you can use it as a verification and OTP purpose too.
Install npm module in your project, where you want to implement an SMS system.
npm install unirest
Code for GET method:
var unirest = require("unirest");
var req = unirest("GET", "https://www.fast2sms.com/dev/bulk");
req.query({
"authorization": "YOUR_API_KEY",
"sender_id": "FSTSMS",
"message": "This is a test message",
"language": "english",
"route": "p",
"numbers": "9999999999,8888888888,7777777777",
});
req.headers({
"cache-control": "no-cache"
});
req.end(function (res) {
if (res.error) throw new Error(res.error);
console.log(res.body);
});
Code for POST method:
var unirest = require("unirest");
var req = unirest("POST", "https://www.fast2sms.com/dev/bulk");
req.headers({
"authorization": "YOUR_API_KEY"
});
req.form({
"sender_id": "FSTSMS",
"message": "This is a test message",
"language": "english",
"route": "p",
"numbers": "9999999999,8888888888,7777777777",
});
req.end(function (res) {
if (res.error) throw new Error(res.error);
console.log(res.body);
});