mardi 7 août 2018

Page loading before model is deserialized

Use case :

I am trying to render a page that compare outputs of 2 performance benchmark runs.

Issue :

Only part of the data is getting deserialized at the time of the page render. On multiple refreshs all of the data gets rendered.

The network tab seems to show that the output is sent correctly by the backend.

Execution:

1) The data is rendered using the api /reports/:reportId.

This api is called twice using 2 reportIds to be compared and the difference is then displayed on the UI.

The /reports/:reportId api returns an output like :

 {
  "data": {
    "id": 87,
    "type": "reports",
    "attributes": {
      "status": "STARTED",
      "startdatetime": 1532511531000,
      "enddatetime": 1533485380052,
      "queries": [
       {
        "startdatetime": 1532511531000,
        "enddatetime": 1533485380056,
        "reportId": 87,
        "id": "Q1"
      }
    ]
   }
  }
}

The output intermittently renders everything but the "queries" array while deserializing the array perfectly in some runs.

2) To parse the queries array I used a custom array transform like :

import DS from 'ember-data';

export default DS.Transform.extend({
   deserialize: function(serialized) {
      return (Ember.typeOf(serialized) == "array")
        ? serialized
        : [];
   },
   serialize: function(deserialized) {
      var type = Ember.typeOf(deserialized);
      if (type == 'array') {
        return deserialized
      } else if (type == 'string') {
        return deserialized.split(',').map(function(item) {return jQuery.trim(item);});
      } else {
        return [];
      }
  }
});

3) The model for reports looks like:

status: DS.attr('string'),
startdatetime: DS.attr('number'),
enddatetime: DS.attr('number'),
queries: DS.attr('array')

4) My route for compare looks like :

import Route from '@ember/routing/route';
import { hash } from 'rsvp';
import { inject as service } from '@ember/service';

export default Route.extend({
model(params) {
   return hash({
     leftrun: this.store.findRecord('report', params.id1),
     rightrun: this.store.findRecord('report', params.id2)
   })
 }
});

On running the page on debug mode when the queries array doesn't get deserialized,

1) I can see that the "status" and other attributes is accessible.

2) The network tab shows that the output for reports/:runId is "pending" (Which doesn't make sense as the "status" is set.) Once the page is fully loaded, the network tab shows that the full data including the queries array was received by the webapp.

Is there an issue with the flow or my transform that is causing this issue?




Aucun commentaire:

Enregistrer un commentaire