Can AutoBeanFactory encode List<BeanObject> ???

295 views
Skip to first unread message

Transplant

unread,
Jan 27, 2012, 4:43:37 PM1/27/12
to Google Web Toolkit
I can't seem to figure out how to tell AutoBeanFactory to encode/
decode lists of objects. I have a simple bean object with string-
valued properties, and another bean object which has a list of the
first object. When I try to encode, I get a NullPointerException from
the AutoBeanCodex implementation. From the documentation in the wiki
(http://code.google.com/p/google-web-toolkit/wiki/AutoBean) it appears
that this is supposed to work, but what am I doing wrong?

Here is my test case:

public class BeanTest extends GWTTestCase {

interface MyFactory extends AutoBeanFactory {
AutoBean<Thing> thing ();
AutoBean<Bunch> bunch ();
}
interface Thing { // simple bean with one string-valued property
String getName ();
}
interface Bunch { // Simple bean with one List<Thing> valued property
List<Thing> getThings ();
}
public void testThing () {
Thing t1 = new Thing() { public String getName() { return
"one"; } };
Thing t2 = new Thing () { public String getName () { return
"two"; } };

MyFactory fact = GWT.create(MyFactory.class);
AutoBean<Thing> encodeBean = fact.create (Thing.class, t1);
String json = AutoBeanCodex.encode(encodeBean).getPayload();
System.out.println ("payload: " + json);

final Thing [] pair = { t1, t2 };
Bunch b = new Bunch() { public List<Thing> getThings() { return
Arrays.asList(pair); } };
AutoBean<Bunch> bunchBean = fact.create (Bunch.class, b);

// The following throws NullPointerException :(
json = AutoBeanCodex.encode(bunchBean).getPayload();
System.out.println ("payload: " + json);
}
}

Colin Alworth

unread,
Jan 28, 2012, 6:30:07 PM1/28/12
to google-we...@googlegroups.com
You are on the right track for this, but you need to wrap each model with an autobean: encodeBean.as() is not the same instance as t1, even though it is obtained from the autobean that wraps t1. You need to wrap each instance, and include the wrapped instance in the eventual tree to be encoded.

The list may also have trouble, it has been a while since I tried to build something like this out. The approach I've taken, rather than manually wrap the whole tree, was to wrap the root object, and use an autobean visitor to walk the rest of the properties, wrapping and continuing further down the tree. I found the code in com.google.web.bindery.requestfactory.shared.impl.AbstractRequestContext.cloneBeanAndCollections(AutoBean<T>) to be helpful as a guide when copying autobeans, along with other aspects of the internals of RequestFactory, which is based on Autobeans for transport.

Transplant

unread,
Jan 30, 2012, 5:54:13 PM1/30/12
to Google Web Toolkit
Thanks Colin,
That explains everything - my mistake was that I thought the
framework would automagically use the MyFactory interface to figure
out how to encode Lists of MyFactory objects. I still feel that it
should be able to do that, but clearly it doesn't. For anyone else who
gets confused by this - here is the working version of the test case:

public void testThing () {
Thing t1 = new Thing() { public String getName()
{ return
"one"; } };
Thing t2 = new Thing () { public String getName ()
{ return
"two"; } };
MyFactory fact = GWT.create(MyFactory.class);
AutoBean<Thing> t1Bean = fact.create (Thing.class,
t1);
AutoBean<Thing> t2Bean = fact.create (Thing.class,
t2);
String json =
AutoBeanCodex.encode(t1Bean).getPayload();
System.out.println ("payload: " + json);
final Thing [] pair = { t1Bean.as(), t2Bean.as() }; //
putting bean-wrapped objects in the list works.
Bunch b = new Bunch() { public List<Thing> getThings()
{ return
Arrays.asList(pair); } };
AutoBean<Bunch> bunchBean = fact.create (Bunch.class,
b);
// The following throws NullPointerException :(
json = AutoBeanCodex.encode(bunchBean).getPayload();
System.out.println ("payload: " + json);
}

On Jan 28, 3:30 pm, Colin Alworth <niloc...@gmail.com> wrote:
> You are on the right track for this, but you need to wrap each model with
> an autobean: encodeBean.as() is not the same instance as t1, even though it
> is obtained from the autobean that wraps t1. You need to wrap each
> instance, and include the wrapped instance in the eventual tree to be
> encoded.
>
> The list may also have trouble, it has been a while since I tried to build
> something like this out. The approach I've taken, rather than manually wrap
> the whole tree, was to wrap the root object, and use an autobean visitor to
> walk the rest of the properties, wrapping and continuing further down the
> tree. I found the code in
> com.google.web.bindery.requestfactory.shared.impl.AbstractRequestContext.cl oneBeanAndCollections(AutoBean<T>)
Reply all
Reply to author
Forward
0 new messages