Create a PathConstructor service, to encapsulate configuration logic about 
context path and application folder


Project: http://git-wip-us.apache.org/repos/asf/tapestry-5/repo
Commit: http://git-wip-us.apache.org/repos/asf/tapestry-5/commit/b67b961c
Tree: http://git-wip-us.apache.org/repos/asf/tapestry-5/tree/b67b961c
Diff: http://git-wip-us.apache.org/repos/asf/tapestry-5/diff/b67b961c

Branch: refs/heads/master
Commit: b67b961c95881dfa81d3174bf98e71a40046055f
Parents: 1dd33e1
Author: Howard M. Lewis Ship <[email protected]>
Authored: Mon Jan 21 16:01:10 2013 -0800
Committer: Howard M. Lewis Ship <[email protected]>
Committed: Tue Jan 22 10:30:54 2013 -0800

----------------------------------------------------------------------
 .../internal/services/PathConstructorImpl.java     |   54 +++++++++++++++
 .../javascript/ModuleAssetRequestHandler.java      |    9 ++-
 .../apache/tapestry5/services/PathConstructor.java |   48 +++++++++++++
 .../services/PathConstructorImplSpec.groovy        |   27 +++++++
 4 files changed, 136 insertions(+), 2 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/tapestry-5/blob/b67b961c/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/PathConstructorImpl.java
----------------------------------------------------------------------
diff --git 
a/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/PathConstructorImpl.java
 
b/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/PathConstructorImpl.java
new file mode 100644
index 0000000..d1e4f1b
--- /dev/null
+++ 
b/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/PathConstructorImpl.java
@@ -0,0 +1,54 @@
+package org.apache.tapestry5.internal.services;
+
+import org.apache.tapestry5.SymbolConstants;
+import org.apache.tapestry5.ioc.annotations.Symbol;
+import org.apache.tapestry5.services.PathConstructor;
+
+public class PathConstructorImpl implements PathConstructor
+{
+    private final String clientPrefix, dispatchPrefix;
+
+    public PathConstructorImpl(
+            @Symbol(SymbolConstants.CONTEXT_PATH) String contextPath,
+            @Symbol(SymbolConstants.APPLICATION_FOLDER) String 
applicationFolder)
+    {
+        StringBuilder b = new StringBuilder("/");
+
+        if (applicationFolder.length() > 0)
+        {
+            b.append(applicationFolder);
+            b.append("/");
+        }
+
+        dispatchPrefix = b.toString();
+
+        clientPrefix = contextPath + dispatchPrefix;
+    }
+
+    public String constructClientPath(String... terms)
+    {
+        return build(clientPrefix, terms);
+    }
+
+    public String constructDispatchPath(String... terms)
+    {
+        return build(dispatchPrefix, terms);
+    }
+
+    private String build(String prefix, String... terms)
+    {
+        StringBuilder b = new StringBuilder(prefix);
+        String sep = "";
+
+        for (String term : terms)
+        {
+            b.append(sep);
+            b.append(term);
+
+            sep = "/";
+        }
+
+
+        return b.toString();
+    }
+}

http://git-wip-us.apache.org/repos/asf/tapestry-5/blob/b67b961c/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/javascript/ModuleAssetRequestHandler.java
----------------------------------------------------------------------
diff --git 
a/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/javascript/ModuleAssetRequestHandler.java
 
b/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/javascript/ModuleAssetRequestHandler.java
index 7506ec5..1d6a1b7 100644
--- 
a/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/javascript/ModuleAssetRequestHandler.java
+++ 
b/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/javascript/ModuleAssetRequestHandler.java
@@ -16,10 +16,10 @@ package org.apache.tapestry5.internal.services.javascript;
 
 import org.apache.tapestry5.internal.services.AssetDispatcher;
 import org.apache.tapestry5.internal.services.ResourceStreamer;
-import org.apache.tapestry5.internal.util.Holder;
 import org.apache.tapestry5.ioc.IOOperation;
 import org.apache.tapestry5.ioc.OperationTracker;
 import org.apache.tapestry5.ioc.Resource;
+import org.apache.tapestry5.services.Dispatcher;
 import org.apache.tapestry5.services.Request;
 import org.apache.tapestry5.services.Response;
 import org.apache.tapestry5.services.assets.AssetRequestHandler;
@@ -31,7 +31,7 @@ import java.io.IOException;
  * Handler contributed to {@link AssetDispatcher} with key "modules". It 
interprets the extra path as a module name,
  * and searches for the corresponding JavaScript module.
  */
-public class ModuleAssetRequestHandler implements AssetRequestHandler
+public class ModuleAssetRequestHandler implements AssetRequestHandler, 
Dispatcher
 {
     private final ModuleManager moduleManager;
 
@@ -46,6 +46,11 @@ public class ModuleAssetRequestHandler implements 
AssetRequestHandler
         this.tracker = tracker;
     }
 
+    public boolean dispatch(Request request, Response response) throws 
IOException
+    {
+        return false;
+    }
+
     public boolean handleAssetRequest(Request request, Response response, 
String extraPath) throws IOException
     {
         // Ensure request ends with '.js'.  That's the extension tacked on by 
RequireJS because it expects there

http://git-wip-us.apache.org/repos/asf/tapestry-5/blob/b67b961c/tapestry-core/src/main/java/org/apache/tapestry5/services/PathConstructor.java
----------------------------------------------------------------------
diff --git 
a/tapestry-core/src/main/java/org/apache/tapestry5/services/PathConstructor.java
 
b/tapestry-core/src/main/java/org/apache/tapestry5/services/PathConstructor.java
new file mode 100644
index 0000000..b6ccb3e
--- /dev/null
+++ 
b/tapestry-core/src/main/java/org/apache/tapestry5/services/PathConstructor.java
@@ -0,0 +1,48 @@
+// Copyright 2013 The Apache Software Foundation
+//
+// 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 org.apache.tapestry5.services;
+
+/**
+ * Central location for logic related to building client-side paths, taking 
into account
+ * the context path (if any), and the {@link 
org.apache.tapestry5.SymbolConstants#APPLICATION_FOLDER}
+ * (if any).
+ *
+ * @since 5.4
+ */
+public interface PathConstructor
+{
+    /**
+     * Constructs a client path, the path portion of an absolute URL. The 
result consists of the
+     * the context path (if any), the application folder (if any), then the 
series of terms.
+     *
+     * @param terms
+     *         additional terms (folder names, or a file name) following the 
context path and application folder.
+     * @return the full path, starting with a leading slash, and including the 
context path, application folder, and the terms,
+     *         all seperated with slashes
+     */
+    String constructClientPath(String... terms);
+
+    /**
+     * Constructs the dispatch path, which is like the client path, but omits 
the context path; this aligns
+     * the result with the value returned from {@link 
org.apache.tapestry5.services.Request#getPath()}, and is used
+     * in code, typically {@link Dispatcher} implementations, that are 
attempting to route based on the incoming request path.
+     *
+     * @param terms
+     *         additional terms (folder names, or a file name) following the 
context path and application folder.
+     * @return path string starting with a leading slash, and including the 
application folder (if any) and the individual terms,
+     *         seperated by slashes
+     */
+    String constructDispatchPath(String... terms);
+}

http://git-wip-us.apache.org/repos/asf/tapestry-5/blob/b67b961c/tapestry-core/src/test/groovy/org/apache/tapestry5/internal/services/PathConstructorImplSpec.groovy
----------------------------------------------------------------------
diff --git 
a/tapestry-core/src/test/groovy/org/apache/tapestry5/internal/services/PathConstructorImplSpec.groovy
 
b/tapestry-core/src/test/groovy/org/apache/tapestry5/internal/services/PathConstructorImplSpec.groovy
new file mode 100644
index 0000000..53166cc
--- /dev/null
+++ 
b/tapestry-core/src/test/groovy/org/apache/tapestry5/internal/services/PathConstructorImplSpec.groovy
@@ -0,0 +1,27 @@
+package org.apache.tapestry5.internal.services
+
+import org.testng.Assert
+import org.testng.annotations.DataProvider
+import org.testng.annotations.Test
+
+class PathConstructorImplSpec extends Assert {
+
+    @DataProvider
+     Object[][] data() {
+        return [
+            ["", "", "/foo/bar", "/foo/bar"],
+            ["", "myapp", "/myapp/foo/bar", "/myapp/foo/bar"],
+            ["/ctx", "", "/ctx/foo/bar", "/foo/bar"],
+            ["/ctx", "myapp", "/ctx/myapp/foo/bar", "/myapp/foo/bar"]
+        ] as Object[][]
+    }
+
+
+    @Test(dataProvider = "data")
+    void doTest(String contextPath, String appFolder, String 
expectedClientPath, String expectedDispatchPath) {
+        def pc = new PathConstructorImpl(contextPath, appFolder)
+
+        assert pc.constructClientPath("foo", "bar") == expectedClientPath
+        assert pc.constructDispatchPath("foo", "bar") == expectedDispatchPath
+    }
+}

Reply via email to