Parsing string json in javascript throws Unexpected token - javascript

var filter1 = " { where:{ businessName:{ $like:'%A'} ,'userId': { $gt: 0} }, limit: 1 }"
I want to make pass it like this JSON
var filter = { where:{ businessName:{ $like:'%A'} ,'userId': { $gt: 0} }, limit: 1 }
I did this to make it like JSON example.
JSON.parse(filter)
But it throws the following exception:
SyntaxError: Unexpected token w in JSON at position 3

Your JSON is not valid. Use "" with all keys and for values, except numbers and bools
var filter1 = '{ "where": { "businessName" :{ "$like":"%A"} ,"userId": { "$gt": 0} }, "limit": 1 }'
var filter1 = '{ "where": { "businessName" :{ "$like":"%A"} ,"userId": { "$gt": 0} }, "limit": 1 }';
var filter = JSON.parse(filter1);
console.log(filter);

It's not valid JSON string. It's more a JavaScript object literal wrapped in quotes.
In JSON standard all keys should be wrapped in quotes, so here is how your JSON would look like:
"{"where":{"businessName":{"$like":"%A"},"userId":{"$gt":0}},"limit":1}"
Since your string is simply a JavaScript object wrapped in quotes, you can arrive at the correct JSON string by simply removing quotes:
var filter1 = { where:{ businessName:{ $like:'%A'} ,'userId': { $gt: 0} }, limit: 1 }
and running it through JSON.stringify:
JSON.stringify(filter1);

Related

Convert an array in string format to javascript array

I have an array which is in string format,
var str = {
id: 123,
changes: "[[atr:test1, old:null, new:null], [atr:messageText, old:test here, new:hello test], [atr:status, old:null, new:1]]"
}
var d = str.changes
I tried to convert the 'changes' array from string format using different methods by combining split(), replace(), slice() etc...and even JSON.parse(), but nothing worked.
Is there any way to convert this into javascript array?
Note that the string is not valid anything but string.
It is not a valid array, and the string is not valid JSON.
If you can, get the server to change it to the valid JSON string
"[{\"atr\":\"test1\", \"old\":null, \"new\":null}, {\"atr\":\"messageText\", \"old\":\"test here\", \"new\":\"hello test\"}, {\"atr\":\"status\", \"old\":null, \"new\":1}]"
If the response is ALWAYS on the format you gave, then you can create valid JSON
var str = {
id: 123,
changes: "[[atr:test1, old:null, new:null], [atr:messageText, old:test here, new:hello test], [atr:status, old:null, new:1]]"
}
// change the inner [ ] to { }
let changes = str.changes.replace(/\[\[/g, "[{").replace(/\], \[/g, "},{").replace(/\]\]/g, "}]")
// change the unquoted keys and values to quoted keys and values
changes = changes.replace(/(\w+):/g, '"$1":').replace(/:([\w ]+)([},])/g, ':"$1"$2')
// parse the object
changes = JSON.parse(changes);
// replace "null" with null - could have been done above bt the regex would be nasty
changes.forEach(item => Object.keys(item).forEach(key => item[key] = item[key] === "null" ? null : item[key]))
console.log(changes)
I think the problem is that the key 'changes' do not any valid JSON. You can validate, format it here.
If there is a valid JSON in 'changes' key, It can be converted to Js array using JSON.parse();, Something like:
var str = { id: 123,
changes: `[
[
{
"atr": "test1",
"old": null,
"new": null
}
],
[
{
"atr": "messageText",
"old": "test here",
"new": "hello test"
}
],
[
{
"atr": "status",
"old": null,
"new": 1
}
]
]`
}
var d = JSON.parse(str.changes);
console.log(d);
//str.changes Object:
[[[object Object] {
atr: "test1",
new: null,
old: null
}], [[object Object] {
atr: "messageText",
new: "hello test",
old: "test here"
}], [[object Object] {
atr: "status",
new: 1,
old: null
}]]

Is there any way to replace double quotes in entire object dynamically based on conditions

I am having one object like below and now I need to remove the double quotes if the any of the value is either Number or null. Other than these three cases, double quotes should be present.
All these values are fetching from textbox, If I provide value as 1234, its getting added as "1234".
so, here itself I am facing this issue. How to avoid this? Please advise
{
"fruits":[{
"name":"apple",
"count":"4",
"filter":{
"unique":[{
"attribute":"isFruit",
"identifier":"9876"
}],
"match_attributes":{
"location":"NewZeland",
"subname":"null"
},
"match_expressions":[{
"attribute":"value1",
"operator":"In",
"values":["test_value","4567","value7"]
},
{
"attribute_name":"isvegetable",
"operator":"In",
"values":["15678"]
}]
}
}]
}
My expected output should be like below,
{
"fruits":[{
"name":"apple",
"count":4,
"filter":{
"unique":[{
"attribute":"isFruit",
"identifier": 9876
}],
"match_attributes":{
"location":"NewZeland",
"subname":null
},
"match_expressions":[{
"attribute":"value1",
"operator":"In",
"values":["test_value",4567,"value7"]
},
{
"attribute_name":"isvegetable",
"operator":"In",
"values":[15678]
}]
}
}]
}
I tried to remove for single value using
string.replace(/['"]+/g, '');
But is there any way to replace it for an entire object. Any help would be appreciated.
You could create your own parser to handle the special cases words you want to convert. In this case 'true', 'false' and 'null'
As for the numbers you can check if it's a number or not using isNaN then format it.
const input = {
"fruits":[{
"name":"apple",
"count":"4",
"filter":{
"unique":[{
"attribute":"isFruit",
"identifier":"true"
}],
"match_attributes":{
"location":"NewZeland",
"subname":"null"
},
"match_expressions":[{
"attribute":"value1",
"operator":"In",
"values":["test_value","4567","value7"]
},
{
"attribute_name":"isvegetable",
"operator":"In",
"values":["false"]
}]
}
}]
};
const dictionary = ["null", "true", "false"]
const parser = word => {
wordWithoutQuotes = word.substring(1, word.length -1)
if (dictionary.includes(wordWithoutQuotes) || !isNaN(wordWithoutQuotes)) return JSON.parse(word)
return word
}
const output = JSON.stringify(input).replace(/".*?"/g, parser);
console.log(output)

coverting the string to json object

I tried to display my data in json format. Firstly i tried JSON.stringify
then it shows in string format so, then again I tried JSON.parse where I get like array of object finally I tried keeping [0] to the parse object it throws 'undefined'...
can you please tell me where I am doing wrong..
I provide the output of the following console.log..
try{
var timekeep = await Orders.findAndCountAll(
{
where : {
cid : orders_info.cid,
},
order: [
['id', 'DESC']
],
limit: 1,
}
);
console.log("RESULT => ", timekeep);
var datjsn = JSON.stringify(timekeep);
var jsonsr = JSON.parse(datjsn);
var data23 = jsonsr[0];
console.log('alpha1'+ datjsn);
console.log('delta2'+ jsonsr);
console.log('beta'+ data23);
output of the console logs
RESULT => { count: 1,
rows:
[ orders {
dataValues: [Object],
_previousDataValues: [Object],
_changed: {},
_modelOptions: [Object],
_options: [Object],
__eagerlyLoadedAssociations: [],
isNewRecord: false } ] }
alpha1 {"count":1,"rows":[ {"id":4006,"mid":1,"cid":41,"wid":7138,"oid":null,"status":null,"options":null,"starttime":"2018-08-15T06:08:55.000Z","duration":null,"ordertotal":50,"counter":null,"closetime":null}]}
delta2 [object Object]
beta undefined
var data23 = jsonsr[0];
In here you have took wrong place. Actually the data is in jsonsr.rows[0].
For this you can use,
jsonsr.rows[0];
or if the key value is not known use the Object.keys to get the all the objects in array and proceeding with loop with the condition of check the object value in array and length greater than 0 can get the all the datas.
The object is sequelize object not just object.
Try to use .get()
var timekeep = await Orders.findAndCountAll(
{
where : {
cid : orders_info.cid,
},
order: [
['id', 'DESC']
],
limit: 1,
}
);
console.log(timekeep.rows[0].get())

convert nested object to one level up object in javascript

given json : -
{
"_id": "5c1c4b2defb4ab11f801f30d",
"name": "Ray15",
"email": "ray15#gmail.com",
"deviceToken": "dgtssgeegwes",
"deviceType": "IOS",
"tokens": [
{
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJfaWQiOiI1YzFjNGIyZGVmYjRhYjExZjgwMWYzMGQiLCJhY2Nlc3MiOiJhdXRoIiwiaWF0IjoxNTQ1MzU4MTI2fQ.YdK0MjOm7Lff22uTFITQdic0gKdMZRpsmRee-yejDpQ"
}
]
}
desired json: -
{
"_id": "5c1c4b2defb4ab11f801f30d",
"name": "Ray15",
"email": "ray15#gmail.com",
"deviceToken": "dgtssgeegwes",
"deviceType": "IOS",
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJfaWQiOiI1YzFjNGIyZGVmYjRhYjExZjgwMWYzMGQiLCJhY2Nlc3MiOiJhdXRoIiwiaWF0IjoxNTQ1MzU4MTI2fQ.YdK0MjOm7Lff22uTFITQdic0gKdMZRpsmRee-yejDpQ"
}
I want to convert JSON with the help of lodash library of npm in javascript or suggest any other library,
it might be a silly question, Please explain it properly, I am a newbie in javascript and try to learn node.js. comment me if you need more explanation.
Thanks for help
You don't really need a library, you can just assign the property and delete the other.
However tokens is an array, which suggest there might be more than one. This will only take the first one (obj.tokens[0].token). Since objects can't have duplicate keys, you will only be able to have one token with your desired format (if that matters).
let obj = {
"_id": "5c1c4b2defb4ab11f801f30d",
"name": "Ray15",
"email": "ray15#gmail.com",
"deviceToken": "dgtssgeegwes",
"deviceType": "IOS",
"tokens": [
{
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJfaWQiOiI1YzFjNGIyZGVmYjRhYjExZjgwMWYzMGQiLCJhY2Nlc3MiOiJhdXRoIiwiaWF0IjoxNTQ1MzU4MTI2fQ.YdK0MjOm7Lff22uTFITQdic0gKdMZRpsmRee-yejDpQ"
}
]
}
obj.token = obj.tokens[0].token
delete obj.tokens
console.log(obj)
There are a number of ways to solve this problem and no one "right" way. However, you may want to consider creating a new object, rather than mutating the original object. Objects are always passed by reference in JavaScript and it's easy to accidentally modify an object inside a function, not realizing that you just changed that object everywhere else it's referenced as well.
Since you mentioned it, here is a way to solve this with Lodash.
const obj = {
"_id": "5c1c4b2defb4ab11f801f30d",
"name": "Ray15",
"email": "ray15#gmail.com",
"deviceToken": "dgtssgeegwes",
"deviceType": "IOS",
"tokens": [
{
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJfaWQiOiI1YzFjNGIyZGVmYjRhYjExZjgwMWYzMGQiLCJhY2Nlc3MiOiJhdXRoIiwiaWF0IjoxNTQ1MzU4MTI2fQ.YdK0MjOm7Lff22uTFITQdic0gKdMZRpsmRee-yejDpQ"
}
]
};
// create a new object without the tokens property
const newObj = _.omit(obj, 'tokens');
// get the first token object from the tokens array
const tokenObj = _.head(obj.tokens);
// get the token string from the token object, defaulting to empty string if not found
newObj.token = _.get(tokenObj, 'token', '');
console.log(newObj);
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.11/lodash.min.js"></script>
Lodash is a great library and used by many projects. It can be especially helpful for new developers. For example, _.head(arr) will return undefined if arr is undefined. However, arr[0] would crash in the same scenario.
Here's one way to solve it without a library.
const obj = {
"_id": "5c1c4b2defb4ab11f801f30d",
"name": "Ray15",
"email": "ray15#gmail.com",
"deviceToken": "dgtssgeegwes",
"deviceType": "IOS",
"tokens": [
{
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJfaWQiOiI1YzFjNGIyZGVmYjRhYjExZjgwMWYzMGQiLCJhY2Nlc3MiOiJhdXRoIiwiaWF0IjoxNTQ1MzU4MTI2fQ.YdK0MjOm7Lff22uTFITQdic0gKdMZRpsmRee-yejDpQ"
}
]
};
// create a copy of the original object.
// note that Object.assign will make a shallow copy of our object,
// so newObj.tokens will be a pointer to obj.tokens.
// in this instance, we don't care, as we are going to remove newObj.tokens anyway.
const newObj = Object.assign({}, obj);
// throw away the tokens property.
// OK to mutate newObj as we know it is not used anywhere else.
delete newObj.tokens;
// get the first token object from the tokens array.
// the (expectedArray || []) pattern ensures we have an array if obj.tokens is null or undefined.
const tokenObj = (obj.tokens || [])[0];
// get the token string from the token object.
// again, using the (expectedObject || {}) pattern in case tokenObj is null or undefined.
const token = (tokenObj || {}).token;
// create a new property called "token" on our newObj object.
// set it to our token value or an empty string if token is null or undefined.
newObj.token = token || '';
// of course, if you know the tokens array will always have a valid token object,
// you can simply use newObj.token = obj.tokens[0].token.
console.log(newObj);
Using destructuring assignment with "empty" representations of your types works nicely. transform produces a reliable output when tokens contains zero, one, or many { token: ... } values.
const emptyUser =
{ _id: 0, name: "", tokens: [] }
const emptyToken =
{ token: "" }
const toSingleTokenUser =
({ tokens: [ { token } = emptyToken ], ...u } = emptyUser) =>
({ ...u, token })
console .log
( toSingleTokenUser ({ _id: 1, name: "a", tokens: [ { token: "t" } ] })
// { _id: 1, name: "a", token: "t" }
, toSingleTokenUser ({ _id: 1, name: "a", tokens: [] })
// { _id: 1, name: "a", token: "" }
, toSingleTokenUser ({ _id: 1, name: "a", tokens: [ { token: "t1" }, { token: "t2" } ] })
// { _id: 1, name: "a", token: "t1" }
, toSingleTokenUser ({ foo: "bar", tokens: [ { token: "t" } ] })
// { foo: "bar", token: "t" }
)

javascript object creation for mongodb query

Tried to make the javascript object for mongodb query but javascript object auto quoted the $and property(due to dollar sign) which in result query error.
var array = [{
name: 'raiwind'
},
{
"rating.ratingGain": 9
}];
var filter = {
$and: array
};
console.log(filter); //output// { '$and': [ { name: 'raiwind' }, { 'rating.ratingGain': 9 } ] }

Categories