Code Only – Further Enhancements


We’ve come a long way since the last post on Code-Only. So it’s high time for another update.


We’ve been working really hard on Code-Only revving the design, and spotting missing capabilities and responding to feedback both internal and external etc. 


The current plan still holds.  Code-Only will not be in .Net 4.0 with the possible exception of the DDL features described in the last post.  For that portion, the implementation and requirements are more clear to us, and because making the DDL stuff work requires changes to things already in the .NET framework, and getting provider writers lined up, we are still working hard to get the DDL changes into .NET 4.0.  The rest of Code-Only will continue to evolve, and we will ship another preview or two, before getting it rolled into .NET as soon as we can after 4.0 ships.




API Refactoring


As hinted above, we’ve spent a lot of time validating code only against real world scenarios, and thinking about how the customer code hangs together etc. As a results we’ve done some API refactoring.


Mappings are now part of Configurations


In the last version Mappings were derived from Configurations, which had some strange side-effects on the API.


We’ve re-arranged things now so that Configurations hold mappings, which are terminated by assignment to a table.


builder.Entity<Customer>()
   .HasKey(c => c.ID)
   .MapSingleType(c => new {
         cid = c.ID,
         nme = c.Name
      }
   )
   .ToTable(“dbo.custs”);


This maps the Customer entity to the ‘dbo.Custs’ table, the ID property to the cid column, the Name property to the nme column, and registers the ID property as the EntityKey / Primary Key.


As you can see we’ve also added a helper method called Entity<TEntity>() so that you can fluently create configurations and mappings. You might also have noticed that we have removed RegisterKey and replaced it with HasKey which we feel is more inline with our goal of having an intentional API.


TPH mapping syntax no longer violates DRY


The previous syntax for specifying a TPH mapping forced you to repeat mappings for columns that could easily have been inherited.


This was unfortunate because we normally encourage TPH because generally it has the best performance characteristics.


This is where MapHierarchy() and Case() come in.


Imagine if we want to write these classes using TPH:


public class Person{
   public virtual int ID {get;set;}
   public virtual string Firstname {get;set;}
   public virtual string Surname {get;set;}
}
public class Employee: Person
{
   public virtual Employee Manager {get;set;}
   public virtual List<Employee> Reports {get;set;}
}


You would now do it like this:


builder
   .Entity<Person>()
   .HasKey(p => p.ID)
   .MapHierarchy()
   .Case<Person>(
      p => new {
         p.ID,
         p.Firstname, 
         p.Surname,
         thisIsADiscriminator = “P”
      }
   )
   .Case<Employee>(
       e => new {
         manager = e.Manager.Id
         thisIsADiscriminator = “E”
       }
   )
   .ToTable(“dbo.People”);


By using Case<> mappings are re-used for derived type, so there is no need to repeat column mappings for ID, Firstname and Surname.


Which means the Employee Case statement is only responsible for mapping properties and references declared by the Employee class, and for specifying a new discriminator value.


The discriminator column and values are there so the Entity Framework can distinguish between rows in the dbo.People table that represent Person objects and those that represent Employee objects.


MapSingleType and MapHierarchy


Because Mappings are now part of the configuration, there is no need to create them independently and assign them.


You now simply MapXXX() methods on the EntityConfiguration.


The available mapping methods are:



  • MapSingleType(λ)

  • MapHierarchy(λ)

  • MapHierarchy().Case<TEntity>(λ).Case<TDerived>(λ).

If you know the Entity Frameworks MSL files these correspond to:



  • Type

  • OfType

  • OfType with an addition requirement for a type discriminator

These mappings can be combined in many interesting ways, but in general this table shows the recommended way to do most common mappings:























Scenario Code
Notes
No Inheritance builder.Entity<A>()
   .MapSingleType(λ)
   .ToTable(“dbo.A”);
Columns not mapped are not part of the Entity.
TPH builder.Entity<A>()
   .MapHierarchy()
   .Case<A>(λ)
   .Case<B>(λ)
   .Case<C>(λ)
   .ToTable(“dbo.ABC”);
Generally each Case expression only maps properties declared by the current type and the discriminator for that type.

But it is possible to override the mapping for inherited properties if required.
TPT builder.Entity<A>()
   .MapHierarchy(λ)
   .ToTable(“dbo.A”);

builder.Entity<B>()
   .MapHierarchy(λ)
   .ToTable(“dbo.B”);

builder.Entity<C>()
   .MapHierarchy(λ)
   .ToTable(“dbo.C”);
Each MapHierarchy expression only maps properties declared by the current type, and properties that make up the entity key.
TPC builder.Entity<A>()
   .MapSingleType(λ)
   .ToTable(“dbo.A”);

builder.Entity<B>()
   .MapSingleType(λ)
   .ToTable(“dbo.B”);

builder.Entity<C>()
   .MapSingleType(λ)
   .ToTable(“dbo.C”);
Each MapSingleType expression maps all properties, both those declared by the current type and those inherited.

Foreign Keys


In Beta2 of .NET 4.0 we added FK Association Support, so Code-Only needs a way to link a FK property and an Navigation Property together.


Given this class:


public class Product{
   public virtual int ID {get;set;}
   public virtual string Name {get;set;}
   public virtual Category Category {get;set;}
   public virtual int CategoryID {get;set;}
}


You need to be able to tell code-only that Category.ID and CategoryID should have the same value.


You do it like this:


builder.Entity<Product>()
   .Relationship(p => p.Category)
   .HasConstraint((p,c) => p.CategoryID == c.ID);


This says that c.ID (i.e. p.Category.ID) must equal p.CategoryID, which tells code-only that p.CategoryID is an FK property and p.Category is a navigation property backed by this FK property.


HasConstraint(λ) can also be used in conjunction with Relationship(λ).FromProperty(λ) like this:


builder.Entity<Product>()
   .Relationship(p => p.Category)
   .FromProperty(c => c.Products)
   .HasConstraint((p,c) => p.CategoryID == c.ID);


Which tells code only that Product.Category and Category.Products are inverses and that Product.CategoryID and Product.Category.ID must be the same, which implies Product.CategoryID is an FK property.


Missing Navigation Properties


Sometimes you don’t have a navigation property or FK property in the Entity which would naturally hold the FK in the database. For example imagine this scenario:


public class Product{
   public virtual int ID {get;set;}
   public virtual string Name {get;set;}
}


public class Category{
   public virtual int ID {get;set;}
   public virtual string Name {get;set;}
   public virtual List<Product> Products {get;set;}
}


Here there is ‘probably’ a one to many relationship between Categories and Products, and that is probably best modeled using an FK in the products table.


If you start mapping the Product entity you need a way to map the FK column, but there is no reference (i.e. Product.Category) and no FK property (i.e. Product.CategoryID) to map.


So we added the ability to create a fake navigation property to help out:


builder.Entity<Product>().MapSingleType(
   p => new {
       pid = p.ID,
       nme = p.Name
       cid = EntityMap.Related<Category>(c => c.Products).ID
   }
).ToTable(“dbo.Products”);


Here the interesting part is EntityMap.Related, it creates a fake navigation property, just so you can use it in the mapping.


The method signature looks like this:


public static TEntity Related<TEntity>(
    Expression<Func<TEntity, object>
);


Notice that this function simply returns TEntity, so in the above mapping fragment, we are mapping the ID property of the Category class to the cid column, in the ‘dbo.Products’ table.


Complex Types


Code-Only’s default behavior is to ignore properties that are not recognized as either a primitive type or an EntityType. So to support Complex Types we need a mechanism to register one, like this:


var addressConf = builder.ComplexType<Address>();


This returns a ComplexTypeConfiguration through which you can configure the properties of the ComplexType in the same way you configure the properties of an Entity:


addressConf.Property(a => a.Street).HasMaxLength(100);
addressConf.Property(a => a.Zip).HasMaxLength(10);


Now if an entity is mapped by convention and it has a ComplexType property we will automatically introduce columns for each property of the ComplexType.


If you want to explicitly map the Entity mapping the ComplexType property is pretty simple too:


builder.Entity<Person>().MapSingleType(
   p => new {
      p.ID,
      fn = p.Firstname,
      sn = p.Surname,
      street = p.Address.Street,
      zip = p.Address.Zip
   }
);


Registering Entity Sets


Some of our early CodeOnly adopters wanted to use Code Only without having an specialized ObjectContext, and in theory with is possible:


builder = contextBuilder.Create<ObjectContext>();
builder.Entity<Person>().HasKey(p => p.ID);


But what we found is you have no control over the name of the set generated. In this case we will generate an EntitySet called PersonSet, but what if I the name should be People?


To address this issues we have added this method:


builder.RegisterSet<Person>(“People”);


Not only is this useful for specifying names,  it also allows you to intentional specify what EntitySets you need. The alternative would be to encode your intent into calls to Entity<TEntity> and Relationship<TRelated>(..).


Association Mapping


We also need to add support for mapping associations that are not co-located with the Entity. For example take the relationship between Jobs and Candidates. If a candidate can apply for multiple jobs this is a classic example of a many to many relationship.


If you want to take control of how this relationship is mapped you need a way to specify the mapping for the relationship, like this:


builder
  .Entity<Job>()
  .Relationship(job => job.Applicants)
  .FromProperty(candidate => candidate.Applications)
  .Map(“dbo.JobApplications”,
           (job,candidate) => new {
               applicantId = candidate.Id,
               jobId = job.Id
            }
       );


This does a number of things, first it indicates that Job.Candidates and Candidate.Applications are opposite ends of the same relationship.


Then the Map() call indicates that the relationship should be stored in the “dbo.JobApplications” join table, with a compound PK made up of the applicantId and jobId columns.


The applicantId holds the candidate.Id, and the jobId holds the job.Id, and in both cases Code Only will emit an FK constraint to ensure referential integrity. 


Interesting Column Names


The existing mapping syntax that uses anonymous types for the table and column definitions, limits you to column names that are valid CLR identifiers.


So for example if you need to map to a column with a space in the name you can’t.


To rectify this we added an alternate mapping syntax:


builder.Entity<Product>().MapSingleType(
   p => EntityMap.Row(
      EntityMap.Column(p.ID, “p i d”),
      EntityMap.Column(p.Name),
      EntityMap.Column(p.CategoryId, “c i d”)
   )
).ToTable(“dbo.Products”);


This snippet of code, maps the Product entity to the “dbo.Products” table and the ID property to a ‘p i d’ column, the Name property to a Name column and the CategoryId property to the ‘c i d’ column.


This alternate API has another advantage too: it makes it easier to create mapping expressions programmatically, primarily because you no longer need to create an anonymous type when building the expression. Which is really useful if you want to configure code-only at runtime.


Extracting the EDMX


We’ve also added the ability to get the EDMX that Code Only is producing internally, either via an XmlWriter or as an XDocument:


DbConnection connection = // some code to get a connection.
XDocument document = builder.GetEdmx(connection);


// or using XmlWriter
var swriter = new StringWriter();
var xwriter = new XmlTextWriter(swriter);
builder.WriteEdmx(connection, xwriter);

This is pretty handy if you want to use Code Only to build your model and mappings but then pull them out so you work with the XML and our designer tooling.


Setting the StoreType


When producing the Storage Model Code Only asks the current database provider to return an appropriate store type for the CLR type and facets specified.


But some CLR types and facet combinations can map to multiple possible database types. For example fixed length byte[] can map to both binary and timestamp. So in this situation SqlClient returns binary by default.


But you might need a timestamp:


builder
   .Entity<Order>()
   .Property(o => o.Version) 
   .HasStoreType(“timestamp”)
   .IsComputed();


This tells Code Only that the Version property of Order (which is a byte[]) is computed in the database, and is actually a ‘timestamp’ column, which is computed in the database after every insert / update.


DDL Provider Model


In our last post we covered our plans around the DDL provider model, so check that out.


Summary


As you can see Code Only is now looking much more complete.


But it isn’t completely finished yet, we are still working on the rough edges, so as always we are very interested to get your feedback.


In particular are there things you think we should add / rename / simplify?


Alex James
Program Manager, Entity Framework Team, Microsoft.

This post is part of the transparent design exercise in the Entity Framework Team. To understand how it works and how your feedback will be used please look at
this post.

Comments (43)

  1. RichB says:

    Very early days. Even the code here doesn’t comply with  basic c# naming conventions – ID is not an acronym. Source analysis will fail.

  2. Alex James says:

    @RichB,

    Clearly there are different schools of thought on ID verses Id.

    But putting that aside for a moment, because it isn’t actually part of code-only, what makes you say it is ‘Very early days’?

    Alex

  3. Alun Harford says:

    The only problem I have with this is the same problem I have with fluent NHibernate: It pushes people to create anaemic domain objects by forcing them to expose the database fields as properties.

    Then, because somebody has never seen a well-mapped domain, they say "Hey! I can code-gen this!" and you’re left with what are basically typed datasets.

  4. Paul Batum says:

    @Alun,

    I appreciate where you are coming from and want you to know that there are some tricks that allow you to use FNH to map private properties. See here for more info:

    http://wiki.fluentnhibernate.org/Fluent_mapping_private_properties

    I imagine that these tricks are also applicable to the EF code-only mappings, though that is just a guess.

  5. Alun Harford says:

    @Paul,

    While it can be done (although I’d not seen the ‘Nested expression exposition class’ technique – cool!) the problem I have is that I generally get brought in onto a project late in the day and if they’ve used FNH I know they won’t have used such tricks (they look like a code smell and they are – they’re just better than the alternative).

    FNH doesn’t help developers fall into the pit of success.

    While that keeps me in a job, it’s still not a good thing!

  6. Alun Harford says:

    @Paul,

    That last post reads more critical than it was when it was in my head – sorry!

    I realise that you don’t have much to work with – it’s more a problem of the language than the framework. Dynamic method invocation in C# 4 could improve matters a little, albeit at the cost of strong typing.

  7. Daniel says:

    Will there be a story around creating _conventions_ based on Code-Only?  For example, will I be able to set up a convention so that all classes in a given namespace get mapped 1:1 to a table of the same name, and use a property Id as a key, and have foreign keys mapped for child collections?  Given what you have shown, I could see this possibly working with a little bit of reflection, but I was wondering if this would be baked in somehow.

  8. Andy says:

    I have an address table that is used in several relationships to different entities, for example for a customer or a business.  The address table is modeled such that it holds the fk to the related entity along with text field that indicates which type of entity the fk goes to.  So an address that goes to customer with pk 3 would have the fk column with the value 3 and the "discriminator" column with a value of ‘cust’.  An address that goes to a business with pk of 3 would have an fk of 3 with discriminator of ‘bus’.

    Can EF code-only support this scenario?  

    -andy

  9. Darren Kopp says:

    Is there any advantage to mapping entities using the anonymous type versus EntityMap.Column? I would probably use the string based approach over the anonymous type method as it’s a bit closer to what other frameworks use.

    Also, why do you need to do EntityMap.Row(EntityMap.Column))? I’m assuming because you need to return an object is why the method call, but why not something like EntityMap.Row().Column("").Column(""), or even EntityMap.Column("").Column(""), etc. Nested parenthesis in an anonymous delegate are always meh to me. Not a huge fan of them.

  10. Damien Guard says:

    @Darren: You can’t chaning the Column calls as they need to expose something that lets you specify constraints, nullability etc. and while theoretically we could add a Column interface to that it would get very confusing very quickly once you have those sorts of calls nested.

    e.g. EntityMap.Column("Name").IsRequired().Column("Address").HasPrecision(5).Column("A")…

    [)amien

  11. Jeremy D. Miller says:

    @Damien,

    In regards to the issue with Column("  ").Column("  ").IsRequired() ……,

    Have you thought about moving to "Object Scoping" for each entity instead of relying on strictly method chaining?  That would probably make the mechanics of your FI simpler and easier to consume rather than having columns chained to other columns.

    I would try really hard to avoid the nested parantheses with the nested functions like this:

    builder.Entity<Product>().MapSingleType(

      p => EntityMap.Row(

         EntityMap.Column(p.ID, “p i d”),

         EntityMap.Column(p.Name),

         EntityMap.Column(p.CategoryId, “c i d”)

      )

    ).ToTable(“dbo.Products”);

    That’s a usability problem with a Fluent Interface.  Maybe go for a nested closure inside the call to MapSingleType<T>() instead.

    And lastly, because you know this question is coming, are you guys looking at Fluent NHibernate at all?  You’re basically building the same functionality and FNH has been through quite a few iterations in the language around usability.

    Jeremy

  12. Darren Kopp says:

    @Damien good point. I would tend to agree with what Jeremy has proposed to avoid the nested parentheses problem. That’s the only major beef i have with the current proposal.

  13. efdesign says:

    @Darren & Jeremy

    There is another subtle benefit of using the lambda syntax we are using.

    Namely that it is possible to create classes that represent the table and map directly to an instance of it:

    MapSingleType(p => new PersonStructure {Id = p.Id, FN = p.Firstname, SN = p.Surname})

    .ToTable(…)

    Now I’m not sure if this is that useful, but you never know.

    Alex

  14. efdesign says:

    @Andy,

    The EF doesn’t support that scenario directly but you could do something like this using views in the SSDL etc.

    But that falls outside the scope of things you can do with Code-Only directly

    Alex

  15. efdesign says:

    @Daniel,

    The conventions used by Code-Only are hardcoded at the moment, but we are investigating what it would take to add some sort of pluggable conventions model.

    What sort of model do you think makes sense?

    Alex

  16. efdesign says:

    Jeremy,

    Not 100% sure what you are driving at with your suggestions. What would object scoping look like? and what sort of nested closure construct are you thinking?

    Alex

  17. Anton says:

    Where can i find the ContextBuilder class?  Is it not included in VS2010 Beta2?

  18. @Anton,

    ContextBuilder and the rest of code-only continues to be part of the feature CTP.  It is NOT part of the core product shipping in VS2010, so it’s not part of beta 2.  We are working on an update to the feature CTP which will work on part of beta 2, and it should be available very soon.

    – Danny

  19. Tolo Oliver says:

    Are the Data Services supported when Code Only is used? I tried to create a small example but I’m getting ‘The ‘metadata id’ keyword is not supported.

  20. Alex D James says:

    @Tolo,

    The metadata id problem is a bug in Entity Framework (not code-only) that we fixed post Beta2.

    The only work-around at the moment is use GetEdmx() to extract the EDMX and split it onto disk and construct the ObjectContext using the more familar metadata=file://C:model.csdl;… syntax instead.

    The problem is that Astoria caches it’s version of the metadata keyed on the metadata portion of the connection string, and then tries to parse that again using EntityConnectionStringBuilder, which fail if there is a metadata id, so if you load the metadata from disk, the problem goes away.

    I’ll probably put something on my blog on this soon.

    Alex

  21. Tolo Oliver says:

    I tried to do something similar but I’m absolutely new to Entity Framework and I had some problems about how to use the edmx. I will try again using your hints.

    Thanks for the help Alex.

  22. Yogesh Jagota says:

    I am making a new application and using C# 4.0 and EF4 CodeOnly for the same. I am loving CodeOnly functionality. One basic thing I cannot find is how can I exclude a public property to be mapped to the database. Is the only way to do this is to map all properties (except the one I don’t want to persist) in the context builder?

  23. Shawn says:

    How do I model a many to many relationship table using code only?

    eg. A table Student, Class, and StudentClass which has a foreign key to both. Classic many-to-many relationship model.

    In EDMX it would be something like:

             &lt;Key&gt;

               &lt;PropertyRef Name="StudentId" /&gt;

               &lt;PropertyRef Name="ClassId" /&gt;

             &lt;/Key&gt;

    Is there anything in EntityConfiguration?

    If not, what are your plans? I’d like to do something like

    Property(sc=>sc.StudentId).CompositeKey();

    Property(sc=>sc.ClassId).CompositeKey();

    Thanks!

    Shawn

  24. Shawn says:

    Should have been more specific on that post…

    Taking your JobApplications example, how can I get a POCO that represents the JobApplications relationship table?

    In a real world scenario it might have the two foreign keys as well as other data/columns (eg. ApplicationTime)

  25. @Shawn,

    Code-only doesn’t change the way EF works with many-many relationships.  In the EF, if you have a link/relationship table that has only foreign keys to the related entities, then the EF can create a many-many relationship and with code-only this can be done by convention or by taking more control over things as described above.

    If you have additional data columns other than the foreign keys in your link table, then the EF will require you to create an entity for that table which has two 1-to-many relationships rather than just having the "outside" entities with a many-to-many relationship.

    – Danny

  26. sipo says:

    MYSQL error The given provider is not supported. Only System.Data.SqlClient is currently supported.

  27. TonyB says:

    Is there a way to do Entity Splitting using code only using a foreign key?  I need my object populated from two tables, the first table has a column that is a foreign key that points to the second table.  You can do that using EDMX but I can’t figure out how to do it with code only.  

    I have a more specific example here:

    http://stackoverflow.com/questions/1955358/entity-splitting-with-code-only

  28. Michael Praschl says:

    Hello,

    I have a domain object that should get some of its properties mapped to an ordinary table, and another property to a column of a view. This view is not updateable because of the CTE it contains. The key used to join table and view is a Guid which is created by the client, not the sql server.

    This is my domain class:

    public class MyDomainClass

    {

    public MyDomainClass()

    {

    Id = Guid.NewGuid();

    }

       public Guid Id {get; set;}

       public string Name {get; set;}

       public string Result {get; set;} // in view

    }

    I am using the current code for the mapping:

    HasKey<Guid>(x => x.Id);

    Property(f => f.Result).IsComputed();

    MapSingleType(f => new

    {

    id = f.Id,

    Name = f.Name,

    }).ToTable("MyTable");

    MapSingleType(f => new

    {

    id = f.Id, // for the join

    result = f.Result, // the result of a recursive CTE (for blazing performance)

    }).ToTable("MyView");

    On Insert I am getting this exception:

    System.Data.UpdateException: An error occurred while updating the entries. See the inner exception for details. —> System.Data.SqlClient.SqlException: Update or insert of view or function ‘dbo.MyView’ failed because it contains a derived or constant field.

    First SaveChanges() does an insert on MyTable for Id and Name. But then it tries to insert the Id into the view, which makes sense since it doesn’t know its a view that already contains the Id. At least, it doesn’t try to insert the Result property, because it was flagged with IsComputed().

    I can’t figure out how I can specify that the Id should not be saved to the view while it _should_ still be saved to the table. I would like to suggest one of the following extensions:

    MapSingleType(…).ToView("MyView");

    MapSingleType(…).ToTable("MyView").AsReadOnly();

    MapSingleType(…).ToTable("MyView")

    .AsReadOnly(x => x.Id)

    .AsReadOnly(x => x.Result);  // Result already excluded by .IsComputed()

    These may also be applicable for the MapHierarchy() method.

    Specifying Stored Procedureds for CRUD could also solve the problem.

    Is there anything coming in the next preview release?

    Regards,

    Michael

  29. kirill says:

    Hello,

    Is it possible to map stored procedure in code only? Now i have only one way to use sp’s – importing functions in the EDMX.

  30. Damien Guard says:

    @kirill: This isn’t possible right now but we are going to consider it for a future update.

    Thanks for your feedback!

    [)amien

  31. Ahmed Fouad says:

    What about the problem mentioned by Alun Harford? IMHO: This is very important guys for designing better domain models (at least for modeling Core Domain) – a paradigm shift from Strongly Typed Data Classes to Behavior only Domain Models.

  32. Mikael Larsson says:

    I have a problem when using "Missing Navigation Properties" as described above in a RIA services project with the [Include] and [Association] attributes. The Include attribute requires the Association attribute, but an association cant be setup since the Missing Navigation Property is not present. Any ideas?

  33. simmdan says:

    @Mikael,

    There are a variety of cases where navigation properties end up being more than just a convenience.  In the case of RIA services, for instance, I’m pretty sure that the nav props are required at least in one of the two directions in order to make sure that the serialization knows how to hook together your related entities.  So I think you should consider building things to have the nav prop.

    – Danny

  34. Mikael Larsson says:

    Thanks Danny,

    Its not a problem this time to do as you suggest, other than i need to add additional properties to my objects which i think is acceptable. But might be other scenarios where its not an option. So i figured there might be something similar to "Missing Navigation Properties" in RIA Services, since i already told the framework how to navigate.

    Anyway love this code-only stuff, great work.

  35. Clint says:

    Hi Alex,

    Great great stuff!

    How would one specify a different store table name as can be done with ToTable("dbo.TableName") on any of the MapXXX extensions WITHOUT having to map the whole entity again (DRY).

    I can do it like this

    builder.Entity<Person>()

       .MapSingleType(

           p => new

               {

                  o.ID,

                  … // Repeat all properties

                })

           .ToTable("dbo.MyPerson");

    I would like to see

    builder.Entity<Person>()

       .ToTable(dbo.MyPerson");

    Have I missed something?

    Clint

  36. jan wensink says:

    this is heavy stuff but its a good practice for me thank you regards jan wensink.

  37. DOTNETFAN says:

    Will Entity Framework supports horizontal partitioning over distributed databases in future. will it compete Hibernate in features . I expect Microsoft entity framework to be more scalable than any other matured OR/M tool

  38. Antonio says:

    I need an entity with dynamic properties for user defined attributes. I use collection properties to resolve this.

    How do I map the data columns with a collection property to the entity?

    Something like this:

               MapHierarchy(

                  p => EntityMap.Row(

                      EntityMap.Column(p.ID, "id"),

                      EntityMap.Column(p.UDA_Columns["Test"], "Test")

                  )

               ).ToTable("Table");

    Regards,

    Antonio

  39. simmdan says:

    Unfortunately the EF doesn’t support this kind of mapping today (with codefirst or other ways of specifying the mapping).  It only supports mapping of properties to scalar types.  Adding support for collection properties of this kind is something we intend to do in a future release.

    – Danny

  40. zalbu says:

    Hello,

    I managed to get MEF parts composing EntityConfigurations into a ContextBuilder, so the data model is "composable". I am now trying to implement physical database naming conventions, in a generic manner. In the EntityConfiguration(of User) I implement something like

         Me.MapHierarchy(

           Function(o) _

             EntityMap.Row(

               EntityMap.Column(o.ID, "user_id"),

               EntityMap.Column(o.Name, "company_name")

             )

           ).ToTable("dbo.user")

    but it should be expressed in something like

         Me.MapHierarchy(

           Function(o) _

             EntityMap.Row(

               (From p In o.GetType.GetProperties()

               Select EntityMap.Column(p, "company_" & p.Name.ToLower)).ToArray

             )

           ).ToTable("dbo.user")

    it seems like the expression provided to MapHierarchy is transformed on CTP and that renders invalid any attempt to use a pattern other than the expected one.

    In the end I would have a EntityConfigurationBase that deals with this and all specific EntityConfigurations derived from it will therefore "automatically" have the desired mapping naming conventions.

    is such a scenario supported? How?

  41. zalbu says:

    Hello,

    I managed to get MEF parts composing EntityConfigurations into a ContextBuilder, so the data model is "composable". I am now trying to implement physical database naming conventions, in a generic manner. In the EntityConfiguration(of User) I implement something like

         Me.MapHierarchy(

           Function(o) _

             EntityMap.Row(

               EntityMap.Column(o.ID, "user_id"),

               EntityMap.Column(o.Name, "company_name")

             )

           ).ToTable("dbo.user")

    but it should be expressed in something like

         Me.MapHierarchy(

           Function(o) _

             EntityMap.Row(

               (From p In o.GetType.GetProperties()

               Select EntityMap.Column(p, "company_" & p.Name.ToLower)).ToArray

             )

           ).ToTable("dbo.user")

    it seems like the expression provided to MapHierarchy is transformed on CTP and that renders invalid any attempt to use a pattern other than the expected one.

    In the end I would have a EntityConfigurationBase that deals with this and all specific EntityConfigurations derived from it will therefore "automatically" have the desired mapping naming conventions.

    is such a scenario supported? How?

  42. Vijay Sitlani says:

    Hello Alex,

    I have Employee Table. My requirement is to self join table to itself.

    Employee Table have below fields-

    EmployeeID

    Name

    ManagerID

    I want to acheive below two things through EF without making server trip.

    1. I want to get subordinates of all employees.

    2. I want to get manage name & ID of all employees.

    I tried but could not acheive above functionalities through EF.

    Is it possible to acheive desired functionalities in EF through self join approach?

    Please guide to resolve the required concerns.

    Regards,

    Vijay Sitlani

  43. Hello says:

    I  have problem with hieracrchy.

    I want to define a base entity and then drive all of my POCO from base. But I always get error Invalid descrimintor column. I do not have any descriminator column as by base entity is just abstract one. How can I resolve this issue? I will appereciate any help on this

          [Serializable]

          public class FSBaseEntity

           {

               public virtual Guid Id { get; set; }

               public virtual Int32 HdVersionNo { get; set;}

               public virtual Guid HdEditStamp { get; set;}

           }

          [Serializable]

          public class PaymentOrder : FSBaseEntity

          {

              public virtual decimal OrderNo { get; set; }

              public virtual byte OrderType { get; set; }

              public virtual decimal SenderAccountNo { get; set; }

          }

Skip to main content