problem when passing a callback in a res.render () - javascript

I'm doing a small application bringing some data from some remote JSON files and the idea is to generate some statistics that are later printed in an EJS file.
I want to pass separately values ​​to render and then use them in the document ejs.
The server file works well, apart from that I have a module in which I develop the functions and a script where I have the routes and execute them:
//rapi.js
const extjson = require ('remote-json');
//---------------------API CONFIG--------------------------
//apikey
const apikey ="xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx";
function get_sum_id(sumname, callback){
const urlsumbySumName = "https://la2.api.riotgames.com/lol/summoner/v3/summoners/by-name/" + sumname + "?api_key=" + apikey;
extjson(urlsumbySumName).get(callback);
}
function get_league_data(sumid, callback){
const urlgetleaguedata ="https://la2.api.riotgames.com/lol/league/v3/positions/by-summoner/"+ sumid + "?api_key="+ apikey;
extjson(urlgetleaguedata).get(callback)
}
module.exports = { get_sum_id, get_league_data};
//---------------------------------------------------------------------
//index.js
const riot = require('./rapi.js');
const express = require('express');
const router = express.Router();
router.get('/',async (req, res) => {
res.render('index');
});
router.post('/profile',async (req, res, next)=>{
const sum = req.body.summoners; //from html form
const sum_id = riot.get_sum_id(sum, function(err, resp, body){body.id});
res.render('profile', {sum,
id: sum_id,
league: riot.get_league_data(sum_id, function(err,resp,body){body})
});
});
module.exports = router;
what I want to do as seen there is to pass the value of that callback directly to the render and reference it. Obviously something I'm doing wrong since it does not work.
outputs:
> in localhost:3000/profile - internal server error. in console:
> TypeError:
> C:\xampp\htdocs\proyectos\legendsop\src\views\profile.ejs:80
> 78| <section class="row border">
> 79| <section class="col-2 border">Perfil</section>
> >> 80| <section class="col-1 border">SOLO/DUO Q <br><%= league[1].tier%></section>
> 81| <section class="col-1 border">FLEX <br><%= league[0].tier%></section>
> 82| <section class="col-4 border">WinRateRolCola</section>
> 83| <section class="col-2 border">EstadisticasCampeones</section>
>
> Cannot read property '1' of undefined
>
> at eval (eval at compile (C:\xampp\htdocs\proyectos\legendsop\node_modules\ejs\lib\ejs.js:618:12),
> <anonymous>:16:32)
> at returnedFn (C:\xampp\htdocs\proyectos\legendsop\node_modules\ejs\lib\ejs.js:653:17)
> at tryHandleCache (C:\xampp\htdocs\proyectos\legendsop\node_modules\ejs\lib\ejs.js:251:36)
> at View.exports.renderFile [as engine] (C:\xampp\htdocs\proyectos\legendsop\node_modules\ejs\lib\ejs.js:482:10)
> at View.render (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\view.js:135:8)
> at tryRender (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\application.js:640:10)
> at Function.render (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\application.js:592:3)
> at ServerResponse.render (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\response.js:1008:7)
> at router.post (C:\xampp\htdocs\proyectos\legendsop\src\routes\index.js:14:5)
> at Layer.handle [as handle_request] (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\router\layer.js:95:5)
> at next (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\router\route.js:137:13)
> at Route.dispatch (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\router\route.js:112:3)
> at Layer.handle [as handle_request] (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\router\layer.js:95:5)
> at C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\router\index.js:281:22
> at Function.process_params (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\router\index.js:335:12)
> at next (C:\xampp\htdocs\proyectos\legendsop\node_modules\express\lib\router\index.js:275:10)
>
> Git GitHub Initialize a new project directory with a Git repository
> Create repository
Excuse me if my English is not understood very well I am Spanish speaking.

This might help you
The purpose of the res.render callback argument
Render the ejs file in callback again
hope this helps
cheers

Related

"Argument str must be a string" error in torrent streaming app [closed]

Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 2 days ago.
Improve this question
I'm trying to build a torrent streaming api-thing, that streams you video files you download with torrents.
Here's my code:
import torrentStream from 'torrent-stream';
import rangeParser from 'range-parser';
import express from 'express';
const app = express();
const magnetURI = 'magnet:?xt=urn:btih:331B74F12A1CE8D00F0F8BE0844F5CC6471C925E&dn=The.Last.of.Us.S01E04.1080p.HMAX.WEBRip.DDP5.1.Atmos.x264-SMURF%5BTGx%5D&tr=udp%3A%2F%2Fopen.stealth.si%3A80%2Fannounce&tr=udp%3A%2F%2Ftracker.tiny-vps.com%3A6969%2Fannounce&tr=udp%3A%2F%2Ftracker.opentrackr.org%3A1337%2Fannounce&tr=udp%3A%2F%2Ftracker.torrent.eu.org%3A451%2Fannounce&tr=udp%3A%2F%2Fexplodie.org%3A6969%2Fannounce&tr=udp%3A%2F%2Ftracker.cyberia.is%3A6969%2Fannounce&tr=udp%3A%2F%2Fipv4.tracker.harry.lu%3A80%2Fannounce&tr=udp%3A%2F%2Fp4p.arenabg.com%3A1337%2Fannounce&tr=udp%3A%2F%2Ftracker.birkenwald.de%3A6969%2Fannounce&tr=udp%3A%2F%2Ftracker.moeking.me%3A6969%2Fannounce&tr=udp%3A%2F%2Fopentor.org%3A2710%2Fannounce&tr=udp%3A%2F%2Ftracker.dler.org%3A6969%2Fannounce&tr=udp%3A%2F%2F9.rarbg.me%3A2970%2Fannounce&tr=https%3A%2F%2Ftracker.foreverpirates.co%3A443%2Fannounce&tr=udp%3A%2F%2Ftracker.opentrackr.org%3A1337%2Fannounce&tr=http%3A%2F%2Ftracker.openbittorrent.com%3A80%2Fannounce&tr=udp%3A%2F%2Fopentracker.i2p.rocks%3A6969%2Fannounce&tr=udp%3A%2F%2Ftracker.internetwarriors.net%3A1337%2Fannounce&tr=udp%3A%2F%2Ftracker.leechers-paradise.org%3A6969%2Fannounce&tr=udp%3A%2F%2Fcoppersurfer.tk%3A6969%2Fannounce&tr=udp%3A%2F%2Ftracker.zer0day.to%3A1337%2Fannounce';
const engine = torrentStream(magnetURI, {
path: './downloads', // location to save the downloaded file
});
engine.on('ready', () => {
const files = engine.files;
// Only select the first video file (you may need to modify this depending on your torrent)
const videoFile = files.find((file) => {
return file.name.endsWith('.mp4') || file.name.endsWith('.mkv') || file.name.endsWith('.avi');
});
if (!videoFile) {
console.log('No video files found in the torrent.');
return;
}
console.log(`Streaming ${videoFile.name} (${videoFile.length} bytes)`);
app.get('/', (req, res) => {
// Set the content type of the response to the video MIME type
res.contentType(videoFile.name.split('.').pop());
// Get the range of bytes to stream from the request headers
const range = req.headers.range;
const parts = rangeParser(videoFile.length, range);
// Set the content range of the response to the range being sent
res.set('Content-Range', `bytes ${parts[0].start}-${parts[0].end}/${videoFile.length}`);
// Stream the file to the response
const stream = videoFile.createReadStream(parts[0]);
stream.pipe(res);
});
app.listen(3000, () => {
console.log('Server listening on port 3000.');
});
});
engine.on('download', (pieceIndex) => {
console.log(`Downloaded piece ${pieceIndex}.`);
});
engine.on('idle', () => {
console.log('Download complete.');
});
but it gave me this error:
TypeError: argument str must be a string
at rangeParser (G:\STREAMING-THING\node_modules\range-parser\index.js:29:11)
at file:///G:/STREAMING-THING/what.js:33:19
at Layer.handle [as handle_request] (G:\STREAMING-THING\node_modules\express\lib\router\layer.js:95:5)
at next (G:\STREAMING-THING\node_modules\express\lib\router\route.js:144:13)
at Route.dispatch (G:\STREAMING-THING\node_modules\express\lib\router\route.js:114:3)
at Layer.handle [as handle_request] (G:\STREAMING-THING\node_modules\express\lib\router\layer.js:95:5)
at G:\STREAMING-THING\node_modules\express\lib\router\index.js:284:15
at Function.process_params (G:\STREAMING-THING\node_modules\express\lib\router\index.js:346:12)
at next (G:\STREAMING-THING\node_modules\express\lib\router\index.js:280:10)
at expressInit (G:\STREAMING-THING\node_modules\express\lib\middleware\init.js:40:5)

Alert & Prompt in Firebase Functions (index.js)

I am trying to make a simple website with Firebase Functions.
I have to display a prompt to ask their import id.
I will then set the answer as a variable.
Then import their data with the import code
Following is that code in index.js
async function getFirestore() {
var importcode = prompt("What is the Import Code?");
const firestore_con = await admin.firestore();
const writeResult = firestore_con
.collection("Exports")
.doc(importcode)
.get()
.then((doc) => {
if (!doc.exists) {
console.log("No such document!");
} else {
return doc.data();
}
})
.catch((err) => {
console.log("Error getting document", err);
});
return writeResult;
}
and I get this in the Debug Log.
i functions: Beginning execution of "us-central1-app"
> /Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/index.js:19
> var importcode = prompt("What is the Import Code?");
> ^
>
> ReferenceError: prompt is not defined
> at getFirestore (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/index.js:19:22)
> at /Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/index.js:39:27
> at Layer.handle [as handle_request] (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/layer.js:95:5)
> at next (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/route.js:137:13)
> at Route.dispatch (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/route.js:112:3)
> at Layer.handle [as handle_request] (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/layer.js:95:5)
> at /Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/index.js:281:22
> at Function.process_params (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/index.js:335:12)
> at next (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/index.js:275:10)
> at expressInit (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/middleware/init.js:40:5)
> at Layer.handle [as handle_request] (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/layer.js:95:5)
> at trim_prefix (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/index.js:317:13)
> at /Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/index.js:284:7
> at Function.process_params (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/index.js:335:12)
> at next (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/router/index.js:275:10)
> at query (/Users/randomkindleofficial/Desktop/monopoly-dynamic/functions/node_modules/express/lib/middleware/query.js:45:5)
I think this happens because index.js runs on the server-side, but are there any alternatives to achieve this?
PS: I only have very basic knowledge in firebase, so this may be a foolish question but still please help :)
The prompt() method can be used in a browser and not on server side i.e. in the Cloud function. I am not sure what your frontend looks like, but you should prompt the user to enter ID in your web app and then pass it in the Cloud function. A simple example using callable functions:
var importcode = prompt("What is the Import Code?");
var getData = firebase.functions().httpsCallable('getData');
getData({ code: importCode })
.then((result) => {
// Read result of the Cloud Function.
var result = result.data;
console.log(result)
});
Then you can read this code in your Cloud function like this:
exports.getData = functions.https.onCall((data, context) => {
console.log(data)
// data contains the import code
// run your Firestore query here
});

Hyperledger Sawtooth: Transaction processor in Javascript

I am trying to implement a transaction processor in javascript SDK based on the following example
https://github.com/hyperledger/sawtooth-core/blob/master/sdk/examples/intkey_javascript/index.js
Here is my code to run a transaction processor in javascript SDK
//validator public key
const validatorAddress = '024c512a6d66917d7d00f52fa299a88594915dab27bddbcd2a80154984d7948c3c';
const IntegerKeyHandler = require('./handler');
const startProcessor = function startProcessor(){
const transactionProcessor = new TransactionProcessor(validatorAddress);
transactionProcessor.addHandler(new IntegerKeyHandler())
transactionProcessor.start()
}
But i am getting invalid argument error
Error: Invalid argument
at exports.Socket.Socket.connect (/var/accubits-workspace/hypeerledger-sawtooth/tuts/node_modules/zeromq/lib/index.js:510:13)
at Stream.connect (/var/accubits-workspace/hypeerledger-sawtooth/tuts/node_modules/sawtooth-sdk/messaging/stream.js:85:18)
at TransactionProcessor.start (/var/accubits-workspace/hypeerledger-sawtooth/tuts/node_modules/sawtooth-sdk/processor/index.js:72:18)
at Object.startProcessor (/var/accubits-workspace/hypeerledger-sawtooth/tuts/helpers/transaction-processor.js:15:26)
at app.get (/var/accubits-workspace/hypeerledger-sawtooth/tuts/index.js:62:26)
at Layer.handle [as handle_request] (/var/accubits-workspace/hypeerledger-sawtooth/tuts/node_modules/express/lib/router/layer.js:95:5)
at next (/var/accubits-workspace/hypeerledger-sawtooth/tuts/node_modules/express/lib/router/route.js:137:13)
at Route.dispatch (/var/accubits-workspace/hypeerledger-sawtooth/tuts/node_modules/express/lib/router/route.js:112:3)
at Layer.handle [as handle_request] (/var/accubits-workspace/hypeerledger-sawtooth/tuts/node_modules/express/lib/router/layer.js:95:5)
at /var/accubits-workspace/hypeerledger-sawtooth/tuts/node_modules/express/lib/router/index.js:281:22
Change the validator address to the url of the validation which can be either tcp://validator:4004 or tcp://localhost:4004
Here's the full code:
'use strict'
const { TransactionProcessor } = require('sawtooth-sdk/processor')
const IntegerKeyHandler = require('./integer_key_handler')
const address = 'tcp://validator:4004' // If you are not running it inside docker container then change the address to this tcp://localhost:4004
const transactionProcessor = new TransactionProcessor(address);
transactionProcessor.addHandler(new IntegerKeyHandler());
transactionProcessor.start();

Monkeypatch res.send

From a college suggestion and following this answer
I'm trying to monkey patch res.send but I get the following error:
TypeError: Cannot read property 'req' of undefined
This is my code
const express = require('express')
const app = express()
app.use((req, res, next ) => {
const oldSend = res.send;
res.send = (data) => {
console.log(data.length);
oldSend(data);
}
next();
})
app.get('/', (req, res) => res.send('Hello World!'))
Full stacktrace:
Example app listening on port 3000!
undefined
TypeError: Cannot read property 'req' of undefined
at send (/Users/code/js/hello/node_modules/express/lib/response.js:110:17)
at ServerResponse.res.send (/Users/code/js/hello/index.js:8:9)
at app.get (/Users/code/js/hello/index.js:12:32)
at Layer.handle [as handle_request] (/Users/code/js/hello/node_modules/express/lib/router/layer.js:95:5)
at next (/Users/code/js/hello/node_modules/express/lib/router/route.js:137:13)
at Route.dispatch (/Users/code/js/hello/node_modules/express/lib/router/route.js:112:3)
at Layer.handle [as handle_request] (/Users/code/js/hello/node_modules/express/lib/router/layer.js:95:5)
at /Users/code/js/hello/node_modules/express/lib/router/index.js:281:22
at Function.process_params (/Users/code/js/hello/node_modules/express/lib/router/index.js:335:12)
at next (/Users/code/js/hello/node_modules/express/lib/router/index.js:275:10)
Where line 110 is:
res.send = function send(body) {
var chunk = body;
var encoding;
var req = this.req; //<-- THIS
var type;
// settings
var app
....
It's because methods are not tied to their instances in JavaScript.
If you call a.fun(), inside the function code, this will initially be set to a. But this happens only because a appears in the method call: fun is otherwise an arbitrary function that has no relationship with a.
In your case, this should work:
oldSend.call(res, data);
The point of call() is to set this.
Found the solution, the oldSend loses it's context(?)
If I add bind(res):
const oldSend = res.send.bind(res);
The problem is gone.

How to get caller ip in node.js + express?

In a node.js with express I'd like to define a footer such as (in layout.jade)
footer
p © Me 2015 - Your IP: #{currentIP}
in app.js, I have:
app.locals.currentIP = function(req) {
return req.ip;
}
When run I get the following error:
> 29| block content 30| footer
> > 31| p © Me 2015 - Your IP: #{currentIP()} 32| 33| script(
> src='https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js'
> ) 34| script( src='javascripts/bootstrap.js' )
>
> Cannot read property 'url' of undefined at app.locals.currentIP
> (c:\workspaces\nodejs.workspace\express_website\app.js:66:13) at
> eval (eval at <anonymous>
> (c:\workspaces\nodejs.workspace\express_website\node_modules\jade\lib\index.js:218:8),
> <anonymous>:199:69) at eval (eval at <anonymous>
> (c:\workspaces\nodejs.workspace\express_website\node_modules\jade\lib\index.js:218:8),
> <anonymous>:225:22) at res
> (c:\workspaces\nodejs.workspace\express_website\node_modules\jade\lib\index.js:219:38)
> at Object.exports.renderFile
> (c:\workspaces\nodejs.workspace\express_website\node_modules\jade\lib\index.js:380:38)
> at Object.exports.renderFile
> (c:\workspaces\nodejs.workspace\express_website\node_modules\jade\lib\index.js:370:21)
> at View.exports.__express [as engine]
> (c:\workspaces\nodejs.workspace\express_website\node_modules\jade\lib\index.js:417:11)
> at View.render
> (c:\workspaces\nodejs.workspace\express_website\node_modules\express\lib\view.js:126:8)
> at tryRender
> (c:\workspaces\nodejs.workspace\express_website\node_modules\express\lib\application.js:639:10)
> at EventEmitter.render
> (c:\workspaces\nodejs.workspace\express_website\node_modules\express\lib\application.js:591:3)
What's wrong?
According to official doc
app.locals properties persist throughout the life of the application,
in contrast with res.locals properties that are valid only for the
lifetime of the request.
In your case it would be better to use res.locals.currentIP instead app.locals.currentIP because lifetime of ip is bound to request rather than application life cycle:
To pass a current user's ip to a view just use:
app.post('/get/ip/address', function (req, res) {
res.locals.currentIP = req.ip
...
});
In a view you have to use the following snippet to output an accepted ip address.
footer
p © Me 2015 - Your IP: #{locals.currentIP}
The error Cannot read property url of undefined at app.locals.currentIP due to your currentIP() fucntion get executes in another context. My suggestion is don't use function for outputting current user's ip but use scalar value as my code above shows.
You could reside res.locals.currentIP in a middleware to get access to currentIP variable in all of your views like the following:
var express = require('express');
var app = express();
app.enable('trust proxy');
app.use(express.static(__dirname + '/public'));
app.use(fucntion (req, res, next) {
res.locals.currentIP = req.ip;
next();
});
// routes does after the middleware !
// ...
app.listen(process.env.PORT || 3000);
Note that your route definitions should be after the middleware that populates res.locals.currentIP.

Categories