On Tue, Dec 17, 2013 at 1:11 AM, Daniel Bünzli wrote: * I used an 'a result = [ `Error | `Ok of 'a ] rather than an exception > 1. The `Error case doesn't give any information about what the error is, so this is equivalent to 'a option. I recommend 'a option as a return type only when there can be only a single error. For example, I think it's okay for Map.find to return None since it clearly means the item was not found. 2. If you have `Error carry a value, you have Core's ('ok, 'err) Result.t (ignoring for the moment that you have polymorphic variants, which is good). Then the question becomes what will 'err be in each specific case. The important criteria is that the types you choose must unify, or else it will be very difficult to compose functions into bigger programs. One option is to always make 'err = string. This is lightweight, let's you provide informative messages, and simplifies your type to contain a single type variable. This is similar to Core's Or_error, but instead of string, they define Error.t which has some other benefits. 3. If you want to enable robust error handling, you get tempted to define 'err as a more specialized type. Adding the criteria that each instance of 'err must unify, you end up using polymorphic variants, e.g. `Error of [> `not_found | `timed_out ]. We used this approach in some production code, but I'm starting to feel it is not worth the hassle. It is very hard to maintain. 4. So we're back to option 2, which doesn't allow robust error handling because the error type isn't rich enough. Thus, the question is why is it any better than raising exceptions. It is not making your code any safer because you're forced to program monadically, where you systematically ignore every error, just like if all your functions were raising exceptions. In the end, the only difference between option 2 and exception-ful style is that your type signature documents the possibility of an error. It only says that "some" error occurs. You still have to define what this error is about in your text documentation. In exchange for this, you've complicated all of your type signatures and forced monadic programming everywhere. In the end, raising exceptions seems fine to me. You can define multiple exceptions to increase the chance that specific errors can be handled when needed. Disclaimer: my opinion about this changes every day. Other comments: * What is the T in Tsdl? I don't see any T on the SDL website. * Your type `barray` would be better named `big_array`. In this case, `bigarray` would also be okay since it would be consistent with the module Bigarray to which this type refers. I don't like random single letters in names, which is also a problem in your Vg and Gg project names. Thanks for all your great libraries!