Announcement

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

    Queuing DMI

    I have a handful of datasources that I write to from a collection of grids/forms using queuing. On the same layout, I have another grid showing a collection of related documents, also retrieved from a datasource, and a Flashlet presenting a Flash view of the selected document.

    When everything is saved, I need to add or replace a document with one I generate server-side using the new data.

    I have a bunch of that wired up now, using an RPCQueueCallback to fire the document generation bit, which I guess is fine - though I can see a case where I might want to rollback the transaction if the document generation fails. It's not clear to me how I'd do that this way.

    For now, the thing that's bothering me is this:

    At least some of the datasources in that queue will be used from other places. I need to refire the document generation and all that whenever any of them is updated. You could of course use the same callback mechanism everywhere, but I'd prefer to manage this in one place, preferably server side.

    It feels like what I really want to do is generate the document via some DMI. I'd register the same DMI on each datasource in question, but I assume that when I queue up e.g., updates to records in 4 datasources, the DMI is going to fire 4 times. Yes? Unless there were a way in the DMI itself to see whether it was already going to be called in the context of the current transaction.

    So is there a good way to leverage the server framework to deal with this kind of thing out of the box?

    (here's hoping this makes some small amount of sense)

    #2
    There's a whole set of server-side APIs around transactions and rollback, see also this sample (and others in the same folder).

    You talk about generating the document via DMI - but how are you doing it now if it's not being done via DMI?

    There's no need to create multiple DMIs that do the same thing. You can just call the single DMI from wherever you need to.

    Comment


      #3
      There's a whole set of server-side APIs around transactions and rollback
      It's not that I'm unsure whether or not SmartGWT supports transaction management - I know it does. What I was wondering was whether there was a better approach than the one I was taking, because:

      how are you doing it now if it's not being done via DMI?
      As I said, I'm doing it now in an RPCQueueCallback. So I'll go and look at your samples again, but what I was wondering was how I'd rollback from an RPCQueueCallback - as far as I can tell the transaction is already committed by the time the callback fires. In any case, the real point was this:

      There's no need to create multiple DMIs that do the same thing. You can just call the single DMI from wherever you need to.
      Right. And if I have that single DMI registered on 4 datasources, and all those datasources are written to in one queued transaction, does the DMI fire 4 times, or once?

      Comment


        #4
        OK, we're clearly answering the wrong questions - maybe you could explain again what you're doing, from the top? Be specific about what you're doing with the generated document, why you would generate it after a transaction rather than during, why you think a DMI would be called 4 times.

        Comment


          #5
          I have 4 datasources, each containing a bit of data I need to create this document. We can just call them ds1, ds2, ds3, and ds4.

          On one layout, I have a DynamicForm and 3 ListGrids repesenting data from the 4 datasources. The end user 'does stuff' and saves edits to the form and all 3 grids at the same time, like so:

          Code:
          RPCManager.startQueue();  
               formDs1.saveData();
               gridDs2.saveAllEdits();
               gridDs3.saveAllEdits();
               gridDs4.saveAllEdits()
          
               ...
          I can't generate the document until I have all the data I need to build it up. The only way I know I have it all is that the RPCQueueCallback (or the saveAllEdits callback on gridDs4) fires. So when that happens, I call out to this servlet. Note that it doesn't have to be a servlet at all, I was just trying to stream the content back to the client so that I could see it work. In the end, that document will get written to another datasource (which is actually represented by another listgrid (and a flashlet, but that's probably irrelevant) on the layout I'm describing)

          Code:
               ...
          
               RPCManager.sendQueue(new RPCQueueCallback() {
          			public void execute(RPCResponse[] responses) {
          
          				RPCRequest req = new RPCRequest();
          				req.setData(String.valueOf(someId));
          				req.setTransport(RPCTransport.HIDDENFRAME);
          				req.setActionURL("/GenerateMyDocument");
          				
          				RPCManager.sendRequest(req, new RPCCallback() {
          					public void execute(RPCResponse response, Object rawData, RPCRequest request) {
          						//notify various ui components that they need refreshing
          					}
          				});
          			}
               }
          Like I said, this works.

          I'll have other layouts that use only 1 or 2 of the 4 datasources in question, and may not need queuing at all. I could repeat the pattern I'm using all over the place, making sure to fire that servlet (or whatever) from a callback each time, but I'd really rather not.

          Feels like a job for DMI, and I think I hear you agreeing on this.

          I need for these documents to get recreated from all the freshest data whenever any of those datasources gets updated. So as you say, I could just write one DMI and register it with all 4 datasources. Easy peasy, problem solved. Any time a datasource record gets written, the DMI fires and my new document gets created.

          But now look back at my first layout. I'm queuing up updates to all 4 datasources in one shot. So ds1 updates, DMI fires (without knowing that ds2 has pending updates). ds2 gets updated next, DMI fires, and so on. I can't have that.

          Is that any clearer?

          Now that I've described the whole thing again, it occurs to me that maybe the simplest thing is just to provide a separate operationId to support the queuing behavior. So for updates to these datasources individually, the document creation is done for you with a DMI. If you want to queue more than one of them together, you're responsible for the callback. Still not perfect, but better than what I have now.
          Last edited by bbruyn; 9 Aug 2011, 15:20.

          Comment


            #6
            You're in the ballpark of the solution now, just a note that server-side you can register on RPCManager to be notified at the end of the transaction. Your DMI code could set up to regen the document at the end of the transaction, with a dirty flag stored as a servletRequest attribute so that only one DataSource actually bothers to regen the document regardless of whether one or more than one DataSource is being updated. Then there's no need for separate operationIds.

            Comment


              #7
              Gee whiz, you're fast. Really appreciate the attention.

              That's just the kind of thing I was looking for. I'll go and have another look through the docs and experiment with it.

              Thanks again.

              Comment

              Working...
              X