Removing nested pscustomobject within Azure Rule JSON - json

Been struggling with deleting a nested object within JSON returned from an Azure Alert Rule query.
Thanks to folks here, I've learned how to add a PSCustomObject within another. In this case, (below) to add a webhook action
"actions": [
{
"$type": "Microsoft.WindowsAzure.Management.Monitoring.Alerts.Models.RuleEmailAction, Microsoft.WindowsAzure.Management.Mon.Client",
"odata.type": "Microsoft.Azure.Management.Insights.Models.RuleEmailAction",
"sendtoserviceowners": true,
"customEmails": [
"email2#domain.com",
"email1#domain.com"
]
}
]
$rule.properties.actions += [PSCustomObject]#{
'$type' = "Microsoft.WindowsAzure.Management.Monitoring.Alerts.Models.RuleWebhookAction, Microsoft.WindowsAzure.Management.Mon.Client";
'odata.type' = "Microsoft.WindowsAzure.Management.Monitoring.Alerts.Models.RuleWebhookAction";
serviceuri = "http://www.webhooktest.com"
}
Which results in
"actions": [
{
"$type": "Microsoft.WindowsAzure.Management.Monitoring.Alerts.Models.RuleWebhookAction, Microsoft.WindowsAzure.Management.Mon.Client",
"odata.type": "Microsoft.Azure.Management.Insights.Models.RuleWebhookAction",
"serviceUri": "http://www.webhooktest.com"
},
{
"$type": "Microsoft.WindowsAzure.Management.Monitoring.Alerts.Models.RuleEmailAction, Microsoft.WindowsAzure.Management.Mon.Client",
"odata.type": "Microsoft.Azure.Management.Insights.Models.RuleEmailAction",
"sendToServiceOwners": false,
"customEmails": [
"email2#domain.com",
"email1#domain.com"
]
}
]
I need to be able to remove the webhook and leave the email. If I could add it using +=, why does trying to remove it with -=
$rule.properties.actions -= [PSCustomObject]#{
'$type' = "Microsoft.WindowsAzure.Management.Monitoring.Alerts.Models.RuleWebhookAction, Microsoft.WindowsAzure.Management.Mon.Client";
'odata.type' = "Microsoft.WindowsAzure.Management.Monitoring.Alerts.Models.RuleWebhookAction";
serviceuri = "http://www.webhooktest.com"
}
result in
result in [System.Object[]] does not contain a method named 'op_Subtraction'
I've not had luck with the Remove() method either. What will work?

Related

Operator "missing" not working properly in JsonLogic

I am using JsonLogic to validate my input payload with the rules defined using JsonLogic. I am able to test the rules using "Play with it" tool and my rules work perfectly fine against my input data.
But when I run the same rules through my .net Core application by passing payload from Postman the rules always return the else condition even when it should the error from if condition.
{
"if": [
{
"missing": [
"ProposedProjectDetails.IsFreezone",
"ProposedProjectDetails.InterestedToLeaseFrom",
"ProposedProjectDetails.IndustryType",
"ProposedProjectDetails.OtherType",
"ProposedProjectDetails.ProjectDescription",
"ProposedProjectDetails.OutputofFacility",
"ProposedProjectDetails.ProductionCapacity",
"ProposedProjectDetails.ProductionCapacityVolume",
"ProposedProjectDetails.MainRawMaterials",
"ProposedProjectDetails.RawMaterialQuantity",
"ProposedProjectDetails.RawMaterialEstimatedCost",
"ProposedProjectDetails.RawMaterialEstimatedTotInvestment",
"ProposedProjectDetails.AnnualSalesRevenue",
"ProposedProjectDetails.ConstructionStartDate",
"ProposedProjectDetails.Skilledjobs",
"ProposedProjectDetails.TotalAccomodationRequired",
"ProposedProjectDetails.TotalWorkerSalary",
"ProposedProjectDetails.EBITDA",
"ProposedProjectDetails.PortCargoImports",
]
},
"Missing mandatory inputs",
"all good"
]
}
Sample input payload is
{
"companyId": "string",
"serviceCode": "IPA",
"serviceType": "string",
"serviceName": "string",
"crmApplicationId": "string",
"crmReferenceNumber": "string",
"portalReferenceNumber": "string",
"data": {
"proposedProjectDetails": {
"outputofFacility": 2,
"productionCapacity": 0,
"productionCapacityVolume": 0,
"others": "string",
"shiftsPerDay": 0
}
}
}
My .Net code which is evaluating this is
public ValidationResponse Validate(JObject validation, JObject data)
{
var evaluator = new JsonLogicEvaluator(EvaluateOperators.Default);
var result = evaluator.Apply(validation, data);
return new ValidationResponse
{
IsValid = (string.Equals("All Fine", result.ToString(), StringComparison.OrdinalIgnoreCase)),
Message = result
};
}
When I run above code with JsonRules and above Payload, I always get all good in the response. But since I am missing required data in payload, it should get the error Missing mandatory inputs which I do get in JsonLogic "Play with it" tool.
Try keeping the names as json mapping fields camel case once like below
"if": [
{
"missing": [
"proposedProjectDetails.isFreezone",
"proposedProjectDetails.interestedToLeaseFrom",
]
},
"Missing mandatory inputs",
"all good"
]
}

Ruby: How to parse json to specific types

I have a JSON that I want to parse in Ruby. Ruby is completely new to me, but I have to work with it :-)
Here is my litte snippet, that should do the parsing:
response = File.read("app/helpers/example_announcement.json")
JSON.parse(response)
this works pretty fine. The only downside is, I do not know the properties at the point where I use it, it is not typesafe. So I created the objects for it
class Announcements
##announcements = Hash # a map key => value where key is string and value is type of Announcement
end
class Announcement
##name = ""
##status = ""
##rewards = Array
end
And this is how the json looks like
{
"announcements": {
"id1" : {
"name": "The Diamond Announcement",
"status": "published",
"reward": [
{
"id": "hardCurrency",
"amount": 100
}
]
},
"id2": {
"name": "The Normal Announcement",
"players": [],
"status": "published",
"reward": []
}
}
}
So I tried JSON parsing like this
response = File.read("app/helpers/example_announcement.json")
JSON.parse(response, Announcements)
But this is not how it works^^can anybody help me with this?

trying to loop through JsonNode but root jsonNode is duplicating the data

I am trying to loop through Jsonnode but root jsonNode is duplicating the data.
Trying to figure out but not sure where i am missing the issue. Will try to explain the issue below.
I have to Jackson API.
Json block is:
{
"queries": [
{
"id": "keyword",
"values": [
"test"
]
},{
"id": "include",
"values": [
false
]
}
]
}
My block of Java code is Iterator fieldNames = root.fieldNames();
while (fieldNames.hasNext()) {
String fieldName = fieldNames.next();
if (fieldName.equalsIgnoreCase("queries")) {
nameNode =root.get(fieldName);
}
JsonNode nameNode = root.get("queries");
for (JsonNode node : nameNode) {
JsonNode elementId = node.path("id").asText();
if (!elementId.isEmpty() && elementId.equalsIgnoreCase("include")) {
check = true;
include = node;
}
}
When debug comes to line for (JsonNode node : nameNode) { , node value is "id": "keyword", "values": [ "test" ] and nameNode is the json shown above but when it comes to next line which is " node.path("id").asText();"
nameNode variable appends "id": "keyword","values": [ "test" ] 2 times.
Now the json is the original json with "id": "keyword","values": [ "test" ] appended 2 times and gives concurrentModificationException.
change your variable node to objNode because node may be predifined value in jackson and you can also try to make for each variable to final

Updating nested array n1ql

The sample doc, I am trying to work with is:
{
"name": "level1",
"childLevel1": [
{
"name": "level2",
"childLevel2": [
{
"name": "level3",
"childLevel3": [
{
"name": "level4",
"attribute1": "data"
}
]
}
]
}
]
}
What we want to do is, with n1ql add one more array element to "childLevel3". I have tried the reference to https://developer.couchbase.com/documentation/server/4.5/n1ql/n1ql-language-reference/update.html
I was able to add a regular attribute to childLevel2 but after that it was not working. This is the query I have been trying out.
Update sample
set child2.childLevel3 = ARRAY_PUT(child2.childLevel3, {'attribute' : 'data2'})
FOR child2 in child1.childLevel2 when child2.name == "level3" END
for child1 in childLevel1 when childLevel1.name == 'level2' END
WHERE name == 'level1'
But it gives me error on parsing, I tried other ways too but nothing works.
Try
UPDATE sample
SET child2.childLevel3 = ARRAY_PUT(child2.childLevel3, {'attribute' : 'data2'})
FOR child2 in child1.childLevel2
FOR child1 in childLevel1
WHEN childLevel1.name == 'level2' AND child2.name == "level3"
END
WHERE name == 'level1';
I had to update an object within a nested array, recently in Couchbase. The answer above helped me to formulate this query in a bucket called "metadata". The data structure is:
{
"documentMetadata": {
"documentId": "42"
},
"results": [
{
"type": "FileStaging",
"status": "NOT STARTED"
}
],
"type": "runLog"
}
The query that worked for me:
UPDATE metadata
SET res.status = 'QUEUED'
FOR res in results
WHEN res.type = 'FileStaging'
END
WHERE type = 'runLog'
AND documentMetadata.documentId = '42'

powershell json object with square brackets

I have an import of 1+ emails that have to be added to a json object. A foreach loop checks to see if the emails are valid (code not addded to this example). When the import contains 2+ cases, the format of the json object is correct:
[
{
"Name": "John Doe",
"Email": "email#gmail.com"
},
{
"Name": "Jane Doe",
"Email": "email#live.com"
}
]
Namely, square brackets with each object in curly brackets, separated by comma.
But when the foreach loop only returns 1 valid email, the format becomes:
{
"Name": "John Doe",
"Email": "email#gmail.com"
}
This is the code I am running:
$body = foreach($row in $mailinglistimp)
{
#{
Email=$row.EPOSTADR
Name=$row.KUNDE_NM
}
}
$body_json = ConvertTo-json $body
How can I force the object to look like this with only one item in the foreach loop?
[
{
"Name": "John Doe",
"Email": "email#gmail.com"
},
]
On a related note, a similar problem was solved by using [int[]] $ids inside another json object, but I cant get a similar code to work using [string[]].
This is somewhat unlikely if you ask me, because you want to declare an array which contains a single item. PowerShell will always see this like a single item and won't add square brackets (array declaration for JSON). But I ran into the same issue when I was making a script to update changes in TOPdesk. So this might help someone.
$requestObject = #()
$action = "Buy a new laptop"
$status = "Rejected"
if($Action){
$requestObject += #{
op = "add"
path = "/progressTrail"
value = $Action
}
}
if($Status){
$requestObject += #{
op = "replace"
path = "/status"
value = $Status
}
}
if($requestObject){
if($requestObject.Count -eq 1){
$requestBody = "[$($requestObject | ConvertTo-Json)]"
}else{
$requestBody = $requestObject | ConvertTo-Json
}
}
The following output is generated:
[
{
"path": "/progressTrail",
"op": "add",
"value": "Buy a new laptop"
},
{
"path": "/status",
"op": "replace",
"value": "Rejected"
}
]
Now if you leave $status empty for instance, you will get the following:
[{
"path": "/progressTrail",
"op": "add",
"value": "Buy a new laptop"
}]
Note that I force the square brackets, when there is only one item in my array ($requestObject.Count -eq 1). This is not very nice imo, but it does the trick.