# Serializing to and from JSON

In this tutorial, we'll see how to serialize and deserialize value objects.

Vogen can automatically generate the code required for this.
It supports System.Text.Json (STJ), Newtonsoft.Json (NSJ), and ServiceStack.Text

First, let's see what we get with no conversion generated. 
In a C# project that references Vogen, create the following type:

```c#
[ValueObject<float>(conversions: Conversions.None)]
public readonly partial struct Celsius { }
```

Now, serialize an instance of `Celsius` to a JSON string using Newtonsoft.Json:

```C#
public record Weather(
    string Summary, 
    Celcius TemperatureTodayInCelsius);

var weather = new()
{
    Summary = "Sunny and hot",
    TemperatureTodayInCelsius = Celsius.From(30)
};

Console.WriteLine(JsonSerializer.Serialize(weather));
```

You'll see:

```Bash
{"Summary":"Sunny and hot","TemperatureTodayInCelsius":{"Value":30}}
```

Note that the serializer has written the temperature as a composite object (`Value:30`).

This isn't ideal as you probably want the primitive value written;
also, Vogen won't be able to deserialize that composite value back into a value object.

To get just the primitive value written, change `Celcius` to this and rerun.

```c#
[ValueObject<float>(Conversions.SystemTextJson)]
public readonly partial struct Celsius { }
```

This outputs:

```Bash
{ Summary = Sunny and hot, TemperatureTodayInCelsius = 30 }
```

As well as treating the value object as a primitive, it also allows it to be deserialized back into a value object.
Not that the default configuration says to generate `System.Text.Json` converters, so you could remove the `Conversions` parameter altogether.

## Serializing with source generation
`System.Text.Json` also has source generators that build up the required mappers during build time.
Vogen is compatible with this. Let's change the example above to use STJ source generation.

Add the following type:

```c#
[JsonSourceGenerationOptions(WriteIndented = true)]
[JsonSerializable(typeof(Weather))]
internal partial class JsonSourceGenerationContext :
    JsonSerializerContext
{
}
```

Now, when serializing, you have to tell STJ to use the converter factory that is generated by Vogen:

```C#
var options = new JsonSerializerOptions
{
    WriteIndented = true,
    Converters =
    {
        new VogenTypesFactory()
    }
};

var ctx = new JsonSourceGenerationContext(options);

var json = JsonSerializer.Serialize(weather, ctx.Weather);
Weather w2 = JsonSerializer.Deserialize(json, ctx.Weather)!;
```

<note>
The namespace used to generate the factory is based on the project name. If the project name contains illegal characters, such as commas, hyphens, or dots, they are replaced with underscores. 
</note>

The STJ converter factory is generated automatically if referencing the new STJ types in the `System.Text.Json.Serialization` namespace.

You can turn this off via the `SystemTextJsonConverterFactoryGeneration` flag in config (either globally or per value object)

## Summary

In this tutorial, we've seen how JSON is serialized if no conversions are specified, and then we've seen the difference
that specifying the conversion makes.

