how extract string into object - mysql

I’m not sure how to explain this but I’ll write an example on how I can create a new data from this using SQL. this is from MongoDb database and I can't change any thing. I was hoping if any one Knows how to execute this using the Select method.
SELECT * FROM mytable
Original data
[{
"id": "2433-10",
"busiName": "ABC",
"srTypeId": "2433-10",
"nodeType": "0",
"pathName": "home",
"busiSort": 10,
"SampleInfo": "1:sql test question identifiers: itemid:12345;itemname:Ford;itemid:12345; itemlocation=USA/itemDate=2014",
"superTypeId": "002",}]
I want extract just SampleInfo into New data
[{
"1":"sql test question identifiers"
"itemid":"12345";
"itemname":"Ford";
"iteminfo":"it's car";
"itemlocation ":"USA";
"itemDate":"2014";
}]

With some initial sanitization(replacing "=" with ":" and "/" with ";") maybe this is what you need:
( This is assuming that you have only single delimiter between the key/values and single delimiter between key and value )
db.collection.aggregate([
{
$addFields: {
newData: {
"$arrayToObject": {
"$map": {
"input": {
$split: [
"$SampleInfo",
";"
]
},
"as": "newD",
"in": {
"$split": [
"$$newD",
":"
]
}
}
}
}
}
}
])
Explained:
Split the SampleInfo based on delimiter ";" ( considering you have "key1:value1;key2:value2;key3:value3" in new array called newData.
Split the keys and values based on the key/value delimiter ":" , convert them to "key":"value" pair in the newData array field.
playground just aggregation
( If you want to just parse and output )
playground update + agg pipleine 4.2+
( If you want to parse and store back to the database under new field: newData )
But afcourse prefered option as suggested above is to sanitize and parse the data before inserting it to the database ...
Same thing via JavaScript Example:
mongos> function stringToObj (string) { var obj = {}; var stringArray = string.split(';'); for(var i = 0; i < stringArray.length; i++){ var kvp = stringArray[i].split(':'); if(kvp[1]){ obj[kvp[0]] = kvp[1] } } return obj; }
mongos> db.collection.find().forEach(function(d){ d.newData=stringToObj(d.SampleInfo);db.collection.save(d); } )
mongos>
Explained:
Define JS function stringToObj ( Converting the string to object )
Loop over all documents via forEach and use the function to parse and modify the document adding new field newData with the content.

Related

get json root key based on value

{
"vitals": {
"title": "Vitals IR",
"name": "vitalsIr",
"formid":"5ed5f7ca158a91827891cab2"
},
"anthropometry": {
"title": "Anthropometry IR",
"name": "anthropometryIr",
"formid":"5ed621ac158a91228191cafd"
}}
How to get the root key name vitals , anthropometry based on formid value
for example if formid value is "5ed621ac158a91228191cafd"
I need output as anthropometry need to achieve this in angular javascript
To loop through a json object using JavaScript, you can preform a for on the keys. E.g for (jsonPropertyName in json) { ... }. You can then query the formId.
For example:
function ProvideRootKey(formId) {
var results;
for (jsonPropertyName in json) {
if (json[jsonPropertyName]['formid'] === formId) {
results = jsonPropertyName
}
}
return results
}
var json = JSON.parse('{ "vitals":{ "title":"Vitals IR", "name":"vitalsIr","formid":"5ed5f7ca158a91827891cab2"}, "anthropometry":{ "title":"Anthropometry IR", "name":"anthropometryIr", "formid":"5ed621ac158a91228191cafd"}}');
console.log(ProvideRootKey('5ed621ac158a91228191cafd'))
Output (in console log):
"anthropometry"
See working example: https://jsfiddle.net/vgo81stm/1/

Restructuring a large amount of values in a JSON file

I have a JSON file with a large amount of the following values:
"values": [
"Foo": 1,
"Bar": 2,
"Baz": 3,
...
],
How do I efficiently convert this into:
"values": [
{
"name": "Foo",
"value": 1
},
{
"name": "Bar",
"value": 2
},
{
"name": "Baz",
"value": 3
},
...
],
Any help would be appreciated!
Okay, so there are two problems with your input. The first is the fact that the given JSON is invalid, so can't directly be parsed. The square brackets after "values" should be curly brackets, to allow for a hash instead of an array:
let raw_old_data =
// Read the old file
fs.readFileSync('./input_data.json').toString()
// Remove all newlines which could interfere with the regex
.replace(/[\r\n]/g, '')
// Replace the square brackets after `"values"` with curly braces
.replace(/"values": \[(.+?)\]/g, '"values": { $1 }');
To convert this (now valid) string to a JSON object, you use JSON.parse:
let old_data = JSON.parse(raw_old_data);
The second problem is that the format in which the values are stored doesn't match your needs. You want to convert from { key: "value" } to [ name: "key", value: "value" ]. The following function can do that, assuming your version of Node supports ES6 (If not, look at Murillo's answer):
function fix_format(obj) {
// This is where we keep the new items in the correct format
let res = [];
// Loop over all values
Object.keys(obj.values).forEach(name => {
let value = obj.values[name];
// Change the format and add to resulting array
res.push({
// If the variable is the same as the key of the hash, it doesn't have to be specified
name,
value,
});
});
return res;
}
All that's then left to do is loop all data from the old object through that function with the Array.map function:
let new_data = old_data.map(fix_format);
And optionally write it back to a file to use with a different program:
fs.writeFileSync('./formatted_data.json', JSON.stringify(data, null, 2));
Note: The 2 in the JSON.stringify function indicates that the resulting JSON should be padded with 2 spaces, to keep it readable.
With ES6:
Object.keys(values).map(name => ({
name,
value: values[name]
}))
Without ES6:
var keys = Object.keys(values);
var newValues = [];
for(var i = 0; i < keys.length; i++){
newValues.push({
name: keys[i],
value: values[keys[i]]
})
}
If your intention is to use the received data i.e obtain data from DB (e.g MSSql, MySql...) using the connection.query(your_custom_sql_query, (err, rows, fields)
for more info:Node.js MySQL Select From Table
I'll recommend you to use:
const myJson = JSON.stringify(rows[0]);

Grabbing a number from .JSON

I have a long list of data, in the following format:
[
{
"ID": "1234",
"date/time": "2016-07-18 18:21:44",
"source_address": "8011",
"lat": "40.585260",
"lng": "-105.084420",
}
]
And I am creating a script to extract the values out of each line. For example, if a line contains "ID": I want to be able to store the value "1234" into a variable, so I can store it in a different format.
Here is my code to detect "ID":
'use strict';
let lineReader = require('line-reader');
//.JSON variables from input file
let id;
//begin creating new object
console.log('var source = {');
//output the file
lineReader.eachLine('dataOut.json', function (line, last) {
//detect ID, and print it out in the new format
if (id =~ /^id:$/) {
console.log('id: "') + console.log('",');
}
//done
if (last) {
console.log('}');
return false; // stop reading
}
});
Once I detect the ID, I'm not sure how I can obtain the value that follows the "ID" on that line.
How can I store the values on a line, after I detect which line they are on?
Unless your json file is stupidly big, you can just require it and then it's an in memory JS object.
var obj = require('./dataOut.json');
// first element
console.log(obj[0]);

Creating CSV view from CouchDB

I know this should be easy, but I just can't work out how to do it despite having spent several hours looking at it today. There doesn't appear to be a straightforward example or tutorial online as far as I can tell.
I've got several "tables" of documents in a CouchDB database, with each "table" having a different value in a "schema" field in the document. All documents with the same schema contain an identical set of fields. All I want to do is be able to view the different "tables" in CSV format, and I don't want to have to specify the list of fieldnames in each schema.
The CSV output is going to be consumed by an R script, so I don't want any additional headers in the output if I can avoid them; just the list of fieldnames, comma separated, with the values in CSV format.
For example, two records in the "table1" format might look like:
{
"schema": "table1",
"field1": 17,
"field2": "abc",
...
"fieldN": "abc",
"timestamp": "2012-03-30T18:00:00Z"
}
and
{
"schema": "table1",
"field1": 193,
"field2": "xyz",
...
"fieldN": "ijk",
"timestamp": "2012-03-30T19:01:00Z"
}
My view is pretty simple:
"all": "function(doc) {
if (doc.schema == "table1") {
emit(doc.timestamp, doc)
}
}"
as I want to sort my records in timestamp order.
Presumably the list function will be something like:
"csv": "function(head, req) {
var row;
...
// Something here to iterate through the list of fieldnames and print them
// comma separated
for (row in getRow) {
// Something here to iterate through each row and print the field values
// comma separated
}
}"
but I just can't get my head around the rest of it.
If I want to get CSV output looking like
"timestamp", "field1", "field2", ..., "fieldN"
"2012-03-30T18:00:00Z", 17, "abc", ..., "abc"
"2012-03-30T19:01:00Z", 193, "xyz", ..., "ijk"
what should my CouchDB list function look like?
Thanks in advance
The list function that works with your given map should look something like this:
function(head,req) {
var headers;
start({'headers':{'Content-Type' : 'text/csv; charset=utf-8; header=present'}});
while(r = getRow()) {
if(!headers) {
headers = Object.keys(r.value);
send('"' + headers.join('","') + '"\n');
}
headers.forEach(function(v,i) {
send(String(r.value[v]).replace(/\"/g,'""').replace(/^|$/g,'"'));
(i + 1 < headers.length) ? send(',') : send('\n');
});
}
}
Unlike Ryan's suggestion, the fields to include in the list are not configurable in this function, and any changes in order or included fields would have to be written in. You would also have to rewrite any quoting logic needed.
Here some generic code that Max Ogden has written. While it is in node-couchapp form, you probably can get the idea:
var couchapp = require('couchapp')
, path = require('path')
;
ddoc = { _id:'_design/csvexport' };
ddoc.views = {
headers: {
map: function(doc) {
var keys = [];
for (var key in doc) {
emit(key, 1);
}
},
reduce: "_sum"
}
};
ddoc.lists = {
/**
* Generates a CSV from all the rows in the view.
*
* Takes in a url encoded array of headers as an argument. You can
* generate this by querying /_list/urlencode/headers. Pass it in
* as the headers get parameter, e.g.: ?headers=%5B%22_id%22%2C%22_rev%5D
*
* #author Max Ogden
*/
csv: function(head, req) {
if ('headers' in req.query) {
var headers = JSON.parse(unescape(req.query.headers));
var row, sep = '\n', headerSent = false, startedOutput = false;
start({"headers":{"Content-Type" : "text/csv; charset=utf-8"}});
send('"' + headers.join('","') + '"\n');
while (row = getRow()) {
for (var header in headers) {
if (row.value[headers[header]]) {
if (startedOutput) send(",");
var value = row.value[headers[header]];
if (typeof(value) == "object") value = JSON.stringify(value);
if (typeof(value) == "string") value = value.replace(/\"/g, '""');
send("\"" + value + "\"");
} else {
if (startedOutput) send(",");
}
startedOutput = true;
}
startedOutput = false;
send('\n');
}
} else {
send("You must pass in the urlencoded headers you wish to build the CSV from. Query /_list/urlencode/headers?group=true");
}
}
}
module.exports = ddoc;
Source:
https://github.com/kanso/kanso/issues/336

How do you return lower-cased JSON from a CFCin ColdFusion?

I have a ColdFusion component that will return some JSON data:
component
{
remote function GetPeople() returnformat="json"
{
var people = entityLoad("Person");
return people;
}
}
Unfortunately, the returned JSON has all the property names in upper case:
[
{
FIRSTNAME: "John",
LASTNAME: "Doe"
},
{
FIRSTNAME: "Jane",
LASTNAME: "Dover
}
]
Is there any way to force the framework to return JSON so that the property names are all lower-case (maybe a custom UDF/CFC that someone else has written)?
Yeah, unfortunately, that is just the way ColdFusion works. When setting some variables you can force lowercase, like with structs:
<cfset structName.varName = "test" />
Will set a the variable with uppercase names. But:
<cfset structName['varname'] = "test" />
Will force the lowercase (or camelcase depending on what you pass in).
But with the ORM stuff you are doing, I don't think you are going to be able to have any control over it. Someone correct me if I am wrong.
From http://livedocs.adobe.com/coldfusion/8/htmldocs/help.html?content=functions_s_03.html
Note: ColdFusion internally represents structure key names using
all-uppercase characters, and, therefore, serializes the key names to
all-uppercase JSON representations. Any JavaScript that handles JSON
representations of ColdFusion structures must use all-uppercase
structure key names, such as CITY or STATE. You also use the
all-uppercase names COLUMNS and DATA as the keys for the two arrays
that represent ColdFusion queries in JSON format.
If you're defining the variables yourself, you can use bracket notation (as Jason's answer shows), but with built-in stuff like ORM I think you're stuck - unless you want to create your own struct, and clone the ORM version manually, lower-casing each of the keys, but that's not really a great solution. :/
This should work as you described.
component
{
remote function GetPeople() returnformat="json"
{
var people = entityLoad("Person");
var rtn = [];
for ( var i = 1; i <= arrayLen( people ); i++ ) {
arrayAppend( rtn, {
"firstname" = people[i].getFirstname(),
"lastname" = people[i].getLastname()
} );
}
return rtn;
}
}
If any of your entity properties return null, the struct key wont exist.
To work around that try this
component
{
remote function GetPeople() returnformat="json"
{
var people = entityLoad("Person");
var rtn = [];
for ( var i = 1; i <= arrayLen( people ); i++ ) {
var i_person = {
"firstname" = people[i].getFirstname(),
"lastname" = people[i].getLastname()
};
if ( !structKeyExists( i_person, "firstname" ) ) {
i_person["firstname"] = ""; // your default value
}
if ( !structKeyExists( i_person, "lastname" ) ) {
i_person["lastname"] = ""; // your default value
}
arrayAppend( rtn, i_person );
}
return rtn;
}
}