Revision: 10560
Author: [email protected]
Date: Tue Aug 23 10:48:49 2011
Log: Implements * globbing for RequestFactory with(), the simpler half
of
the proposal in
http://code.google.com/p/google-web-toolkit/issues/detail?id=6697
Also fixes bugs exposed in using null members in collections
Review at http://gwt-code-reviews.appspot.com/1520808
Review by: [email protected]
http://code.google.com/p/google-web-toolkit/source/detail?r=10560
Modified:
/trunk/user/src/com/google/web/bindery/requestfactory/server/Resolver.java
/trunk/user/src/com/google/web/bindery/requestfactory/shared/impl/ProxySerializerImpl.java
/trunk/user/test/com/google/web/bindery/requestfactory/gwt/client/RequestFactoryPolymorphicTest.java
/trunk/user/test/com/google/web/bindery/requestfactory/gwt/client/RequestFactoryTest.java
/trunk/user/test/com/google/web/bindery/requestfactory/server/SimpleFoo.java
/trunk/user/test/com/google/web/bindery/requestfactory/shared/SimpleFooRequest.java
=======================================
---
/trunk/user/src/com/google/web/bindery/requestfactory/server/Resolver.java
Fri Jun 17 03:15:41 2011
+++
/trunk/user/src/com/google/web/bindery/requestfactory/server/Resolver.java
Tue Aug 23 10:48:49 2011
@@ -198,6 +198,11 @@
* not been previously resolved for the next batch of work.
*/
public void addPaths(String prefix, Collection<String> requestedPaths)
{
+ if (clientObject == null) {
+ // No point trying to follow paths past a null value
+ return;
+ }
+
// Identity comparison intentional
if (toResolve == EMPTY) {
toResolve = new TreeSet<String>();
@@ -207,6 +212,8 @@
for (String path : requestedPaths) {
if (path.startsWith(prefix)) {
toResolve.add(path.substring(prefixLength));
+ } else if (path.startsWith("*.")) {
+ toResolve.add(path.substring("*.".length()));
}
}
toResolve.removeAll(resolved);
@@ -310,7 +317,14 @@
* references.
*/
static boolean matchesPropertyRef(Set<String> propertyRefs, String
newPrefix) {
- return propertyRefs.contains(newPrefix.replaceAll("\\[\\d+\\]", ""));
+ /*
+ * Match all fields for a wildcard
+ *
+ * Also, remove list index suffixes. Not actually used, was in
anticipation
+ * of OGNL type schemes. That said, Editor will slip in such things.
+ */
+ return propertyRefs.contains("*")
+ || propertyRefs.contains(newPrefix.replaceAll("\\[\\d+\\]", ""));
}
/**
@@ -567,7 +581,7 @@
*/
private Resolution resolveClientValue(Object domainValue, Type
clientType) {
if (domainValue == null) {
- return null;
+ return new Resolution(null);
}
boolean anyType = clientType == null;
=======================================
---
/trunk/user/src/com/google/web/bindery/requestfactory/shared/impl/ProxySerializerImpl.java
Fri Jul 1 09:12:59 2011
+++
/trunk/user/src/com/google/web/bindery/requestfactory/shared/impl/ProxySerializerImpl.java
Tue Aug 23 10:48:49 2011
@@ -93,6 +93,10 @@
}
public String serialize(BaseProxy rootObject) {
+ if (rootObject == null) {
+ return "null";
+ }
+
final AutoBean<? extends BaseProxy> root =
AutoBeanUtils.getAutoBean(rootObject);
if (root == null) {
// Unexpected, some kind of foreign implementation of the BaseProxy?
=======================================
---
/trunk/user/test/com/google/web/bindery/requestfactory/gwt/client/RequestFactoryPolymorphicTest.java
Fri Jun 10 11:06:22 2011
+++
/trunk/user/test/com/google/web/bindery/requestfactory/gwt/client/RequestFactoryPolymorphicTest.java
Tue Aug 23 10:48:49 2011
@@ -55,6 +55,8 @@
protected int id = idCount++;
+ private A nextA;
+
public String getA() {
return a;
}
@@ -62,6 +64,13 @@
public int getId() {
return id;
}
+
+ public A getNextA() {
+ if (nextA == null) {
+ nextA = new A();
+ }
+ return nextA;
+ }
public int getVersion() {
return 0;
@@ -77,6 +86,8 @@
*/
@ProxyFor(A.class)
public interface AProxy extends EntityProxy, HasA {
+ AProxy getNextA();
+
// Mix in getA() from HasA
void setA(String value);
}
@@ -146,9 +157,19 @@
private String c = "c";
+ private C nextC;
+
public String getC() {
return c;
}
+
+ public C getNextC() {
+ if (nextC == null) {
+ nextC = new C();
+ }
+
+ return nextC;
+ }
public void setC(String value) {
c = value;
@@ -161,6 +182,8 @@
public interface C1Proxy extends B1Proxy {
String getC();
+ C1Proxy getNextC();
+
void setC(String value);
}
@@ -606,6 +629,50 @@
public String getModuleName() {
return "com.google.web.bindery.requestfactory.gwt.RequestFactorySuite";
}
+
+ public void testChain() {
+ delayTestFinish(TEST_DELAY);
+ Context ctx = factory.ctx();
+ ctx.CasA().with("nextA.nextA").fire(new Receiver<AProxy>() {
+ @Override
+ public void onSuccess(AProxy response) {
+ new
CastAndCheckReceiver(AProxy.class).onSuccess(response.getNextA().getNextA());
+ assertNull(response.getNextA().getNextA().getNextA());
+ assertNull(((C1Proxy) response).getNextC());
+ finishTest();
+ }
+ });
+ }
+
+ public void testChainWithExtras() {
+ delayTestFinish(TEST_DELAY);
+ Context ctx = factory.ctx();
+ ctx.CasA().with("nextC.nextC").fire(new Receiver<AProxy>() {
+ @Override
+ public void onSuccess(AProxy response) {
+ assertNull(response.getNextA());
+ C1Proxy cast = (C1Proxy) response;
+ new
CastAndCheckReceiver(C1Proxy.class).onSuccess(cast.getNextC().getNextC());
+ assertNull(cast.getNextC().getNextC().getNextC());
+ finishTest();
+ }
+ });
+ }
+
+ public void testChainWithWildcards() {
+ delayTestFinish(TEST_DELAY);
+ Context ctx = factory.ctx();
+ ctx.CasA().with("*.*").fire(new Receiver<AProxy>() {
+ @Override
+ public void onSuccess(AProxy response) {
+ new
CastAndCheckReceiver(AProxy.class).onSuccess(response.getNextA().getNextA());
+ C1Proxy cast = (C1Proxy) response;
+ new
CastAndCheckReceiver(C1Proxy.class).onSuccess(cast.getNextC().getNextC());
+ assertNull(cast.getNextC().getNextC().getNextC());
+ finishTest();
+ }
+ });
+ }
public void testCreation() {
delayTestFinish(TEST_DELAY);
=======================================
---
/trunk/user/test/com/google/web/bindery/requestfactory/gwt/client/RequestFactoryTest.java
Fri Aug 5 09:53:30 2011
+++
/trunk/user/test/com/google/web/bindery/requestfactory/gwt/client/RequestFactoryTest.java
Tue Aug 23 10:48:49 2011
@@ -700,6 +700,23 @@
}
});
}
+
+ public void testForwardReferenceWildcardDecode() {
+ delayTestFinish(DELAY_TEST_FINISH);
+
simpleFooRequest().getTripletReference().with("selfOneToManyField.*.fooField")
+ .fire(new Receiver<SimpleFooProxy>() {
+ @Override
+ public void onSuccess(SimpleFooProxy response) {
+ response = checkSerialization(response);
+ assertNotNull(response.getSelfOneToManyField().get(0));
+
assertNotNull(response.getSelfOneToManyField().get(0).getSelfOneToManyField());
+
assertNotNull(response.getSelfOneToManyField().get(0).getSelfOneToManyField().get(0));
+
assertNotNull(response.getSelfOneToManyField().get(0).getSelfOneToManyField().get(0)
+ .getFooField());
+ finishTestAndReset();
+ }
+ });
+ }
public void testGetEventBus() {
assertEquals(eventBus, req.getEventBus());
@@ -979,6 +996,19 @@
delayTestFinish(DELAY_TEST_FINISH);
simpleFooRequest().returnNullSimpleFoo().fire(new NullReceiver());
}
+
+ public void testNullEntityFieldResult() {
+ delayTestFinish(DELAY_TEST_FINISH);
+
simpleFooRequest().getSimpleFooWithNullRelationship().with("fooField.fooField.fooField").fire(
+ new Receiver<SimpleFooProxy>() {
+ @Override
+ public void onSuccess(SimpleFooProxy v) {
+ checkSerialization(v);
+ assertNull(v.getFooField());
+ finishTestAndReset();
+ }
+ });
+ }
/**
* Test that a null value can be sent in a request.
@@ -1084,6 +1114,63 @@
}
});
}
+
+ public void testNullValueInEntityListResponse() {
+ delayTestFinish(DELAY_TEST_FINISH);
+ final Request<SimpleFooProxy> fooReq =
+
req.simpleFooRequest().getNullInEntityList().with("selfOneToManyField");
+ fooReq.fire(new Receiver<SimpleFooProxy>() {
+ @Override
+ public void onSuccess(SimpleFooProxy v) {
+ List<SimpleFooProxy> manyFoos = v.getSelfOneToManyField();
+ assertEquals(3, manyFoos.size());
+
+ assertNotNull(manyFoos.get(0));
+ assertNull(manyFoos.get(1));
+ assertNotNull(manyFoos.get(2));
+
+ finishTestAndReset();
+ }
+ });
+ }
+
+ public void testNullValueInEntityListResponseWithWildcard() {
+ delayTestFinish(DELAY_TEST_FINISH);
+ final Request<SimpleFooProxy> fooReq =
+
req.simpleFooRequest().getNullInEntityList().with("selfOneToManyField.*.fooField");
+ fooReq.fire(new Receiver<SimpleFooProxy>() {
+ @Override
+ public void onSuccess(SimpleFooProxy foo0) {
+ List<SimpleFooProxy> manyFoos = foo0.getSelfOneToManyField();
+ assertEquals(3, manyFoos.size());
+
+ assertSame(foo0, manyFoos.get(0).getSelfOneToManyField().get(0));
+ assertNull(manyFoos.get(1));
+ assertSame(foo0, manyFoos.get(2).getSelfOneToManyField().get(0));
+ assertSame(foo0, manyFoos.get(2).getFooField().getFooField());
+
+ finishTestAndReset();
+ }
+ });
+ }
+
+ public void testNullValueInEntityListResponseWithLongResolvePaths() {
+ delayTestFinish(DELAY_TEST_FINISH);
+ final Request<SimpleFooProxy> fooReq =
+
req.simpleFooRequest().getNullInEntityList().with("selfOneToManyField.selfOneToManyField.selfOneToManyField");
+ fooReq.fire(new Receiver<SimpleFooProxy>() {
+ @Override
+ public void onSuccess(SimpleFooProxy v) {
+ assertEquals(3, v.getSelfOneToManyField().size());
+
+ assertNotNull(v.getSelfOneToManyField().get(0));
+ assertNull(v.getSelfOneToManyField().get(1));
+ assertNotNull(v.getSelfOneToManyField().get(2));
+
+ finishTestAndReset();
+ }
+ });
+ }
/**
* Test that a null value can be sent within a list of objects.
@@ -2044,6 +2131,31 @@
}
});
}
+
+ public void testPropertyRefsOnWildcardChain() {
+ delayTestFinish(DELAY_TEST_FINISH);
+ final Request<SimpleFooProxy> fooReq =
+ req.simpleFooRequest().getLongChain().with("fooField.*.*.fooField");
+ fooReq.fire(new Receiver<SimpleFooProxy>() {
+ @Override
+ public void onSuccess(SimpleFooProxy foo0) {
+ assertNull(foo0.getSelfOneToManyField()); // didn't ask for it
+
+ SimpleFooProxy foo1 = foo0.getFooField(); // "fooField
+ SimpleFooProxy foo2 = foo1.getFooField(); // .*
+ SimpleFooProxy foo3 = foo2.getFooField(); // .*
+ SimpleFooProxy foo4 = foo3.getFooField();
// .fooField"
+ SimpleFooProxy foo5 = foo4.getFooField();
+
+ assertNotNull(foo1);
+ assertNotNull(foo2);
+ assertNotNull(foo3);
+ assertNotNull(foo4);
+ assertNull(foo5);
+ finishTestAndReset();
+ }
+ });
+ }
public void testPropertyRefsOnSameObjectReturnedTwice() {
delayTestFinish(DELAY_TEST_FINISH);
=======================================
---
/trunk/user/test/com/google/web/bindery/requestfactory/server/SimpleFoo.java
Fri Jun 17 03:15:41 2011
+++
/trunk/user/test/com/google/web/bindery/requestfactory/server/SimpleFoo.java
Tue Aug 23 10:48:49 2011
@@ -124,6 +124,53 @@
foo3.persist();
return Arrays.asList(foo1, foo2, foo3);
}
+
+ public static SimpleFoo getLongChain() {
+ SimpleFoo foo0 = new SimpleFoo();
+ SimpleFoo foo1 = new SimpleFoo();
+ SimpleFoo foo2 = new SimpleFoo();
+ SimpleFoo foo3 = new SimpleFoo();
+ SimpleFoo foo4 = new SimpleFoo();
+ SimpleFoo foo5 = new SimpleFoo();
+
+ foo0.setSelfOneToManyField(Arrays.asList(foo1, foo2));
+ foo0.setFooField(foo1);
+ foo1.setFooField(foo2);
+ foo2.setFooField(foo3);
+ foo3.setFooField(foo4);
+ foo4.setFooField(foo5);
+ foo5.setFooField(foo5);
+
+ foo0.persist();
+ foo1.persist();
+ foo2.persist();
+ foo3.persist();
+ foo4.persist();
+ foo5.persist();
+
+ return foo0;
+ }
+
+ public static SimpleFoo getNullInEntityList() {
+ SimpleFoo foo0 = new SimpleFoo();
+ SimpleFoo foo1 = new SimpleFoo();
+ SimpleFoo foo2 = new SimpleFoo();
+ SimpleFoo foo2FooField = new SimpleFoo();
+
+ foo0.setSelfOneToManyField(Arrays.asList(foo1, null, foo2));
+
+ foo1.setSelfOneToManyField(Arrays.asList(foo0));
+
+ foo2.setSelfOneToManyField(Arrays.asList(foo0));
+ foo2.setFooField(foo2FooField);
+ foo2FooField.setFooField(foo0);
+
+ foo0.persist();
+ foo1.persist();
+ foo2.persist();
+ foo2FooField.persist();
+ return foo0;
+ }
public static List<Integer> getNumberList() {
ArrayList<Integer> list = new ArrayList<Integer>();
@@ -140,6 +187,12 @@
list.add(3);
return list;
}
+
+ public static SimpleFoo getSimpleFooWithNullRelationship() {
+ SimpleFoo foo = new SimpleFoo();
+ foo.persist();
+ return foo;
+ }
/**
* This tests that the server detects and disallows the use of persisted
=======================================
---
/trunk/user/test/com/google/web/bindery/requestfactory/shared/SimpleFooRequest.java
Fri Jun 17 03:15:41 2011
+++
/trunk/user/test/com/google/web/bindery/requestfactory/shared/SimpleFooRequest.java
Tue Aug 23 10:48:49 2011
@@ -49,10 +49,16 @@
Request<List<SimpleFooProxy>> getFlattenedTripletReference();
- Request<List<Integer>> getNumberList();
-
+ Request<SimpleFooProxy> getLongChain();
+
+ Request<SimpleFooProxy> getNullInEntityList();
+
+ Request<List<Integer>> getNumberList();
+
Request<Set<Integer>> getNumberSet();
+ Request<SimpleFooProxy> getSimpleFooWithNullRelationship();
+
Request<SimpleFooProxy> getSimpleFooWithNullVersion();
Request<SimpleFooProxy> getSimpleFooWithSubPropertyCollection();
--
http://groups.google.com/group/Google-Web-Toolkit-Contributors