-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #13 from altasoft/feature/EFValueConverter
Added support for EntityFrameworkCore ValueConverters
- Loading branch information
Showing
9 changed files
with
248 additions
and
5 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,126 @@ | ||
|
||
# Generating EntityFrameworkCore Value Converters | ||
|
||
1. In the `.csproj` file where **AltaSoft.DomainPrimitives.Generator** is located, add the following item: | ||
|
||
```xml | ||
<PropertyGroup> | ||
<DomainPrimitiveGenerator_GenerateEntityFrameworkCoreValueConverters>true</DomainPrimitiveGenerator_GenerateEntityFrameworkCoreValueConverters> | ||
</PropertyGroup> | ||
``` | ||
|
||
**Note:** Ensure EntityFrameworkCore is added in the references. | ||
|
||
After this, ValueConverters for each DomainPrimitive will be generated. | ||
|
||
## Example | ||
Given a domain primitive `AsciiString`: | ||
|
||
```csharp | ||
/// <summary> | ||
/// A domain primitive type representing an ASCII string. | ||
/// </summary> | ||
/// <remarks> | ||
/// The AsciiString ensures that its value contains only ASCII characters. | ||
/// </remarks> | ||
public partial class AsciiString : IDomainValue<string> | ||
{ | ||
/// <inheritdoc/> | ||
public static PrimitiveValidationResult Validate(string value) | ||
{ | ||
var input = value.AsSpan(); | ||
|
||
// ReSharper disable once ForCanBeConvertedToForeach | ||
for (var i = 0; i < input.Length; i++) | ||
{ | ||
if (!char.IsAscii(input[i])) | ||
return "value contains non-ascii characters"; | ||
} | ||
|
||
return PrimitiveValidationResult.Ok; | ||
} | ||
} | ||
``` | ||
|
||
The following converter will be generated: | ||
|
||
```csharp | ||
//------------------------------------------------------------------------------ | ||
// <auto-generated> | ||
// This code was generated by 'AltaSoft DomainPrimitives Generator'. | ||
// Changes to this file may cause incorrect behavior and will be lost if the code is regenerated. | ||
// </auto-generated> | ||
//------------------------------------------------------------------------------ | ||
#nullable enable | ||
|
||
using AltaSoft.DomainPrimitives.XmlDataTypes; | ||
using System; | ||
using Microsoft.EntityFrameworkCore; | ||
using Microsoft.EntityFrameworkCore.Storage.ValueConversion; | ||
using AltaSoft.DomainPrimitives; | ||
|
||
namespace AltaSoft.DomainPrimitives.XmlDataTypes.EntityFrameworkCore.Converters; | ||
|
||
/// <summary> | ||
/// ValueConverter for <see cref="AsciiString"/> | ||
/// </summary> | ||
public sealed class AsciiStringValueConverter : ValueConverter<AsciiString, string> | ||
{ | ||
/// <summary> | ||
/// Constructor to create AsciiStringValueConverter | ||
/// </summary> | ||
public AsciiStringValueConverter() : base(v => v, v => v) | ||
{ | ||
} | ||
} | ||
``` | ||
|
||
**Note:** All Domain Primitives have implicit conversion to/from their primitive type. Therefore, no explicit conversion is required. | ||
|
||
## Helper Extension Method | ||
|
||
A helper extension method is also generated to add domain primitive conversions globally to `ModelConfigurationBuilder`: | ||
|
||
```csharp | ||
//------------------------------------------------------------------------------ | ||
// <auto-generated> | ||
// This code was generated by 'AltaSoft DomainPrimitives Generator'. | ||
// Changes to this file may cause incorrect behavior and will be lost if the code is regenerated. | ||
// </auto-generated> | ||
//------------------------------------------------------------------------------ | ||
#nullable enable | ||
|
||
using AltaSoft.DomainPrimitives.XmlDataTypes; | ||
using Microsoft.EntityFrameworkCore; | ||
using AltaSoft.DomainPrimitives.XmlDataTypes.EntityFrameworkCore.Converters; | ||
|
||
namespace AltaSoft.DomainPrimitives.XmlDataTypes.Converters.Extensions; | ||
|
||
/// <summary> | ||
/// Helper class providing methods to configure EntityFrameworkCore ValueConverters for DomainPrimitive types of AltaSoft.DomainPrimitives.XmlDataTypes | ||
/// </summary> | ||
public static class ModelConfigurationBuilderExt | ||
{ | ||
/// <summary> | ||
/// Adds EntityFrameworkCore ValueConverters for specific custom types to ensure proper mapping to EFCore ORM. | ||
/// </summary> | ||
/// <param name="configurationBuilder">The ModelConfigurationBuilder instance to which converters are added.</param> | ||
public static ModelConfigurationBuilder AddDomainPrimitivePropertyConversions(this ModelConfigurationBuilder configurationBuilder) | ||
{ | ||
configurationBuilder.Properties<AsciiString>().HaveConversion<AsciiStringValueConverter>(); | ||
configurationBuilder.Properties<GDay>().HaveConversion<GDayValueConverter>(); | ||
configurationBuilder.Properties<GMonth>().HaveConversion<GMonthValueConverter>(); | ||
configurationBuilder.Properties<GMonthDay>().HaveConversion<GMonthDayValueConverter>(); | ||
configurationBuilder.Properties<GYear>().HaveConversion<GYearValueConverter>(); | ||
configurationBuilder.Properties<GYearMonth>().HaveConversion<GYearMonthValueConverter>(); | ||
configurationBuilder.Properties<NegativeInteger>().HaveConversion<NegativeIntegerValueConverter>(); | ||
configurationBuilder.Properties<NonEmptyString>().HaveConversion<NonEmptyStringValueConverter>(); | ||
configurationBuilder.Properties<NonNegativeInteger>().HaveConversion<NonNegativeIntegerValueConverter>(); | ||
configurationBuilder.Properties<NonPositiveInteger>().HaveConversion<NonPositiveIntegerValueConverter>(); | ||
configurationBuilder.Properties<PositiveInteger>().HaveConversion<PositiveIntegerValueConverter>(); | ||
return configurationBuilder; | ||
} | ||
} | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters