NeutralinoJS storage - javascript

This is NeutralinoJS storage API for writing JSON. Is it possible to update JSON file (push data), not just overvrite data with new JS object. How to do that???
// Javascript Object to be stored as JSON
let data = {
bucket : 'test',
content : {
item : 10
}
}
// stores the data into JSON based data store.
Neutralino.storage.putData(data,
// executes on successful storage of data
function () {
console.log('Data saved to storage/test.json');
},
// executes if an error occurs
function () {
console.log('An error occured while saving the Data');
}
);

The Neutralino.storage api takes string instead of JSON to save into local storage.
And you can create your JavaScript Objects to String Very easily, for example:
const myUser = {
name: "John Doe",
age: 19,
married: false
}
const myUserString = JSON.stringify(myUser);
console.log(myUserString); // {"name":"John Doe","age":19,"married":false}
Here you can see how we used JSON.stringify method to convert our JavaScript Object into string.
Now We Can Also Convert generated string back to our javascript object, example:
const myUserString = '{"name":"John Doe","age":19,"married":false}';
const myUser = JSON.parse(myUserString);
console.log(myUser);
So now we can easily store our Objects and arrays to local storage and easily modify them, example:
async function saveToStorage(myUser) {
let myUserString = JSON.stringify(myUser);
await Neutralino.storage.setData('myUser', myUserString);
});
async function loadFromStorage() {
let myUserString = await Neutralino.storage.getData('myUser');
let myUser = JSON.parse('myUser');
return myUser;
}
saveToStorage({
name: "John Doe",
age: 19,
married: false
}).then(async () => {
let myUser = await loadFromStorage();
myUser.name = "Jane Doe"
await saveToStorage(myUser);
});

Related

How do I stream Product objects in object mode with the fetch API

I am processing data from a server which returns JSON objects. I read that it is possible to process data in different modes, byob and object mode. Unfortunately, I cannot seem to find any examples demonstrating that scenario. I don't want to have to read a byte buffer, decode and then process the result JSON if there is a way to get the chunks as objects instead? I can see the data in my browser but when I assign it to a Product object in my UI, no products show. Here is my sample code:
interface Product {
productId: string,
productName: string,
barcode: string,
quantityOnHold: number
}
Here is how I am attempting to use the Fetch API. I'd like to use the highWaterMark that I read about but don't know how to use to return objects.
const retrieveProducts = async () => {
const products = [];
const productBody ={
category: 'fragrance',
productCodes: [122222, 555555, 444444444]
}
const response = await fetch('/products', {
method: 'POST',
body: JSON.stringify(productBody)
})
const readableStream = response.body.pipeThrough(new TextDecoderStream());
readableStream.pipeTo(new WritableStream({
write(chunk) {
console.log("Chunk received", chunk);
products.push(JSON.parse(chunk)); // does not work!!
// I want to be able add products
// i.e. products.push(....)
},
close() {
console.log("All products successfully processed!");
},
abort(e) {
console.error("An error occurred!", e);
}
}));
}

Get json data from from django-rest-api with react frontend into a variable

I am new to react and javascript. I am trying to get some data INTO A VARIABLE in react from django-rest API.
I am using this variable in another function using react-beautiful-dnd.
I have the API set up and CORS also set up.
This is the output in http://127.0.0.1:8000/api/column_names/
I am trying to get this as a json object in react frontend.
const getData = async () => {
let response = await fetch("http://127.0.0.1:8000/api/column_names/");
let data = await response.json();
console.log(data); // line 29
return data;
};
let columnFromBackend = getData();
console.log(columnFromBackend); // line 34
This is the output
Is there any way to get this data into the variable columnFromBackend
I am trying to get the equivalent of this value.
let columnFromBackend = {
idone: {
name: "In progress",
items: [{ id: "hjnmkjnh", content: "first" }],
},
idtwo: {
name: "Todod",
items: [],
},
};
If I declare the variable directly like this, then this is the output that I am getting and what I am trying to get from the api.
You need to change your second to last line to
let columnFromBackend = await getData();
Which version of node are you using?
Go to node_modules/react-scripts/config and open webpack.config.js file
then look for module.exports and add
experiments:{ topLevelAwait: true }
Then change let columnFromBackend = getData(); to let columnFromBackend = await getData();

Writing to a XLSX template and then sending it as a response in a different function, always returns undefined

What I'm trying to do
Requests come into my server to download a file containing data. The downloading part is in the front-end and works. I grab the data on my backend and then I want to write it into an existing template and return the data.
This is the handler for the request.
async handle(request: Request, response: Response) {
try {
const fileName = 'test.xlsx'
const binary = objectsToTemplateWorkBook()
response.setHeader(
'Content-Disposition',
'attachment; filename=' + fileName
)
response.setHeader('Content-Type', 'application/vnd.openxmlformats')
response.end(binary, 'binary')
} catch (error) {
console.log(error)
response.send(error)
}
}
This is the function that is supposed to write the data into the template.
export const objectsToTemplateWorkBook = ():
Promise<any> => {
var XlsxTemplate = require('xlsx-template')
var dataBlob
// Load an XLSX file into memory
const blob = fs.readFile(
path.join(__dirname, 'test_template.xlsx'),
function (err, data) {
console.log(__dirname)
// Create a template
var template = new XlsxTemplate(data)
// Replacements take place on first sheet
var sheetNumber = 1
// Set up some placeholder values matching the placeholders in the template
var values = {
people: [
{ name: 'John Smith', age: 20 },
{ name: 'Bob Johnson', age: 22 },
],
}
// Perform substitution
template.substitute(sheetNumber, values)
// Get binary data
dataBlob = template.generate()
// ...
}
)
return dataBlob
}
The function seems to write the data to the template because if I log the dataBlob inside the fs.Readfile method it shows me the file. However, the return dataBlob always returns undefined. I know this is due to the async nature, but I have no idea how to fix it quite honestly. So my question to you is: how can I get the dataBlob to my handler to send it as a response?
You can't get the return from a callback function like you're doing here, since they run asynchronously, their return will never be acessible because the external return will be executed before the inner code.
To solve this specific problem you can you the fs.readFileSync function, that executes synchronously and returns a value, that being the buffer you need to pass in your xlsxTemplate constructor. This way, the code turns into:
export const objectsToTemplateWorkBook = ():
Promise<any> => {
var XlsxTemplate = require('xlsx-template')
var dataBlob
// Load an XLSX file into memory
const data = fs.readFileSync(path.join(__dirname, 'test_template.xlsx'))
console.log(__dirname)
// Create a template
var template = new XlsxTemplate(data)
// Replacements take place on first sheet
var sheetNumber = 1
// Set up some placeholder values matching the placeholders in the template
var values = {
people: [
{ name: 'John Smith', age: 20 },
{ name: 'Bob Johnson', age: 22 },
],
}
// Perform substitution
template.substitute(sheetNumber, values)
// Get binary data
dataBlob = template.generate()
// ...
return dataBlob
}
With this you get access to the file buffer returned from the synchronous read file and is able to perform the rest of your operations. Hope it helps :D

How serialize MongoDb ObjectId("uniqueid") to JSON in nodejs?

Let's assume we have a query builder service B that spits out mongo db query when called. This query is received by service A and it executes it as is with mongo db official nodejs driver.
How do I send something like :
[{
_id: new mongo.ObjectID("5f3258cfbaaccedaa5dd2d96"),
phone: "666"
}, {
_id: new mongo.ObjectID("5f3258cfbaaccedaa5dd2da2"),
phone: "555"
}]
from service B to service A?
EDIT:
The following works perfectly fine:
var q = { _id: new mongo.ObjectID("5f3258cfbaaccedaa5dd2d96") };
const result = await this.db.collection("persons").find(q).toArray();
The following doesn't work:
var q = { _id: { $oid: "5f3258cfbaaccedaa5dd2d96" } }
const result = await this.db.collection("persons").find(q).toArray();
Now,
var q = { _id: new mongo.ObjectID("5f3258cfbaaccedaa5dd2d96") };
JSON.stringify(q)
gives you : {"_id":"5f3258cfbaaccedaa5dd2d96"} and if you pass this to service A. You can not use it in service A as follows:
const result = await this.db.collection("persons").find(qStr).toArray();
Or as,
const result = await this.db.collection("persons").find(JSON.parse(qStr)).toArray();
You need to:
Serialize your documents to extended json on one end
Deserialize your documents from extended json to language-native data structures on the other end
See https://github.com/mongodb/js-bson#node-no-bundling for how to serialize and deserialize.
You cannot feed extended json-type annotated hashes to driver functions that expect native types (which are all of them, basically, other than the one that specifically parses extended json), like you tried to do.
var q = { _id: new mongo.ObjectID("5f3258cfbaaccedaa5dd2d96") };
const serializedQ = BSON.serialize(q);
const deserializedQ = BSON.deserialize(serializedQ);
const result = await this.db.collection("persons").find(deserializedQ).toArray();
There is a standard that MongoDB calls "Extended JSON" that defines how you can encode all BSON data types in regular JSON.
It will become something like
{ _id : {$oid: "5f3258cfbaaccedaa5dd2d96"} }
Most MongoDB tools will be able to convert to and from that format.

React Native - How to save map using AsyncStorage

I try to save user inputs as a JS map using AsyncStorage in my React Native app.
It shows no errors when saving, but I got "[object Map]" when I tried to get the data back.
There is the simplified version of my user map. the actual User object has way more properties than this, but the ID is always same as the map key.
const dataKey = 'user-data';
let data = new Map();
data.set(1, { name: 'John', id: 1, title: 'Mr.' })
data.set(2, { name: 'Johanna', id: 2, title: 'Miss.' })
There is the code for saving the data.
async saveDate = (dataKey, data) => {
try {
await AsyncStorage.setItem(dataKey, data.toString());
} catch (err) {
console.log(err);
}
}
There will be more than 200 users in this map.
Any idea how to save complex data structure in react native?
Instead of converting your data to a string you need to save it as JSON. Change
await AsyncStorage.setItem(dataKey, data.toString());
to
await AsyncStorage.setItem(dataKey, JSON.stringify(data));
See this link to the official documents for more details: https://facebook.github.io/react-native/docs/asyncstorage.html#mergeitem
Like one of the other answers states, you need to save the data as JSON.
However, with you won't be able to simply convert data to JSON. Instead you will need to spread the array entries of Map and pass that to JSON.stringify().
So change
await AsyncStorage.setItem(dataKey, data.toString());
to
await AsyncStorage.setItem(dataKey, JSON.stringify([...data]));
And then when you want to get the item from Async you will need to convert it back to Map, i.e.
const jsonData = AsyncStorage.getItem(dataKey)
const mapData = new Map(jsonData)
The provided answers will not quite work. You can't create the new Map after reading back json without parsing first. This works:
saveData = async () => {
const dataKey = 'user-data';
let data = new Map();
data.set(1, { name: 'John', id: 1, title: 'Mr.' })
data.set(2, { name: 'Johanna', id: 2, title: 'Miss.' })
try {
await AsyncStorage.setItem(dataKey, JSON.stringify([...data]));
} catch (err) {
console.log(err);
}
const jsonData = await AsyncStorage.getItem(dataKey)
const parseData = JSON.parse(jsonData)
const mapData = new Map(parseData)
console.log(mapData);
//get a list of IDs
console.log(Array.from(mapData.keys()));
}
For 200 values this is a lot of overhead. I would consider using sprintf/sscanf libraries and just store a string, for instance one row of data per line.
This will only work if every row in the table has the same amount of elements and you don't change the layout. Of course it would all be on you to convert the string back to objects so you can recreate the Map. Just a thought!

Categories

Resources