On Mon, 02 Jul 2012 22:13:18 +0200, Reinier Zwitserloot
<
rein...@gmail.com> wrote:
> We'd like to work on the first kind: val, @Data and friends, @Cleanup.
> We'd
> like to work less on features of the second kind: @Getter(lazy=true),
> @Synchronized, @Delegate. As cool as they are, lack of use means they
> aren't as stable as they ought to be.
Are you sure your metric is ok? Because, for instance:
1. I'm using @Delegate a lot, but it's ok so I've never filed an issue on
it
2. I could numerically use @Delegate much less than @Getter for obvious
reasons, since they apply to different granularity in the code.
Nevertheless @Delegate saves to me much more code and annoyances than
@Getter.
Just to make another quick example, a couple of days ago I had to patch
Spring so the property to point to XML beans files is not hardwired in
web.xml, but it's computed at runtime in function of a system property. To
accomplish that I had to subclass ContextLoaderListener so I can feed it a
patched property "contextConfigLocation". Unfortunately, it doesn't expose
a setter method for that, so I have to "fool" it by
passing a decorator of ServletContext, from which it reads the property by
means of getInitParameter(). ServletContext can't be subclassed, since
it's instantiated by the webcontainer: only decorating it can work.
For the curious one, code is below (ok, I should blog about it).
This pattern of customization things that doens't expose a setter method
happens relatively often and the solution is to provide a decorator of the
original object exposing the property / behaviour that I want to change.
Now, @Delegate is not only invaluable because of the code it saves me, but
above all it's a time saver whem I'm prototyping (often different
alternate solutions because at the beginning I don't have a clear path in
my mind).
Probably to better measure popularity of a Lombok annotation we should set
up a poll (with well designed questions).
@RequiredArgsConstructor
class DynamicConfigLocationServletContext implements ServletContext {
public static final String CONTEXT_CONFIG_LOCATION =
"contextConfigLocation";
interface Exclusions {
public String getInitParameter(String string);
}
@Nonnull @Delegate(excludes=Exclusions.class)
private final ServletContext delegate;
@Nonnull
private final String contextConfigLocation;
@Override
public String getInitParameter(final @Nonnull String name) {
return name.equals(CONTEXT_CONFIG_LOCATION) ? contextConfigLocation
:
delegate.getInitParameter(name);
}
}
public class DynamicConfigLocationContextLoaderListener extends
ContextLoaderListener {
@Override
public void contextInitialized(ServletContextEvent event)
final ServletContext servletContext = event.getServletContext();
final String contextConfigLocation =
servletContext.getInitParameter(DynamicConfigLocationServletContext.CONTEXT_CONFIG_LOCATION)
+ ",classpath*:/beans/*" + getCustomization() +
"*Beans.xml";
final ServletContext servletContextDelegate = new
DynamicConfigLocationServletContext(servletContext, contextConfigLocation);
super.contextInitialized(new
ServletContextEvent(servletContextDelegate));
}
@Nonnull
private String getCustomization() {
...
}
}
--
Fabrizio Giudici - Java Architect, Project Manager
Tidalwave s.a.s. - "We make Java work. Everywhere."
fabrizio...@tidalwave.it
http://tidalwave.it -
http://fabriziogiudici.it