Onclick function pug from node - node.js

I passed function to render in my pug file. What I want is when the button is clicked, the function should start, but the function starts when I enter the site. Below is how I passed function and using this in PUG file
Router
const start = require('../bot')
exports.home = (req, res) => {
res.render('home', {
functionOne: start.mainFunction()
});
}
PUG File
html
head
link(rel="stylesheet" href="https://fonts.googleapis.com/css?family=Montserrat:300,400,500,700")
link(rel="stylesheet" href="/css/main.css")
body
button(type="button" id="mybutton" onclick="functionOne")

The res.render statement is only meant to send data to the template, you can't send a function through there. The Express documentation explains this.
The function is running when you request the page because that's actually what you're telling it to do when you include that function in there.
You will need to write some client-side JavaScript to make an AJAX call or form POST then create a new ExpressJS route on the server to capture that and run the function.

Related

using HTTP.request in ejs render

example in Express I have a route that linked to my ejs middleware.
Code 1 :
app.all("/sample", function(req,res,next){
ejs.renderFile("./sample.ejs", {req,res,next,require,module:require("module")} {}, function(e, dt){
res.send(dt.toString());
});
});
everything fine in the first code. and in sample.ejs (second code) I want to request to some text file in Internet and return to HTML (and should use HTTP module)
Code 2:
<%
var http=require("http");
var url=require("url");
var opt = url.parse("http://website.com/thisfile.txt");
/* it will return "Hello World!" btw */
var dt = ""
var hReq = http.request(opt, function(hRes){
hRes.on("data", function(chunk){
dt+=chunk.toString();
});
});
hReq.end();
%>
<h2>Here is the data is <%= dt %></h2>
and while i try to my browser. it just give me
Code 3:
<h2>Here is the data is </h2>
where I want it gave me
Code 4:
<h2>Here is the data is Hello World!</h2>
How could I get that?
I just want to use HTTP Module or Net Socket Module. and I just want to edit the Code 2. Code 1 is permanently like that.
While EJS can run full JavaScript, you generally want to leave as much as possible out of the template and put more of your logic in your main express request handler.
Since the rendering is done server side anyway, nothing will change other than making it easier to read and test.
You should consider moving the HTTP request made in your EJS template into your app.all('/sample') handler and then just inject the result into your template. In this case that would be the final string collected from the HTTP request. You'll then end up with something like this. (This is untested code).
Also, while it is not required at all, I'd suggest taking a look at something like the request, this makes HTTP requests much easier!
var request = require('request');
app.all("/sample", function(req,res,next){
// Make the HTTP request
request('http://www.website.com/file.txt', function(err, response, body) {
// Render the ejs template
ejs.renderFile("./sample.ejs", {file: body}, function(e, dt) {
// Send the compiled HTML as the response
res.send(dt.toString());
});
});
});

Restify : how do I present a prefilled signin form?

Here is my flow.
I have a form (html template with js code ) that needs to be prefilled with some user properties and presented on the path /signup
These properties are passed as url params. There is a javascript in the page that will read this url params and then populate the fields.
I use restify.
Is there a way to present the page using restify ? If so how?
So far I have used restify to return data and not html.
What you will need to do is inject the parameters into your html template using some type of template engine for Node.JS. There are quite a few that you can use:
Jade
Mustache
Handlebars
Your route would look something like this if you were to use Handlebars to render your HTML page with populated fields using the parameters within the URL.
server.get('/signup/:firstname/:lastname', function (req, res, next) {
fs.readFile(__dirname + '/index.html', function (err, data) {
var template = Handlebars.compile("<form><input type='text' value='{{firstname}}'></form>");
res.setHeader('Content-Type', 'text/html');
res.writeHead(200);
res.end(template({firstname:"Dee", lastname:"Taylor"}));
});
});

Send PDF as response to client

I'm facing a strange behaviour with PdfKit. I'm using Nodejs and Express. When I call my route that generate the PDF, the route itself is called twice, and I don't understand why.
Below is the smallest code that recreate this:
var express = require('express'),
app = express();
app.get('/', function (req, res) {
console.log('Route called with referer', req.headers.referer);
var PdfDocument = require('pdfkit'),
doc = new PdfDocument();
doc.pipe(res);
doc.addPage();
doc.end();
});
app.listen(7373, function () {
console.log('started');
});
In the terminal, I have these logs, refreshing only one time the page from the browser:
node tmp/server.js
started
Route called with referer undefined
Route called with referer http://127.0.0.1:7373/
Anyone knows why the route is called one more time automatically?
Ok, after some analysis, I found that it's the browser's PDF viewer that launch a second call. When using wget or curl, I see only one call and one log. So just be aware that code is parsed twice when diplaying the page from the browser.

Passing Variable from NodeJS to client-side JS file

Is it possible to pass a server-side JavaScript variable to a <script> tag in an HTML view?
In my routes file I have:
exports.index = function(req, res){
res.sendfile('views/index.html', {
data: {foo: bar}
});
};
If I was using a Jade template, I could do:
script(type='text/javascript').
var local_data =!{JSON.stringify(data)}
To access the data object. However, that doesn't work for an html file. Is there a work-around for this?
Have a route send the data using res.json() and use AJAX in the html to fetch the JSON data.
http://www.w3schools.com/ajax/

Is there a way to get the HTML of a JADE Template before sending it via response

What I usually do is:
res.render('myJadeTemplate');
but I want to add another transformation to the html before attaching it to the response.
How can I get the rendered HTML then modify it and send it over via res.send()
If you are using Express3. There is an additional (and optional) parameter to res.render() that is a callback that will give you the rendered HTML rather than sending it directly to the client.
res.render('myJadeTemplate', function (err, html) {
// html => rendered HTML from jade template
});
Ok I found a solution:
var jade = require('jade');
var fs = require('fs');
var jadetemplate = jade.compile(fs.readFileSync('code.jade', 'utf8'));
var html = jadetemplate({
params:"{Some parames}"
});
console.log(html);
Thanks for this thread
Node says Jade has no method "renderFile", why?

Resources