DevExpress XAF – Domain Components : Mapper une interface à une table existante

Contrairement à XPO, les “Domain Components” XAF ne permettent pas nativement de préciser le nom de la table ou le schémas de sécurité dans la base de donnée pour le stockage d’une entité.
C’est l’attribut [Persistent] qui permet de définir cette information en XPO grâce à sa propriété MapTo.
Malheureusement cette attribut est incompatible avec les “Domain Components” et l’attribut [PersistentDc] qui le remplace ne possède pas cette propriété.

Voici donc une solution générique pour contourner le problème sans avoir à écrire du code pour chaque table.

La solution consiste en :
- La création d’un attribut personnalisé de remplacement pour l’attribut [Persistent("MapTo")]
- Une méthode permettant d’ajouter automatiquement l’attribut [Persistent("MapTo")] sur les classes générées par xaf
- L’appel de cette méthode sur l’évènement “SettingUp” de l’application ou en surchargeant sa méthode  “OnSettingUp”

Il suffira donc d’ajouter cette attribut sur les interfaces créées en lui donnant le nom de la table de destination en paramètre.

 

Code de l’attribut :

  1. [AttributeUsage(AttributeTargets.Interface | AttributeTargets.Field, AllowMultiple=false)]
  2. public class PersistentDcMapToAttribute : Attribute
  3. {
  4.     public string MapTo { get; set; }
  5.  
  6.     public PersistentDcMapToAttribute(String mapTo)
  7.     {
  8.         MapTo = mapTo;
  9.     }
  10. }

 

Méthode pour appliquer l’attribut sur les classes générées :

  1. public class PersistentDcMapToRegistrator
  2. {
  3.     public static void Register()
  4.     {
  5.         var persistentStore = ((XpoTypeInfoSource)XafTypesInfo.PersistentEntityStore);
  6.  
  7.         foreach (var dcType in persistentStore.GeneratedEntities)
  8.         {
  9.             var entityClassInfo = persistentStore.GetEntityClassInfo(dcType);
  10.  
  11.             //Applique l’attribut sur la classe si nécessaire
  12.             var persistentDcMapToAttribute = dcType.GetCustomAttribute<PersistentDcMapToAttribute>(true);
  13.             if (persistentDcMapToAttribute != null)
  14.             {
  15.                 entityClassInfo.AddAttribute(new PersistentAttribute(persistentDcMapToAttribute.MapTo));
  16.             }
  17.  
  18.             //Applique l’attribut sur chaque membre si nécessaire
  19.             ITypeInfo dcTypeInfo = XafTypesInfo.Instance.FindTypeInfo(dcType);
  20.             foreach (IMemberInfo dcMember in dcTypeInfo.OwnMembers)
  21.             {
  22.                 var attribute = dcMember.FindAttribute<PersistentAttribute>(true);
  23.                 if (attribute != null >> attribute.MapTo != null)
  24.                 {
  25.                     XPMemberInfo xpMember = entityClassInfo.GetMember(dcMember.Name);
  26.                     xpMember.RemoveAttribute(typeof(PersistentAttribute));
  27.                     xpMember.AddAttribute(new PersistentAttribute(attribute.MapTo));
  28.                 }
  29.             }
  30.         }
  31.     }
  32. }

Cette solution à été réalisée avec les version 12.2.x des composants.

Merci à Anatol du support DevExpress pour son aide : http://www.devexpress.com/Support/Center/Question/Details/Q329441

Développeur .Net / Sql Server / DevExpress