In r8817, we landed a patch that allows @Prefix(""), i.e. a
non-prefixed PlaceTokenizer, and produces a "separator-less" history
token as a result. The token parsing however wasn't updated, and such
a token would always go the fallback route to the default place,
without ever being "parsed".
See also: http://code.google.com/p/google-web-toolkit/issues/detail?id=5899
Review by: robertvawter@google.com
git-svn-id: https://google-web-toolkit.googlecode.com/svn/trunk@9635 8db76d5a-ed1c-0410-87a9-c151d255dfc7
diff --git a/user/src/com/google/gwt/place/impl/AbstractPlaceHistoryMapper.java b/user/src/com/google/gwt/place/impl/AbstractPlaceHistoryMapper.java
index 1fb4ae2..c8399db 100644
--- a/user/src/com/google/gwt/place/impl/AbstractPlaceHistoryMapper.java
+++ b/user/src/com/google/gwt/place/impl/AbstractPlaceHistoryMapper.java
@@ -51,13 +51,18 @@
public Place getPlace(String token) {
int colonAt = token.indexOf(':');
- if (colonAt > 0) {
- String initial = token.substring(0, colonAt);
- String rest = token.substring(colonAt + 1);
- PlaceTokenizer<?> tokenizer = getTokenizer(initial);
- if (tokenizer != null) {
- return tokenizer.getPlace(rest);
- }
+ String initial;
+ String rest;
+ if (colonAt >= 0) {
+ initial = token.substring(0, colonAt);
+ rest = token.substring(colonAt + 1);
+ } else {
+ initial = "";
+ rest = token;
+ }
+ PlaceTokenizer<?> tokenizer = getTokenizer(initial);
+ if (tokenizer != null) {
+ return tokenizer.getPlace(rest);
}
return null;
}
diff --git a/user/test/com/google/gwt/place/impl/PlaceHistoryMapperGeneratorTest.java b/user/test/com/google/gwt/place/impl/PlaceHistoryMapperGeneratorTest.java
index c17e15a..402477b 100644
--- a/user/test/com/google/gwt/place/impl/PlaceHistoryMapperGeneratorTest.java
+++ b/user/test/com/google/gwt/place/impl/PlaceHistoryMapperGeneratorTest.java
@@ -28,6 +28,7 @@
import com.google.gwt.place.testplaces.Place3;
import com.google.gwt.place.testplaces.Place4;
import com.google.gwt.place.testplaces.Place5;
+import com.google.gwt.place.testplaces.Place6;
import com.google.gwt.place.testplaces.Tokenizer2;
import com.google.gwt.place.testplaces.Tokenizer3;
import com.google.gwt.place.testplaces.Tokenizer4;
@@ -39,11 +40,11 @@
public class PlaceHistoryMapperGeneratorTest extends GWTTestCase {
@WithTokenizers({
Place1.Tokenizer.class, Tokenizer2.class, Tokenizer3.class,
- Tokenizer4.class})
+ Tokenizer4.class, Place6.Tokenizer.class})
interface LocalNoFactory extends PlaceHistoryMapper {
};
- @WithTokenizers(Tokenizer4.class)
+ @WithTokenizers({Tokenizer4.class, Place6.Tokenizer.class})
interface LocalWithFactory extends
PlaceHistoryMapperWithFactory<TokenizerFactory> {
};
@@ -71,6 +72,7 @@
Place3 place3 = new Place3("charlie");
Place4 place4 = new Place4("delta");
Place5 place5 = new Place5("echo");
+ Place6 place6 = new Place6("foxtrot");
public void testTopLevelWithoutFactory() {
AbstractPlaceHistoryMapper<?> subject = GWT.create(NoFactory.class);
@@ -148,6 +150,12 @@
assertTrue(subject.getTokenizer("Place3") instanceof Tokenizer3);
}
assertTrue(subject.getTokenizer("Place4") instanceof Tokenizer4);
+
+ // Empty prefix
+ String history6 = subject.getPrefixAndToken(place6).toString();
+ assertEquals(place6.content, history6);
+ assertTrue(subject.getTokenizer("") instanceof Place6.Tokenizer);
+ assertTrue(subject.getPlace("noPrefix") instanceof Place6);
Place place = new Place() {
};
diff --git a/user/test/com/google/gwt/place/rebind/PlaceHistoryGeneratorContextTest.java b/user/test/com/google/gwt/place/rebind/PlaceHistoryGeneratorContextTest.java
index 3c639fc..c53795f 100644
--- a/user/test/com/google/gwt/place/rebind/PlaceHistoryGeneratorContextTest.java
+++ b/user/test/com/google/gwt/place/rebind/PlaceHistoryGeneratorContextTest.java
@@ -39,6 +39,7 @@
import com.google.gwt.place.testplaces.Place2;
import com.google.gwt.place.testplaces.Place3;
import com.google.gwt.place.testplaces.Place4;
+import com.google.gwt.place.testplaces.Place6;
import com.google.gwt.place.testplaces.Tokenizer2;
import com.google.gwt.place.testplaces.Tokenizer3;
import com.google.gwt.place.testplaces.Tokenizer4;
@@ -83,6 +84,7 @@
rtn.add(new RealJavaResource(Place2.class));
rtn.add(new RealJavaResource(Place3.class));
rtn.add(new RealJavaResource(Place4.class));
+ rtn.add(new RealJavaResource(Place6.class));
rtn.add(new RealJavaResource(Tokenizer2.class));
rtn.add(new RealJavaResource(Tokenizer3.class));
rtn.add(new RealJavaResource(Tokenizer4.class));
@@ -133,16 +135,17 @@
JClassType place2 = typeOracle.getType(Place2.class.getName());
JClassType place3 = typeOracle.getType(Place3.class.getName());
JClassType place4 = typeOracle.getType(Place4.class.getName());
+ JClassType place6 = typeOracle.getType(Place6.class.getName());
PlaceHistoryGeneratorContext context = createContext(TreeLogger.NULL,
typeOracle, NoFactory.class.getName(), null);
// Found all place prefixes?
- assertEquals(new HashSet<String>(Arrays.asList(Place1.Tokenizer.PREFIX,
+ assertEquals(new HashSet<String>(Arrays.asList("", Place1.Tokenizer.PREFIX,
"Place2", "Place3", "Place4")), context.getPrefixes());
// Found all place types and correctly sorted them?
- assertEquals(Arrays.asList(place3, place4, place1, place2),
+ assertEquals(Arrays.asList(place3, place4, place1, place2, place6),
new ArrayList<JClassType>(context.getPlaceTypes()));
// correctly maps place types to their prefixes?
@@ -150,12 +153,14 @@
assertEquals("Place2", context.getPrefix(place2));
assertEquals("Place3", context.getPrefix(place3));
assertEquals("Place4", context.getPrefix(place4));
+ assertEquals("", context.getPrefix(place6));
// there obviously shouldn't be factory methods
assertNull(context.getTokenizerGetter(Place1.Tokenizer.PREFIX));
assertNull(context.getTokenizerGetter("Place2"));
assertNull(context.getTokenizerGetter("Place3"));
assertNull(context.getTokenizerGetter("Place4"));
+ assertNull(context.getTokenizerGetter(""));
// correctly maps prefixes to their tokenizer type?
assertEquals(typeOracle.getType(Place1.Tokenizer.class.getCanonicalName()),
@@ -166,6 +171,8 @@
context.getTokenizerType("Place3"));
assertEquals(typeOracle.getType(Tokenizer4.class.getName()),
context.getTokenizerType("Place4"));
+ assertEquals(typeOracle.getType(Place6.Tokenizer.class.getCanonicalName()),
+ context.getTokenizerType(""));
}
public void testWithFactory() throws UnableToCompleteException,
@@ -177,6 +184,7 @@
JClassType place2 = typeOracle.getType(Place2.class.getName());
JClassType place3 = typeOracle.getType(Place3.class.getName());
JClassType place4 = typeOracle.getType(Place4.class.getName());
+ JClassType place6 = typeOracle.getType(Place6.class.getName());
JClassType factory = typeOracle.getType(TokenizerFactory.class.getName());
PlaceHistoryGeneratorContext context = createContext(TreeLogger.NULL,
@@ -184,12 +192,12 @@
TokenizerFactory.class.getName());
// Found all place prefixes?
- assertEquals(new HashSet<String>(Arrays.asList(Place1.Tokenizer.PREFIX,
+ assertEquals(new HashSet<String>(Arrays.asList("", Place1.Tokenizer.PREFIX,
TokenizerFactory.PLACE2_PREFIX, "Place3", "Place4")),
context.getPrefixes());
// Found all place types and correctly sorted them?
- assertEquals(Arrays.asList(place3, place4, place1, place2),
+ assertEquals(Arrays.asList(place3, place4, place1, place2, place6),
new ArrayList<JClassType>(context.getPlaceTypes()));
// correctly maps place types to their prefixes?
@@ -197,6 +205,7 @@
assertEquals(TokenizerFactory.PLACE2_PREFIX, context.getPrefix(place2));
assertEquals("Place3", context.getPrefix(place3));
assertEquals("Place4", context.getPrefix(place4));
+ assertEquals("", context.getPrefix(place6));
// correctly map prefixes to their factory method (or null)?
assertEquals(factory.getMethod("getTokenizer1", EMPTY_JTYPE_ARRAY),
@@ -206,6 +215,7 @@
assertEquals(factory.getMethod("getTokenizer3", EMPTY_JTYPE_ARRAY),
context.getTokenizerGetter("Place3"));
assertNull(context.getTokenizerGetter("Place4"));
+ assertNull(context.getTokenizerGetter(""));
// correctly maps prefixes to their tokenizer type (or null)?
assertNull(context.getTokenizerType(Place1.Tokenizer.PREFIX));
@@ -213,6 +223,8 @@
assertNull(context.getTokenizerType("Place3"));
assertEquals(typeOracle.getType(Tokenizer4.class.getName()),
context.getTokenizerType("Place4"));
+ assertEquals(typeOracle.getType(Place6.Tokenizer.class.getCanonicalName()),
+ context.getTokenizerType(""));
}
public void testDuplicatePrefix() {
diff --git a/user/test/com/google/gwt/place/testplacemappers/NoFactory.java b/user/test/com/google/gwt/place/testplacemappers/NoFactory.java
index 39ef9e9..4f96fa5 100644
--- a/user/test/com/google/gwt/place/testplacemappers/NoFactory.java
+++ b/user/test/com/google/gwt/place/testplacemappers/NoFactory.java
@@ -18,6 +18,7 @@
import com.google.gwt.place.shared.PlaceHistoryMapper;
import com.google.gwt.place.shared.WithTokenizers;
import com.google.gwt.place.testplaces.Place1;
+import com.google.gwt.place.testplaces.Place6;
import com.google.gwt.place.testplaces.Tokenizer2;
import com.google.gwt.place.testplaces.Tokenizer3;
import com.google.gwt.place.testplaces.Tokenizer4;
@@ -27,6 +28,6 @@
*/
@WithTokenizers({
Place1.Tokenizer.class, Tokenizer2.class, Tokenizer3.class,
- Tokenizer4.class})
+ Tokenizer4.class, Place6.Tokenizer.class})
public interface NoFactory extends PlaceHistoryMapper {
}
\ No newline at end of file
diff --git a/user/test/com/google/gwt/place/testplacemappers/WithFactory.java b/user/test/com/google/gwt/place/testplacemappers/WithFactory.java
index 29976a9..4cddee3 100644
--- a/user/test/com/google/gwt/place/testplacemappers/WithFactory.java
+++ b/user/test/com/google/gwt/place/testplacemappers/WithFactory.java
@@ -17,13 +17,14 @@
import com.google.gwt.place.shared.PlaceHistoryMapperWithFactory;
import com.google.gwt.place.shared.WithTokenizers;
+import com.google.gwt.place.testplaces.Place6;
import com.google.gwt.place.testplaces.Tokenizer4;
import com.google.gwt.place.testplaces.TokenizerFactory;
/**
* Used by tests of {@link com.google.gwt.place.rebind.PlaceHistoryMapperGenerator}.
*/
-@WithTokenizers(Tokenizer4.class)
+@WithTokenizers({Tokenizer4.class, Place6.Tokenizer.class})
public interface WithFactory extends
PlaceHistoryMapperWithFactory<TokenizerFactory> {
}
\ No newline at end of file
diff --git a/user/test/com/google/gwt/place/testplaces/Place6.java b/user/test/com/google/gwt/place/testplaces/Place6.java
new file mode 100644
index 0000000..4c609c6
--- /dev/null
+++ b/user/test/com/google/gwt/place/testplaces/Place6.java
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2011 Google Inc.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.google.gwt.place.testplaces;
+
+import com.google.gwt.place.shared.Place;
+import com.google.gwt.place.shared.PlaceTokenizer;
+import com.google.gwt.place.shared.Prefix;
+
+/**
+ * Used by tests of {@link com.google.gwt.place.rebind.PlaceHistoryMapperGenerator}.
+ */
+public class Place6 extends Place {
+ public final String content;
+
+ public Place6(String token) {
+ this.content = token;
+ }
+
+ /**
+ * Tokenizer.
+ */
+ @Prefix("")
+ public static class Tokenizer implements PlaceTokenizer<Place6> {
+ public Place6 getPlace(String token) {
+ return new Place6(token);
+ }
+
+ public String getToken(Place6 place) {
+ return place.content;
+ }
+ }
+}