2016-04-01 6 views
1

Ich habe eine EF-Konvention erstellt, die einen Schemanamen für eine Klasse basierend auf der Schnittstelle, die es direkt oder indirekt implementiert, festgelegt.Wie kann ich den Typ eines Objekts von einem EF EntitySet erhalten

public class TableNameConvention<T> : IStoreModelConvention<EntitySet> 
{ 
    private readonly string SchemaName; 

    public TableNameConvention(string schemaName) 
    { 
     this.SchemaName = schemaName; 
    } 

    public virtual void Apply(EntitySet entitySet, DbModel model) 
    { 
     // Get the name of the Entity 
     string name = entitySet.Name; 

     // Check TEntityType Assembly for entitySet type 
     Type type = typeof(T).Assembly.GetTypes().Where(x => x.Name == name).SingleOrDefault(); 

     // Check if type was found 
     if (type != null) 
     { 
      // Check if type implements Type Parameter and if so, set schema 
      if (typeof(T).IsAssignableFrom(type)) entitySet.Schema = SchemaName; 
     } 

     entitySet.Table = FormatName(name); 
    } 

Dies funktioniert in 95% der Zeit. Wenn in der Assembly jedoch eine andere Klasse mit demselben Namen vorhanden ist, wird die Standardeinstellung zurückgegeben. Ich kann das zu FirstOrDefault ändern, aber es gibt immer noch keine Garantie, dass die erste die ist, nach der ich eigentlich suche.

Ich weiß, dass ohne den voll qualifizierten Namen wird es nie 100% sein, aber hat jemand irgendwelche Vorschläge, um die Chancen auf den richtigen Typ zu verbessern?

UPDATE

geändert ich folgende:

Type type = AppDomain.CurrentDomain.GetAssemblies() 
         .SelectMany(t => t.GetTypes()) 
         .Where(t => t.IsClass && t.Namespace == typeof(T).Namespace) 
         .FirstOrDefault(t => t.Name.Equals(name)); 

Es wird nur funktionieren, wenn die abgeleitete Klasse im gleichen Namensraum wie die Basisklasse ist, though. Also, wenn jemand andere Vorschläge hat, bitte helfen!

Antwort

0

Die kurze Antwort ist, dass es keine Möglichkeit gibt, die Entity tatsächliche Type direkt von einem EF EntitySet, zumindest nicht in dem Speichermodell zu erhalten.

Um den Code über Arbeit zu machen, habe ich die Klasse wie folgt aktualisiert:

private readonly string SchemaName; 
private readonly string Namespace; 

public TableNameConvention(string schemaName, string @namespace) 
{ 
    this.SchemaName = schemaName; 
    this.Namespace = @namespace; 
} 

und dann aktualisiert, wenn Methode auf der Abfrage von der AppDomain die Art zu erhalten Linq

Type type = AppDomain.CurrentDomain.GetAssemblies() 
        .SelectMany(t => t.GetTypes()) 
        .Where(t => t.IsClass && t.Namespace == this.Namespace) 
        .FirstOrDefault(t => t.Name.Equals(name)); 
0

Würde das funktionieren?

 // Check TEntityType Assembly for entitySet type 
     Type type = typeof(T).Assembly.GetTypes().Where(x => x == entitySet.GetType()).SingleOrDefault(); 
+0

, das nicht Arbeit. Die Variable 'entitySet' verweist auf ein Objekt vom Typ 'EntitySet', nicht auf den eigentlichen Typ der zugrunde liegenden Klasse. –

Verwandte Themen