Skip to content

Enum Type Mapping with .NET 9 #3480

@alainkaiser

Description

@alainkaiser

Hi guys

I justed created a minimal .NET 9 WebAPI project and wanted to test out the new enum type mapping with .net 9 and npgsql as described here:
https://www.npgsql.org/efcore/mapping/enum.html?tabs=with-connection-string%2Cwith-datasource

To share a little bit more about my setup:

DbContext

public class ApplicationDbContext : DbContext
{
    public DbSet<Initiative> Initiatives => Set<Initiative>();

    protected override void OnModelCreating(ModelBuilder modelBuilder)
    {
        modelBuilder.ApplyConfigurationsFromAssembly(typeof(ApplicationDbContext).Assembly);
    }

    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        optionsBuilder.UseNpgsql(
            "User ID=admin;Password=admin;Server=localhost;Port=5435;Database=mydb;Include Error Detail=true;",
            o => o.MapEnum<InitiativeStatus>("initiative_status"));
    }
}

Model

public class Initiative
{
    public int Id { get; set; }

    public string Title { get; set; } = string.Empty;

    public string ShortDescription { get; set; } = string.Empty;

    public int Points { get; set; }

    public InitiativeStatus InitiativeStatus { get; set; } = InitiativeStatus.Draft;
}
public enum InitiativeStatus
{
    Draft = 10,
    DraftRejected = 11,
    Submitted = 12,
    Approved = 13,
    Published = 14,
    Archived = 15,
    Deleted = 16
}

Model Configuration with Data Seeding

public class InitiativeConfiguration : IEntityTypeConfiguration<Initiative>
{
    public void Configure(EntityTypeBuilder<Initiative> builder)
    {
        builder
            .ToTable("Initiative");

        builder
            .HasData([
                    new Initiative
                    {
                        Id = 1,
                        Title = "Initiative 1",
                        ShortDescription = "Short description 1",
                        Points = 10,
                        InitiativeStatus = InitiativeStatus.Draft
                    },
                    new Initiative
                    {
                        Id = 2,
                        Title = "Initiative 2",
                        ShortDescription = "Short description 2",
                        Points = 20,
                        InitiativeStatus = InitiativeStatus.DraftRejected
                    },
                    new Initiative
                    {
                        Id = 3,
                        Title = "Initiative 3",
                        ShortDescription = "Short description 3",
                        Points = 30,
                        InitiativeStatus = InitiativeStatus.Submitted
                    },
                    new Initiative
                    {
                        Id = 4,
                        Title = "Initiative 4",
                        ShortDescription = "Short description 4",
                        Points = 40,
                        InitiativeStatus = InitiativeStatus.Approved
                    },
                    new Initiative
                    {
                        Id = 5,
                        Title = "Initiative 5",
                        ShortDescription = "Short description 5",
                        Points = 50,
                        InitiativeStatus = InitiativeStatus.Published
                    },
                    new Initiative
                    {
                        Id = 6,
                        Title = "Initiative 6",
                        ShortDescription = "Short description 6",
                        Points = 60,
                        InitiativeStatus = InitiativeStatus.Archived
                    },
                    new Initiative
                    {
                        Id = 7,
                        Title = "Initiative 7",
                        ShortDescription = "Short description 7",
                        Points = 70,
                        InitiativeStatus = InitiativeStatus.Deleted
                    }
                ]
            );
    }
}

Test API Endpoint

[HttpGet("initiatives")]
    public async Task<IActionResult> GetInitiatives()
    {
        var initiativesPublishesOrGreater = await context.Initiatives
            .Where(i => i.InitiativeStatus >= InitiativeStatus.Published)
            .ToListAsync();
        
        return Ok(initiativesPublishesOrGreater);
    }

The goal of this Endpoint is to return all Initiatives which have at least the Status "Published". So far so good.
When I inspect the database, I see that a custom enum type is generated for the InitiativeStatus enum and that the values are stored as strings (see screenshot).

Image

But the endpoint does not what it should do. When I request data from the endpoint, the data which comes back looks like this:

[
  {
    "id": 3,
    "title": "Initiative 3",
    "shortDescription": "Short description 3",
    "points": 30,
    "initiativeStatus": 12
  },
  {
    "id": 5,
    "title": "Initiative 5",
    "shortDescription": "Short description 5",
    "points": 50,
    "initiativeStatus": 14
  }
]

So as you can see, I get back Initiatives with the Status "Submitted" and "Published". I expected to get all Initiatives on which the Status is at least "Published" (Published, Archived, Deleted).

What is missing in my code to make this work? It is obvious that the comparison is made on the string values of the enum. For this reason, the initiatives are also returned with the status Submitted.

Thanks in advance for your feedback.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions