You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tapestry.apache.org by hl...@apache.org on 2007/12/01 20:57:20 UTC

svn commit: r600189 - in /tapestry/tapestry5/trunk/tapestry-core/src: main/java/org/apache/tapestry/annotations/ main/java/org/apache/tapestry/internal/services/ main/java/org/apache/tapestry/services/ main/resources/org/apache/tapestry/ site/ site/apt...

Author: hlship
Date: Sat Dec  1 11:57:19 2007
New Revision: 600189

URL: http://svn.apache.org/viewvc?rev=600189&view=rev
Log:
TAPESTRY-1935: Create an annotation to add a CSS stylesheet to the rendered page

Added:
    tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/annotations/IncludeStylesheet.java
    tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/ComponentResourcesOperation.java
    tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/IncludeStylesheetWorker.java
    tapestry/tapestry5/trunk/tapestry-core/src/site/apt/guide/css.apt
    tapestry/tapestry5/trunk/tapestry-core/src/test/app1/css/
    tapestry/tapestry5/trunk/tapestry-core/src/test/app1/css/app.css
Modified:
    tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/AssetInjectionProvider.java
    tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/services/TapestryModule.java
    tapestry/tapestry5/trunk/tapestry-core/src/main/resources/org/apache/tapestry/tapestry.js
    tapestry/tapestry5/trunk/tapestry-core/src/site/site.xml
    tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/IntegrationTests.java
    tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/app1/components/Border.java
    tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/AssetInjectionProviderTest.java
    tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/MethodPrefixTarget.java

Added: tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/annotations/IncludeStylesheet.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/annotations/IncludeStylesheet.java?rev=600189&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/annotations/IncludeStylesheet.java (added)
+++ tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/annotations/IncludeStylesheet.java Sat Dec  1 11:57:19 2007
@@ -0,0 +1,40 @@
+// Copyright 2007 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.tapestry.annotations;
+
+import java.lang.annotation.*;
+
+
+/**
+ * Used to automatically include a CSS stylesheet when rendering the page.  The value is an asset reference; relative
+ * paths are relative to the Java class, or a "context:" prefix can be used to reference resources in the web application.
+ * <p/>
+ * This saves the work of injecting the asset into a field and injecting the PageRenderSupport environmental service, and invoking the method.
+ * <p/>
+ * Does not support setting a media type; if that is required. use {@link org.apache.tapestry.PageRenderSupport#addStylesheetLink(org.apache.tapestry.Asset, String)}
+ * directly.
+ *
+ * @see org.apache.tapestry.annotations.Path
+ */
+@Target({ElementType.TYPE})
+@Retention(RetentionPolicy.RUNTIME)
+@Documented
+public @interface IncludeStylesheet
+{
+    /**
+     * One or more paths to be injected. Symbols in the path will be expanded.
+     */
+    String[] value();
+}

Modified: tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/AssetInjectionProvider.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/AssetInjectionProvider.java?rev=600189&r1=600188&r2=600189&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/AssetInjectionProvider.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/AssetInjectionProvider.java Sat Dec  1 11:57:19 2007
@@ -16,6 +16,7 @@
 
 import org.apache.tapestry.annotations.Path;
 import org.apache.tapestry.ioc.ObjectLocator;
+import org.apache.tapestry.ioc.Resource;
 import org.apache.tapestry.ioc.services.SymbolSource;
 import org.apache.tapestry.model.MutableComponentModel;
 import org.apache.tapestry.services.AssetSource;
@@ -49,27 +50,21 @@
 
         String expanded = _symbolSource.expandSymbols(path.value());
 
-        String sourceFieldName = transformation.addInjectedField(
-                AssetSource.class,
-                "assetSource",
-                _assetSource);
+        String sourceFieldName = transformation.addInjectedField(AssetSource.class, "assetSource", _assetSource);
+
+        String baseResourceFieldName = transformation.addInjectedField(Resource.class, "baseResource",
+                                                                       componentModel.getBaseResource());
+
         String resourcesFieldName = transformation.getResourcesFieldName();
 
-        String statement = format(
-                "%s = (%s) %s.findAsset(%s.getBaseResource(), \"%s\", %s.getLocale());",
-                fieldName,
-                fieldType.getName(),
-                sourceFieldName,
-                resourcesFieldName,
-                expanded,
-                resourcesFieldName);
+        String statement = format("%s = (%s) %s.findAsset(%s, \"%s\", %s.getLocale());", fieldName, fieldType.getName(),
+                                  sourceFieldName, baseResourceFieldName, expanded, resourcesFieldName);
 
         transformation.extendConstructor(statement);
 
         transformation.makeReadOnly(fieldName);
 
         return true;
-
     }
 
 }

Added: tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/ComponentResourcesOperation.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/ComponentResourcesOperation.java?rev=600189&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/ComponentResourcesOperation.java (added)
+++ tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/ComponentResourcesOperation.java Sat Dec  1 11:57:19 2007
@@ -0,0 +1,31 @@
+// Copyright 2007 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.tapestry.internal.services;
+
+import org.apache.tapestry.ComponentResources;
+
+/**
+ * A kind of callback that can easily be injected into a transformed class to perform complex work.
+ * <p/>
+ * These callbacks are often injected into a transformed component class via {@link org.apache.tapestry.services.ClassTransformation#addInjectedField(Class, String, Object)}. Bear in mind
+ * that such callbacks must be <em>threadsafe</em>, since every instance of such a class will share a single instance of the operation.
+ */
+public interface ComponentResourcesOperation
+{
+    /**
+     * Perform some operation that requires the components' resources.
+     */
+    void perform(ComponentResources resources);
+}

Added: tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/IncludeStylesheetWorker.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/IncludeStylesheetWorker.java?rev=600189&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/IncludeStylesheetWorker.java (added)
+++ tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/internal/services/IncludeStylesheetWorker.java Sat Dec  1 11:57:19 2007
@@ -0,0 +1,95 @@
+// Copyright 2007 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.tapestry.internal.services;
+
+import org.apache.tapestry.Asset;
+import org.apache.tapestry.ComponentResources;
+import org.apache.tapestry.PageRenderSupport;
+import org.apache.tapestry.annotations.IncludeStylesheet;
+import org.apache.tapestry.ioc.internal.util.CollectionFactory;
+import org.apache.tapestry.ioc.services.SymbolSource;
+import org.apache.tapestry.model.MutableComponentModel;
+import org.apache.tapestry.services.AssetSource;
+import org.apache.tapestry.services.ClassTransformation;
+import org.apache.tapestry.services.ComponentClassTransformWorker;
+import org.apache.tapestry.services.TransformConstants;
+
+import java.util.List;
+import java.util.Locale;
+
+public class IncludeStylesheetWorker implements ComponentClassTransformWorker
+{
+    private final AssetSource _assetSource;
+
+    private final PageRenderSupport _pageRenderSupport;
+
+    private final SymbolSource _symbolSource;
+
+    public IncludeStylesheetWorker(AssetSource assetSource, PageRenderSupport pageRenderSupport,
+                                   SymbolSource symbolSource)
+    {
+        _assetSource = assetSource;
+        _pageRenderSupport = pageRenderSupport;
+        _symbolSource = symbolSource;
+    }
+
+    public void transform(ClassTransformation transformation, final MutableComponentModel model)
+    {
+        IncludeStylesheet annotation = transformation.getAnnotation(IncludeStylesheet.class);
+
+        if (annotation == null) return;
+
+        final List<String> paths = CollectionFactory.newList();
+
+        for (String value : annotation.value())
+        {
+            String expanded = _symbolSource.expandSymbols(value);
+
+            paths.add(expanded);
+        }
+
+        ComponentResourcesOperation op = new ComponentResourcesOperation()
+        {
+            // Remember that ONE instances of this op will be injected into EVERY instance
+            // of the component ... that means that we can't do any aggresive caching
+            // inside the operation (the operation must be threadsafe).
+
+            public void perform(ComponentResources resources)
+            {
+                Locale locale = resources.getLocale();
+
+                for (String assetPath : paths)
+                {
+                    Asset asset = _assetSource.findAsset(model.getBaseResource(), assetPath, locale);
+
+                    _pageRenderSupport.addStylesheetLink(asset, null);
+                }
+            }
+        };
+
+        String opFieldName = transformation.addInjectedField(ComponentResourcesOperation.class, "includeCSSOperation",
+                                                             op);
+
+        String resourcesName = transformation.getResourcesFieldName();
+
+        String body = String.format("%s.perform(%s);", opFieldName, resourcesName);
+
+        // This is what I like about this approach; the injected body is tiny.  The downside is that
+        // the object that gets injected is hard to test, hard enough that we'll just concentrate on
+        // the integration test, thank you.
+
+        transformation.extendMethod(TransformConstants.SETUP_RENDER_SIGNATURE, body);
+    }
+}

Modified: tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/services/TapestryModule.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/services/TapestryModule.java?rev=600189&r1=600188&r2=600189&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/services/TapestryModule.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry/services/TapestryModule.java Sat Dec  1 11:57:19 2007
@@ -245,10 +245,10 @@
      * <li>Environment -- allows fields to contain values extracted from the {@link Environment}
      * service</li>
      * <li>Inject -- used with the {@link Inject} annotation, when a value is supplied</li>
-     * <li>InjectResources -- used with the {@link Inject} annotation, when no value is supplied</li>
      * <li>InjectPage -- adds code to allow access to other pages via the {@link InjectPage} field
      * annotation</li>
      * <li>InjectBlock -- allows a block from the template to be injected into a field</li>
+     * <li>IncludeStylesheet -- supports the {@link org.apache.tapestry.annotations.IncludeStylesheet} annotation</li>
      * <li>SupportsInformalParameters -- checks for the annotation</li>
      * <li>Meta -- checks for meta data and adds it to the component model
      * <li>ApplicationState -- converts fields that reference application state objects
@@ -283,6 +283,8 @@
         configuration.add("ApplicationState", new ApplicationStateWorker(applicationStateManager));
 
         configuration.add("Inject", new InjectWorker(locator, injectionProvider));
+
+        configuration.add("IncludeStylesheet", locator.autobuild(IncludeStylesheetWorker.class));
 
         configuration.add("MixinAfter", new MixinAfterWorker());
         configuration.add("Component", new ComponentWorker(resolver));

Modified: tapestry/tapestry5/trunk/tapestry-core/src/main/resources/org/apache/tapestry/tapestry.js
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/main/resources/org/apache/tapestry/tapestry.js?rev=600189&r1=600188&r2=600189&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/main/resources/org/apache/tapestry/tapestry.js (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/main/resources/org/apache/tapestry/tapestry.js Sat Dec  1 11:57:19 2007
@@ -455,7 +455,7 @@
         // (borders and such).  Typically, such a Zone div will initially be invisible.
         // The show and update functions apply to the Zone div, not the update div.
 
-        var updates = div.select("DIV.t-zone-update");
+        var updates = this.div.select("DIV.t-zone-update");
 
         this.updatediv = updates.length == 0 ? this.div : updates[0];
     },

Added: tapestry/tapestry5/trunk/tapestry-core/src/site/apt/guide/css.apt
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/site/apt/guide/css.apt?rev=600189&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/site/apt/guide/css.apt (added)
+++ tapestry/tapestry5/trunk/tapestry-core/src/site/apt/guide/css.apt Sat Dec  1 11:57:19 2007
@@ -0,0 +1,56 @@
+ ---
+ Tapestry CSS Support
+ ---
+
+Tapestry CSS Support
+
+  Cascading Style Sheets (CSS) is an important technology, even with Tapestry.  Tapestry works best when the
+  rendered HTML is simple and semantic -- semantic meaning HTML that goes back to its roots, simple, straightforward,
+  with tags used for structure and, as much as possible, details about font, color and layout delegated to CSS.
+
+Default CSS Stylesheet
+
+  Tapestry includes a built-in stylesheet, default.css, is all HTML documents (documents that have an outer
+  \<html\> element and a nested \<head\> element).  The default.css stylesheet is always ordered <first> ... any additional stylesheets
+  will come after.  This allows Tapestry's default styles to be overridden.
+
+  All the styles in the default stylesheet are prefixed with "t-" (for Tapestry).
+
+Adding your own CSS
+
+  A page or component that is rendering the \<head\> tag can add a stylesheet directly in the markup.
+
++---+
+<head>
+  <link href="/css/myapp.css" rel="stylesheet" type="text/css"/>
+  . . .
++---+
+
+  If you want to leverage Tapestry's localization support, you may want to make use of an expansion and the asset: binding prefix:
+
+
++---+
+<head>
+  <link href="${asset:context:css/myapp.css}" rel="stylesheet" type="text/css"/>
+  . . .
++---+
+
+  The "asset:" prefix means that the remainder of the expansion is a path to a resource.  The "context:" part
+  indicates that it should look for the resource in the web application root (src/main/webapp in your workspace).  If you
+  left this out, it would look for the file on the classpath, relative to the component's Java class.
+
+Using the IncludeStylesheet Annotation
+
+ Another approach to adding a stylesheet is to include an
+ {{{../../apidocs/org/apache/tapestry/annotations/IncludeStylesheet.html}IncludeStylesheet}} annotation on your component class:
+
++---+
+@IncludeStylesheet("context:css/myapp.css")
+public class MyComponent
+{
+
+}
++---+
+
+ As with  {{{ajax.html}included JavaScript libraries}}, the stylesheet will only be added once,
+ regardless of the number of components that include it via the annotation.

Modified: tapestry/tapestry5/trunk/tapestry-core/src/site/site.xml
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/site/site.xml?rev=600189&r1=600188&r2=600189&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/site/site.xml (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/site/site.xml Sat Dec  1 11:57:19 2007
@@ -61,6 +61,7 @@
             <item name="Input Validation" href="guide/validation.html"/>
             <item name="BeanEditForm Guide" href="guide/beaneditform.html"/>
             <item name="Component Events" href="guide/event.html"/>
+            <item name="CSS" href="guide/css.html"/>
             <item name="Ajax" href="guide/ajax.html"/>
             <item name="Page Lifecycle" href="guide/lifecycle.html"/>
             <item name="Component Mixins" href="guide/mixins.html"/>

Added: tapestry/tapestry5/trunk/tapestry-core/src/test/app1/css/app.css
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/test/app1/css/app.css?rev=600189&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/test/app1/css/app.css (added)
+++ tapestry/tapestry5/trunk/tapestry-core/src/test/app1/css/app.css Sat Dec  1 11:57:19 2007
@@ -0,0 +1,3 @@
+BODY {
+    font-family: "Trebuchet MS";
+}
\ No newline at end of file

Modified: tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/IntegrationTests.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/IntegrationTests.java?rev=600189&r1=600188&r2=600189&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/IntegrationTests.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/IntegrationTests.java Sat Dec  1 11:57:19 2007
@@ -43,6 +43,10 @@
     {
         start("AssetDemo");
 
+        // Test for https://issues.apache.org/jira/browse/TAPESTRY-1935
+
+        assertSourcePresent("<link href=\"/css/app.css\" rel=\"stylesheet\" type=\"text/css\">");
+
         assertText("//img[@id='icon']/@src", "/images/tapestry_banner.gif");
 
         // doesn't prove that the image shows up in the client browser (it does, but

Modified: tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/app1/components/Border.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/app1/components/Border.java?rev=600189&r1=600188&r2=600189&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/app1/components/Border.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/integration/app1/components/Border.java Sat Dec  1 11:57:19 2007
@@ -14,9 +14,12 @@
 
 package org.apache.tapestry.integration.app1.components;
 
+import org.apache.tapestry.annotations.IncludeStylesheet;
+
 /**
  * Here's a component with a template, including a t:body element.
  */
+@IncludeStylesheet("context:css/app.css")
 public class Border
 {
 

Modified: tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/AssetInjectionProviderTest.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/AssetInjectionProviderTest.java?rev=600189&r1=600188&r2=600189&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/AssetInjectionProviderTest.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/AssetInjectionProviderTest.java Sat Dec  1 11:57:19 2007
@@ -17,6 +17,7 @@
 import org.apache.tapestry.annotations.Path;
 import org.apache.tapestry.internal.test.InternalBaseTestCase;
 import org.apache.tapestry.ioc.ObjectLocator;
+import org.apache.tapestry.ioc.Resource;
 import org.apache.tapestry.ioc.services.SymbolSource;
 import org.apache.tapestry.model.MutableComponentModel;
 import org.apache.tapestry.services.AssetSource;
@@ -57,6 +58,7 @@
         ClassTransformation ct = mockClassTransformation();
         MutableComponentModel model = mockMutableComponentModel();
         Path annotation = mockPath();
+        Resource baseResource = mockResource();
 
         String fieldName = "myField";
         Class fieldType = Object.class;
@@ -69,6 +71,11 @@
         train_expandSymbols(symbolSource, value, expanded);
 
         train_addInjectedField(ct, AssetSource.class, "assetSource", assetSource, "as");
+
+        train_getBaseResource(model, baseResource);
+
+        train_addInjectedField(ct, Resource.class, "baseResource", baseResource, "br");
+
         train_getResourcesFieldName(ct, "rez");
 
         // This only tests that the code is generated as expected (which is a bit brittle), it
@@ -76,8 +83,7 @@
         // tests for that.
 
         ct
-                .extendConstructor(
-                        "myField = (java.lang.Object) as.findAsset(rez.getBaseResource(), \"foo.gif\", rez.getLocale());");
+                .extendConstructor("myField = (java.lang.Object) as.findAsset(br, \"foo.gif\", rez.getLocale());");
 
         ct.makeReadOnly(fieldName);
 

Modified: tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/MethodPrefixTarget.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/MethodPrefixTarget.java?rev=600189&r1=600188&r2=600189&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/MethodPrefixTarget.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry/internal/services/MethodPrefixTarget.java Sat Dec  1 11:57:19 2007
@@ -1,3 +1,17 @@
+// Copyright 2007 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.tapestry.internal.services;
 
 public class MethodPrefixTarget