Question

Je viens de commencer avec l'entité Framework 4.1, en essayant le mode "Database First". Lorsque EF génère une classe de modèle avec le "ADO.NET DBContext Generator", ne devrait-il pas identifier la clé principale de la classe avec un attribut [clé]? Sans cela, il semble incompatible avec le T4 MVCSCaFolding.

Voici les détails:

En utilisant l'interface graphique du concepteur de modèle de données d'entité, j'ai ajouté une table "pays" simple au modèle de ma base de données existante. L'interface graphique identifie correctement un seul champ de clé d'identité entier nommé "PK" comme ma clé principale. (Hélas! Je suis un nouvel utilisateur, donc je ne peux pas ajouter de capture d'écran. J'ai inclus le CSDL à la place ci-dessous.) Cependant, lorsque EF génère du code à l'aide du "ADO.NET DBContext Generator", il n'identifie pas le PK champ comme champ de clé dans la classe générée (voir l'extrait de code ci-dessous).

Le CSDL pour la table "country":

<edmx:ConceptualModels>
  <Schema Namespace="EpiDataModel" Alias="Self" xmlns:annotation="http://schemas.microsoft.com/ado/2009/02/edm/annotation" xmlns="http://schemas.microsoft.com/ado/2008/09/edm">
    <EntityContainer Name="EpiModelEntities" annotation:LazyLoadingEnabled="true">
      <EntitySet Name="countries" EntityType="EpiDataModel.country" />
    </EntityContainer>
    <EntityType Name="country">
      <Key>
        <PropertyRef Name="PK" />
      </Key>
      <Property Name="PK" Type="Int32" Nullable="false" annotation:StoreGeneratedPattern="Identity" />
      <Property Name="Abbreviation" Type="String" Nullable="false" MaxLength="200" Unicode="false" FixedLength="false" />
      <Property Name="Name" Type="String" MaxLength="1024" Unicode="false" FixedLength="false" />
      <Property Name="Description" Type="String" MaxLength="1024" Unicode="false" FixedLength="false" />
      <Property Name="Sequence" Type="Int32" />
    </EntityType>
  </Schema>
</edmx:ConceptualModels>

Voici le code automatique:

//------------------------------------------------------------------------------
// <auto-generated>
//    This code was generated from a template.
//
//    Manual changes to this file may cause unexpected behavior in your application.
//    Manual changes to this file will be overwritten if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

using System;
using System.Collections.Generic;

namespace MvcApplication1.Areas.Epi.Models
{
    public partial class country
    {
        public int PK { get; set; }
        public string Abbreviation { get; set; }
        public string Name { get; set; }
        public string Description { get; set; }
        public Nullable<int> Sequence { get; set; }
    }
}

Cela provoque un problème lorsque j'essaie d'échafaudage un contrôleur en utilisant le modèle T4 MVCSCafolding. J'obtiens une erreur "Aucune propriété ne semble être des clés principales." La commande et la sortie de la console NuGet Package Manager sont ci-dessous:

PM> scaffold controller MvcApplication1.Areas.Epi.Models.country -Area Epi -NoChildItems -DbContextType MvcApplication1.Areas.Epi.Models.EpiModelEntities -Force
Scaffolding countriesController...
Get-PrimaryKey : Cannot find primary key property for type 'MvcApplication1.Areas.Epi.Models.country'. No properties appear to be primary keys.
At C:\work\EPI\EPIC_MVC3\sandbox\MvcApplication1\packages\MvcScaffolding.1.0.6\tools\Controller\MvcScaffolding.Controller.ps1:74 char:29
+ $primaryKey = Get-PrimaryKey <<<<  $foundModelType.FullName -Project $Project -ErrorIfNotFound
    + CategoryInfo          : NotSpecified: (:) [Get-PrimaryKey], Exception
    + FullyQualifiedErrorId : T4Scaffolding.Cmdlets.GetPrimaryKeyCmdlet

Cependant, si je modifie manuellement la classe générée pour ajouter un attribut [clé] au champ, alors la même commande d'échafaudage exactement ci-dessus fonctionne bien:

using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations; // manually added

namespace MvcApplication1.Areas.Epi.Models
{
    public partial class country
    {
        [Key]                        // manually added
        public int PK { get; set; }
        public string Abbreviation { get; set; }
        public string Name { get; set; }
        public string Description { get; set; }
        public Nullable<int> Sequence { get; set; }
    }
}

Alors pourquoi la base de données EF n'est-elle pas en premier et le T4 MVCSCaFolding jouant bien ensemble? Et même sans le problème d'échafaudage, les classes EF n'ont-elles pas besoin de savoir quels sont les champs clés?

Pas de solution correcte

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top