template design for sending mail using nodejs - node.js

This is my code. When it runs in Postman it shows error like cannot get method.
var sendTempMail = function (req,res)
{
const nodemailer = require('nodemailer');
let transporter = nodemailer.createTransport({
host: 'smtp.gmail.com',
auth: {
user: 'transactions#gmail.com',
pass: 'qwertyu#'
}
});
let mailOptions = {
from: 'transactions#gmail.com',
to: 'xxxxxx#gmail.com','yyyyyyyy#gmail.com',zzzzzz#mydomain.com,//here to:receiver not accept more than one
subject: 'mail notification Test',
text: 'Hello !!!!!!!!!everything works fine'
html:<h1>Notification mail</h1>
<head>
<style>
table, th, td {
border: 1px solid black;
border-collapse: collapse;
}
th, td {
padding: 10px;
text-align: left;
}
</style>
</head>
<body>
<table style="width:100%">
<tr>
<th>Firstname</th>
<th>Lastname</th>
<th>Age</th>
</tr>
<tr>
<td>Jill</td>
<td>Smith</td>
<td>50</td>
</tr>
<tr>
<td>Eve</td>
<td>Jackson</td>
<td>94</td>
</tr>
<tr>
<td>John</td>
<td>Doe</td>
<td>80</td>
</tr>
</table>
</body>
};
transporter.sendMail(mailOptions, (error, info) => {
if (error) {
return console.log("mail not sent" +error.message);
}
console.log('success');
});
};
module.exports = {
newTemplate :newTemplate,
sendTempMail : sendTempMail
};

Please paste your error message with your question. However I can see one mistake that the HTML parameter has all raw html pasted there. It should be in string format.
Please check line no 44 in the code in below link
https://github.com/nodemailer/nodemailer/blob/master/examples/full.js

Related

Node.js Socket.io Error when trying to connect client to server

I am trying to create a Web chat and to do this 1st we need to set up a client to server connection via Node and Socket.io - and it is not working.
The server code is here:
https://collectiveboost.com/cb_node/chat_app/server.js
And it runs fine when started via: node server.js
printing results to putty command line of: “Socket io Server Chat Started...”
But on client side the socket.io connection is not happening :(
And we have tried it both ways, that is via global socket.io as you can see here:
https://collectiveboost.com/cb_node/chat_app/index.htm
this results in Error:
Failed to load resource: the server responded with a status of 404 (Not Found)
Uncaught Reference Error: io is not defined at (index):14
And via local version of the client-side JS file which can be reached via: node_modules/socket.io/client-dist/socket.io.js
as stated on:
https://socket.io/get-started/chat
which you can see here:
https://collectiveboost.com/cb_node/chat_app/index_2.htm
this results in Error:
polling-xhr.js:157 GET https://collectiveboost.com/socket.io/?EIO=4&transport=polling&t=Nt9UN_R 404 (Not Found)
So what are we doing wrong?
How can we connect the client side Web page socket.io to server?
Thanks
please try this code and its very usefull to you.
Its a basic simple chat system.
Server Code
var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http);
app.get('/', function(req, res) {
res.sendFile(__dirname + '/index6.html');
});
var username = '';
var rooms;
io.on('connection', function(socket) {
console.log("User connected");
socket.on('join', function(name) {
username = name;
//console.log(username)
io.emit('chat-msg', `${username.toUpperCase()} Welcome`);
})
socket.join(rooms)
socket.on('chat msg', function(msg) {
//console.log(msg);
io.sockets.in(rooms).emit('chat msg', msg)
//console.log(array)
})
socket.on('disconnect', function(name) {
console.log("disconnet")
io.emit('chat-msg', `${username.toUpperCase()} disconnected`)
})
});
http.listen(5600, function() {
console.log('listening on localhost:5600');
});
Client Code
<!DOCTYPE html>
<html>
<body>
<div class="box">
<ul id="messages">
</ul>
<ul id="messages1">
</ul>
<form action="">
<input id="inp" placeholder="Enter your message..." autocomplete="off" required /><button>Send</button>
</form>
<script src="/socket.io/socket.io.js"></script>
<script src="https://code.jquery.com/jquery-3.4.1.min.js"></script>
<script>
var name = prompt("enter name")
var socket = io();
socket.emit('join', name);
$('form').submit(function(event) {
event.preventDefault();
socket.emit("chat msg", (name + " : " + $("#inp").val()));
//$('#messages').append($('<li id="list">').text('You: ' +$('#inp').val()));
$('#inp').val('');
});
socket.on('chat-msg', function(msg) {
$('#messages').append($('<li id="list"><br>').text(msg));
})
socket.on('chat msg', function(msg) {
$('#messages1').append($('<li id="list1"><br>').text(msg));
})
socket.on('left', function(data) {
document.write(data.description)
})
</script>
</div>
<style>
.box {
border: 1px solid red;
height: auto;
width: 500px;
position: absolute;
right: 300px;
border-radius: 10px;
padding: 30px;
}
#inp {
position: absolute;
bottom: 10px;
right: 200px;
outline: none;
border: soild blue;
border-radius: 5px;
}
ul {
list-style-type: none;
padding: 50px;
text-align: center;
}
#list {
text-align: center;
background-color: #6195e8;
color: #fffafa;
border-radius: 10px;
}
#list1 {
text-align: right;
background-color: #6bdde3;
color: #ed001c;
}
button {
color: White;
background-color: green;
width: 80px;
border-radius: 10px;
position: absolute;
right: 150px;
bottom: 10px;
}
#messages li {
padding: 5px 10px;
}
</style>
</body>
</html>

Node.js Cheerio returning empty with no errors

i am trying to get data from table with structure like this:
<table id="ros_table" class="info" style="display: none;">
<tr>
<th>First</th>
<th>Second</th>
<th>Third</th>
<th>Forth</th>
<th>Fifth</th>
<th>Six</th>
</tr>
<tr>
<td style="white-space: nowrap;">120241</td>
<td style="white-space: nowrap;">69801:001:0255</td>
<td>Name</td>
<td>Name 2</td>
<td><span style="white-space: nowrap;">90400 m<sup>2</sup></span> <span style="white-space: nowrap;">(9.04 ha)</span></td>
<td style="white-space: nowrap;">jah</td>
</tr>
And the code im useing is this:
fetchData(url).then( (res) => {
const html = res.data;
const $ = cheerio.load(html);
const statsTable = $('.table#ros_table > tr');
statsTable.each(function() {
let title = $(this).find('td').text();
console.log(title);
});
})
async function fetchData(url){
console.log("Looking for stuff you need...")
// Make the call
let response = await axios(url).catch((err) => console.log(err));
if(response.status !== 200){
console.log("Blah, this did not work out");
return;
}
return response;
}
It works fine with just a simple que, but for some reason i can get it to work for this table.
You need to return something out of each .then() block, i assume you want something like this?:
fetchData(url).then( (res) => {
const html = res.data;
const $ = cheerio.load(html);
const statsTable = $('.table#ros_table > tr');
return statsTable.map(function() {
return $(this).find('td').text();
});
})

How do i auto-refresh my log rather then refreshing it manually

I currently have a log box which shows the log from my backend. I have a button to refresh the log and the latest set of logs shows up. How do I set it to a auto-refresh log?
I have the code below for the button and switchbox
<div class="form-group row m-b-10">
<label class="col-form-label">Auto-Refresh:</label>
<div class="col-md">
<div class="switcher switcher-success">
<input type="checkbox" v-model="checked" name="switcher_checkbox_2" id="switcher_checkbox_2" checked="true" value="1" v-on:change="toggle">
<label for="switcher_checkbox_2"></label>
</div>
<div class="switcher switcher-success">
<button v-if="!checked" #click="logNode(namespace)" class="btn btn-xs btn-success">Refresh</button>
</div>
</div>
And the function for the refresh button is below. How do I call a function for the log to load on auto refresh when the switchbox is on?
logNode(namespace) {
console.log(namespace)
this.hidemodal = true;
this.logShow = true;
var requestobj = {
Namespace: namespace,
};
var apiobj = {
tablename: "bnm",
Id: VueCookies.get("activeNetwork_Id"),
method: "post"
};
var obj = {
apiobj: apiobj,
mainobj: requestobj
};
this.$store
.dispatch("logsAPI", obj)
.then(response => {
console.log(response);
console.log("test result");
if (response.data || response.status == 200) {
this.logString = response.data.Logstr;
this.$notify({
group: "querynotify",
title: "Success",
type: "success",
position: "top-right",
text: "Sucessfully Created Logs " + ":\n" + response.data.Username
});
} else {
this.$notify({
group: "querynotify",
title: "Error",
type: "warn",
position: "top-right",
text: "Error Creating Logs " + ":\n" + response.data.Username
});
}
})
.catch(error => {
this.$notify({
group: "querynotify",
title: "Error",
type: "error",
position: "top-right",
text: "Error View this node Log" +
":\n" +
error.data.err +
":\n" +
error.data.details
});
});
},
When you check box is checked, you can use setInterval() and when your checkbox is unchecked clearInterval.
Please check below working snippet.
*Note in this snippet, I have just used simple log for demo purpose. In that demo you can put your logic.
new Vue({
el: '#app',
data: {
checked: false,
autoRef:null
},
methods: {
toggle() {
if(this.checked){
this.autoRef = setInterval(() => {
this.logNode('Auto refresh called');
}, 3000);
}else{
clearInterval(this.autoRef);
}
},
logNode(msg) {
console.log(msg)
}
}
});
.btn-success {
background: green;
padding: 10px;
border: 1px solid #ccc;
color: #fff;
}
<link href="https://cdn.jsdelivr.net/npm/vuetify#1.2.2/dist/vuetify.min.css" rel="stylesheet" />
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/vuetify#1.2.2/dist/vuetify.min.js"></script>
<div id="app" class="form-group row m-b-10">
<label class="col-form-label">Auto-Refresh:</label>
<div class="col-md">
<div class="switcher switcher-success">
<input type="checkbox" v-model="checked" name="switcher_checkbox_2" id="switcher_checkbox_2" checked="true" value="1" v-on:change="toggle">
<label for="switcher_checkbox_2"></label>
</div>
<div v-if="!checked" class="switcher switcher-success">
<button ref="myButton" #click="logNode('on button click')" class="btn btn-xs btn-success">Refresh</button>
</div>
</div>

How to display mongoDB collection in html?

I am a beginner with mongoose and would like to display a mongoDB document(s) from "exColl" collection in a file called "example.ejs" in a basic html list however I have hit various problems. There are other posts on this topic yet I remain stumped by this.
-I do have a working chunk of code that outputs all documents from exColl.find({}) using res.json, obviously putting them in json format. However I have been unable to adapt this code into something that works using res.render for example.
-When I define a variable in app.js and try to access it in example.ejs the variable is not found, therefore even if I could save the results of exColl.find({}) in a variable I don't see how I would be able to enter it into the HTML
Clearly I don't know what I don't know which is very frustrating. If someone could help fill my conceptual gaps that would be fantastic.
---Edit----
Adding a snippet I have tried
app.get("/example", function (req, res){
exColl.find({})
.exec(function (err, examples){
if (err) {
res.send("an error has occurred")
} else res.render(examples: examples);
});
});
In .ejs file
<p> <%= examples %> </p>
Your problem seems to be the EJS syntax which you should review here: EJS Docs. Consider the following test project structure:
.
├── index.js
├── package.json
├── setup.js
└── views
├── index.ejs
└── table.ejs
I create a test DB with setup.js so that we have some dummy posts to display:
const mongoose = require("mongoose");
mongoose.connect("mongodb://localhost:8081/test", {
useNewUrlParser: true
});
const Post = mongoose.model("Post", {
title:String,
body: String
});
const toMake = [
{title: "hello", body: "world"},
{title: "foo", body: "bar"},
{title: "fizz", body: "buzz"},
{title: "a", body: "b"}
];
Post.insertMany(toMake)
.then(()=>{
console.log("done");
mongoose.connection.close();
})
.catch(err => console.error(err));
I create an EJS template views/table.ejs to render my posts as a table:
<table>
<thead>
<tr>
<th>Title</th>
<th>Body</th>
</tr>
</thead>
<tbody>
<% posts.forEach(post => { %>
<tr>
<td><%= post.title %></td>
<td><%= post.body %></td>
</tr>
<% }) %>
</tbody>
</table>
I then create an EJS template views/index.ejs to use the table template
<main>
<h1>Posts</h1>
<%- include("table", {posts}); %>
</main>
I also make a server to respond to requests in index.js and run it with node index.js:
const express = require("express");
const mongoose = require("mongoose");
mongoose.connect("mongodb://localhost:8081/test", {
useNewUrlParser: true
});
const app = express();
const Post = mongoose.model("Post", {
title: String,
body: String
});
app.set("view engine", "ejs");
app.get("/", async (req, res) => {
const posts = await Post.find({});
res.render("index", {posts});
});
app.listen(3000, () => console.log("Listening"));
And when I curl localhost:3000 I get the rendered HTML:
<main>
<h1>Posts</h1>
<table>
<thead>
<tr>
<th>Title</th>
<th>Body</th>
</tr>
</thead>
<tbody>
<tr>
<td>hello</td>
<td>world</td>
</tr>
<tr>
<td>foo</td>
<td>bar</td>
</tr>
<tr>
<td>fizz</td>
<td>buzz</td>
</tr>
<tr>
<td>a</td>
<td>b</td>
</tr>
</tbody>
</table>
</main>
No matter what, I will need to feed data to the res.render() function and populate the render scope with all the data needed to render.
However, I have made table.ejs reusable. So lets say that I have another page that I want to be able to show some of the posts in a tabular fashion.
I have another EJS template: views/profile.ejs that looks like this:
<main>
<h1>2 Posts</h1>
<%- include("table", {posts: posts.slice(0, 2)}); %>
</main>
And I add another route to my application at /sliced:
app.get("/sliced", async (req, res) => {
const posts = await Post.find({});
res.render("profile", {posts});
});
Whenever I curl localhost:3000/sliced I get only the first 2 items in the posts since I only populated the include's scope with a slice of all the posts:
<main>
<h1>2 Posts</h1>
<table>
<thead>
<tr>
<th>Title</th>
<th>Body</th>
</tr>
</thead>
<tbody>
<tr>
<td>hello</td>
<td>world</td>
</tr>
<tr>
<td>foo</td>
<td>bar</td>
</tr>
</tbody>
</table>
</main>

pages.forEach() is not a function

I am trying to display a list of items from a mongodb database in a Node.js application. I am using ejs as a templating engine. I am encountering the following error on the page:
Code for router:
const express = require('express');
const router = express.Router();
// Get page model
var Page = require('../models/page');
// GET page index
router.get('/', function(req, res) {
Page.findOne({}).sort({sorting: 1}).exec(function(err, pages) {
res.render('admin/pages', {
pages: pages
});
});
});
EJS code:
<%- include('../_layouts/adminheader') %>
<h2 class="page-title">Pages</h2>
Add a new page
<br><br>
<table class="table table-striped">
<thead>
<tr>
<th>Title</th>
<th>Edit</th>
<th>Delete</th>
</tr>
</thead>
<tbody>
<% pages.forEach(function(page) { %>
<tr>
<td><%= page.title %></td>
<td>Edit</td>
<td>Delete</td>
</tr>
<% }); %>
</tbody>
</table>
<%- include('../_layouts/adminfooter') %>
You should replace .findOne() by .find(), .findOne() only return one page object, whereas .find() return an array of objects:
Page.find({}).sort({sorting: 1}).exec(function(err, pages) {
res.render('admin/pages', {
pages: pages
});
});

Resources