Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Fluent NHibernate - Flatten multiple rows into a single entity

I have a database table that I cannot change which contains data like:

FooTable
Id     | EntityAUniqueId | EntityBUniqueId | EntityCUniqueId
============================================================
1      | A1              | B1              | C1
2      | A1              | B1              | C2
3      | A1              | B2              | C3
4      | A1              | B2              | C4
5      | A2              | B3              | C5
6      | A2              | B3              | C6
7      | A2              | B4              | C7
8      | A2              | B4              | C8

I want to map this to the following structure:

interface IEntityA
{
    string UniqueId { get; }
    IEnumerable<IEntityB> { get; }
}

interface IEntityB
{
    string UniqueId { get; }
    IEnumerable<IEntityC> { get; }
}

interface IEntityC
{
    string UniqueId { get; }
}

class EntityA : IEntityA { ... }
class EntityB : IEntityB { ... }
class EntityC : IEntityC { ... }

The data above would result in the following entities being pulled:

EnityA(A1)
  |-EnityB(B1)
  |   |-EntityC(C1)
  |   |-EntityC(C2)
  |-EnityB(B2)
      |-EntityC(C3)
      |-EntityC(C4)
EnityA(A2)
  |-EnityB(B3)
  |   |-EntityC(C5)
  |   |-EntityC(C6)
  |-EnityB(B4)
      |-EntityC(C7)
      |-EntityC(C8)

At present I only need to write to the table not read.

I am using FluentNHibernate with AutoMapping and conventions.

I started going down the road of Components but realised that this was not what they were intended for. One possible solution would be to use three views on the table but this adds additional issues and I would like to avoid it if possible and I cant help feeling that there must be something already in the framework to deal with this.

If the interfaces confuse the answer please feel free to omit them from the solution.

like image 810
Bronumski Avatar asked Nov 14 '22 00:11

Bronumski


1 Answers

So you have denormalized data in your table. I don't know how to handle it with the kind of mapping you're requesting. I can think of 2 workaround solutions.

1) Create views in the database to normalize your data, and create mappings against those views. Views like

ViewEntityA
-----------
IdColumn: EntityAUniqueId
AnyDataColumns

ViewEntityB
-----------
IdColumn: EntityBUniqueId
FkColumn: EntityAUniqueId
AnyDataColumns

ViewEntityC
-----------
IdColumn: EntityCUniqueId
FkColumn: EntityBUniqueId
AnyDataColumns

You can then write view insert/update/delete trigger logic (Reference1, Reference 2) to handle NHibernate updates.

2) Map the table as is. Manually map into the .net object hierarchy in C#. Update all database tables without utilizing NHibernate's entity relationships.

like image 132
Alex Avatar answered Dec 31 '22 15:12

Alex