none
Silverlight:1:N Relationship mapping eines Firmeneintrags verwenden

    Frage

  • Hallo Leute,

    ich suche nach einer Möglichkeit einen Firmeneintrag zu erstellen und dabei das Mapping aus einer 1:N Relationship zu verwenden und zwar in Silverlight.

    Das Beispiel unten zeigt, dass durch Anlegen eines untergeordneten Firmeneintrags aus einem bestehenden Firmeneintrags, das Feld Email aus der Hauptfirma vorbefühlt wird. Das Mapping wird hierzu aus dem Customizing verwendet. Wie kann ich das gleiche Verhalten in Silverlight verwenden? Zu sehen ist natürlich, dass der Datensatz nach dem befüllen im CRM nicht erstellt wird.

    Mögliche Optionen: (Viel zu aufwändig)
    - Datensatz für Erstellen
    - Metadaten der Firmenentität laden
    - Datensatz Anhand der Metadateninformationen updaten

    Alternativ-Optionen? Ein Associate-Request war ebenfalls noch ne idee, bracht mich aber nicht weiter.

    AssociateRequest associateRequest = new AssociateRequest();
    associateRequest.Target = new EntityReference("account", account1Guid);
    associateRequest.RelatedEntities = new EntityReferenceCollection();
    associateRequest.RelatedEntities.Add(new EntityReference("account", account2Guid));
    associateRequest.Relationship = new Relationship("account_parent_account");
    associateRequest.Relationship.PrimaryEntityRole = EntityRole.Referenced;
    _service.Execute(associateRequest);

    Vielen Dank schon im Voraus.


    Freitag, 31. Mai 2013 08:12

Antworten

  • Vielen Dank für die Antworten.

    Schade das im CRM-SDK kein Request hierfür zur Verfügung steht. So verursacht die Silverlight-Applikation sonst nur unnötig viel Traffic für das Anfragen und verarbeiten von weiteren Daten, die dann wiederum die Anwendung langsamer machen.

    Das Beispiel mit dem autoMapAttributes() ist eine gute Reference. Vielen Dank.

    Gruß
    Martin

    • Als Antwort markiert Martin Pfund Montag, 10. Juni 2013 10:35
    Freitag, 7. Juni 2013 08:07

Alle Antworten

  • Hallo Martin,

    das die Daten das Mappings automatisch übernommen werden, funktioniert nur über die GUI. Wenn du Datensätze über das SDK selbst erstellst, musst du dich selber um diese Funktionalität kümmern, einen Automatismus gibt es an dieser Stelle nicht.


    Viele Grüße

    Michael Sulz
    MVP für Microsoft Dynamics CRM
    Blog
    Website XING LinkedIn Facebook Twitter

    Freitag, 31. Mai 2013 08:37
    Moderator
  • Hallo,

    Ich fand die Aufgabenstellung sehr interessant und hatte schon mal in diese Richtung etwas recherchiert.

    Folgende Methode erwartet die Zielentität (z.B. Tochterfirma) und das Schema 

    (z.B. "account_parent_account") :

    static void autoMapAttributes(Entity NewEntity, string RelationScheme, IOrganizationService Service) {
      var _relationRequest = new RetrieveRelationshipRequest() {
        RetrieveAsIfPublished = true,
        Name = RelationScheme
      };
    
      var _relation = Service.Execute(_relationRequest) as RetrieveRelationshipResponse;
      var _relationMeta = (OneToManyRelationshipMetadata)_relation.Results.FirstOrDefault().Value;
          
      if(NewEntity.GetAttributeValue<EntityReference>(_relationMeta.ReferencingAttribute) == null) {
        throw new Exception("No referenced ID in look up field.");
      }
      else {
        Guid _referencedID = NewEntity.GetAttributeValue<EntityReference>(_relationMeta.ReferencingAttribute).Id;
    
        using(OrganizationServiceContext osc = new OrganizationServiceContext(Service)) {
          Guid _mapID = osc.CreateQuery("entitymap").SingleOrDefault<Entity>(x =>
            x.GetAttributeValue<string>("targetentityname") == _relationMeta.ReferencingEntity && 
            x.GetAttributeValue<string>("sourceentityname") == _relationMeta.ReferencedEntity).Id;
           
          var _attributes = osc.CreateQuery("attributemap").Where<Entity>(x => 
            x.GetAttributeValue<Guid>("entitymapid") == _mapID &&
            x.GetAttributeValue<Guid>("parentattributemapid") == null
          );
    
          Entity _source = osc.CreateQuery(_relationMeta.ReferencedEntity).First<Entity>(x => x.GetAttributeValue<Guid>(_relationMeta.ReferencedAttribute) == _referencedID);
          Entity _target = new Entity(_relationMeta.ReferencingEntity);
          _target.Id = NewEntity.Id;
    
          foreach(var item in _attributes) {
            if((string)item["targetattributename"] != _relationMeta.ReferencingAttribute)
              _target.Attributes[(string)item["targetattributename"]] = _source.GetAttributeValue<object>((string)item["sourceattributename"]);
          }
          Service.Update(_target);
        }
      }      
    }


    Aufgerufen wird es dann z.B. so:

    // z.B. Firma mit den Daten aus der übergeordneten Mutterfirma
    autoMapAttributes(_target,"account_parent_account",_service);
    
    // z.B. Kontakt mit den Daten aus der übergeordneten Firma
    autoMapAttributes(_target,"contact_customer_accounts",_service);
     

    Die Methode ruft durch den Schemanamen und das Lookup Feld die korrespondierende Entität ab und füllt die Felder des Zielobjektes anhand der Daten aus Deinem erwähnten Mapping der 1:N Verbindung.

    Der Code kann vielleicht noch optimiert werden, aber bei mir ist er gerade ganz gut gelaufen.

    Beste Grüße

    Steve


    Steve Sämmang, Vienna, Austria
    Blog: xrm.io Website: simplic.at

    Montag, 3. Juni 2013 13:33
  • Vielen Dank für die Antworten.

    Schade das im CRM-SDK kein Request hierfür zur Verfügung steht. So verursacht die Silverlight-Applikation sonst nur unnötig viel Traffic für das Anfragen und verarbeiten von weiteren Daten, die dann wiederum die Anwendung langsamer machen.

    Das Beispiel mit dem autoMapAttributes() ist eine gute Reference. Vielen Dank.

    Gruß
    Martin

    • Als Antwort markiert Martin Pfund Montag, 10. Juni 2013 10:35
    Freitag, 7. Juni 2013 08:07