EF6 Конфигурирование обязательных отношений (один-к-нулю или один) - PullRequest
3 голосов
/ 20 мая 2019

У меня есть две таблицы базы данных с именем

SegmentSet SegmentSetGeometry

Они имеют первичный ключ с именем SegmentSetId.(SegmentSetGeometry (зависимый) сегментSetId является внешним ключом для SegmentSet (первичный)).

SegmentSets может иметь 0 или 1 SegmentSetGeometries

У меня есть два класса, представляющих эти таблицы, которые называются SegmentSet и SegmentSetGeometry:

public class SegmentSet
{
    public long SegmentSetId { get; set; }
    // ...
    public virtual SegmentSetGeometry SegmentSetGeometry { get; set; }
}

public class SegmentSetGeometry
{
    public long SegmentSetId { get; set; }
    public DbGeometry Geometry { get; set; }

    public virtual SegmentSet SegmentSet { get; set; }
}

Вот их конфигурации:

public class SegmentSetConfiguration: EntityTypeConfiguration<SegmentSet>
{
    public SegmentSetConfiguration()
    {
        ToTable("SegmentSet");
        HasKey(x => x.SegmentSetId);

        // ...

        HasOptional(x => x.SegmentSetGeometry)
            .WithRequired(x => x.SegmentSet);
    }
}

public class SegmentSetGeometryConfiguration : EntityTypeConfiguration<SegmentSetGeometry>
{
    public SegmentSetGeometryConfiguration()
    {
        ToTable("SegmentSetGeometry");
        HasKey(x => x.SegmentSetId);
    }
}

При попытке получить SegmentSet из базы данных появляется следующая ошибка:

Invalid column name 'SegmentSet_SegmentSetId'.

Я нашел эту ссылку https://docs.microsoft.com/en-us/ef/ef6/modeling/code-first/fluent/relationships и решил поменять отношения и попытался:

public class SegmentSetConfiguration: EntityTypeConfiguration<SegmentSet>
{
    public SegmentSetConfiguration()
    {
        ToTable("SegmentSet");
        HasKey(x => x.SegmentSetId);

        // ...
    }
}

public class SegmentSetGeometryConfiguration : EntityTypeConfiguration<SegmentSetGeometry>
{
    public SegmentSetGeometryConfiguration()
    {
        ToTable("SegmentSetGeometry");
        HasKey(x => x.SegmentSetId);
        HasRequired(x => x.SegmentSet)
            .WithOptional(x=>x.SegmentSetGeometry);

    }
}

Но все равно не работает.Я использую пример, который они дают, и он не работает, и я посмотрел на все подобные переполнения стека и все еще не работает

1 Ответ

0 голосов
/ 21 мая 2019

Чтобы отобразить эти два вместе, вы должны отобразить с требуемой стороны отношений, и только с этой одной стороны. Отображение обеих сторон может привести к искажению EF, что может стать причиной вашей проблемы.

public class SegmentSet
{
    public long SegmentSetId { get; set; }
    // ...
    public virtual SegmentSetGeometry Geometry { get; set; }
}

public class SegmentSetGeometry
{
    public long SegmentSetId { get; set; }
    // ...
    public virtual SegmentSet SegmentSet { get; set; }
}

public class SegmentSetConfiguration: EntityTypeConfiguration<SegmentSet>
{
    public SegmentSetConfiguration()
    {
        ToTable("SegmentSets");
        HasKey(x => x.SegmentSetId);
        // Note: Do not map the HasOptional here... Only map the required on the other side.
    }
}

public class SegmentSetGeometryConfiguration : EntityTypeConfiguration<SegmentSetGeometry>
{
    public SegmentSetGeometryConfiguration()
    {
        ToTable("SegmentSetGeometries");
        HasKey(x => x.SegmentSetId);
        HasRequired(x => x.SegmentSet)
            .WithOptional(x=>x.Geometry);

    }
}

Это должно работать, как и ожидалось, с использованием PK на каждой таблице для отношения 1..0 / 1.

Редактировать: Стоит также проверить, загружаются ли конфигурации сущностей. Это может объяснить, почему EF возвращается к соглашению. В DbContext:

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    base.OnModelCreating(modelBuilder);
    modelBuilder.Configurations.AddFromAssembly(GetType().Assembly);
}

Вышеприведенное предполагает, что конфигурации типов сущностей находятся в той же сборке, что и определение DbContext. В противном случае: typeof(SegmentSetGeometryConfiguration).Assembly сработает.

...