Unexpected token '.' while trying to use Nodemailer SES transport sdk - node.js

I need to extend the functionality of my SMTP feature to handle bulk emails. It works fine, however when a big amount of emails presented it sends them very slowly (about 2-3 per second). Our current AWS plan allows up to 15 emails per second. I read NodeMailer documentation and tried to implement the SES SDK, however it crashes my app right away.
Here is an error:
/home/node/app/node_modules/#aws-sdk/client-ses/dist-cjs/protocols/Aws_query.js:3734
if (input.ReplacementTags?.length === 0) {
^
SyntaxError: Unexpected token '.'
at wrapSafe (internal/modules/cjs/loader.js:915:16)
at Module._compile (internal/modules/cjs/loader.js:963:27)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:1027:10)
at Module.load (internal/modules/cjs/loader.js:863:32)
at Function.Module._load (internal/modules/cjs/loader.js:708:14)
at Module.require (internal/modules/cjs/loader.js:887:19)
at require (internal/modules/cjs/helpers.js:74:18)
at Object.<anonymous> (/home/node/app/node_modules/#aws-sdk/client-ses/dist-cjs/commands/CloneReceiptRuleSetCommand.js:8:21)
at Module._compile (internal/modules/cjs/loader.js:999:30)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:1027:10)
[nodemon] app crashed - waiting for file changes before starting...
Here is my dependency list:
"#aws-sdk/client-ses": "^3.204.0",
"#aws-sdk/credential-provider-node": "^3.204.0",
"nodemailer": "^6.4.16"
And here is my nodeMailer code:
require('dotenv').config()
const nodemailer = require('nodemailer')
const Settings = require('./agentLogic/settings')
const Util = require('./util')
let aws = require('#aws-sdk/client-ses') // new feature I'm trying to implement
let {defaultProvider} = require('#aws-sdk/credential-provider-node') // new feature I'm trying to implement
const ses = new aws.SES({
apiVersion: '2010-12-01',
region: 'us-west-2',
defaultProvider,
}) // new feature I'm trying to implement
let currentSMTP = {}
async function emailService() {
currentSMTP = await Settings.getSMTP()
const decryptedPassword = Util.decrypt(
currentSMTP.dataValues.value.auth.pass,
currentSMTP.dataValues.value.IV,
)
const transporter = nodemailer.createTransport({
host: currentSMTP.dataValues.value.host,
// Defaults to 587 if "secure" is false or no value provided or 465 if true
port:
currentSMTP.dataValues.value.encryption === false
? 587
: !currentSMTP.dataValues.value.encryption
? 587
: currentSMTP.dataValues.value.encryption,
// False for STARTTLS (must use port 587), true for TLS (must use port 465)
secure: !currentSMTP.dataValues.value.encryption
? false
: currentSMTP.dataValues.value.encryption,
auth: {
user: currentSMTP.dataValues.value.auth.mailUsername
? currentSMTP.dataValues.value.auth.mailUsername
: currentSMTP.dataValues.value.auth.email,
pass: decryptedPassword,
},
tls: {
// Change to "false" to not fail on invalid certs
rejectUnauthorized: true,
},
SES: {ses, aws}, // new feature I'm trying to implement
sendingRate: 15, // new feature I'm trying to implement (I need this to match our current AWS SMTP plan of 15 emails/second)
})
return transporter
}
const sendMail = async (message) => {
const transporter = await emailService()
return new Promise((resolve, reject) => {
transporter.sendMail(message, (error, info) => {
if (error) {
console.log('Error occurred')
console.log(error.message)
reject('error')
} else {
console.log('Message sent successfully!')
console.log(nodemailer.getTestMessageUrl(info))
resolve(true)
}
// Only needed when using pooled connections
transporter.close()
})
})
}
Please, note that by default all the SMTP settings are not set. The user may or may not set the SMTP on demand. But the app comes without some SMTP preset values (such as host, username, email etc)
Can anyone help me understand why I'm getting and how to fix it?

Related

Unexpected token ')' Nodejs with Couchdb

I am using nodejs 14 and couchdb database 3.1.1
I am trying to connect and display list of couchdb databases using nodejs but following error occur
const NodeCouchDb = require('node-couchdb');`
const couch = new NodeCouchDb();
// node-couchdb instance with Memcached
const MemcacheNode = require('node-couchdb-plugin-memcached');
const couchWithMemcache = new NodeCouchDb({
cache: new MemcacheNode
});
// node-couchdb instance talking to external service
const couchExternal = new NodeCouchDb({
host: 'couchdb.external.service',
protocol: 'https',
port: 5984
});
// not admin party
const couchAuth = new NodeCouchDb({
auth: {
user: 'admin',
pass: 'godhelp'
}
});
couch.listDatabases()
.then(
dbs => dbs.map(...),
err => {
// request error occured
});
ERROR After Compiled :
dbs => dbs.map(...),
^
SyntaxError: Unexpected token ')'
at wrapSafe (internal/modules/cjs/loader.js:988:16)
at Module._compile (internal/modules/cjs/loader.js:1036:27)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:1101:10)
at Module.load (internal/modules/cjs/loader.js:937:32)
at Function.Module._load (internal/modules/cjs/loader.js:778:12)
at Function.executeUserEntryPoint [as runMain] (internal/modules/run_main.js:76:12)
at internal/main/run_main_module.js:17:47
I think there is a syntax error in your code, but more fundamentally node-couchdb seems to be an inactive library that has not been updated in more than four years. I would recommend using nano, which is the official Apache CouchDB NodeJS library.
Here's a simple NodeJS script (index.js) using nano to list your databases.
const nano = require('nano')(process.env.COUCH_URL)
const main = async function() {
const response = await nano.db.list()
console.log(response)
}
main ()
You will need to create an environment variable called COUCH_URL:
export COUCH_URL="http://user:password#localhost:5984"
and then run the script:
node index.js
#[ 'deeds' ]

How to use greenlock module in node without express

I've been trying to use the greenlock.js module for Node to try and obtain ssl certificates for a domain registered in cloudflare.
I have seen some examples on greenlock-express, however, I would like to use this module without needing to use express.
The issue is that I obtain the following error when creating the greenlock object:
internal/validators.js:120
throw new ERR_INVALID_ARG_TYPE(name, 'string', value);
^
TypeError [ERR_INVALID_ARG_TYPE]: The "path" argument must be of type string. Received undefined
at validateString (internal/validators.js:120:11)
at Object.resolve (path.js:980:7)
at Object.Init._init (/git_reps/greenlock_test/node_modules/#root/greenlock/lib/init.js:128:14)
at Object.greenlock._create (/git_reps/greenlock_test/node_modules/#root/greenlock/greenlock.js:58:22)
at Object.G.create (/git_reps/greenlock_test/node_modules/#root/greenlock/greenlock.js:482:15)
at Object.<anonymous> (/git_reps/greenlock_test/greenlock-test.js:13:27)
at Module._compile (internal/modules/cjs/loader.js:1138:30)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:1158:10)
at Module.load (internal/modules/cjs/loader.js:986:32)
at Function.Module._load (internal/modules/cjs/loader.js:879:14) {
code: 'ERR_INVALID_ARG_TYPE'
}
My code is as follows, I have not even implemented any other function yet because it breaks here:
1 'use strict'
2
3 const pkg = require ('./package.json');
4 const Greenlock = require('greenlock');
5 const acmeDnsCloudflare = require('acme-dns-01-cloudflare');
6
7 const cloudflareDns01 = new acmeDnsCloudflare({
8 token: 'dummyToken',
9 verifyPropagation: true,
10 verbose: true
11 });
13 let greenlock = Greenlock.create({
14 configDir: './greenlock.d/config.json',
15 packageAgent: pkg.name + '/' + pkg.version,
16 maintainerEmail: 'maintaner#example.com',
17 staging: true,
18 notify: function(event, details){
19 if('error'=== event){
20 console.error(details);
21 }
22 }
23 });
I don't know wich version you're using, using current 4.0.5 the challenge module has to be defined as a string and is instanciate internally by GreenLock
"use strict";
var config_ovh = require('./my_modules/config_ovh');
var pkg = require("./package.json");
var Greenlock = require("#root/greenlock");
var greenlock = Greenlock.create({
packageRoot: __dirname,
configDir: "./greenlock.d/",
packageAgent: pkg.name + "/" + pkg.version,
maintainerEmail: "me#domain.fr",
staging: true,
notify: function (event, details) {
if ("error" === event) {
console.error('greenlock notify :' + event, details);
}
},
});
greenlock.manager
.defaults({
agreeToTerms: true,
subscriberEmail: "me#domain.fr",
store: {
module: "greenlock-store-fs",
basePath: "./certs",
},
challenges: {
"dns-01": {
module: "acme-dns-01-ovh",
appKey: config_ovh.appKey,
appSecret: config_ovh.appSecret,
consumerKey: config_ovh.consumerKey,
region: "ovh-eu",
propagationDelay: 5000,
},
},
})
.then(function (fullConfig) {
//...
});
var altnames = [
"sub1.domain.fr",
"sub2.domain.fr",
];
greenlock
.add({
subject: altnames[0],
altnames: altnames,
})
.then(function () {
// saved config to db (or file system)
console.log('greenlock then', arguments);
});
This code successfully generates the certificates (acme-dns-01-ovh being my own implementation for the OVH DNS challenge), but the process terminates and I currently don't see how the auto-renewal works...

How do I fix my Discord bot being offline?

I got recently interested in discord bots coding and I don't know what the problem is with this error, I tried different solutions I can find but all of them are not working and my bot is still offline on the server.
Error: Invalid transport, must be an object with a log method.
at new LegacyTransportStream (C:\Users\redacted\Desktop\NinyaBot\node_modules\winston-transport\legacy.js:18:11)
at DerivedLogger.add (C:\Users\redacted\Desktop\NinyaBot\node_modules\winston\lib\winston\logger.js:345:11)
at Object.winston.<computed> [as add] (C:\Users\redacted\Desktop\NinyaBot\node_modules\winston\lib\winston.js:110:68)
at Object.<anonymous> (C:\Users\redacted\Desktop\NinyaBot\bot.js:6:8)
at Module._compile (internal/modules/cjs/loader.js:1133:30)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:1153:10)
at Module.load (internal/modules/cjs/loader.js:977:32)
at Function.Module._load (internal/modules/cjs/loader.js:877:14)
at Function.executeUserEntryPoint [as runMain] (internal/modules/run_main.js:74:12)
at internal/main/run_main_module.js:18:47
this is the code i used that i found online.
var Discord = require('discord.io');
var logger = require('winston');
var auth = require('./auth.json');
// Configure logger settings
logger.remove(logger.transports.Console);
logger.add(logger.transports.Console, {
colorize: true
});
logger.level = 'debug';
// Initialize Discord Bot
var bot = new Discord.Client({
token: auth.token,
autorun: true
});
bot.on('ready', function (evt) {
logger.info('Connected');
logger.info('Logged in as: ');
logger.info(bot.username + ' - (' + bot.id + ')');
});
bot.on('message', function (user, userID, channelID, message, evt) {
// Our bot needs to know if it will execute a command
// It will listen for messages that will start with `!`
if (message.substring(0, 1) == '!') {
var args = message.substring(1).split(' ');
var cmd = args[0];
args = args.splice(1);
switch(cmd) {
// !ping
case 'ping':
bot.sendMessage({
to: channelID,
message: 'Pong!'
});
break;
// Just add any case commands if you want to..
}
}
});
The error showed in console is about line 6, however maybe is not what makes the
bot appears offline.
logger.add(logger.transports.Console, {
colorize: true
});
And should be fixed with something like
logger.add(new logger.transports.Console({
format: winston.format.combine(
winston.format.colorize(),
winston.format.simple()
)
}));
Watch to new word. Now transports require a new object to work and for colorize you can set it combining the formats.
Here you can find more info about it https://www.npmjs.com/package/winston#common-transport-options
I recommend using discord.js https://discordjs.guide/creating-your-bot/#creating-the-bot-file
Use this code and it work just fine:
const Discord = require('discord.js');
const client = new Discord.Client();
client.once('ready', () => {
console.log('Ready!');
});
client.login('your-token-goes-here');

I was writing Discord bot with index.js and .env and I messed with this error while running this in terminal "node index.js"

I want develop my own discord bot here's the contents:
Index code
const { Client } = require("discord.js");
const { config } = require("dotenv");
// Declares our bot,
// the disableEveryone prevents the client to ping #everyone
const client = new Client({
disableEveryone: true
});
config({
path: __dirname + "/.env"
})
// When the bot's online, what's in these brackets will be executed
client.on("ready", () => {
console.log(`Hi, ${client.user.username} is now online!`);
// Set the user presence
client.user.setPresence({
status: "online",
game: {
name: "me getting developed",
type: "WATCHING"
}
});
})
// When a message comes in, what's in these brackets will be executed
client.on("message", async message => {
console.log(`${message.author.username} said: ${message.content}`);
});
// Login the bot
client.login(process.env.TOKEN);
Output
disableEveryone = true
^^^^^^^^^^^^^^^^^^^^^^
SyntaxError: Invalid shorthand property initializer
at Module._compile (internal/modules/cjs/loader.js:891:18)
at Object.Module._extensions..js (internal/modules/cjs/loader.js:991:10)
at Module.load (internal/modules/cjs/loader.js:811:32)
at Function.Module._load (internal/modules/cjs/loader.js:723:14)
at Function.Module.runMain (internal/modules/cjs/loader.js:1043:10)
at internal/main/run_main_module.js:17:11
Invalid shorthand property initializer indicates that you used an invalid property initializer. In this case, it looks like you used "=" instead of ":" to declare the property value "true" on property "disableEveryone".
Saving the code as shared and running it again should solve your problem.

NodeMailer - Transport option must be a transport instance or configuration object

I am trying to create a email verification mailer following the example from here. I added both email-template and nodemailer packages. I made the transporter available as an adapter throughout my application. Below is the code for mailer.ts:
import * as mailer from 'nodemailer';
import * as dotenv from 'dotenv';
dotenv.load({ path: '.env' });
var mailConfig = {
host: process.env.MAIL_HOST,
port: process.env.MAIL_PORT,
auth: {
user: process.env.MAIL_USERNAME,
pass: process.env.MAIL_PASSWORD
}
};
var transporter = mailer.createTransport(mailConfig);
module.exports = transporter;
I am trying to build a wrapper around email-template like below signup.ts:
const EmailTemplate = require('email-templates');
var mailer = require('../mailer');
var sendEmailVerficationLink = mailer.templateSender(
new EmailTemplate({
views: { root: './verify' }
}), {
from: process.env.MAIL_FROM,
});
exports.sendVerficationLink = function (obj) {
sendEmailVerficationLink({
to: obj.email,
subject: 'Verify your Email'
}, {
name: obj.username,
token: obj.otp
}, function (err, info) {
if (err) {
console.log(err)
} else {
console.log('Sign up mail sent to ' + obj.email + ' for verification.');
}
});
};
In my actual controller, I try to send the mail as below user.ts:
var verify = require('../utils/mailer-templates/signup');
signup = (req, res) => {
..
verify.sendVerficationLink(obj); // send the actual user object
..
}
But I keep getting this error:
Error: Transport option must be a transport instance or configuration object
[1] at new Email (C:\Users\User\Documents\Vivavii-REST\node_modules\email-templates\lib\index.js:82:83)
[1] at Object.<anonymous> (C:\Users\User\Documents\Vivavii-REST\dist\utils\mailer-templates\signup.js:3:54)
[1] at Module._compile (module.js:641:30)
[1] at Object.Module._extensions..js (module.js:652:10)
[1] at Module.load (module.js:560:32)
[1] at tryModuleLoad (module.js:503:12)
[1] at Function.Module._load (module.js:495:3)
[1] at Module.require (module.js:585:17)
[1] at require (internal/module.js:11:18)
[1] at Object.<anonymous> (C:\Users\User\Documents\Vivavii-REST\dist\controllers\user.js:14:14)
[1] at Module._compile (module.js:641:30)
[1] at Object.Module._extensions..js (module.js:652:10)
[1] at Module.load (module.js:560:32)
[1] at tryModuleLoad (module.js:503:12)
[1] at Function.Module._load (module.js:495:3)
[1] at Module.require (module.js:585:17)
Main issue You used outdated example. In the example nodemailer has 2.7.2 version and unknown email-templates. Current nodemailer version is 4.4.1.
In the latest email-templates version you don't need directly work with nodemailer. You can pass configuration in transport params. Here is fixed version of your code:
const EmailTemplate = require('email-templates');
const dotenv = require('dotenv');
dotenv.load({ path: '.env' });
const emailTemplate = new EmailTemplate({
message: {
from: process.env.MAIL_FROM
},
transport: {
host: process.env.MAIL_HOST,
port: process.env.MAIL_PORT,
auth: {
user: process.env.MAIL_USERNAME,
pass: process.env.MAIL_PASSWORD
}
}
});
function sendVerficationLink(obj) {
return emailTemplate.send({
template: 'verify',
message: {
to: obj.email
},
locals: {
name: obj.username,
token: obj.otp
}
});
};
exports.sendVerficationLink = sendVerficationLink;
Some details:
mailer.ts is redundant
in project there is folder emails with templates. More infomation

Resources