Need help with your JSON?
Try our JSON Formatter tool to automatically identify and fix syntax errors in your JSON. JSON Formatter tool
C# and .NET JSON Formatter Implementation
JSON (JavaScript Object Notation) has become the de facto standard for data interchange in modern applications. Whether you're building web APIs, configuration systems, or data storage solutions, you'll inevitably work with JSON. While parsing and serializing JSON are common tasks, JSON formattingis equally important for both human readability and machine efficiency.
Formatting JSON typically involves controlling whitespace and indentation. The two primary styles are:
- Pretty-Printing: Adding indentation and line breaks to make the JSON structure clear and easy for humans to read. Useful for debugging, configuration files, and documentation.
- Compacting: Removing all unnecessary whitespace (spaces, tabs, newlines) to minimize the size of the JSON string. Useful for reducing bandwidth in network communication or saving storage space.
In this guide, we'll explore how to implement these formatting techniques in C# using the most common .NET libraries: the built-in `System.Text.Json` and the popular third-party `Newtonsoft.Json`.
Understanding .NET's JSON Libraries
Before diving into formatting, it's crucial to understand the two major players in the .NET JSON ecosystem:
System.Text.Json
(STJ): Introduced in .NET Core 3.0 and the default in .NET 5+. It's designed for high performance, low memory allocation, and security. It's the recommended choice for new .NET applications.Newtonsoft.Json
(Json.NET): A long-standing and very popular third-party library. It's feature-rich, flexible, and has a wide range of configuration options and support for complex scenarios (like handling circular references, custom conversions, etc.). Many existing .NET projects use it.
Both libraries provide ways to serialize and deserialize JSON, and crucially, control its formatting.
Implementing Formatting with System.Text.Json (STJ)
System.Text.Json
provides formatting options primarily through the JsonSerializerOptions
class when serializing objects or Utf8JsonWriter
when writing JSON manually. For formatting an existing JSON string, you'll typically parse it into a Document Object Model (DOM) representation using JsonDocument
and then write it out with formatting.
Pretty-Printing JSON with STJ
To pretty-print an object or a JsonDocument
, you use JsonSerializerOptions
with the WriteIndented
property set to true
.
Example: Pretty-Printing using System.Text.Json
using System.Text.Json;
public static class StjJsonFormatter
{
public static string PrettyPrint(string jsonString)
{
try
{
// Option 1: Parse then write (best for already existing JSON strings)
using (JsonDocument doc = JsonDocument.Parse(jsonString))
{
var options = new JsonSerializerOptions
{
WriteIndented = true // This is the key for pretty-printing
};
return JsonSerializer.Serialize(doc.RootElement, options);
}
/*
// Option 2: Directly serialize an object with options
// (If you have the object, not the string)
// var myObject = new { Name = "Alice", Age = 30 };
// var options = new JsonSerializerOptions { WriteIndented = true };
// return JsonSerializer.Serialize(myObject, options);
*/
}
catch (JsonException ex)
{
// Handle invalid JSON input
Console.WriteLine($"Error parsing JSON: {ex.Message}");
return "Invalid JSON Input";
}
}
}
// Example Usage:
// string compactJson = "{\"name\":\"Bob\",\"isStudent\":true,\"courses\":[\"Physics\",\"Chemistry\"]}";
// string prettyJson = StjJsonFormatter.PrettyPrint(compactJson);
// Console.WriteLine(prettyJson);
/* Expected Output:
{
"name": "Bob",
"isStudent": true,
"courses": [
"Physics",
"Chemistry"
]
}
*/
Compacting JSON with STJ
Compacting JSON with STJ is often simpler, as the default serialization behavior is to minimize whitespace.
Example: Compacting using System.Text.Json
using System.Text.Json;
public static class StjJsonFormatter
{
public static string Compact(string jsonString)
{
try
{
// Option 1: Parse then write (best for already existing JSON strings)
using (JsonDocument doc = JsonDocument.Parse(jsonString))
{
// Default options do not include indentation, resulting in compact output
var options = new JsonSerializerOptions
{
// WriteIndented = false is the default, no need to set explicitly
};
return JsonSerializer.Serialize(doc.RootElement, options);
}
/*
// Option 2: Directly serialize an object with default options
// var myObject = new { Name = "Alice", Age = 30 };
// return JsonSerializer.Serialize(myObject); // Default is compact
*/
}
catch (JsonException ex)
{
// Handle invalid JSON input
Console.WriteLine($"Error parsing JSON: {ex.Message}");
return "Invalid JSON Input";
}
}
}
// Example Usage:
// string prettyJson = @"
// {
// ""name"": ""Charlie"",
// ""city"": ""London""
// }";
// string compactJson = StjJsonFormatter.Compact(prettyJson);
// Console.WriteLine(compactJson);
/* Expected Output:
{"name":"Charlie","city":"London"}
*/
Notice that for compacting, you often don't need special options; the default serialization behavior handles it.
Using JsonDocument
for Flexibility
When formatting an arbitrary JSON string (not an object you've just created), parsing it into a JsonDocument
first, as shown in the examples, is the standard approach.JsonDocument
provides a read-only DOM that represents the JSON structure. You can then write this structure back out with different formatting options. This is efficient because it avoids full deserialization into C# objects if you only need to reformat.
Implementing Formatting with Newtonsoft.Json
Newtonsoft.Json
uses JsonConvert.SerializeObject
with the Formatting
enumeration to control indentation. It also provides a powerful JObject/JArray (LINQ to JSON) API for working with JSON as a dynamic object model.
Pretty-Printing JSON with Newtonsoft.Json
Pretty-printing with Newtonsoft is done by setting the Formatting
parameter of JsonConvert.SerializeObject
to Formatting.Indented
.
Example: Pretty-Printing using Newtonsoft.Json
using Newtonsoft.Json;
using Newtonsoft.Json.Linq; // Required for JObject/JArray parsing
public static class NewtonsoftJsonFormatter
{
public static string PrettyPrint(string jsonString)
{
try
{
// Option 1: Parse then write (best for already existing JSON strings)
// JToken is the base class for JObject, JArray, JValue etc.
JToken parsedJson = JToken.Parse(jsonString);
// Formatting.Indented applies indentation
return parsedJson.ToString(Formatting.Indented);
/*
// Option 2: Directly serialize an object with formatting
// (If you have the object, not the string)
// var myObject = new { Product = "Book", Price = 19.95 };
// return JsonConvert.SerializeObject(myObject, Formatting.Indented);
*/
}
catch (JsonReaderException ex)
{
// Handle invalid JSON input
Console.WriteLine($"Error parsing JSON: {ex.Message}");
return "Invalid JSON Input";
}
}
}
// Example Usage:
// string compactJson = "{\"id\":101,\"active\":false}";
// string prettyJson = NewtonsoftJsonFormatter.PrettyPrint(compactJson);
// Console.WriteLine(prettyJson);
/* Expected Output:
{
"id": 101,
"active": false
}
*/
Compacting JSON with Newtonsoft.Json
To compact JSON using Newtonsoft.Json, you can either omit the Formatting
parameter or explicitly set it to Formatting.None
.
Example: Compacting using Newtonsoft.Json
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
public static class NewtonsoftJsonFormatter
{
public static string Compact(string jsonString)
{
try
{
// Option 1: Parse then write (best for already existing JSON strings)
JToken parsedJson = JToken.Parse(jsonString);
// Formatting.None removes indentation (this is often the default)
return parsedJson.ToString(Formatting.None);
/*
// Option 2: Directly serialize an object without formatting parameter
// var myObject = new { Item = "Laptop", Qty = 1 };
// return JsonConvert.SerializeObject(myObject); // Default is compact
*/
}
catch (JsonReaderException ex)
{
// Handle invalid JSON input
Console.WriteLine($"Error parsing JSON: {ex.Message}");
return "Invalid JSON Input";
}
}
}
// Example Usage:
// string prettyJson = @"
// {
// ""status"": ""Ok"",
// ""code"": 200
// }";
// string compactJson = NewtonsoftJsonFormatter.Compact(prettyJson);
// Console.WriteLine(compactJson);
/* Expected Output:
{"status":"Ok","code":200}
*/
Similar to STJ, the default behavior for JsonConvert.SerializeObject
when no Formatting
option is specified is typically to produce compact JSON.
Using JObject/JArray for Manipulation
Newtonsoft's LINQ to JSON API (JObject
, JArray
, JValue
, etc.) is very powerful for reading, modifying, and writing JSON structures dynamically without mapping to C# classes. When you use JToken.Parse
or JObject.Parse
/JArray.Parse
, you get a mutable DOM that you can manipulate before writing it back out using ToString()
with the desired Formatting
. This is useful for more complex formatting tasks, like sorting object keys.
Performance Considerations
For typical use cases, both STJ and Newtonsoft are fast enough for formatting. However, when dealing with very large JSON strings or processing JSON in performance-critical loops, consider the following:
- Parsing Cost: Converting a JSON string into a DOM (
JsonDocument
orJToken
) requires reading and understanding the entire string. This parsing step is often the most expensive part. - STJ vs. Newtonsoft: Generally,
System.Text.Json
is designed to be faster and allocate less memory thanNewtonsoft.Json
for common scenarios, especially parsing and serialization. If performance is paramount and STJ meets your feature needs, it's the preferred choice. - Streaming: For extremely large JSON files that don't fit comfortably in memory, consider using streaming APIs (like
Utf8JsonReader
andUtf8JsonWriter
in STJ, orJsonReader
andJsonWriter
in Newtonsoft). These allow you to process the JSON token by token without building a full in-memory DOM. Formatting directly via streaming writers gives you fine-grained control but is more complex than using the DOM approach.
For simple pretty-printing or compacting of strings that fit in memory, the parse-then-write approach with JsonDocument
(STJ) or JToken
(Newtonsoft) is idiomatic and readable.
Choosing the Right Tool
The choice between System.Text.Json
and Newtonsoft.Json
for JSON formatting depends on your project's context:
- New Projects (.NET Core 3.0+ / .NET 5+): Start with
System.Text.Json
. It's built-in, high-performance, and sufficient for most formatting tasks (pretty/compact). - Existing Projects using Newtonsoft: Continue using
Newtonsoft.Json
for consistency. It's well-maintained and provides powerful formatting options including its flexible LINQ to JSON API for more complex manipulations.
Conclusion
Implementing JSON formatting in C# is a straightforward task thanks to the capabilities of both System.Text.Json
and Newtonsoft.Json
. Whether you need to enhance readability through pretty-printing or optimize size by compacting, the core methods involve utilizing serialization options or writing from a parsed JSON structure with specific formatting flags. Understanding the strengths of each library allows you to pick the best approach for your specific formatting needs within the .NET ecosystem.
Need help with your JSON?
Try our JSON Formatter tool to automatically identify and fix syntax errors in your JSON. JSON Formatter tool