VogenEfCoreConverters is not adding EfCoreConverter to entities
Describe the bug
I'm currently working using an onion architecture and entity framework on .net 9.
I have declared my aggregate entity and value objects (vogen) on the domain layer, and the VogenEfCoreConverters on the infrastructure layer and referenced the value objects, but When I go to the entity configuration, I cant use the .HasConversion(new UserDisplayName.EfCoreValueConverter()) because the method doesnt exists.
I also tried to use the hasVogenConversion() which is generated but produces this error when creating/getting an entity:
System.InvalidCastException: Invalid cast from 'System.String' to 'Core.UserAggregate.Structures.UserEmail'.
Steps to reproduce
- Create VO on the domain layer:
[ValueObject<string>]
[Instance("Unspecified", "")]
public partial class UserDisplayName
{
private static Validation Validate(string input)
{
if (string.IsNullOrWhiteSpace(input))
return Validation.Invalid("Display name cannot be empty.");
if (input.Length > 64)
return Validation.Invalid("Display name cannot be longer than 64 characters.");
if (!Regex.IsMatch(input, @"^\p{L}+$"))
return Validation.Invalid("Display name contains invalid characters.");
return Validation.Ok;
}
private static string NormalizeInput(string input) =>
CultureInfo.CurrentCulture.TextInfo.ToTitleCase(Regex.Replace(input.Trim(), @"\s+", " "));
}
- Added to the Aggregate Entity
public class User : EntityBase<Guid>, IAggregateRoot
{
public UserEmail Email { get; private set; }
public string Password { get; private set; }
public UserDisplayName DisplayName { get; private set; }
public DateTime CreatedAt { get; private set; }
public User(UserEmail email, string password, UserDisplayName displayName)
{
Id = Guid.NewGuid();
Email = email;
Password = password;
DisplayName = displayName;
CreatedAt = DateTime.Now;
}
protected User()
{
Id = Guid.NewGuid();
Email = UserEmail.Unspecified;
Password = string.Empty;
DisplayName = UserDisplayName.Unspecified;
} // For EF Core
}
- Add the partial Converter on infra layer:
[EfCoreConverter<UserEmail>]
[EfCoreConverter<UserDisplayName>]
public partial class VogenEfCoreConverters;
- Add the EF configuration
public class UserConfiguration : IEntityTypeConfiguration<User>
{
public void Configure(EntityTypeBuilder<User> builder)
{
builder.Property(u => u.Email).HasVogenConversion().IsRequired();
builder.Property(u => u.Password).IsRequired();
builder
.Property(u => u.DisplayName)
.HasVogenConversion()
.IsRequired()
.HasMaxLength(DataSchemaConstants.DEFAULT_NAME_LENGTH);
builder.Property(u => u.CreatedAt).IsRequired();
}
}
Expected behaviour
The VO should own its EF converter when using the VogenEfCoreConverters with decorators
Thanks for the bug report @Cordelia242 - I'll hopefully get around to this soon!