Skip to content

Commit

Permalink
Added documentation
Browse files Browse the repository at this point in the history
  • Loading branch information
SteveDunn committed Sep 9, 2024
1 parent 280d936 commit 3fa6a2a
Show file tree
Hide file tree
Showing 7 changed files with 65 additions and 2 deletions.
7 changes: 7 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,13 @@
[![Sparkline](https://stars.medv.io/stevedunn/vogen.svg)](https://stars.medv.io/stevedunn/vogen)
## Give a Star! :star:
If you like or are using this project please give it a star. Thanks!

Pronounced "Voh Jen"

<audio controls>
<source src="assets/voh-jen.wav" type="audio/wav">
Your browser does not support the audio element.
</audio>

# Vogen: cure your Primitive Obsession

Expand Down
Binary file added assets/voh-jen.wav
Binary file not shown.
2 changes: 2 additions & 0 deletions docs/site/Writerside/topics/reference/Configuration.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ Most values are present in both `ValueObject` and `VogenDefaults`. The parameter
* `parsableForPrimitives` - specifies what is generated for `Parse` and `TryParse` methods - defaults to `ParsableForPrimitives.HoistMethodsAndInterfaces`
* `tryFromGeneration` - specifies what to write for `TryFrom` methods—defaults to `TryFromGeneration.GenerateBoolAndErrorOrMethods`
* `isInitializedMethodGeneration` - specifies whether to generate an `IsInitialized()` method - defaults to `IsInitializedMethodGeneration.Generate`
* `primitiveEqualityGeneration` - specified whether to generate primitive comparison operators.

The values that are specified only to global configuration are:

Expand All @@ -39,6 +40,7 @@ The values that are specified only to global configuration are:
* `openApiSchemaCustomizations` - determines what is generated to assist in OpenAPI scenarios, for instance, generate a schema filter for Swashbuckle, or generate an extension method with `MapType` calls - defaults to `OpenApiSchemaCustomizations.Omit`
* `explicitlySpecifyTypeInValueObject` - specifies whether individual value objects should explicitly define the primitive type that they wrap -
defaults to `false`
* `disableStackTraceRecordingInDebug` - disables stack trace recording; in Debug buids, a stack trace is recorded and is thrown in the exception when something is created in an uninitialized state, e.g. after deserialization

Several code analysis warnings exist for invalid configuration, including:

Expand Down
34 changes: 34 additions & 0 deletions docs/site/Writerside/topics/reference/FAQ.md
Original file line number Diff line number Diff line change
Expand Up @@ -526,4 +526,38 @@ There are two solutions:
}

...
```

### Are value objects any bigger than the primitives that they wrap?
They are by default, but they can be configured so that they're not.

They're bigger because Vogen generates code that stores a field named `_isInitialized`. This
is used to check that the instance is initialized, e.g. after deserializing.
If you don't want that, then you can specify in your project that you don't want validation, e.g.

```xml
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net8.0</TargetFramework>
<DefineConstants>VOGEN_NO_VALIDATION</DefineConstants>
</PropertyGroup>
```

With this set, when we run in debug mode, we can see that there's no size difference:

```c#
[ValueObject]
public readonly partial struct Age;

Console.WriteLine(Marshal.SizeOf<Age>());
Console.WriteLine(Marshal.SizeOf<int>());

// outputs 4, 4
```

In debug builds, Vogen, by default, includes a stack trace field. This is used in the exception when an uninitialized value object is accessed.
If it is important that your debug builds have the same size value objects as your release builds, then add the following in your global config:

```c#
[assembly: VogenDefaults(disableStackTraceRecordingInDebug: true)]
```
4 changes: 2 additions & 2 deletions src/Vogen.SharedTypes/VogenDefaultsAttribute.cs
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,8 @@ public class VogenDefaultsAttribute : Attribute
/// <param name="fromPrimitiveCasting">Controls how cast operators are generated for casting from the primitive to the Value Object.
/// Options are implicit or explicit or none. Explicit is preferred over implicit if you really need them, but isn't recommended.
/// See &lt;see href="https://github.com/SteveDunn/Vogen/wiki/Casting"/&gt; for more information.</param>
/// <param name="disableStackTraceRecordingInDebug">If Debug, a stack trace is recorded if something is created in an uninitialized state.
/// This stack trace is heap based which might be unwanted if your Value Object is stack based.</param>
/// <param name="disableStackTraceRecordingInDebug">disables stack trace recording; in Debug builds, a stack trace is recorded and is
/// thrown in the exception when something is created in an uninitialized state, e.g. after deserialization</param>
/// <param name="parsableForStrings">Specifies the functionality around parsing (IParsable etc.)</param>
/// <param name="parsableForPrimitives">Specifies the functionality around parsing (IParsable etc.)</param>
/// <param name="tryFromGeneration">Controls what is generated for the TryFrom methods.</param>
Expand Down
19 changes: 19 additions & 0 deletions tests/SnapshotTests/GeneralStuff/GeneralTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,25 @@ public partial class MyVo;
.RunOn(TargetFramework.Net8_0);
}

[Fact]
public async Task Disable_stack_trace_in_debug()
{
var source =
"""
using System;
using Vogen;
[assembly: VogenDefaults(disableStackTraceRecordingInDebug: true)]
[ValueObject]
public partial class MyVo;
""";

await new SnapshotRunner<ValueObjectGenerator>()
.WithSource(source)
.RunOn(TargetFramework.Net8_0);
}

[Theory]
[InlineData("struct")]
[InlineData("class")]
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@


0 comments on commit 3fa6a2a

Please sign in to comment.