What model can be used for partial success when calling a method that invokes a proxy to aggregate data from multiple endpoints?

As an example, let's say I have the following class:

public class FruitBasket {
    private List<Apple> apples;
    private List<Orange> oranges;
    // getters and setters...
}

      

Now, suppose I also have a method somewhere that receives FruitBasket

.

public FruitBasket getFruitBasket() {
    //...
}

      

Now suppose the method getFruitBasket

combines data from two different sources that are accessed through a proxy. For example, there is a server AppleTree

to get objects of a type Apple

, and a server OrangeTree

to get objects of a type Orange

, and they are accessed through a proxy named OrchardGate

. It is for this reason that I want to write one getFruitBasket

method, not getApples

u getOranges

, to minimize the latency when called from my application to OrchardGate

.

In the case where the objects Apple

and objects Orange

were received successfully, no problem, I can just return FruitBasket

. In the event that there is an access issue either internally OrchardGate

or both in AppleTree

and out OrangeTree

, I can also handle that by throwing out the child RuntimeException

(or even Exception

if I add it to the sentence getFruitBasket

throws

if needed).

However, what happens in the event of partial success? What happens if I access the server AppleTree

, but I cannot access the server OrangeTree

due to some kind of transport problem between OrchardGate

and OrangeTree

?

As far as I can see, there are only four options and everything is absolutely terrible:

  • I could make an exception, which means that even if the objects Apple

    were retrieved successfully, FruitBasket

    there will be no return due to missing objects Orange

    .
  • I could ignore the error and just return an empty list of objects Orange

    . This would mean that the client would not be able to see an error when looking for objects Orange

    , instead it would look like OrangeTree

    there were no objects on the server Orange

    .
  • I could add a field to FruitBasket

    called errorCodes

    , which contains a list of errors that occur when accessing FruitBasket

    . Then I could add an error code to this list titled PATH_FLOODED

    to denote the error that I am facing. However, this field errorCodes

    does not belong to the domain object at all FruitBasket

    . This field is not relevant to FruitBasket

    , but only in the transaction to be retrieved FruitBasket

    .
  • I could have made an exception, but attached an incomplete one FruitBasket

    to the exception. This is also awful, because exceptions should only contain error information - they should not contain fruit baskets.

I have documented this problem in Java, but I am assuming this problem is spread across multiple languages. I was very surprised not to discuss this. Is there a standard pattern for writing methods that can return partial success? Or is there something I missed?

+3


source to share


3 answers


I think you need another method that can be called loadFruitBasket()

that downloads Apple and Orange objects from the server. Since you need to access the servers to get apples and oranges, you can set boolean

on the right and then true

when access was successful or false

after that it was unsuccessful. Then, before using, getFruitBasket()

you can specify the class that loaded the FruitBasket if it is hasApples()

or hasOranges()

. with this you don't need to access the servers that many times and can display diffreent erros.



+1


source


I don't see anything wrong with this approach.

I could add a field to the FruitBasket called errorCodes that contains a list of errors that are thrown when accessing the FruitBasket. Then I could add an error code to this list called PATH_FLOODED to indicate the error I was facing. However, this errorCodes field does not belong to the FruitBasket domain object at all. This field does not apply to FruitBasket, but only in a transaction to retrieve FruitBasket



FruitBasketTransaction {
  FruitBasket fruitBasket;
  List<Error> errorCodes;

  // ... constructor and getters
}

public FruitBasketTransaction getFruitBasket() {
  // ...
}

// In your application somewhere
FruitBasketTransaction transaction = getFruitBasketTransaction();
if contains(transaction.errorCodes, APPLE_ERROR) {
  // ... tell the user
}
if contains(transaction.errorCodes, ORANGE_ERROR) {
  // ... tell the user
}

giveFruitToUser(transaction.getFruitBasket());

      

+1


source


A partial result, a snapshot in time . The same applies to a translation system that collects various online dictionaries and services that may or may not be available. Generally with search / abort controls.

In general, there is a minimum threshold at which you make the results available, say one agent provides their results.

The sample is not about results, but about managing search tasks in the process, providing results. It also requires a bit of change management. When using a partial result to create a fruit basket at a later stage, you may want to redo the basket with more options once it becomes available.

A provides a time string : service

data packages[]

`Service A:   (start) [pack 0] (t1) [pack 1] (t2) [pack 2] (t3) {running}
`Service B:   (start) (t1) [pack 3] (t2) (t3) [pack 4] (t4) {ended}

      

Which metaphor to use depends a little: project management, for example, or in the case of production.

0


source







All Articles