[project lombok] @ConstructorProperties

1,268 views
Skip to first unread message

Jonathan

unread,
May 18, 2010, 10:05:20 AM5/18/10
to Project Lombok
Very cool project. I've been looking for something like Lombok for a
couple of years and was nearly driven to throw a hacked apt plugin
together, but I'm glad someone did it right :)

One minor change that would make the @Data generated constructor even
more useful would be to add the @ConstructorProperties(...) annotation
to the generated constructor if it takes arguments. See this link:

http://java.sun.com/javase/6/docs/api/java/beans/ConstructorProperties.html

The most obvious use of this annotation is that it enables XmlEncoder
to automatically encode immutable POJOs as XML (normally, XmlEncoder
can't do immutable objects without special handling). Right now, I
just override the generated constructor with my own and add the
annotation, but it seems logical for Lombok to include it.

With this change, the example in the link above could be written

@Data
public class Point {
private final int x, y;
}


...which would just be awesome.

--
You received this message because you are subscribed to the Google
Groups group for http://projectlombok.org/

To post to this group, send email to project...@googlegroups.com
To unsubscribe from this group, send email to
project-lombo...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/project-lombok?hl=en

Reinier Zwitserloot

unread,
May 19, 2010, 10:05:44 AM5/19/10
to project...@googlegroups.com
I never knew about @ConstructorProperties. java.beans.ConstructorProperties is everywhere, right? I see no reason not to add it. Could you file an issue?

--Reinier Zwitserloot

Jonathan

unread,
May 19, 2010, 10:49:03 AM5/19/10
to Project Lombok
Of course. I submitted it as issue 122 (it's obviously not a "defect"
but I couldn't see how to change it...)
@ConstructorProperties is new to Java 6.

On May 19, 9:05 am, Reinier Zwitserloot <rein...@zwitserloot.com>
wrote:
> I never knew about @ConstructorProperties. java.beans.ConstructorProperties
> is everywhere, right? I see no reason not to add it. Could you file an
> issue?
>
> --Reinier Zwitserloot
>
> On Tue, May 18, 2010 at 4:05 PM, Jonathan <jonathancros...@hotmail.com>wrote:
>
>
>
> > Very cool project.  I've been looking for something like Lombok for a
> > couple of years and was nearly driven to throw a hacked apt plugin
> > together, but I'm glad someone did it right :)
>
> > One minor change that would make the @Data generated constructor even
> > more useful would be to add the @ConstructorProperties(...) annotation
> > to the generated constructor if it takes arguments.  See this link:
>
> >http://java.sun.com/javase/6/docs/api/java/beans/ConstructorPropertie...
>
> > The most obvious use of this annotation is that it enables XmlEncoder
> > to automatically encode immutable POJOs as XML (normally, XmlEncoder
> > can't do immutable objects without special handling).  Right now, I
> > just override the generated constructor with my own and add the
> > annotation, but it seems logical for Lombok to include it.
>
> > With this change, the example in the link above could be written
>
> > @Data
> > public class Point {
> >       private final int x, y;
> > }
>
> > ...which would just be awesome.
>
> > --
> > You received this message because you are subscribed to the Google
> > Groups group forhttp://projectlombok.org/
>
> > To post to this group, send email to project...@googlegroups.com
> > To unsubscribe from this group, send email to
> > project-lombo...@googlegroups.com<project-lombok%2Bunsu...@googlegroups.com>
> > For more options, visit this group at
> >http://groups.google.com/group/project-lombok?hl=en
>
> --
> You received this message because you are subscribed to the Google
> Groups group forhttp://projectlombok.org/
>
> To post to this group, send email to project...@googlegroups.com
> To unsubscribe from this group, send email to
> project-lombo...@googlegroups.com
> For more options, visit this group athttp://groups.google.com/group/project-lombok?hl=en

Maaartin-1

unread,
Jun 29, 2010, 2:07:11 PM6/29/10
to project...@googlegroups.com
Sometimes it may be necessary to add different annotations to generated
constructors. What I'm interested in is com.google.inject.Inject, which
is to be added to exactly one constructor, probably to the minimal or
maximal one. Users of other DI frameworks may need some other annotation
(I'm not sure about the current state of JSR-330) and currently I see no
way how to specify it without resorting to strings.

Note that a generated constructor is quite useless when you need to work
around the missing annotation (it's possible but hardly shorter than the
constructor itself).

This seems to be a case for a option or even better calling some user's
code (both of which is currently a problem). I'd be quite happy with a
solution for Guice only.

Petr Jiricka

unread,
Jul 1, 2010, 5:48:33 AM7/1/10
to project...@googlegroups.com
On Jun 29, 2010, at 8:07 PM, Maaartin-1 wrote:

> Sometimes it may be necessary to add different annotations to
> generated
> constructors. What I'm interested in is com.google.inject.Inject,
> which
> is to be added to exactly one constructor, probably to the minimal or
> maximal one. Users of other DI frameworks may need some other
> annotation
> (I'm not sure about the current state of JSR-330) and currently I
> see no
> way how to specify it without resorting to strings.

JSR 330 is done, and JBoss Weld 1.0.1 is a stable implementation of
it: http://seamframework.org/Weld. It is already used in GlassFish
3.x, and will be used in the upcoming JBoss 6. I believe it can also
be used standalone with Java SE apps (though I haven't tried).

Petr

>
> Note that a generated constructor is quite useless when you need to
> work
> around the missing annotation (it's possible but hardly shorter than
> the
> constructor itself).
>
> This seems to be a case for a option or even better calling some
> user's
> code (both of which is currently a problem). I'd be quite happy with a
> solution for Guice only.
>

Reinier Zwitserloot

unread,
Jul 19, 2010, 5:54:52 PM7/19/10
to Project Lombok
We've decided to add it after all, with an already deprecated
annotation parameter for the new @RequiredArgsConstructor and
@AllArgsConstructor annotations to disable the generation of it, in
case you need to make sure you can compile it with a JVM 1.5.

See issue #122 on the issue tracker.

It's also in the edge release, which can be downloaded from
http://projectlombok.org/download-edge.html
> > Groups group forhttp://projectlombok.org/

Syntax

unread,
Jul 27, 2010, 12:43:15 AM7/27/10
to Project Lombok
I have hit a bit of a bump as a result of the addition of
ConstructorProperties

My class which is written in Lombok enabled Java is delomboked and
then compiled by GWT (Google Web Toolkit) into javascript.

The GWT compiler does not support the java.beans.ConstructorProperties
annotation so my classes marked with the @Data annotation are no
longer compatible with the GWT compiler.

GWT errors during compilation:
[java] [ERROR] Errors in 'file:/the/path/to/the/file/
MyPresenter.java'
[java] [ERROR] Line 388: java.beans cannot be resolved to a
type
[java] [ERROR] Line 388: The attribute value is undefined
for the annotation type ConstructorProperties

The generated code at this line is:
@java.beans.ConstructorProperties({"var"})
@java.lang.SuppressWarnings("all")
public Context(final int var) {
this.var= var;
}

The source is:
@Data
public static class Context{
private final int var;
}

Any way that I can disable the java.beans.ConstructorProperties auto
generation with @Data?


On Jul 20, 5:54 am, Reinier Zwitserloot <reini...@gmail.com> wrote:
> We've decided to add it after all, with an already deprecated
> annotation parameter for the new @RequiredArgsConstructor and
> @AllArgsConstructor annotations to disable the generation of it, in
> case you need to make sure you can compile it with a JVM 1.5.
>
> See issue #122 on the issue tracker.
>
> It's also in the edge release, which can be downloaded fromhttp://projectlombok.org/download-edge.html

Roel Spilker

unread,
Jul 27, 2010, 9:46:28 AM7/27/10
to project...@googlegroups.com
Yes, you can. In addition to the @Data, you need to specify @RequiredArgsConstructor(suppressConstructorProperties=true)

Can you let us know if that works?

We might consider extending the @Data annotation with this parameter in the future. But no promises...

Roel

> -----Oorspronkelijk bericht-----
> Van: j.dix...@gmail.com
> [mailto:project...@googlegroups.com] Namens Syntax
> Verzonden: 27 July 2010 06:43
> Aan: Project Lombok
> Onderwerp: [project lombok] Re: @ConstructorProperties

> Google Groups group for http://projectlombok.org/

Syntax

unread,
Jul 28, 2010, 9:48:44 PM7/28/10
to Project Lombok
Thank you! this works as expected; however if the depreciated
suppressConstructorProperties annotation property was to be removed it
would break (obviously).

Why was suppressConstructorProperties depreciated upon addition?

On Jul 27, 9:46 pm, Roel Spilker <R.Spil...@topdesk.com> wrote:
> Yes, you can. In addition to the @Data, you need to specify @RequiredArgsConstructor(suppressConstructorProperties=true)
>
> Can you let us know if that works?
>
> We might consider extending the @Data annotation with this parameter in the future. But no promises...
>
> Roel
>
> > -----Oorspronkelijk bericht-----
> > Van: j.dixon...@gmail.com

Reinier Zwitserloot

unread,
Jul 28, 2010, 9:55:46 PM7/28/10
to project...@googlegroups.com
The javadoc explains why: http://projectlombok.org/api/index.html

We may change our mind because of GWT, but we also may not; having to pay attention to GWT is rather difficult as the lombok project grows; half the classes a true java can rely upon are just missing. Perhaps if we add more features that won't even work in GWT, we'll solve this problem in a different way; add a GWT option to delombok, which specifically disables and rejiggers how certain lombok handlers work. The one (and so far only) thing that would do if we were to create such a feature today is omit the @ConstructorProperties annotations.

 --Reinier Zwitserloot



Groups group for http://projectlombok.org/

Syntax

unread,
Jul 28, 2010, 10:00:13 PM7/28/10
to Project Lombok
suppressConstructorProperties
Deprecated. Java 1.5 has already been end-of-lifed. As java
1.5 loses ground this method will eventually be removed.

This raises an interesting concern; going forwards. Perhaps GWT will
add support for @ConstructorProperties to their compiler. I will post
a comment on the GWT group to discuss this further. It would be nice
if the annotation could be used in the GWT RPC to avoid the need to
provide no-args constructor for RPC enabled classes.

Reinier Zwitserloot

unread,
Jul 29, 2010, 1:01:30 AM7/29/10
to Project Lombok
All they really need to do is toss ConstructorProperties in the set of
classes you can legally use in GWT source. It would do absolutely
nothing whatsoever; annotations don't survive the GWT process. It's
just there as a token effort to allow java code that is used not just
as food for the GWT compiler, but also used in other java projects.
For example, @Override is usable in GWT, even though it does jack*.

Possibly GWT is officially still on Java 1.5. Either way, if you get
the GWT team to add ConstructorProperties, that'd be fantastic!


*) It's been a while since I last did anything with GWT, so maybe
things have changed since then.

Keith Haber

unread,
Jul 29, 2010, 9:09:50 PM7/29/10
to Project Lombok
GWT has a mechanism for creating your own JRE emulation classes called
"super-source."

http://code.google.com/webtoolkit/doc/latest/DevGuideOrganizingProjects.html#DevGuideModuleXml

(Scroll down to the section "Overriding one package implementation
with another" or just search for "super-source".)

I haven't tried this myself, but it seems likely that you can use this
to add GWT compatibility for the @ConstructorProperties annotation to
your project without having to hope the GWT developers add it in a
future release.

Hope this helps. Good luck.

Keith

Syntax

unread,
Aug 5, 2010, 4:08:20 AM8/5/10
to Project Lombok
Thank you for the reference to super-source, that is very helpful!

Given the use of super-source ConstructorProperties should not be a
problem anymore.

On Jul 30, 9:09 am, Keith Haber <kjha...@gmail.com> wrote:
> GWT has a mechanism for creating your own JRE emulation classes called
> "super-source."
>
>    http://code.google.com/webtoolkit/doc/latest/DevGuideOrganizingProjec...

Roel Spilker

unread,
Aug 5, 2010, 5:15:19 AM8/5/10
to project...@googlegroups.com
Hi Syntax,

Can you mail the things you did to the mailing list. I'd really like other lombok users the benefit from your findings. We could maybe also put it on the yet to be created FAQ.

Roel

> -----Oorspronkelijk bericht-----
> Van: j.dix...@gmail.com
> [mailto:project...@googlegroups.com] Namens Syntax
> Verzonden: 05 August 2010 10:08


> Aan: Project Lombok
> Onderwerp: [project lombok] Re: @ConstructorProperties
>

> Google Groups group for http://projectlombok.org/

Syntax

unread,
Aug 5, 2010, 11:34:26 AM8/5/10
to Project Lombok
Off topic: Thanks to Keith for his suggestion (super source) & Thanks
to the Lombok team for their great work!


Q: Can I use Lombok with GWT? The ConstructorProperties annotation is
not supported by the GWT compiler.
A: Using GWT's super-source behavior (http://code.google.com/
webtoolkit/doc/latest/
DevGuideOrganizingProjects.html#DevGuideModuleXml) you can provide
your own copy of @ConstructorProperties for the GWT compiler.


1) Create your Lombok annotated class
@Data
public class Greeting {
// NB: My class is immutable; If you want to use GWT RPC with
immutable classes you need to write a custom field serializer.
// Otherwise make this field non-final and update your
lombok annotations
private final String greeting;
}


2) Create your JRE emulation package. If your GWT module package is
com.example.lombok then your jre emulation package is
com.example.lombok.jre


3) Defining your ConstructorProperties class
i) Create the com.example.lombok.jre.java.beans package
ii) Copy the sun ConstructorProperties class into this package
ii) NB: You should not have to make any changes, it is a simple
annotation and compiles as-is. Especially do not update the package;
even though java.beans gives a compiler warnings in an IDE (such as
Eclipse). You should exclude the contents of your JRE package from
your Eclipse build path to disable the error.


4) Define the super-type in your GWT module (GWTLombokDemo.gwt.xml)
<?xml version="1.0" encoding="UTF-8"?>
<module rename-to='gwtlombok'>
<inherits name='com.google.gwt.user.User'/>
<inherits name='com.google.gwt.user.theme.standard.Standard'/>
<entry-point class='com.example.lombok.client.GWTLombok'/>

<source path='client'/>
<source path='shared'/>

<super-source path='jre'/>
</module>


5) Use delombok and the GWT compiler to create your war artifact
(servlet)
<?xml version='1.0' encoding='UTF-8'?>
<project name="GWTLombokDemo" default="build">
<target name="build">
<!-- Clean up -->
<delete file="target/GWTLombokDemo.war" />
<!-- Build -->
<antcall target="lombok-compile" />
<antcall target="gwt-compile" />
<antcall target="zip-webapp" />
</target>

<target name="lombok-compile" description="Delombok the code;
replaces annotations with standard java code">
<taskdef classname="lombok.delombok.ant.DelombokTask"
classpath="lib/lombok.jar" name="delombok" />
<delombok verbose="true" encoding="UTF-8" to="src-gen" from="src" /
>
</target>

<target name="gwt-compile" description="Convert the standard java
code into javascript for the browser">
<property name="gwt-home" value = "E:/eclipse-java-helios-win32-
x86_64/eclipse/plugins/com.google.gwt.eclipse.sdkbundle.
2.0.4_2.0.4.v201006301309/gwt-2.0.4" />
<java classname="com.google.gwt.dev.Compiler" failonerror="true"
fork="true">
<arg value="-style" />
<arg value="PRETTY" />
<arg value="com.example.lombok.GWTLombokDemo" />
<classpath path="src-gen;
${gwt-home}/gwt-dev.jar;
${gwt-home}/gwt-user.jar;
war/WEB-INF/lib/gwt-servlet.jar" />
</java>
</target>

<target name="zip-webapp" description="Build the servlet">
<zip zipfile="target/GWTLombokDemo.war" whenempty="create">
<fileset dir="war/">
</fileset>
</zip>
</target>
</project>


6) The result of the above is
Compilation output:
Buildfile: E:\workspaces\GWTlocal\GWTLombok\build.xml
build:
[delete] Deleting: E:\workspaces\GWTlocal\GWTLombok\target
\GWTLombokDemo.war
lombok-compile:
[delombok] File: com\example\lombok\client\Greeting.java [delombok-
ed]
[delombok] File: com\example\lombok\client\GreetingService.java
[unchanged]
[delombok] File: com\example\lombok\client\GreetingServiceAsync.java
[unchanged]
[delombok] File: com\example\lombok\client
\Greeting_CustomFieldSerializer.java [unchanged]
[delombok] File: com\example\lombok\client\GWTLombok.java [unchanged]
[delombok] Copying resource file: com\example\lombok
\GWTLombok.gwt.xml
[delombok] File: com\example\lombok\jre\java\beans
\ConstructorProperties.java [unchanged]
[delombok] File: com\example\lombok\server\GreetingServiceImpl.java
[unchanged]
gwt-compile:
[java] Compiling module com.example.lombok.GWTLombok
[java] Compiling 6 permutations
[java] Compiling permutation 0...
[java] Compiling permutation 1...
[java] Compiling permutation 2...
[java] Compiling permutation 3...
[java] Compiling permutation 4...
[java] Compiling permutation 5...
[java] Compile of permutations succeeded
[java] Linking into E:workspaces\GWTlocal\GWTLombok\war
\gwtlombok.
[java] Link succeeded
[java] Compilation succeeded -- 24.239s
zip-webapp:
[zip] Building zip: E:workspaces\GWTlocal\GWTLombok\target
\GWTLombokDemo.war
BUILD SUCCESSFUL
Total time: 26 seconds


Greeting.Java (after delombok)
// Generated by delombok at Thu Aug 05 23:09:16 WST 2010
package com.example.lombok.client;

public class Greeting {
private final String greeting;

@java.beans.ConstructorProperties({"greeting"})
@java.lang.SuppressWarnings("all")
public Greeting(final String greeting) {
this.greeting = greeting;
}

@java.lang.SuppressWarnings("all")
public String getGreeting() {
return this.greeting;
}

@java.lang.Override
@java.lang.SuppressWarnings("all")
public boolean equals(final java.lang.Object o) {
if (o == this) return true;
if (o == null) return false;
if (o.getClass() != this.getClass()) return false;
final Greeting other = (Greeting)o;
if (this.getGreeting() == null ? other.getGreeting() != null : !
this.getGreeting().equals(other.getGreeting())) return false;
return true;
}

@java.lang.Override
@java.lang.SuppressWarnings("all")
public int hashCode() {
final int PRIME = 31;
int result = 1;
result = result * PRIME + (this.getGreeting() == null ? 0 :
this.getGreeting().hashCode());
return result;
}

@java.lang.Override
@java.lang.SuppressWarnings("all")
public java.lang.String toString() {
return "Greeting(greeting=" + this.getGreeting() + ")";
}
}


The war file produced by GWT is your servlet, drop it into Tomcat/
Jetty or any other servlet container to run it; alternatively if you
configure Eclipse to use your delomboked source instead of lombok
annotated source on its build path you can use development mode in
Eclipse to run your delomboked code.

I hope this helps someone in the future; If I have missed anything or
you have any questions please don't hesitate to ask :)


On Aug 5, 5:15 pm, Roel Spilker <R.Spil...@topdesk.com> wrote:
> Hi Syntax,
>
> Can you mail the things you did to the mailing list. I'd really like other lombok users the benefit from your findings. We could maybe also put it on the yet to be created FAQ.
>
> Roel
>
>
>
>
>
> > -----Oorspronkelijk bericht-----
> > Google Groups group forhttp://projectlombok.org/

Syntax

unread,
Aug 5, 2010, 11:36:38 AM8/5/10
to Project Lombok
Google groups has massacred the formatting of my last post. I
apologise if it looks a little messed up, I actually worked quite hard
trying to keep it readable.
> ...
>
> read more »

Roel Spilker

unread,
Aug 5, 2010, 11:38:22 AM8/5/10
to project...@googlegroups.com
That's great. Now people can google it :-)

> Groups group for http://projectlombok.org/

Reply all
Reply to author
Forward
0 new messages