On Fri, Aug 2, 2013 at 4:44 AM, Phil Harvey <p...@philharveyonline.com>wrote:

> I agree that o.a.q.p.Proton is, overall, an improvement.  I was partly
> responsible for creating the ProtonFactoryLoader and XXXFactory classes,
> and acknowledge that they make life too hard for the user.
> This was a result of trying to meet the following design goals:
> 1. User code should not need to have a compile-time dependency on any
> proton-c/j/jni classes.  Given our current separation of the proton-api
> from the proton-impl/proton-jni modules, it means user code should only
> depend on proton-api at compile-time.
> 2. Classes from the various "top level packages", such as engine, messenger
> etc, should be kept separate unless they really need to be together.
> I still believe in goal 1 (though this will be discussed at greater length
> on the related thread [1]), but am relaxed about item 2.

Thanks for describing the goals, it's helpful to have them written down. I
personally don't feel that the Proton class is violating (2) in an
important way so long as engine and messenger remain otherwise unentwined.

I generally agree with (1) also, however I think it could use some further
refinement. At the root of (1) is the desire to make it clear and obvious
to developers if/when they are depending on the characteristics of a given
implementation rather than on a more abstracted interface. Probably the
most common example of this sort of thing within Java would be typical
collections usage of interface/impl splits, e.g.:

    List foo = new ArrayList();
    ArrayList bar = new ArrayList();
    LinkedList baz = new LinkedList();

The suggested pattern for the Proton class would be following this pattern

    Proton p = new ProtonJ();
    ProtonJ pj = new ProtonJ();
    ProtonC pc = new ProtonC();

Now this pattern of course doesn't really speak to classpaths at all. The
classpath issue is really entirely orthogonal to the interface/impl
distinction. Right now we have separate classpaths, but a muddled
interface/impl distinction since the impl jar adds new interfaces into
packages belonging to the API jar, and the API jar has stuff in it that is
really part of a specific impl. Likewise, you can have a clear
interface/impl distinctions within a single jar as is the case with java

I'd argue that the classpath thing is really a distinct goal/requirement
and is really more about a discovery mechanism for independent or third
party implementations. I don't personally feel that this is a necessary
requirement for us at this point, but I'm fairly relaxed if other people
would like to support it.

Given the above refinement of (1) into (1a) interface/impl split and (1b)
independently implementable API, I would find it a bit odd to put the
ProtonJ/ProtonC classes into the API package since that would introduce a
dependency from the API package back to those impls (even if its only a
runtime dependency) and would effectively give those impls an elevated
position which in some sense is fine, but also seems contrary to the
independently implementable notion in the first place. It seems like what
you'd want in the API package is purely a generic discovery mechanism that
would work for any implementation.

As I said above, I don't feel like such a discovery mechanism is really a
requirement for us right now. I think actually having a complicated
discovery/factory pattern is in some ways detrimental as it creates a
barrier to entry for all users when most don't care about the flexibility
it offers (at least right now) and if they do care about that flexibility
it is easy enough for them to build their own. In fact modulo exception
handling it is really just one extra line of code:

    Class impl = Class.forName(System.getProperty("blah"));
    Proton p = (Proton) impl.newInstance();

So I'd personally say go for the simple interface/impl split pattern that
everyone knows and is used to and don't worry about a generic discovery
mechanism until we actually have enough implementations for it to be


Reply via email to