Announcement

Collapse
No announcement yet.
X
  • Filter
  • Time
Clear All
new posts

    DataSource updateCaches() automatically collapses expanded record

    Hi Isomorphic,

    I use SmartClient Version: v9.0p_2015-09-19/Enterprise Deployment (built 2015-09-19) and IE9 browser, I have a data grid with expandable records (nested grid). After changing the master record by pressing a button, I would like to preserve the current record expanded. Let me mention in this context that I use only SQL datasources.

    This is how I trigger the DS change (the database change has already taken place on the Oracle side via RPC request):

    final Criteria criteria = new Criteria(
    "schedule_id", designElementsInstance.preparationsGrid.getSelectedRecord()
    .getAttribute("SCHEDULE_ID"));

    DSRequest dsRequest = new DSRequest();
    dsRequest.setOperationType(DSOperationType.FETCH);
    dsRequest.setOperationId("fetch_id");

    DataSource.get("disseminationPrepDS")
    .fetchData(criteria, new DSCallback() {
    @Override
    public void execute(
    final DSResponse response,
    final Object rawData,
    final DSRequest request) {
    request.setOperationType(DSOperationType.UPDATE);
    // response.setInvalidateCache(true);
    DataSource.get(
    "disseminationPrepDS")
    .updateCaches(response,
    request);

    }
    }, dsRequest);

    This is the redraw activity caused by updateCaches of the master record:

    17:02:06.065:MUP9:INFO:redraws:isc_IButton_58_label:Scheduling redraw (setContents)
    [a]MathFunction.getStackTrace(_1=>undef, _2=>undef, _3=>undef, _4=>undef, _5=>undef)
    Canvas.$q9(_1=>"setContents", _2=>undef)
    Canvas.markForRedraw(_1=>"setContents")
    Canvas.setContents(_1=>"Enable")
    StatefulCanvas.setTitle(_1=>"Enable")
    [a]MathFunction.setProperties(Obj{title:Enable})
    [a]MathFunction.setProperty(_1=>"title", _2=>"Enable")
    StatefulCanvas.handleActivate(_1=>Obj, _2=>undef)
    StatefulCanvas.handleClick(_1=>Obj, _2=>undef)
    [c]EventHandler.bubbleEvent(_1=>[IButton ID:isc_IButton_58], _2=>"click", _3=>undef, _4=>undef)
    [c]EventHandler.handleClick(_1=>[IButton ID:isc_IButton_58], _2=>undef)
    [c]EventHandler.$k5(_1=>Obj{type:mouseup}, _2=>undef)
    [c]EventHandler.handleMouseUp(_1=>Obj{type:mouseup}, _2=>undef)
    [c]EventHandler.dispatch(_1=>[c]EventHandler.handleMouseUp(), _2=>undef)
    anonymous(event=>undef)
    "if (!isc.Browser.isIE && event == null) return;var returnVal=arguments.callee.$ch.isc.EH.dispatch(arguments.callee.$j2,event);return returnVal;"

    17:02:06.077:MUP9:INFO:redraws:isc_IButton_58:Scheduling redraw (setTitle)
    [a]MathFunction.getStackTrace(_1=>undef, _2=>undef, _3=>undef, _4=>undef, _5=>undef)
    Canvas.$q9(_1=>"setTitle", _2=>undef)
    Canvas.markForRedraw(_1=>"setTitle")
    StatefulCanvas.setTitle(_1=>"Enable")
    [a]MathFunction.setProperties(Obj{title:Enable})
    [a]MathFunction.setProperty(_1=>"title", _2=>"Enable")
    StatefulCanvas.handleActivate(_1=>Obj, _2=>undef)
    StatefulCanvas.handleClick(_1=>Obj, _2=>undef)
    [c]EventHandler.bubbleEvent(_1=>[IButton ID:isc_IButton_58], _2=>"click", _3=>undef, _4=>undef)
    [c]EventHandler.handleClick(_1=>[IButton ID:isc_IButton_58], _2=>undef)
    [c]EventHandler.$k5(_1=>Obj{type:mouseup}, _2=>undef)
    [c]EventHandler.handleMouseUp(_1=>Obj{type:mouseup}, _2=>undef)
    [c]EventHandler.dispatch(_1=>[c]EventHandler.handleMouseUp(), _2=>undef)
    anonymous(event=>undef)
    "if (!isc.Browser.isIE && event == null) return;var returnVal=arguments.callee.$ch.isc.EH.dispatch(arguments.callee.$j2,event);return returnVal;"

    17:02:06.100:TMR2:DEBUG:redraws:clearRedrawQueue: 2 redraws (2 items), 12ms
    17:02:06.113:TMR3:INFO:redraws:isc_Dissemination_DesignElements$1_0:Scheduling redraw (767 children) (Expanded Record)
    [a]MathFunction.getStackTrace(_1=>undef, _2=>undef, _3=>undef, _4=>undef, _5=>undef)
    Canvas.$q9(_1=>"Expanded Record", _2=>undef)
    Canvas.markForRedraw(_1=>"Expanded Record")
    [a]MathFunction.invokeSuper(_1=>null, _2=>"markForRedraw", _3=>undef, _4=>undef, _5=>undef, _6=>undef, _7=>undef, _8=>undef, _9=>undef, _10=>undef)
    [a]MathFunction.Super(_1=>"markForRedraw", _2=>Obj{length:1}, _3=>undef)
    Layout.markForRedraw("Expanded Record")
    [c]Class.fireCallback(_1=>Obj, _2=>undef, _3=>Array[1], _4=>[ListGrid ID:isc_Dissemination_DesignElements$1_0], _5=>true) on [Class Timer]
    [c]Timer.$in(_1=>"$ir4384", _2=>4489, _3=>undef)
    anonymous()
    "isc.Timer.$in(_5,_6)"

    17:02:06.417:TMR5:DEBUG:redraws:clearRedrawQueue: 1 redraws (1 items), 265ms
    17:02:06.572:INFO:redraws:isc_globalWarn_headerLabel:Immediate redraw (no reason provided)
    [a]MathFunction.getStackTrace(_1=>undef, _2=>undef, _3=>undef, _4=>undef, _5=>undef)
    Canvas.$q9(_1=>undef, _2=>false)
    Canvas.redraw(_1=>undef)
    Button.setOverflow("visible")
    [a]HStack.$157h()
    [a]HStack.visibilityChanged(_1=>true)
    Canvas.$807()
    Canvas.parentVisibilityChanged(_1=>"inherit", _2=>[Dialog ID:isc_globalWarn], undef, undef, undef)
    Array.map(_1=>"parentVisibilityChanged", _2=>"inherit", _3=>[Dialog ID:isc_globalWarn], _4=>undef, _5=>undef, _6=>undef)
    ** recursed on Canvas.parentVisibilityChanged

    17:02:06.717:TMR2:INFO:redraws:isc_Dissemination_DesignElements$1_0_body:Scheduling redraw (746 children) (dataChanged)
    [a]MathFunction.getStackTrace(_1=>undef, _2=>undef, _3=>undef, _4=>undef, _5=>undef)
    Canvas.$q9(_1=>"dataChanged", _2=>undef)
    Canvas.markForRedraw(_1=>"dataChanged", undef, undef, undef, undef)
    Array.map(_1=>"markForRedraw", _2=>"dataChanged", _3=>undef, _4=>undef, _5=>undef, _6=>undef)
    ListGrid.$25a(_1=>"dataChanged")
    ListGrid.redrawForDataChanged()
    ListGrid.dataChanged(_1=>"update", _2=>Obj, _3=>0, _4=>Array[1], _5=>undef, _6=>undef)
    anonymous(operationType=>"update", originalRecord=>Obj, rowNum=>0, updateData=>Array[1], filterChanged=>undef, dataFromCache=>undef)
    thunk(operationType=>"update", originalRecord=>Obj, rowNum=>0, updateData=>Array[1], filterChanged=>undef, dataFromCache=>undef)
    dataChangedObservation("update", Obj, 0, Array[1], undef, undef)
    ResultSet.$ee(_1=>undef, _2=>undef)
    ResultSet.handleUpdate(_1=>"update", _2=>Array[1], _3=>false, _4=>Obj)
    ResultSet.dataSourceDataChanged(_1=>Obj, _2=>Obj)
    anonymous(dsResponse=>Obj, dsRequest=>Obj)
    thunk(dsResponse=>Obj, dsRequest=>Obj)
    dataChangedObservation(Obj, Obj)
    DataSource.updateCaches(_1=>Obj, _2=>Obj)
    [c]Class.fireCallback(_1=>$376(), _2=>"dsResponse,data,dsRequest", _3=>Array[3], _4=>[DataSource ID:disseminationPrepDS], _5=>undef) on [Class DataSource]
    [a]MathFunction.fireCallback(_1=>$376(), _2=>"dsResponse,data,dsRequest", _3=>Array[3], _4=>undef)
    DataSource.fireResponseCallbacks(_1=>Obj, _2=>Obj, _3=>Obj, _4=>Obj)
    DataSource.$38b(_1=>Array[1], _2=>Obj, _3=>Obj, _4=>Obj, _5=>Obj)
    DataSource.$50h(_1=>Obj, _2=>Array[1], _3=>Obj)
    ** recursed on [c]Class.fireCallback

    17:02:07.224:TMR3:DEBUG:redraws:clearRedrawQueue: 1 redraws (1 items), 474ms


    Is there a way to convince updateCaches() to not collapse the selected record ?

    Thank you

    #2
    Since the expansion record is potentially based on the data inside the record that has been updated, and in ways the framework cannot always anticipate (since getExpansionComponent() is an override point), it makes sense to automatically discard the existing expansion component when a record is updated. If it makes sense to do so in your app, you can re-expand it via expandRecord().

    Comment


      #3
      Hi Isomorphic,

      I understand your point of view, however the program takes decisions by itself based on potential, non-verifiable facts. We are the owner of the data and we would prefer to take this decision by ourselves. Is there a way for you to give us the choice of when to collapse a record in the context above?

      Thank you in advance

      Comment


        #4
        See previous post: it seems like you may have missed that you can re-expand programmatically.

        Comment


          #5
          Hi

          I did not miss the fact that I can expand programmatically. This is an obvious fact. A programmatic expand also retrieves data from the server, additionally users can see clearly that the record is closed and then expanded. I thought these disadvantages were clear. Let me reiterate that i am the data owner and i prefer to take this decision when to collapse the record. If it is possible to have this flexibility, great.

          Thanks

          Comment


            #6
            Looking back at this, there are some basic issues with your code:

            1. you set the operationType on the DSRequest object. It's expected on the DSResponse

            2. you're re-using a DSResponse from a fetch operation. You should be creating a new DSResponse, as the DSResponse from the fetch operation potentially has a lot of settings on it, as well as internal state maintained by the framework, which don't make sense with updateCaches().

            It looks like these kinds of issues could cause collapsing of records which don't need to be collapsed (the framework is actually selective about whether collapse is performed), so correcting them might prevent the collapse that you don't want - we can't tell definitively because you've never shared your settings and/or code for the expansion modes you're using.

            Comment


              #7
              I am glad to find out that records should not be collapsed on updateCaches(), changed according to your suggestions:

              try {
              final Criteria criteria = new Criteria(
              "schedule_id", designElementsInstance.preparationsGrid.getSelectedRecord()
              .getAttribute("SCHEDULE_ID"));
              final DSRequest dsRequest = new DSRequest();
              dsRequest.setOperationType(DSOperationType.FETCH);
              dsRequest.setOperationId("fetch_id");

              DataSource.get("disseminationPrepDS")
              .fetchData(criteria, new DSCallback() {
              @Override
              public void execute(
              final DSResponse response,
              final Object rawData,
              final DSRequest request) {
              DSResponse updateResponse = new DSResponse();
              updateResponse.setOperationType(DSOperationType.UPDATE);
              ListGridRecord updateRecord = new ListGridRecord(response.getData()[0].getJsObj());
              updateResponse.setData(updateRecord);

              DataSource.get(
              "disseminationPrepDS")
              .updateCaches(updateResponse, request);
              }
              }, dsRequest);

              The UPDATE operationType is set on DSResponse and i set the data of the response to the original response, which requires an (array of) ListGridRecord instead of Record. updateRecord contains the proper data, that has been verified by me, and we are always sure that the fetched data contains only one record.
              However in this case updateCaches does not work, meaning it does not update the selected grid record, with no error messages whatsoever. Could you check why updateCaches does not work for this case ?
              Thank you

              Comment


                #8
                Adding the line :
                request.setOperationType(DSOperationType.UPDATE);

                to the above causes updateCaches() to work, but the record is again collapsed. Note that I created the DSResponse from scratch. Grateful for a solution for this.
                Thanks in advance

                Comment


                  #9
                  The second argument to updateCaches() (a DSRequest) is not required. However, if you do pass a request, you definitely do not want to pass a dsRequest that says it is a "fetch" whereas the response says "update", as this makes no sense.

                  You also don't want to be re-using a request that has actually executed, as previously covered for the response argument.

                  Comment


                    #10
                    If I don't need to use the request for updateCaches(), updateCaches() will work but the record is again collapsed:

                    final Criteria criteria = new Criteria(
                    "schedule_id", designElementsInstance.preparationsGrid.getSelectedRecord()
                    .getAttribute("SCHEDULE_ID"));
                    final DSRequest dsRequest = new DSRequest();
                    dsRequest.setOperationType(DSOperationType.FETCH);
                    dsRequest.setOperationId("fetch_id");

                    DataSource.get("disseminationPrepDS")
                    .fetchData(criteria, new DSCallback() {
                    @Override
                    public void execute(
                    final DSResponse response,
                    final Object rawData,
                    final DSRequest request) {
                    DSResponse updateResponse = new DSResponse();
                    updateResponse.setOperationType(DSOperationType.UPDATE);
                    ListGridRecord updateRecord = new ListGridRecord(response.getData()[0].getJsObj());

                    updateResponse.setData(updateRecord);

                    DataSource.get(
                    "disseminationPrepDS")
                    .updateCaches(updateResponse);

                    }
                    }, dsRequest);


                    The above makes updateCaches() work, but the record is collapsed automatically. Again note that I create DSResponse from scratch, as suggested by you. Grateful for any solution which will make the record not collapse.
                    Thank you

                    Comment

                    Working...
                    X