I am puzzled by the following design of the method:
Map<String, BigDecimal> foo(Parameter p){ ... }
This method takes a complex Parameter and returns a map name -> value. In many cases, based on certain underlying calues of the parameter, the resulting map will be the same, furthermore, there are only a few different maps that can ever be returned, so these will be cached. However, when the map is initially created, there can potentially be different types of errors – certain String value might be incorrect, certain value might be < 0 and therefore should be skipped etc. These errors might be of different nature then. I would like to return this map, but also be able to flag these errros, ideally only once, when the initialization of each map is performed. What would be the cleanest way to do this?
This is a fairly unusual requirement – if you can generate a valid result in spite of the internal errors, you should probably return that result; and if not, throw the exception.
But if you do want to return this additional information, then I see you have broadly two options available:
foo(), accumulate any internal errors in some field. Expose an additionalgetFooErrors()method to allow callers to inspect what happened. And possibly agetFooErrorSeverity()method if you need to tell callers the degree to which these errors impacted on the quality of your result map.Immutable/functional. Return the information from above (exceptions and maybe a severity score) as part of your method. Instead of returning a
Map<String, BigDecimal>, return an object which contains the map, as well as the exception details. E.g:The first approach is similar to how
java.io.PrintWriterworks in the standard library. It swallows any IOExceptions encountered by its I/O methods, and exposes a checkError() method to allow callers to see if the writer encountered any exceptions.I prefer the second because it doesn’t impact thread-safety, it gives the client all the information up-front, and it’s neatly coupled with the scope where the error was encountered.