6 votes

Manipulation des propriétés calculées avec breezejs et l'api web

J'expérimente BreezeJS avec l'API Web en utilisant l'attribut BreezeControllerAttribute. Comment les propriétés calculées d'une entité doivent-elles être exposées ? Le seul moyen que j'ai trouvé pour le faire de manière fiable est de créer un DTO intermédiaire qui hérite de l'entité ou d'utiliser une projection. Normalement, je devrais utiliser une propriété en lecture seule pour ce scénario, mais ces propriétés semblent être ignorées.

14voto

Ward Points 9920

Lorsque Breeze fait correspondre les données de propriété JSON aux entités, il ignore les propriétés qu'il ne reconnaît pas . C'est pourquoi les données des propriétés calculées de votre classe serveur sont ignorées même si vous les voyez dans le JSON sur le fil.

Heureusement, vous pouvez apprendre à Breeze à reconnaître la propriété en en l'enregistrant comme une propriété non cartographiée . Je vais vous montrer comment. Laissez-moi d'abord vous expliquer le contexte.

Contexte

Votre propriété calculée serait "connue" du client Breeze s'il s'agissait d'une propriété calculée par la base de données. Les propriétés (régulières et calculées) adossées à la base de données sont reprises dans les métadonnées en tant que propriétés mappées.

Mais dans votre cas (si je comprends bien), la propriété est définie dans la logique de la classe côté serveur, et non dans la base de données. Elle ne figure donc pas parmi les propriétés mappées dans les métadonnées. Elle est cachée des métadonnées. Il s'agit d'une propriété d'instance non mappée.

Je suppose que vous ne le cachez pas au sérialiseur. Si vous regardez le trafic réseau pour une requête de la classe, vous pouvez voir vos données de propriété calculées arriver sur le client. Le problème est que Breeze les ignore lorsqu'il "matérialise" les entités à partir des résultats de ces requêtes.

Solution avec exemple

La solution consiste à enregistrer la propriété calculée dans le MetadataStore .

J'ai modifié le site entityExtensionTests.js de l'échantillon DocCode pour inclure ce scénario ; vous pouvez obtenir ce code sur GitHub ou attendre la prochaine version de Breeze.

Ou bien suivez simplement le code ci-dessous, en commençant par cet extrait de la page d'accueil. Employee classe dans NorthwindModel.cs :

// Unmapped, server-side calculated property
\[NotMapped\] // Hidden from Entity Framework; still serialized to the client
public string FullName { 
    get { return LastName + 
             (String.IsNullOrWhiteSpace(FirstName)? "" : (", " + FirstName)); }
}

Et voici le test automatisé dans entityExtensionTests.js

test("unmapped property can be set by a calculated property of the server class", 2,
  function () {

    var store = cloneModuleMetadataStore(); // clones the Northwind MetadataStore

    // custom Employee constructor
    var employeeCtor = function () {
        //'Fullname' is a server-side calculated property of the Employee class
        // This unmapped property will be empty for new entities
        // but will be set for existing entities during query materialization
        this.FullName = ""; 
    };

    // register the custom constructor
    store.registerEntityTypeCtor("Employee", employeeCtor);

    var fullProp = store.getEntityType('Employee').getProperty('FullName');
    ok(fullProp && fullProp.isUnmapped,
        "'FullName' should be an unmapped property after registration");

    var em = newEm(store); // helper creates a manager using this MetadataStore

    var query = EntityQuery.from('Employees').using(em);

    stop(); // going async
    query.execute().then(success).fail(handleFail).fin(start);

    function success(data) {
        var first = data.results\[0\];
        var full = first.FullName();

        // passing test confirms that the FulllName property has a value
        ok(full, "queried 'Employee' should have a fullname ('Last, First'); it is "+full);
    }

});

Ce que vous devez faire se trouve dans cette petite partie de l'exemple de test :

var yourTypeCtor = function () {
    this.calculatedProperty = ""; // "" or instance of whatever type is is supposed to be
};

// register your custom constructor
store.registerEntityTypeCtor("YourType", yourTypeCtor);

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X