Merge and match objects that match AngularJS - javascript

Hello I would like to merge and match two json objects. I would like to do with the Angular way. Any help would be greatly appreciated. Thank you everyone. Here is an example:
// First json object
{
"UserID":"john.davis",
"edpi":null,
"UserApp":[
{
"Name":"name3",
"Link":"/Protect3.php"
},
{
"Name":"name5",
"Link":"/Admin/Launch.html"
},
{
"Name":"name2",
"Link":"aaap/defaultBH.php"
}
]
}
// Second json object
[
{
"color":"color1",
"icon": "content/images/icons/administrator.svg",
"Name": "name5"
},
{
"color":"color3",
"icon": "content/images/icons/administrator.svg",
"Name": "name3"
},
{
"color":"color2",
"icon": "content/images/icons/behavior.svg",
"Name": "name2"
}
]
Hoping to get this
[
{
"TokenName":"name3",
"TokenLink":"../Protect3.asp",
"color":{
"color":"color3",
"icon": "content/images/icons/administrator.svg",
"match": "name3"
}
},
{
"Name":"name5",
"Link":"/Admin/Launch.html",
"color":{
"color":"color1",
"icon": "content/images/icons/administrator.svg",
"match": "name5"
}
},
{
"Name":"name2",
"Link":"aaap/defaultBH.php"
"color":{
"color":"color2",
"icon": "content/images/icons/behavior.svg",
"match": "name2"
}
}
]

I figured it out. Here is the code below.
function mergeArraysOnProperty(array1, array2, property) {
array1.forEach(function(element1) {
array2.forEach(function(element2) {
if (element1[property] === element2[property]) {
for (var newProperty in element2) {
if (element2.hasOwnProperty(newProperty)) {
element1[newProperty] = element2[newProperty];
}
}
}
});
});
return array1;
};
$scope.newjson = mergeArraysOnProperty(userapp, color, "Name");
console.log($scope.newjson);

Related

How to retrieve and process the data from the open dialog form?

I'm trying to process the response data in the open dialog but got stuck in this the retrieval.
I followed the step by step procedure given in this link: https://developers.google.com/chat/how-tos/dialogs but unfortunately, it didn't work as well.
Here is the sample code:
My goal is to get the data from the dialog form then process it. My pain point is in the code: event.common.formInputs.firstnumber.stringInputs.value[0] where it returns undefined reading value.
function openDialog(event) {
return {
"action_response": {
"type": "DIALOG",
"dialog_action": {
"dialog": {
"body": {
"sections": [
{
"header": "Addition Calculator:",
"widgets": [
{
"textInput": {
"label": "First Number",
"type": "SINGLE_LINE",
"name": "firstnumber"
}
},
{
"textInput": {
"label": "Second Number",
"type": "SINGLE_LINE",
"name": "secondnumber"
}
},
{
"textInput": {
"label": "Third Number",
"type": "SINGLE_LINE",
"name": "thirdnumber"
}
},
{
"buttonList": {
"buttons": [
{
"text": "Submit",
"onClick": {
"action": {
"function": "giveAnswer"
}
}
}
]
},
"horizontalAlignment": "END"
}
]
}
]
}
}
}
}
};
}
function giveAnswer(event) {
var firstterm = parseFloat(event.common.formInputs.firstnumber.stringInputs.value[0])
var secondterm = parseFloat(event.common.formInputs.secondnumber.stringInputs.value[0])
var thirdterm = parseFloat(event.common.formInputs.thirdnumber.stringInputs.value[0])
var sum = firstterm+secondterm+thirdterm
return {
"cardsV2": [{
"cardId": "addContact",
"card": {
"header": {
"title": "The SUM is:",
"subtitle": "Answer",
"imageUrl": "https://images.emojiterra.com/google/noto-emoji/v2.034/128px/1f4f1.png",
"imageType": "SQUARE"
},
"sections": [
{
"widgets": [
{
"textParagraph": {
"text": sum
}
}
]
}
]
}
}
]
}
}
I tried the example in here but didn't work as well. https://developers.google.com/chat/how-tos/dialogs#receive_form_data_from_dialogs

LogicApp/JavaScript - Split JSON data to multiple objects and arrays

I have below JSON data coming from source system into my Logic App:
[
{
"project":"abc",
"assignees":"123,456"
},
{
"project":"xyz",
"assignees":"123,468"
}
]
I want to split the "assignees", create arrays within objects, and produce below final output:
[
{
"metadata":{
"type":"project"
},
"name":"Project ABC",
"assignee":[
{
"metadata":{
"type":"assignment"
},
"employeeId":"123"
},
{
"metadata":{
"type":"assignment"
},
"employeeId":"123"
}
]
},
{
"metadata":{
"type":"project"
},
"name":"Project ABC",
"assignee":[
{
"metadata":{
"type":"assignment"
},
"employeeId":"123"
},
{
"metadata":{
"type":"assignment"
},
"employeeId":"468"
}
]
}
]
Can this be achieved in Logic App only? If not, can this be achieved using inline JavaScript code and how?
I don't know anything about LogicApp or how it works, but if all you want is javascript code that can make this transformation you can do something like this:
const src=[
{
"project":"abc",
"assignees":"123,456"
},
{
"project":"xyz",
"assignees":"123,468"
}
]
const transformed=src.map(entry=>({
"metadata":{type:"project"},
name:"Project "+entry.project.toUpperCase(),
assignee:entry.assignees.split(",").map(assignee=>({
metadata:{type:"assignment"},
emplyeeId:assignee
}))
}))
I initialize a variable named source to store same data source with yours.
And here provide a sample of inline javascript code for your reference:
var source = workflowContext.actions.Initialize_variable.inputs.variables[0].value;
var result = [];
source.forEach(sItem=>{
var resultItem = {
"metadata":{
"type":"project"
},
"name":"Project " + sItem.project.toUpperCase()
}
var assignee = [];
var assigneesSplit = sItem.assignees.split(",");
assigneesSplit.forEach(item=>{
var assigneItem = {
"metadata":{
"type":"assignment"
},
"employeeId":item
}
assignee.push(assigneItem);
});
resultItem.assignee = assignee;
result.push(resultItem);
});
return result;
After running the logic app, we can get the result data like:
[
{
"metadata": {
"type": "project"
},
"name": "Project ABC",
"assignee": [
{
"metadata": {
"type": "assignment"
},
"employeeId": "123"
},
{
"metadata": {
"type": "assignment"
},
"employeeId": "456"
}
]
},
{
"metadata": {
"type": "project"
},
"name": "Project XYZ",
"assignee": [
{
"metadata": {
"type": "assignment"
},
"employeeId": "123"
},
{
"metadata": {
"type": "assignment"
},
"employeeId": "468"
}
]
}
]
It seems there are some mistakes in your expected data sample(such as the second project name and the second employeeId in first assignee field). If they are not typo, please let me know, I will modify my js inline code to implement your expected json data.

Is there any way to replace the existing object inside JSON array with new object based on key

I am having a dynamic JSON array in below format,
let main_data = [
{
"client":[
{
"name":"aaaa",
"count":"1",
"filter":{
"type":{
"name":"test3"
}
}
},
{
"name":"bbbb",
"count":"9",
"filter":{
"type":{
"name":"test2"
}
}
}
]
},
{
"compute":[
{
"name":"cccc",
"count":"6",
"filter":{
"type":{
"name":"test"
}
}
}
]
}
]
Here key "name" is unique. When updating a form, I will get an json array like below,
let new_data = [
{
"client":[
{
"name":"bbbb",
"count":"1234",
"type":{
"name":"updated_name"
}
}
}
]
}
]
I need to check the "name" in the json array in "main_data" and remove the existing one and update with the new "updated_data" into the "main_data". (no Jquery please)
Expected output,
let main_data = [
{
"client":[
{
"name":"aaaa",
"count":"1",
"filter":{
"type":{
"name":"test3"
}
}
},
{
"name":"bbbb",
"count":"123",
"filter":{
"type":{
"name":"updated_name"
}
}
}
]
},
{
"compute":[
{
"name":"cccc",
"count":"6",
"filter":{
"type":{
"name":"test"
}
}
}
]
}
]
Is there any way to achive this. Any help would be much appreciated. Thanks in advance.
Try this
let main_data = [{
client: [{
name: "aaaa",
count: "1",
filter: {
type: {
name: "test3"
}
}
},
{
name: "bbbb",
count: "9",
filter: {
type: {
name: "test2"
}
}
}
]
},
{
compute: [{
name: "cccc",
count: "6",
filter: {
type: {
name: "test"
}
}
}]
}
];
let new_data = [{
client: [{
name: "bbbb",
count: "1234",
filter: {
type: {
name: "updated_name"
}
}
}]
}];
const res = main_data.map((item, index) => {
if (item.client) {
const clients = item.client.map(client => {
if (client.name === new_data[0].client[0].name) {
client = new_data[0].client[0];
}
return client;
});
return {
client: clients
};
}
return item;
});
console.log(res);
There may very well be a fancy way to get this done but one can always just find the matching item and replace it. eg.
let main_data = [
{
"client": [
{
"name": "aaaa",
"count": "1",
"filter": {
"type": {
"name": "test3"
}
}
},
{
"name": "bbbb",
"count": "123",
"filter": {
"type": {
"name": "updated_name"
}
}
}
]
},
{
"compute": [
{
"name": "cccc",
"count": "6",
"filter": {
"type": {
"name": "test"
}
}
}
]
}
];
let new_data = [
{
"client": [
{
"name": "bbbb",
"count": "1234",
"type": {
"name": "updated_name"
}
}
]
}
];
console.log("before:" + JSON.stringify(main_data));
newItem = new_data[0]["client"][0];
mainDataList = main_data[0]["client"];
for (i = 0; i < mainDataList.length; i++) {
if (mainDataList[i].name == newItem.name) {
mainDataList[i] = newItem;
}
}
console.log("after:" + JSON.stringify(main_data));
will output
before:[{"client":[{"name":"aaaa","count":"1","filter":{"type":{"name":"test3"}}},{"name":"bbbb","count":"123","filter":{"type":{"name":"updated_name"}}}]},{"compute":[{"name":"cccc","count":"6","filter":{"type":{"name":"test"}}}]}]
after:[{"client":[{"name":"aaaa","count":"1","filter":{"type":{"name":"test3"}}},{"name":"bbbb","count":"1234","type":{"name":"updated_name"}}]},{"compute":[{"name":"cccc","count":"6","filter":{"type":{"name":"test"}}}]}]
Here's a simple way to do this, let's say your new data is at variable newData:
main_data.client.filter(item => item.name === newData.name).push(newData)

Check for more than one key value pair in JSON data

I have JSON data formatted with multiple products which each have multiple variants and has data showing if the variant is available as well as the size of the variant.
"products":[
{
"variants":[
{
"available":true,
"selectedOptions":[
{
"name":"Size",
"value":"M"
}
]
},
{
"available":true,
"selectedOptions":[
{
"name":"Size",
"value":"L"
}
]
}
]
},
{
"variants":[
{
"available":true,
"selectedOptions":[
{
"name":"Size",
"value":"S"
}
]
},
{
"available":false,
"selectedOptions":[
{
"name":"Size",
"value":"L"
}
]
}
]
}
]
I want to traverse the JSON data and tell if the size of the product variant is large ("value":"L") and if the product is available ("available":true). I'm able to check for one or the other but I'm not sure how to check both at the same time. This is what I have so far:
o = products;
function traverse(o) {
for (var i in o) {
if(o[i] == true){
console.log([i,o[i]]);
}
if(o[i] == 'L'){
console.log([i,o[i]]);
}
if (o[i] !== null && typeof(o[i])=="object") {
traverse(o[i]);
}
}
}
console.log(o);
traverse(o);
}
You can use this approach to loop over the possible variants per product and identify the target according to availability and size.
This approach uses the function find and forEach for traversing the Object.
The function find looks for a selectedOption with size L and the nested forEach to check the availability.
var obj = { "products": [{ "variants": [{ "available": true, "selectedOptions": [{ "name": "Size", "value": "M" }] }, { "available": true, "selectedOptions": [{ "name": "Size", "value": "L" }] } ] }, { "variants": [{ "available": true, "selectedOptions": [{ "name": "Size", "value": "S" }] }, { "available": false, "selectedOptions": [{ "name": "Size", "value": "L" }] } ] } ]};
obj.products.forEach((p, i) => {
p.variants.forEach((v) => {
if (v.available) {
var found = v.selectedOptions.find((s) => s.value === 'L');
if (found) {
console.log(`Found a product at index '${i}' with variant ['${v.available}' | '${found.value}']`);
}
}
});
});
.as-console-wrapper { max-height: 100% !important; top: 0; }

How to search JSON as a path

I have a JSON as shown below
{
"name": "Soft Drinks",
"T2": [
{
"name": "Bottled",
"T3": [
{
"name": "Apple",
"leaf": [
{
"name": "Apple 500 ML"
},
{
"name": "Apple 1 Ltr"
}
]
}
]
},
{
"name": "Fountain",
"T3": [
{
"name": "Apple",
"leaf": [
{
"name": "Apple Regular, 500 ML"
}
]
}
]
},
{
"name": "Tin",
"T3": [
{
"name": "Apple",
"leaf": [
{
"name": "Apple Regular, 300 ML"
}
]
}
]
}
]
}
I will get a Input String as Path means this way as an array
1st case :
Input : Soft Drinks,Bottled
Output : ["Apple"]
2nd case :
Input : Soft Drinks,Fountain,Apple
Output
[
"leaf",
[
{
"name": "Apple Regular, 500 ML"
}
]
]
Could anybody please help me how to resolve this?
I am forming this input array when navigated through the Jquery Accordian, so depending on the click, I need to show the respective data.
For your reference the screen looks this way
Some changes: every node has keys name and leaf,
var drinks = [
{
"name": "Soft Drinks",
"leaf": [
{
"name": "Bottled",
"leaf": [
{
"name": "Apple",
"leaf": [
{
"name": "Apple 500 ML"
},
{
"name": "Apple 1 Ltr"
}
]
}
]
},
{
"name": "Fountain",
"leaf": [
{
"name": "Apple",
"leaf": [
{
"name": "Apple Regular, 500 ML"
}
]
}
]
},
{
"name": "Tin",
"leaf": [
{
"name": "Apple",
"leaf": [
{
"name": "Apple Regular, 300 ML"
}
]
}
]
}
]
}
];
var drinkParser = (function () {
function DrinksCollection(nodes) {
extend(this, nodes);
this.length = nodes.length;
this.parent = null;
}
/*
* Method extend from Underscore.js 1.6.0
* http://underscorejs.org
* (c) 2009-2014 Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors
* Underscore may be freely distributed under the MIT license.
*/
function extend(obj) {
Array.prototype.slice.call(arguments, 1).forEach(function (source) {
if (source) {
for (var prop in source) {
obj[prop] = source[prop];
}
}
});
return obj;
}
function nodeMatcher(node, selectorExpr) {
var type = typeof selectorExpr;
if (type === "string") {
return node.name === selectorExpr;
} else if (type === "function") {
return !!selectorExpr(node);
} else {
throw new TypeError("Cannot filter node with selector " + selectorExpr);
}
}
DrinksCollection.prototype = {
toArray: function () {
return Array.prototype.slice.call(this);
},
find: function (selectorExpr) {
var foundNodes = [];
this.walk(function (node) {
if (nodeMatcher(node, selectorExpr)) {
foundNodes.push(node);
}
});
return this.pushStack(foundNodes);
},
each: function (callback) {
this.toArray().forEach(callback);
return this;
},
map: function (callback) {
return this.toArray().map(callback);
},
walk: function (callback) {
function walk(node, index) {
callback.call(node, node, index);
(node.leaf || []).forEach(walk);
}
this.each(walk);
return this;
},
pushStack: function (nodes) {
var newInstance = new DrinksCollection(nodes);
newInstance.parent = this;
return newInstance;
},
children: function () {
var allChildren = [];
this.each(function (node) {
allChildren = allChildren.concat(node.leaf);
});
return this.pushStack(allChildren);
},
props: function (propName) {
return this.map(function (node) {
return node[propName];
});
},
names: function () {
return this.props("name");
}
};
return function (nodes) {
return new DrinksCollection(nodes);
}
}());
(function parseDrinks() {
console.log(drinkParser(drinks).find('Soft Drinks').find('Bottled').children().names()); // [ 'Apple' ]
console.log(drinkParser(drinks).find('Soft Drinks').find('Bottled').find('Apple').children().map(function (drink) {
return drink;
})); // [ { name: 'Apple 500 ML' }, { name: 'Apple 1 Ltr' } ]
}());

Categories