I'm building out a project that is making a call to a blockchain API. Unfortunately, the data I'm getting back is circular so while it works in Postman my server errors when trying to convert it to JSON. I tried using JSON.stringify but nothing changed.
Here's the controller function:
blockchainController.search = (req, res) => {
axios({
method: 'GET',
url: `https://chain.api.btc.com/v3/address/${req.body.address}/tx`
})
.then(data => {
res.json({
message: 'Transactions loaded',
data: data
})
})
.catch(err => {
console.log(err);
res.send(err);
})
};
Any ideas for a workaround or a fix? I'd like to be able to send this data to my front-end but it ain't happening.
A solution could be to use a library designed to prune circular references.
I happen to have built such library: https://github.com/Canop/JSON.prune
You can simply call it with
let json = JSON.prune(yourCircularObject);
This adds some "-pruned-" marks whenever a reference is ignored.
If you prefer a "silent" removal, you can do
let json = JSON.prune(yourCircularObject, {prunedString: undefined });
Related
I started writing a program that will automate user actions, by now it's meant to be an easier menu to make faster actions by just sending requests to the official website by clicks on my own page. (something like web-bot but not exactly).
My problem is when i send login request in response i get back user_id, server, session_id etc. And I need to save that session_id to make the other actions.
How can i save this to variable.
All in JavaScript.
I was looking in the internet since yesterday for an answer and i still can't find (or understand) how to get this
I tried
function login(){ fetch('url', { method: 'POST', headers: { //headers }, body: //my Id's }) })
//There's the problem to solve
.then(res => res.text()) .then(data => obj = data) .then(() => console.log(obj)) console.log(body.session_id);
// I even tried the substring but 1. It won't work as I want because There are sometimes //more and less letters. 2. I get and error "Cannot read properties of undefined (reading //'substr')"
`session = obj;
session_id = session.substring(291,30)
console.log(session_id)`
It looks like you're using the text() method on the Response object returned from fetch(), which will give you a string representation of the response.
You probably want to be using the json() method instead, and from that you can get your session_id.
This guide has some more useful information that may help you: https://javascript.info/fetch
Ok it works now with
`async function login(){ let session = await fetch('url', {
//code
}
let result = await session.json();
console.log(result);
session_id = result.data.user.session_id;
user_id = result.data.user.id;`
I have written a simple function to handle upload of files in my sails.js app.
let upload = file.upload((err, uploadedFiles) => {
if (err) {
return res.serverError(err);
} else {
return res.send({ data: uploadedFiles });
}
});
When the upload is complete I am redirected to a page displaying raw json, which contains the uploaded file information (including the path).
raw json response
What I am expecting when I console.log(upload) is the same information, however I am getting the writestream instead.
console.log output
This is a problem for me because I would like to be able to extract the file name from the object and use it in another part of my program, but I can't do this because all I am able to access is the writestream.
I have tried using async/await and callbacks and can't seem to fix my issue.
Hopefully someone can help me!
Thanks
A helpful person on the sails Gitter suggested that I use this package, which supports async/await: https://www.npmjs.com/package/sails-hook-uploads
I tested it out with the following code and it works:
let upload = await sails
.uploadOne(file, {
maxBytes: 3000000,
})
.intercept('E_EXCEEDS_UPLOAD_LIMIT', 'tooBig')
.intercept(
(err) => new Error('The photo upload failed: ' + util.inspect(err))
);
I create server (node.js / express / boby-parser)
and I need to get array of objects 'users'.
its part of code from server.js file:
let users = [{
name: 'user1',
}];
app.get('/users/', (req, res) => {
const filePath = path.join(pth.dir, 'build', 'index.html');
res.json(users);
res.sendFile(filePath);
});
Its my code from frontend:
const handleResponse = (response) => {
return response.text().then(text => {
const data = text && JSON.parse(text);
if (!response.ok) {
const error = (data && data.message) || response.statusText;
return Promise.reject(error);
}
return data;
});
};
const getAll = (baseUrl) => {
const requestOptions = {
method: 'GET'
};
return fetch(baseUrl, requestOptions).then(handleResponse);
};
Something wrong with my code at server. (I just dodnt know how to use express server).
when I use getAll function I got JSON text replace my page. Can anyone help? How should I write app.get() in server.js. Or do I need write in server part one app.get() to get page or another app.get() to get JSON data?
Why are you trying to send a file in the response?:
res.sendFile(filePath);
For starters, the response content can either be JSON or a file (or any of a variety of other things of course), but not both. With data like JSON or XML it's possible to combine multiple objects into one larger object for a single response, but this won't work if the content types are entirely different as it is with a file.
Looking at your client-side code, you're not even doing anything with that file. You only read the JSON data:
return response.text().then(text => {
const data = text && JSON.parse(text);
if (!response.ok) {
const error = (data && data.message) || response.statusText;
return Promise.reject(error);
}
return data;
});
So the simplest approach here would just be to not try to send back the file:
app.get('/users/', (req, res) => {
res.json(users);
});
Edit: Based on comments below, you seem to be struggling with the different requests the client makes to the server. The browser loading the page is one request with one response. If that page includes JavaScript that needs to fetch data, that would be a separate AJAX request with its own response containing just that data.
It’s possible to use JSON (or any data) server-side to populate a page template and return a whole page with the data. For that you’d need to use (or build) some kind of templating engine in the server-side code to populate the page before returning it.
The res.json() represents the HTTP response that an Express app sends when it gets an HTTP request. On the other hand, res.sendFile() transfers the file at the given path.
In both cases, the flow is essentially transferred to client who might have made the request.
So no, you cannot use res.sendFile and res.json together.
var options = {
headers: {
'name': 'user1',
}
};
res.sendFile(path.join(__dirname, 'build', 'index.html'), options);
Thats really the closest you can do to achieve the desired task.
I'm trying use Wmata's metro gtfs apis but I'm not getting anything back. I tried using a fetch and also their own javascript example but I keep getting this type of response back.
I am able to get a response from their other feeds but just not any of the gtfs ones. When I try using postman I get a bunch of gibberish:
1495323752907:32:0020200213 *RED0ǃ��"9360(˅��"7993(����"3969(ш��"22094(����"3542(㋕�"2640(����"4387(͎��"4364( ����"5660(
I don't get what's going on.
const url =
"https://api.wmata.com/gtfs/rail-gtfs-static.zip?api_key=e13626d03d8e4c03ac07f95541b3091b";
let config = {
method: "GET",
mode: "no-cors"
};
fetch(url, config)
.then(res => console.log("res", res))
.catch(err => console.log("err", err));
How to properly post data to server using Sapper JS lib ?
Saying : I have a page 'board-editor' where I can select/unselect tiles from an hexagonal grid written in SVG, and adds/substract hex coordinates in an store array.
Then user fills a form, with board: name, author, and version... Clicking on save button would POST the form data plus the array in store. The server's job, is to store the board definition in a 'static/boards/repository/[name].json' file.
Today, there's few details on the net to use correctly Sapper/Svelte with POSTing data concerns.
How to proceed ? Thanks for replies !
EDIT:
to avoid reposting of the whole page, which implies to loss of the app state, I consider using a IFRAME with a form inside.... but how to init a copy of sapper inside the IFRAME to ensure I can use the this.fetch() method in it ?
I use Sapper + Svelte for a website, it's really amazing! In my contact form component, data are sent to the server. This is how it's done without iframe. The data sent and received is in JSON format.
On the client side (component):
var data = { ...my contact JSON data... }
var url = '/process/contact' // associated script = /src/routes/process/contact.js
fetch(url, {
method: 'POST',
body: JSON.stringify(data),
headers: {
'Content-Type': 'application/json'
}
})
.then(r => {
r.json()
.then(function(result) {
// The data is posted: do something with the result...
})
})
.catch(err => {
// POST error: do something...
console.log('POST error', err.message)
})
On the server side:
script = /src/routes/process/contact.js
export async function post(req, res, next) {
/* Initializes */
res.setHeader('Content-Type', 'application/json')
/* Retrieves the data */
var data = req.body
// Do something with the data...
/* Returns the result */
return res.end(JSON.stringify({ success: true }))
}
Hope it helps!
Together with the solution above, you might get undefined when you try to read the posted data on the server side.
If you are using the standard degit of Sapper you are using Polka. In order to enable body-parse in Polka you can do the following.
npm install body-parser
In server.js, add the following
const { json } = require('body-parser');
And under polka() add imported
.use(json())
So that it in the end says something like
...
const { json } = require('body-parser');
polka() // You can also use Express
.use(json())
.use(
compression({ threshold: 0 }),
sirv('static', { dev }),
sapper.middleware()
)
.listen(PORT, err => {
if (err) console.log('error', err);
});