Skip to content
9 changes: 7 additions & 2 deletions src/readme.graph.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@
azure: false
powershell: true
version: latest
#use: "@autorest/[email protected]"
use: "$(this-folder)../autorest.powershell"
export-properties-for-dict: false
metadata:
Expand Down Expand Up @@ -651,7 +650,13 @@ directive:
// Fix double = in date parameter. Temp fix for https://github.com/Azure/autorest.powershell/issues/1025.
let dateAssignmentRegex = /(date="\n.*)(\+.*"=")(.*\+.*date)/gmi
$ = $.replace(dateAssignmentRegex, '$1 $3');
return $;

// Allow sending of serialized null properties located in cleanedBody
$ = $.replace(/request\.Content\s*=\s*new\s+global::System\.Net\.Http\.StringContent\(\s*null\s*!=\s*body\s*\?\s*body\.ToJson\(null\)\.ToString\(\)\s*:\s*@"{}",\s*global::System\.Text\.Encoding\.UTF8\);/g,'request.Content = new global::System.Net.Http.StringContent(cleanedBody, global::System.Text.Encoding.UTF8);');

$ = $.replace(/request\.Content\s*=\s*new\s+global::System\.Net\.Http\.StringContent\(\s*null\s*!=\s*body\s*\?\s*new\s+Microsoft\.Graph\.PowerShell\.Runtime\.Json\.XNodeArray\(.*?\)\s*:\s*null,\s*global::System\.Text\.Encoding\.UTF8\);/g,'request.Content = new global::System.Net.Http.StringContent(cleanedBody, global::System.Text.Encoding.UTF8);');

return $
}

# Fix enums with underscore.
Expand Down
77 changes: 50 additions & 27 deletions tools/Custom/JsonExtensions.cs
Original file line number Diff line number Diff line change
@@ -1,62 +1,85 @@
namespace Microsoft.Graph.PowerShell.JsonUtilities
{
using Newtonsoft.Json.Linq;
using System;
using System.Linq;

public static class JsonExtensions
{
/// <summary>
/// Removes JSON properties that have a value of "defaultnull" and converts properties with values of "null" to actual JSON null values.
/// Recursively removes properties with the value "defaultnull" from a JSON structure
/// and replaces string values that are "null" with actual null values.
/// This method supports both JObject (JSON objects) and JArray (JSON arrays),
/// ensuring proper cleanup of nested structures.
/// </summary>
/// <param name="jsonObject">The JObject to process and clean.</param>
/// <returns>
/// A JSON string representation of the cleaned JObject with "defaultnull" properties removed and "null" values converted to JSON null.
/// </returns>
/// <param name="token">The JToken (JObject or JArray) to process.</param>
/// <returns>The cleaned JSON string with "defaultnull" values removed and "null" strings converted to null.</returns>
/// <example>
/// JObject json = JObject.Parse(@"{""name"": ""John"", ""email"": ""defaultnull"", ""address"": ""null""}");
/// string cleanedJson = json.RemoveDefaultNullProperties();
/// Console.WriteLine(cleanedJson);
/// // Output: { "name": "John", "address": null }
/// </example>
public static string RemoveDefaultNullProperties(this JObject jsonObject)
public static string RemoveDefaultNullProperties(this JToken token)
{
try
{
foreach (var property in jsonObject.Properties().ToList())
if (token is JObject jsonObject)
{
if (property.Value.Type == JTokenType.Object)
foreach (var property in jsonObject.Properties().ToList())
{
RemoveDefaultNullProperties((JObject)property.Value);
}
else if (property.Value.Type == JTokenType.Array)
{
foreach (var item in property.Value)
if (property.Value.Type == JTokenType.Object)
{
if (item.Type == JTokenType.Object)
{
RemoveDefaultNullProperties((JObject)item);
}
RemoveDefaultNullProperties(property.Value);
}
else if (property.Value.Type == JTokenType.Array)
{
RemoveDefaultNullProperties(property.Value);
}
else if (property.Value.Type == JTokenType.String && property.Value.ToString() == "defaultnull")
{
property.Remove();
}
else if (property.Value.Type == JTokenType.String && property.Value.ToString() == "null")
{
property.Value = JValue.CreateNull();
}
}
else if (property.Value.Type == JTokenType.String && property.Value.ToString() == "defaultnull")
{
property.Remove();
}
else if (property.Value.Type == JTokenType.String && (property.Value.ToString() == "null"))
}
else if (token is JArray jsonArray)
{
// Process each item in the JArray
for (int i = jsonArray.Count - 1; i >= 0; i--)
{
property.Value = JValue.CreateNull();
var item = jsonArray[i];

if (item.Type == JTokenType.Object)
{
RemoveDefaultNullProperties(item);
}
else if (item.Type == JTokenType.String && item.ToString() == "defaultnull")
{
jsonArray.RemoveAt(i); // Remove the "defaultnull" string from the array
}
else if (item.Type == JTokenType.String && item.ToString() == "null")
{
jsonArray[i] = JValue.CreateNull(); // Convert "null" string to actual null
}
}
}
}
catch (System.Exception)
catch (System.Exception ex)
{
return jsonObject.ToString(); // Return the original string if parsing fails
Console.WriteLine($"Error cleaning JSON: {ex.Message}");
return token.ToString(); // Return the original JSON if any error occurs
}
return jsonObject.ToString();

return token.ToString();
}

public static string ReplaceAndRemoveSlashes(this string body)
{
return body.Replace("/", "").Replace("\\", "").Replace("rn", "").Replace("\"{", "{").Replace("}\"", "}");
}
}
}
}
24 changes: 23 additions & 1 deletion tools/Tests/JsonUtilitiesTest/JsonExtensionsTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ public void RemoveDefaultNullProperties_ShouldConvertStringNullToJsonNull()

// Assert
Assert.Null(result["position"]?.Value<string>());
Assert.Equal("",result["team"]?.ToString());
Assert.Equal("", result["team"]?.ToString());
Assert.Equal("Tim", result["displayname"]?.ToString());
Assert.Equal(2000000, result["salary"]?.ToObject<int>());
}
Expand Down Expand Up @@ -124,5 +124,27 @@ public void RemoveDefaultNullProperties_ShouldNotAlterValidData()
Assert.Equal("[email protected]", result["email"]?.ToString());
Assert.Equal(2000000, result["salary"]?.ToObject<int>());
}

//Add tests for json arrays
[Fact]
public void RemoveDefaultNullProperties_ShouldRemoveDefaultNullValuesInJsonArray()
{
// Arrange
JArray json = JArray.Parse(@"[
{ ""displayname"": ""Tim"", ""email"": ""defaultnull"" }

]");

// Act
string cleanedJson = json.RemoveDefaultNullProperties();
JArray result = JArray.Parse(cleanedJson);

// Assert
Assert.Equal("Tim", result[0]?["displayname"]?.ToString());
Assert.False(result[0].ToObject<JObject>().ContainsKey("email"));

}


}

Loading