In general dependency on implementation is bad, dependency on interface is
better.  One of the problems we've had with Qpid historically is it become
hard to test as we have dependencies on implementation everywhere.

>From an end user perspective the difference is only replacing

X x  = new X();

with

X x = XFactory.newInstance();

But it makes it a lot easier to properly describe the functionality being
returned. For implementation reasons, the concrete class may have public
methods that are not intended to be exposed to the application programmer
but only to other cooperating classes.  To avoid confusion, and to make it
clear to us the delta between the "shared" API and the API extensions that
we are supporting for the pure Java implementation the interfaces seem like
the right way to go for me.

The idea is that those who need the extension features will still have a
very clear way to get the implementation that provides these, without ever
having to cast.

-- Rob





On 24 January 2013 20:03, Rafael Schloming <r...@alum.mit.edu> wrote:

> On Thu, Jan 24, 2013 at 5:06 AM, Rob Godfrey <rob.j.godf...@gmail.com
> >wrote:
>
> > On 23 January 2013 17:36, Phil Harvey <p...@philharveyonline.com> wrote:
> > >
> > > As part of the Proton JNI work, I would like to remove all calls to
> > > proton-j implementation constructors from "client code".  I intend that
> > > factories will be used instead [1], thereby abstracting away whether
> the
> > > implementation is pure Java or proton-c-via-JNI.
> > >
> > > I'd like to check that folks are happy with me making this change, and
> to
> > > mention a couple of problems I've had.
> > >
> > > In this context, "client code" is anything outside the current
> > > sub-component, where our sub-components are Engine, Codec, Driver,
> > Message
> > > and Messenger, plus each of the contrib modules, and of course third
> > party
> > > code.
> > >
> > > To enforce this abstraction, I am planning to make the constructors of
> > the
> > > affected classes package-private where possible.  I believe that,
> > although
> > > third party projects might already be calling these constructors, it is
> > > acceptable for us to change its public API in this manner while Proton
> is
> > > such a young project.
> > >
> >
> > +1 to all of the above
> >
> > >
> > > Please shout if you disagree with any of the above.
> > >
> > > Now, onto my problem.  I started off with the
> > org.apache.qpid.proton.engine.
> > > impl package, and found that  o.a.q.p.hawtdispatch.impl.AmqpTransport
> > calls
> > > various methods on ConnectionImpl and TransportImpl, so simply using a
> > > Connection and Transport will not work.  I don't know what to do about
> > > this, and would welcome people's opinions.
> > >
> >
> > So, the simplest change would be to change the factories to use
> > covariant return types
> >
> > e.g. EngingFactoryImpl becomes:
> >
> >     @Override
> >     public ConnectionImpl createConnection()
> >     {
> >         return new ConnectionImpl();
> >     }
> >
> >     @Override
> >     public TransportImpl createTransport()
> >     {
> >         return new TransportImpl();
> >     }
> >
> >
> > ... etc
> >
> > Code that requires the extended functionality offered by the pure Java
> > implementation can thus instantiate the desired Factory directly.
> >
>
> What's the point of going through the factory in this scenario rather than
> directly instantiating the classes as Hiram suggests? Is there some class
> of thing the factory would/could do that the constructor can't/shouldn't?
>
> A second refinement might be to actually separate out the interface
> > and implementation within the pure Java implementation so that we have
> > a well defined "extended" Java API.  This interface could then be the
> > return type of the factory.
> >
>
> Maybe I'm misunderstanding, but what's the point of using an interface here
> if you're still locked into the pure Java impl? Are you expecting to swap
> out that impl under some circumstances?
>
> --Rafael
>

Reply via email to