>
> Also it makes everything feel stiff and decoupled in a not useful way.
>

> Stiff is the opposite of decoupled. And interfaces are quite useful, but
I'm not really in the mood of explaining why. OOP and IoC already do that
for me.

Nope. Completely wrong :). Stiff means not changeable in terms of thinking
and feel. Its like this once famous code smell attitude.


Are you using test first? Sometimes you sound like a waterfall programmer
(design, implement, verify).


>

> Today I am totally against using interfaces for services as long as you
> control the code and also are the end user of your code. It is simplier
> and clearer.
>

> Now try to write an unit test.

What would be the problem? I always extend the implementation class or mock
methods away. With all these final methods and classes being used when this
abstract stuff was famous 15-10 years ago, it can now considered not that
usefull anymore. Never program defensive unless it can be used to prevent
hard to spot bugs introduced by accidental miss usages.

But lets stop arguing :) It is not an OOP practice to program abstract to
express an implementation detail. And if you start write small methods the
abstractness you might favor in having in interfaces is not as good as the
abstractness that well placed and often encountered method names brings
into the picture.

----

Here is the code and documentation piece why I thought it was not possible
to use concrete service implemenations.

public <T> ServiceBindingOptions bind(Class<T> serviceClass)
    {
        if (serviceClass.isInterface())
        {
            try
            {
                String expectedImplName = serviceClass.getName() + "Impl";

                ClassLoader classLoader = proxyFactory.getClassLoader();

                Class<T> implementationClass = (Class<T>)
classLoader.loadClass(expectedImplName);

                if (!implementationClass.isInterface() &&
serviceClass.isAssignableFrom(implementationClass))
                {
                    return bind(
                            serviceClass, implementationClass);
                }
                throw new
RuntimeException(IOCMessages.noServiceMatchesType(serviceClass));
            } catch (ClassNotFoundException ex)
            {
                throw new RuntimeException(String.format("Could not find
default implementation class %sImpl. Please provide this class, or bind the
service interface to a specific implementation class.",
                        serviceClass.getName()));
            }
        }

        return bind(serviceClass, serviceClass);
    }

See the last line wins. Thought it only works with interfaces and throws a
runtime exception if no implementation is found. The user guide also states:

"Following the convention over configuration principle, the autobuilding of
services can be even less verbose. If a service interface is passed as a
single argument to the bind() method, Tapestry will try to find an
implementation in the same package whose name matches the name of the
service interface followed by the suffix *Impl*."

So I just overlooked the intention of the method after all. But yet again
its about style and cognitive attitude. I for myself find the method above
harder to read as it should and also the implementation does not reflect
once intention about this method, here is a better way to represent the
intention:

public <T> ServiceBindingOptions bind(Class<T> serviceType) {
        if (serviceType.isInterface())
             bindInterface(serviceType, findImplementation(serviceType));
        else
              bindConcrete(serviceType);
}

See easy to understand. Thats the problem when you are used to write short
methods (the best advise I ever got, thanks mr beck :)). The problem also
is that class is used ambitious since Java has interfaces to be thought
about as classes. Java should have better be off using the type ->(Class |
Interface) speaking.

Also remember that every if requires an else or you do something wrong in
first place. If is splitting the program flow and therefore partitionate
the problem space of the method and therefore should particionate the
solution space as well. Therefore write a method. I often see lots of ifs
in tapestry making the source code leaving me with a feel of reading
something written by a slight autistic person (those who do something but
think beyond what they do, so making it harder for a focused reader to
understand).

Well but enought talk. OOP is good and if you read fowler, beck, evans and
martin of the last decade (old, I am) you will see that their style differs
in the way they think. Check out the 10year old discussion of state vs.
behavioural testing around fowler and his mates at thought works. He was
wrong in 'rejecting' behavioural testing as a good way to test. And yet
again those discussion emerge everywhere anytime. So lets stop here.

I write small methods, coupled in the how and decoupled in the what realm.
That's what I do. And from now on, I try to write not about it anymore.
Enough said and we already came to the conclusion that we disagree on that.





2013/10/16 Thiago H de Paula Figueiredo <thiag...@gmail.com>

> Also, see @PostInjection:
>
> /**
>  * Annotation for methods that should be invoked after injection. This
> occurs last: after constructor injection and
>  * after field injection. It should be placed on a <strong>public
> method</strong>. Any return value from the method is
>  * ignored. The order of invocation for classes with multiple marked
> methods (including methods inherited from
>  * super-classes) is not, at this time, defined.
>  * <p/>
>  * Tapestry also honors the {@link javax.annotation.**PostConstruct}
> annotation, and treats it identically to
>  * PostInjection. This is both more flexible than PostConstruct (in that
> methods may have parameters, and multiple methods
>  * may be annotated) but also falls short (Tapestry will only seek out
> public methods).
>  */
> @Target(ElementType.METHOD)
> @Retention(RetentionPolicy.**RUNTIME)
> @Documented
> @UseWith(AnnotationUseContext.**SERVICE)
> public @interface PostInjection
>
> {
> }
>
> --
> Thiago H. de Paula Figueiredo
> Tapestry, Java and Hibernate consultant and developer
> http://machina.com.br
>
> ------------------------------**------------------------------**---------
> To unsubscribe, e-mail: 
> users-unsubscribe@tapestry.**apache.org<users-unsubscr...@tapestry.apache.org>
> For additional commands, e-mail: users-h...@tapestry.apache.org
>
>

Reply via email to