Yes, the results are guaranteed to be the same order of the requests.

However, the first one that fails will cause the entire multi to be
aborted. So, if say the first one fails, then you won't know if the others
after that would have failed.

I'd suggest doing something entire different, such as (pseudo-code):

List<Ops> ops
for(path in paths)
  if (!Exists(path)) {
    ops.add(Op.Create(path));
 }

Does that make sense? I'm suggesting you use the non-multi code to check if
it exists or not. If not, you can append any ops related to that path into
your ops list.


On Thu, Mar 1, 2012 at 11:14 PM, Shelley, Ryan <ryan.shel...@disney.com>wrote:

> Right, I did this:
>
> (psuedo-code)
> List<Ops> ops
> For(path in paths)
>  ops.add( Op.check(path, -1) )
> EndFor
>
> List<OpResult> Results = Zk.multi(ops)
>
> This causes an exception to be thrown on the first path that doesn't
> exist. It doesn't return back a list with one OpResult flagged with an
> error. I was under the impression I'd get back a bunch of OpResult objects
> with flags of error, or otherwise, and then I could build another list of
> operations to create what's needed (which, even if it did work, the
> CheckResult object doesn't include the path, so I'm just hoping the
> results are in the same order as the operations were listed in, as I have
> to infer the path I'll need to build from the position of the OpResult in
> the list).
>
>
>
> On 3/1/12 3:05 PM, "Ted Dunning" <ted.dunn...@gmail.com> wrote:
>
> >No. I meant one call full of checks and a second call with any necessary
> >creates.
> >
> >Sent from my iPhone
> >
> >On Mar 1, 2012, at 11:17 AM, "Shelley, Ryan" <ryan.shel...@disney.com>
> >wrote:
> >
> >> Ok, I tried this with the Op.create and found that it will throw a
> >> KeeperException on the first path that doesn't exist. It doesn't return
> >> back an OpResult with an "error" type. I can still use this, and just
> >> catch the exception and create the node in the exception, but I was
> >>under
> >> the impression that I could do this in two trips. One trip to get back a
> >> list of OpResults from the check that would inform me if the path
> >>existed
> >> or not, and a second trip to create all the paths that don't exist (and
> >>as
> >> a note, the CheckResult object doesn't include the path, so I have to
> >> infer it from the order of my original list of paths used to create the
> >> multi-check).
> >>
> >> -Ryan
> >>
> >> On 2/29/12 7:16 PM, "Ted Dunning" <ted.dunn...@gmail.com> wrote:
> >>
> >>> On Wed, Feb 29, 2012 at 7:04 PM, Marshall McMullen <
> >>> marshall.mcmul...@gmail.com> wrote:
> >>>
> >>>> Yes, Ted's right. The multi has to fail as that's part of the contract
> >>>> it
> >>>> guarantees.
> >>>>
> >>>> The only thing you could do, which will significantly narrow the race
> >>>> condition, is as you're *building *the multi, check if the path
> >>>>already
> >>>> exists. If so, then don't add the create op for that path into the
> >>>> multi.
> >>>> Of course this may not work in every situation, but we use that
> >>>> approach in
> >>>> many code paths and it works well.
> >>>>
> >>>
> >>> Another approach is to compose one multi with Op.exists() for each
> >>>level
> >>> so
> >>> that you find everything you need, then create another with the correct
> >>> Op.create() operations.  That gets the problem down to two server
> >>> round-trips but still has the race condition.
> >>
>
>

Reply via email to