Modified: 
websites/production/tapestry/content/building-tapestry-from-source.html
==============================================================================
--- websites/production/tapestry/content/building-tapestry-from-source.html 
(original)
+++ websites/production/tapestry/content/building-tapestry-from-source.html Sat 
Feb  3 18:21:36 2018
@@ -44,13 +44,26 @@
 
   <div class="wrapper bs">
 
-        <div id="navigation"><div class="nav"><ul class="alternate"><li><a  
href="index.html">Home</a></li><li><a  href="getting-started.html">Getting 
Started</a></li><li><a  href="documentation.html">Documentation</a></li><li><a  
href="download.html">Download</a></li><li><a  
href="about.html">About</a></li><li><a  class="external-link" 
href="http://www.apache.org/licenses/LICENSE-2.0";>License</a></li><li><a  
href="community.html">Community</a></li><li><a  class="external-link" 
href="http://www.apache.org/security/";>Security</a></li><li><a  
class="external-link" href="http://www.apache.org/";>Apache</a></li><li><a  
class="external-link" 
href="http://www.apache.org/foundation/sponsorship.html";>Sponsorship</a></li><li><a
  class="external-link" 
href="http://www.apache.org/foundation/thanks.html";>Thanks</a></li></ul></div></div>
+        <div id="navigation"><div class="nav"><ul class="alternate"><li><a  
href="index.html">Home</a></li><li><a  href="getting-started.html">Getting 
Started</a></li><li><a  href="documentation.html">Documentation</a></li><li><a  
href="download.html">Download</a></li><li><a  
href="about.html">About</a></li><li><a  class="external-link" 
href="http://www.apache.org/licenses/LICENSE-2.0";>License</a></li><li><a  
href="community.html">Community</a></li><li><a  class="external-link" 
href="http://www.apache.org/security/";>Security</a></li><li><a  
class="external-link" href="http://www.apache.org/";>Apache</a></li><li><a  
class="external-link" 
href="http://www.apache.org/foundation/sponsorship.html";>Sponsorship</a></li><li><a
  class="external-link" 
href="http://www.apache.org/foundation/thanks.html";>Thanks</a></li></ul></div>
+
+</div>
 
           <div id="top">
-            <div id="smallbanner"><div class="searchbox" 
style="float:right;margin: .3em 1em .1em 1em"><span style="color: #999; 
font-size: 90%">Tapestry docs, issues, wikis &amp; blogs:</span><form 
enctype="application/x-www-form-urlencoded" method="get" 
action="http://tapestry.apache.org/search.html";> 
- <input type="text" name="q"> 
- <input type="submit" value="Search"> 
-</form></div><div class="emblem" style="float:left"><p><a  
href="index.html"><span class="confluence-embedded-file-wrapper"><img 
class="confluence-embedded-image confluence-external-resource" 
src="http://tapestry.apache.org/images/tapestry_small.png"; 
data-image-src="http://tapestry.apache.org/images/tapestry_small.png";></span></a></p></div><div
 class="title" style="float:left; margin: 0 0 0 3em"><h1 
id="SmallBanner-PageTitle">Building Tapestry from Source</h1></div></div>
+            <div id="smallbanner"><div class="searchbox" 
style="float:right;margin: .3em 1em .1em 1em"><span style="color: #999; 
font-size: 90%">Tapestry docs, issues, wikis &amp; blogs:</span>
+<form enctype="application/x-www-form-urlencoded" method="get" 
action="http://tapestry.apache.org/search.html";>
+  <input type="text" name="q">
+  <input type="submit" value="Search">
+</form>
+
+</div>
+
+
+<div class="emblem" style="float:left"><p><a  href="index.html"><span 
class="confluence-embedded-file-wrapper"><img class="confluence-embedded-image 
confluence-external-resource" 
src="http://tapestry.apache.org/images/tapestry_small.png"; 
data-image-src="http://tapestry.apache.org/images/tapestry_small.png";></span></a></p></div>
+
+
+<div class="title" style="float:left; margin: 0 0 0 3em"><h1 
id="SmallBanner-PageTitle">Building Tapestry from Source</h1></div>
+
+</div>
       <div class="clearer"></div>
       </div>
 
@@ -62,7 +75,7 @@
       </div>
 
       <div id="content">
-                <div id="ConfluenceContent"><p>This is a guide to building 
Tapestry itself from source code. This is primarily of interest to Tapestry 
<em>contributors</em>, rather than Tapestry <em>users</em>.</p><p>Although 
Tapestry <em>users</em> are free to use any build mechanism for their own 
projects (and first class Maven support is provided), to build Tapestry itself 
from source you will use Gradle.</p><p>Note: Both command line and Eclipse 
Gradle IDE/EGit instructions are given here. Generally you'll want to chose 
approach one or the other, rather than mixing them.</p><h2 
id="BuildingTapestryfromSource-Prerequisites">Prerequisites</h2><ul><li>Install 
a <strong>Java JDK</strong> (Sun/Oracle, not OpenJDK), version 1.7 (just to 
prevent VU#225657, see: <a  class="external-link" 
href="http://www.kb.cert.org/vuls/id/225657"; 
rel="nofollow">http://www.kb.cert.org/vuls/id/225657</a>), or version 1.8 for 
Tapestry 5.5 and later.</li><li>Install an <strong>IDE</strong> (IDEA IntelliJ 
 is recommended (and free to Tapestry committers), but Eclipse will also work. 
NetBeans is reported to work as well.</li><li><strong>Firefox</strong>: For 
Tapestry 5.4.x and earlier, install Firefox browser <a  class="external-link" 
href="https://ftp.mozilla.org/pub/firefox/releases/42.0/"; 
rel="nofollow">version 42</a> or earlier, needed for the integration tests 
(because newer versions require a newer version of Selenium than Tapestry's 
Java version requirements allow).</li><li><s>Set the Firefox browser's 
"preferred language" to English (en), because some tests will otherwise 
fail.</s> (Fixed; see <a  class="external-link" 
href="https://issues.apache.org/jira/browse/TAP5-2413";>TAP5-2413</a>)</li><li>Install
 a <strong>Git</strong> client<ul><li>Command-line users: <a  
class="external-link" href="http://git-scm.com/downloads"; 
rel="nofollow">http://git-scm.com/downloads</a></li><li>Eclipse users: install 
EGit from the Eclipse Marketplace, then in In Window &gt; Preferences &gt; Team 
&
 gt; Git, set your "Default repository folder" (e.g. <code>~/git</code> or 
<code>%HOME%\git</code>). Note that for Eclipse 4.4 (Luna) and later Git 
support is built in.</li></ul></li><li>Install <strong>Gradle</strong> 
1.0-milestone-3 or newer (or a Gradle plugin to your IDE),<ul><li>Command-line 
users: nothing to do (Tapestry's Gradle wrapper, gradlew, will download Gradle 
automatically on first use).</li><li>Eclipse users: Install Gradle IDE (aka 
Gradle Integration for Eclipse), from the Eclipse Marketplace. Note that for 
Eclipse 4.6 (Neon) and later, Gradle support is built 
in.</li></ul></li></ul><h2 
id="BuildingTapestryfromSource-GettingStarted">Getting Started</h2><p>Please 
read <a  class="external-link" 
href="https://git-wip-us.apache.org/";>https://git-wip-us.apache.org/</a> 
first.</p><p>Windows users (especialy EGit users) should probably set the 
core.autocrlf config setting to <code>false</code> so that local diffs won't 
highlight line ending differences.</p><h3 id="BuildingT
 apestryfromSource-ClonetheRepository">Clone the Repository</h3><p>Clone 
Tapestry from the Git repo:</p><ul><li><p>Command-line git users:</p><div 
class="table-wrap"><table class="confluenceTable"><tbody><tr><td colspan="1" 
rowspan="1" class="confluenceTd"><p>Non Committers:</p></td><td colspan="1" 
rowspan="1" class="confluenceTd"><p>git clone</p><a  class="external-link" 
href="http://git-wip-us.apache.org/repos/asf/tapestry-5.git";>http://git-wip-us.apache.org/repos/asf/tapestry-5.git</a><p>&#160;</p></td></tr><tr><td
 colspan="1" rowspan="1" class="confluenceTd"><p>Committers:</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>git clone</p><a  
class="external-link" 
href="https://git-wip-us.apache.org/repos/asf/tapestry-5.git";>https://git-wip-us.apache.org/repos/asf/tapestry-5.git</a><p>&#160;</p></td></tr></tbody></table></div></li><li>Eclipse
 EGit users:<ul><li>Switch to Git perspective; then copy one of the URLs above 
into paste buffer</li><li>Right-click &gt; Paste reposi
 tory path or URI. This will bring up the Clone Git Repository 
dialog.</li><li>Committers: make sure Protocol is https, and enter your Apache 
commiter LDAP user name &amp; password</li><li>click Next.</li><li>Select the 
branches you're interested in (e.g 5.3 and master), click Next</li><li>Select 
Directory to where you want the project source code (e.g. 
<code>~/git/tapestry-5</code> or 
<code>%HOME%\git\tapestry-5</code>)</li><li>Select whichever "Initial Branch" 
you're interested in (e.g. master)</li><li>Set "Remote name" to "origin" (the 
default)</li><li><strong>VERY IMPORTANT</strong>: uncheck the "Import all 
existing projects" checkbox (we'll do this using Gradle, below)</li><li>Click 
Finish. (Be patient; the clone operation might take a few 
minutes.)</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-GradlePreparation">Gradle 
Preparation</h3><ul><li>Command-line gradle users only:<ul><li>If you're using 
Eclipse but <strong>not</strong> Gradle IDE do <code>./gradlew eclipse</co
 de></li><li>The command-line Gradle's eclipse plugin doesn't include the 
provided project dependencies; you need to add them manually (Java Build Path 
&gt; Projects &gt; Add tapestry-test). The plugin also generates a root eclipse 
project, so you'll need to delete the ".project" file in the root folder, and 
then you can import all Tapestry sub-projects at 
once.</li></ul></li><li>Eclipse Gradle IDE users:<ul><li>Switch to Java (or 
JEE) perspective and right-click &gt; Import... &gt; Gradle &gt; Gradle Project 
&gt; Next.</li><li>Set the "Root folder" to where you put your Tapestry source 
in the previous section (e.g. <code>~/git/tapestry-5</code> or 
<code>%Home%\git\tapestry-5</code>)</li><li>Click <code>Build Model. When it 
completes, s</code>elect the top-level (the top-level module and all 
sub-modules).</li><li>Be sure the "Enable dependency management" and "Create 
workingset 'tapestry-5' checkboxes are checked.</li><li>Click 
<code>Finish</code>. (Be patient; the import operation m
 ight take a few minutes.)</li></ul></li><li>Eclipse EGit users: Do a Git 
"Share" on the project:<ul><li>Still in the Java (or JEE) perspective, select 
all of the Tapestry projects (top-level and sub-modules) and right-click &gt; 
Team &gt; Share Project... &gt; Git &gt; Next &gt; Ensure all are selected, 
click <code>Finish</code>.</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-Antlr">Antlr</h3><p>The 
<code>tapestry-core</code> project will initially have errors because of 
missing Java classes that are produced by ANTLR the first time the project is 
built. To fix this:</p><ul><li>Eclipse Gradle IDE users:<ul><li>Right click on 
the <code>build.gradle</code> file within tapestry-core and click Run As &gt; 
"Gradle build...", check <strong>only</strong> the generateGrammarSource task, 
and change the "Name" field to something like "tapestry-core antlr", then click 
Apply and Run.</li><li>When it's finished, the antlr-generated classes (e.g. 
PropertyExpressionLexer.java) will be in cr
 eated in $buildDir/generated-sources/antlr/, but Eclipse doesn't yet know 
about that path. To fix that, right click on the <code>tapestry-core</code> 
project &gt; Properties &gt; Java Build Path &gt; Source &gt; Add Folder &gt; 
find <code>tapestry-core/build/generated-sources/antlr</code> and check the 
checkbox next to it, then click <code>OK</code>.</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-CoffeeScript">CoffeeScript</h3><p>If you want to 
run tests from within Eclipse, Tapestry will complain that it won't find 
certain JavaScript files that normally are generated during compile time from 
their Coffeescript sources. In order to generate the JavaScript files you need 
to have Coffeescript installed and in your path. Simply install <a  
class="external-link" href="http://nodejs.org/download/"; 
rel="nofollow">Node.js</a> and afterwards run <code>npm install -g 
coffee-script</code>. The installation should take care of 
everything.</p><ul><li>Eclipse Gradle IDE users:<ul><li>Righ
 t click on the <code>build.gradle</code> file within tapestry-core and click 
Run As &gt; "Gradle build...", check <strong>only</strong> the 
tapestry-core:compileCoffeeScript and tapestry-core:compileTestCoffeeScript 
tasks, and change the "Name" field to something like "tapestry-core 
coffeescript", then click Apply and Run.</li><li>When it's finished, the 
coffeescript-generated JavaScript files (e.g. t5-core-dom-jquery.js) will be in 
created in $buildDir/generated-sources/compiled-coffeescript/ and 
$buildDir/generated-sources/compiled-test-coffeescript/, but Eclipse doesn't 
yet know about that path. To fix that, right click on the 
<code>tapestry-core</code> project &gt; Properties &gt; Java Build Path &gt; 
Source &gt; Add Folder &gt; find 
<code>tapestry-core/build/generated-sources/compiled-coffeescript</code> and 
<code>tapestry-core/build/generated-sources/compiled-test-coffeescript</code> 
and check the checkbox next to it, then click 
<code>OK</code>.</li></ul></li></ul><h3 id="Buil
 
dingTapestryfromSource-GenerateCoffeeScriptandAntlrfilesautomaticallywhenchanged">Generate
 CoffeeScript and Antlr files automatically when changed</h3><p>If you want to 
have Eclipse compile the JavaScript files and lexer classes from their 
Coffeescript sources and Antlr files automatically when they change, you can do 
that by configuring an additional builder for the <code>tapestry-core</code> 
project:</p><ul><li>Eclipse Gradle IDE users:<ul><li>Right click on the 
<code>tapestry-core</code> project and select properties.</li><li>Select the 
"Builders" entry from the list on the left and click "New.." in the right 
panel.</li><li>Select "Program" and click "Ok".</li><li>Give the program a 
meaningful name, e.g. "compile coffeescript and antlr".</li><li>Switch to the 
"Main" tab.</li><li>For "Location:" click "Browse Workspace..." and select 
gradlew (for Mac/Linux) or <code>gradlew.bat (for Windows)</code> in the 
Tapestry root project. If the root project is called "tapestry-5" the entry 
 should look similar to "${workspace_loc:/tapestry-5/gradlew.bat}".</li><li>For 
"Working Directory:" click "Browse Workspace..." and select the Tapestry root 
project.</li><li>For "Arguments:" enter 
<code>tapestry-core:generateGrammarSource tapestry-core:compileCoffeeScript 
tapestry-core:compileTestCoffeeScript</code></li><li>Switch to the "Build 
Options" tab.</li><li>Make sure that only "Allocate Console", "After a 
"Clean"", "During manual builds", "During auto builds" and "Specify working set 
of relevant resources" are checked.</li><li>Click "Specify 
Resources...".</li><li>From the "tapestry-core" project select 
"src/main/antlr", "src/main/coffeescript", and 
"src/test/coffeescript".</li><li>Click "Finish".</li><li>Click 
"OK".</li><li>Click "OK".</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-Building">Building</h3><p>You can build 
individual modules, or (from the root folder) build 
everything.</p><ul><li>Command-line users:<br clear="none"> *( "gradlew" is the 
gradle wrapper 
 shell script (gradlew) or batch file (gradlew.bat) found in the root folder of 
the Tapestry source.<ul><li><code>./gradlew 
build</code></li></ul></li><li>Eclipse Gradle IDE users:<ul><li>Right click on 
the top-level project (or any sub-project) and select Run As &gt; Gradle 
Build..., which starts an External Tools Configuration dialog box. Enter a 
reasonable name, select the tasks you want to run (for example, 
tapestry-core/install), and click Run.</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-SeleniumSetup">Selenium Setup</h3><p>It is 
necessary that you have a compatible version of Firefox installed. &#160;On a 
Mac, you should install it in ~/Applications (rather than 
/Applications).</p><p>You should modify your ~/.bash_profile (or equivalent), 
to add ~/Applications/Firefox.app/Contents/MacOS to the PATH variable.</p><h3 
id="BuildingTapestryfromSource-RunningIndividualTests">Running Individual 
Tests</h3><p>Eclipse users:</p><ul><li>Install the <a  class="external-link" 
href
 ="http://testng.org/doc/eclipse.html"; rel="nofollow">TestNG plugin</a> to 
allow running of individual TestNG unit tests from within in 
Eclipse.</li><li>Right-click on any test class and select Run As &gt;TestNG 
Test</li></ul><p>Command-line users:</p><ul><li>./gradlew 
-Dtest.single=myclassname</li><li>./gradlew 
-Dtest.single=myclassname.mymethod</li></ul><p>where myclassname is the test 
class, such as FormTest</p><p>The Tapestry integration tests will repeatedly 
start up a Firefox browser.</p><ul><li>Ensure that your environment will allow 
a connection to <a  class="external-link" href="https://localhost:9090"; 
rel="nofollow">https://localhost:9090</a></li></ul><h3 
id="BuildingTapestryfromSource-SkippingTests">Skipping Tests</h3><p>Running the 
Tapestry integration tests can take 10 minutes or more (mostly because of 
Selenium tests, which repeatedly start and stop the Firefox browser), so you 
won't want to run them every time you try a change.</p><ul><li>Command-line 
users:<ul><li><co
 de>To build while skipping all tests: ./gradlew build -x 
test</code></li><li>You can skip tests on a specific module by adding a colon 
and the module name. For example: <code>-x 
test:tapestry-ioc</code></li></ul></li><li>Eclipse Gradle IDE users:<ul><li>In 
your External Tools Configuration, add the same -x test option as above at 
Arguments &gt; Program Arguments.</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-RunningtheIntegrationTestAppsManually">Running 
the Integration Test Apps Manually</h3><p>The Tapestry source includes several 
web apps that are used by the automated Selenium integration tests. You can 
also run these apps manually to try out nearly every browser-visible aspect of 
Tapestry.</p><ul><li>Command-line users:<ul><li>./gradlew 
runTestApp1</li></ul></li><li>Eclipse users:<ul><li>Use the run-jetty-run 
plugin in Eclipse, with the context directory selected from among the 
<code>test</code> context directories. For example, in the tapestry-core 
module, right click o
 n the /src/test/app1 (or app2, etc) folder, and select Run As &gt; Run Jetty, 
then open your browser to <a  class="external-link" 
href="http://localhost:8080/tapestry-core"; 
rel="nofollow">http://localhost:8080/tapestry-core</a></li></ul></li></ul><h3 
id="BuildingTapestryfromSource-MakingCodeChanges">Making Code 
Changes</h3><p>Once you have cloned or pulled the latest changes to your local 
Git repository, you can start working on it. Whenever you make some changes to 
the codebase, it's good to have a related issue filed in JIRA and to use a 
similarly named branch in your local Git repository. For example, to create a 
branch for an issue with the key TAP5-123:</p><div class="code panel pdl" 
style="border-width: 1px;"><div class="codeContent panelContent pdl">
+                <div id="ConfluenceContent"><p>This is a guide to building 
Tapestry itself from source code. This is primarily of interest to Tapestry 
<em>contributors</em>, rather than Tapestry <em>users</em>.</p><p>Although 
Tapestry <em>users</em> are free to use any build mechanism for their own 
projects (and first class Maven support is provided), to build Tapestry itself 
from source you will use Gradle.</p><p>Note: Both command line and Eclipse 
Gradle IDE/EGit instructions are given here. Generally you'll want to chose 
approach one or the other, rather than mixing them.</p><h2 
id="BuildingTapestryfromSource-Prerequisites">Prerequisites</h2><ul><li>Install 
a <strong>Java JDK</strong> (Sun/Oracle, not OpenJDK), version 1.7 (just to 
prevent VU#225657, see: <a  class="external-link" 
href="http://www.kb.cert.org/vuls/id/225657"; 
rel="nofollow">http://www.kb.cert.org/vuls/id/225657</a>), or version 1.8 for 
Tapestry 5.5 and later.</li><li>Install an <strong>IDE</strong> (IDEA IntelliJ 
 is recommended (and free to Tapestry committers), but Eclipse will also work. 
NetBeans is reported to work as well.</li><li><strong>Firefox</strong>: For 
Tapestry 5.4.x and earlier, install Firefox browser <a  class="external-link" 
href="https://ftp.mozilla.org/pub/firefox/releases/42.0/"; 
rel="nofollow">version 42</a> or earlier, needed for the integration tests 
(because newer versions require a newer version of Selenium than Tapestry's 
Java version requirements allow).</li><li><s>Set the Firefox browser's 
"preferred language" to English (en), because some tests will otherwise 
fail.</s> (Fixed; see <a  class="external-link" 
href="https://issues.apache.org/jira/browse/TAP5-2413";>TAP5-2413</a>)</li><li>Install
 a <strong>Git</strong> client<ul><li>Command-line users: <a  
class="external-link" href="http://git-scm.com/downloads"; 
rel="nofollow">http://git-scm.com/downloads</a></li><li>Eclipse users: install 
EGit from the Eclipse Marketplace, then in In Window &gt; Preferences &gt; Team 
&
 gt; Git, set your "Default repository folder" (e.g. <code>~/git</code> or 
<code>%HOME%\git</code>). Note that for Eclipse 4.4 (Luna) and later Git 
support is built in.</li></ul></li><li>Install <strong>Gradle</strong> 
1.0-milestone-3 or newer (or a Gradle plugin to your IDE),<ul><li>Command-line 
users: nothing to do (Tapestry's Gradle wrapper, gradlew, will download Gradle 
automatically on first use).</li><li>Eclipse users: Install Gradle IDE (aka 
Gradle Integration for Eclipse), from the Eclipse Marketplace. Note that for 
Eclipse 4.6 (Neon) and later, Gradle support is built 
in.</li></ul></li></ul><h2 
id="BuildingTapestryfromSource-GettingStarted">Getting Started</h2><p>Please 
read <a  class="external-link" 
href="https://git-wip-us.apache.org/";>https://git-wip-us.apache.org/</a> 
first.</p><p>Windows users (especialy EGit users) should probably set the 
core.autocrlf config setting to <code>false</code> so that local diffs won't 
highlight line ending differences.</p><h3 id="BuildingT
 apestryfromSource-ClonetheRepository">Clone the Repository</h3><p>Clone 
Tapestry from the Git repo:</p><ul><li><p>Command-line git users:</p><div 
class="table-wrap"><table class="confluenceTable"><tbody><tr><td colspan="1" 
rowspan="1" class="confluenceTd"><p>Non Committers:</p></td><td colspan="1" 
rowspan="1" class="confluenceTd"><p>git clone</p><a  class="external-link" 
href="http://git-wip-us.apache.org/repos/asf/tapestry-5.git";>http://git-wip-us.apache.org/repos/asf/tapestry-5.git</a><p>&#160;</p></td></tr><tr><td
 colspan="1" rowspan="1" class="confluenceTd"><p>Committers:</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>git clone</p><a  
class="external-link" 
href="https://git-wip-us.apache.org/repos/asf/tapestry-5.git";>https://git-wip-us.apache.org/repos/asf/tapestry-5.git</a><p>&#160;</p></td></tr></tbody></table></div></li><li>Eclipse
 EGit users:<ul><li>Switch to Git perspective; then copy one of the URLs above 
into paste buffer</li><li>Right-click &gt; Paste reposi
 tory path or URI. This will bring up the Clone Git Repository 
dialog.</li><li>Committers: make sure Protocol is https, and enter your Apache 
commiter LDAP user name &amp; password</li><li>click Next.</li><li>Select the 
branches you're interested in (e.g 5.3 and master), click Next</li><li>Select 
Directory to where you want the project source code (e.g. 
<code>~/git/tapestry-5</code> or 
<code>%HOME%\git\tapestry-5</code>)</li><li>Select whichever "Initial Branch" 
you're interested in (e.g. master)</li><li>Set "Remote name" to "origin" (the 
default)</li><li><strong>VERY IMPORTANT</strong>: uncheck the "Import all 
existing projects" checkbox (we'll do this using Gradle, below)</li><li>Click 
Finish. (Be patient; the clone operation might take a few 
minutes.)</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-GradlePreparation">Gradle 
Preparation</h3><ul><li>Command-line gradle users only:<ul><li>If you're using 
Eclipse but <strong>not</strong> Gradle IDE do <code>./gradlew eclipse</co
 de></li><li>The command-line Gradle's eclipse plugin doesn't include the 
provided project dependencies; you need to add them manually (Java Build Path 
&gt; Projects &gt; Add tapestry-test). The plugin also generates a root eclipse 
project, so you'll need to delete the ".project" file in the root folder, and 
then you can import all Tapestry sub-projects at 
once.</li></ul></li><li>Eclipse Gradle IDE users:<ul><li>Switch to Java (or 
JEE) perspective and right-click &gt; Import... &gt; Gradle &gt; Gradle Project 
&gt; Next.</li><li>Set the "Root folder" to where you put your Tapestry source 
in the previous section (e.g. <code>~/git/tapestry-5</code> or 
<code>%Home%\git\tapestry-5</code>)</li><li>Click <code>Build Model. When it 
completes, s</code>elect the top-level (the top-level module and all 
sub-modules).</li><li>Be sure the "Enable dependency management" and "Create 
workingset 'tapestry-5' checkboxes are checked.</li><li>Click 
<code>Finish</code>. (Be patient; the import operation m
 ight take a few minutes.)</li></ul></li><li>Eclipse EGit users: Do a Git 
"Share" on the project:<ul><li>Still in the Java (or JEE) perspective, select 
all of the Tapestry projects (top-level and sub-modules) and right-click &gt; 
Team &gt; Share Project... &gt; Git &gt; Next &gt; Ensure all are selected, 
click <code>Finish</code>.</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-Antlr">Antlr</h3><p>The 
<code>tapestry-core</code> project will initially have errors because of 
missing Java classes that are produced by ANTLR the first time the project is 
built. To fix this:</p><ul><li>Eclipse Gradle IDE users:<ul><li>Right click on 
the <code>build.gradle</code> file within tapestry-core and click Run As &gt; 
"Gradle build...", check <strong>only</strong> the generateGrammarSource task, 
and change the "Name" field to something like "tapestry-core antlr", then click 
Apply and Run.</li><li>When it's finished, the antlr-generated classes (e.g. 
PropertyExpressionLexer.java) will be in cr
 eated in $buildDir/generated-sources/antlr/, but Eclipse doesn't yet know 
about that path. To fix that, right click on the <code>tapestry-core</code> 
project &gt; Properties &gt; Java Build Path &gt; Source &gt; Add Folder &gt; 
find <code>tapestry-core/build/generated-sources/antlr</code> and check the 
checkbox next to it, then click <code>OK</code>.</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-CoffeeScript">CoffeeScript</h3><p>If you want to 
run tests from within Eclipse, Tapestry will complain that it won't find 
certain JavaScript files that normally are generated during compile time from 
their Coffeescript sources. In order to generate the JavaScript files you need 
to have Coffeescript installed and in your path. Simply install <a  
class="external-link" href="http://nodejs.org/download/"; 
rel="nofollow">Node.js</a> and afterwards run <code>npm install -g 
coffee-script</code>. The installation should take care of 
everything.</p><ul><li>Eclipse Gradle IDE users:<ul><li>Righ
 t click on the <code>build.gradle</code> file within tapestry-core and click 
Run As &gt; "Gradle build...", check <strong>only</strong> the 
tapestry-core:compileCoffeeScript and tapestry-core:compileTestCoffeeScript 
tasks, and change the "Name" field to something like "tapestry-core 
coffeescript", then click Apply and Run.</li><li>When it's finished, the 
coffeescript-generated JavaScript files (e.g. t5-core-dom-jquery.js) will be in 
created in $buildDir/generated-sources/compiled-coffeescript/ and 
$buildDir/generated-sources/compiled-test-coffeescript/, but Eclipse doesn't 
yet know about that path. To fix that, right click on the 
<code>tapestry-core</code> project &gt; Properties &gt; Java Build Path &gt; 
Source &gt; Add Folder &gt; find 
<code>tapestry-core/build/generated-sources/compiled-coffeescript</code> and 
<code>tapestry-core/build/generated-sources/compiled-test-coffeescript</code> 
and check the checkbox next to it, then click 
<code>OK</code>.</li></ul></li></ul><h3 id="Buil
 
dingTapestryfromSource-GenerateCoffeeScriptandAntlrfilesautomaticallywhenchanged">Generate
 CoffeeScript and Antlr files automatically when changed</h3><p>If you want to 
have Eclipse compile the JavaScript files and lexer classes from their 
Coffeescript sources and Antlr files automatically when they change, you can do 
that by configuring an additional builder for the <code>tapestry-core</code> 
project:</p><ul><li>Eclipse Gradle IDE users:<ul><li>Right click on the 
<code>tapestry-core</code> project and select properties.</li><li>Select the 
"Builders" entry from the list on the left and click "New.." in the right 
panel.</li><li>Select "Program" and click "Ok".</li><li>Give the program a 
meaningful name, e.g. "compile coffeescript and antlr".</li><li>Switch to the 
"Main" tab.</li><li>For "Location:" click "Browse Workspace..." and select 
gradlew (for Mac/Linux) or <code>gradlew.bat (for Windows)</code> in the 
Tapestry root project. If the root project is called "tapestry-5" the entry 
 should look similar to "${<a  class="external-link" 
href="http://workspace_loc/tapestry-5/gradlew.bat"; 
rel="nofollow">workspace_loc:/tapestry-5/gradlew.bat</a>}".</li><li>For 
"Working Directory:" click "Browse Workspace..." and select the Tapestry root 
project.</li><li>For "Arguments:" enter 
<code>tapestry-core:generateGrammarSource tapestry-core:compileCoffeeScript 
tapestry-core:compileTestCoffeeScript</code></li><li>Switch to the "Build 
Options" tab.</li><li>Make sure that only "Allocate Console", "After a 
"Clean"", "During manual builds", "During auto builds" and "Specify working set 
of relevant resources" are checked.</li><li>Click "Specify 
Resources...".</li><li>From the "tapestry-core" project select 
"src/main/antlr", "src/main/coffeescript", and 
"src/test/coffeescript".</li><li>Click "Finish".</li><li>Click 
"OK".</li><li>Click "OK".</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-Building">Building</h3><p>You can build 
individual modules, or (from the root folder) build
  everything.</p><ul><li>Command-line users:<br clear="none"> *( "gradlew" is 
the gradle wrapper shell script (gradlew) or batch file (gradlew.bat) found in 
the root folder of the Tapestry source.<ul><li><code>./gradlew 
build</code></li></ul></li><li>Eclipse Gradle IDE users:<ul><li>Right click on 
the top-level project (or any sub-project) and select Run As &gt; Gradle 
Build..., which starts an External Tools Configuration dialog box. Enter a 
reasonable name, select the tasks you want to run (for example, 
tapestry-core/install), and click Run.</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-SeleniumSetup">Selenium Setup</h3><p>It is 
necessary that you have a compatible version of Firefox installed. &#160;On a 
Mac, you should install it in ~/Applications (rather than 
/Applications).</p><p>You should modify your ~/.bash_profile (or equivalent), 
to add ~/Applications/Firefox.app/Contents/MacOS to the PATH variable.</p><h3 
id="BuildingTapestryfromSource-RunningIndividualTests">Runn
 ing Individual Tests</h3><p>Eclipse users:</p><ul><li>Install the <a  
class="external-link" href="http://testng.org/doc/eclipse.html"; 
rel="nofollow">TestNG plugin</a> to allow running of individual TestNG unit 
tests from within in Eclipse.</li><li>Right-click on any test class and select 
Run As &gt;TestNG Test</li></ul><p>Command-line users:</p><ul><li>./gradlew 
-Dtest.single=myclassname</li><li>./gradlew 
-Dtest.single=myclassname.mymethod</li></ul><p>where myclassname is the test 
class, such as FormTest</p><p>The Tapestry integration tests will repeatedly 
start up a Firefox browser.</p><ul><li>Ensure that your environment will allow 
a connection to <a  class="external-link" href="https://localhost:9090"; 
rel="nofollow">https://localhost:9090</a></li></ul><h3 
id="BuildingTapestryfromSource-SkippingTests">Skipping Tests</h3><p>Running the 
Tapestry integration tests can take 10 minutes or more (mostly because of 
Selenium tests, which repeatedly start and stop the Firefox browser), so y
 ou won't want to run them every time you try a change.</p><ul><li>Command-line 
users:<ul><li><code>To build while skipping all tests: ./gradlew build -x 
test</code></li><li>You can skip tests on a specific module by adding a colon 
and the module name. For example: <code>-x 
test:tapestry-ioc</code></li></ul></li><li>Eclipse Gradle IDE users:<ul><li>In 
your External Tools Configuration, add the same -x test option as above at 
Arguments &gt; Program Arguments.</li></ul></li></ul><h3 
id="BuildingTapestryfromSource-RunningtheIntegrationTestAppsManually">Running 
the Integration Test Apps Manually</h3><p>The Tapestry source includes several 
web apps that are used by the automated Selenium integration tests. You can 
also run these apps manually to try out nearly every browser-visible aspect of 
Tapestry.</p><ul><li>Command-line users:<ul><li>./gradlew 
runTestApp1</li></ul></li><li>Eclipse users:<ul><li>Use the run-jetty-run 
plugin in Eclipse, with the context directory selected from among th
 e <code>test</code> context directories. For example, in the tapestry-core 
module, right click on the /src/test/app1 (or app2, etc) folder, and select Run 
As &gt; Run Jetty, then open your browser to <a  class="external-link" 
href="http://localhost:8080/tapestry-core"; 
rel="nofollow">http://localhost:8080/tapestry-core</a></li></ul></li></ul><h3 
id="BuildingTapestryfromSource-MakingCodeChanges">Making Code 
Changes</h3><p>Once you have cloned or pulled the latest changes to your local 
Git repository, you can start working on it. Whenever you make some changes to 
the codebase, it's good to have a related issue filed in JIRA and to use a 
similarly named branch in your local Git repository. For example, to create a 
branch for an issue with the key TAP5-123:</p><div class="code panel pdl" 
style="border-width: 1px;"><div class="codeContent panelContent pdl">
 <pre class="brush: java; gutter: false; theme: Default" 
style="font-size:12px;">git branch TAP5-123 origin/master</pre>
 </div></div><p>With per-issue branches you can easily switch back and forth 
between different issues without worrying about unwanted side-effects from 
unfinished changes to other issues. Whenever you want to work on the TAP5-123 
example issue, simply checkout that branch and start making your 
changes:</p><div class="code panel pdl" style="border-width: 1px;"><div 
class="codeContent panelContent pdl">
 <pre class="brush: java; gutter: false; theme: Default" 
style="font-size:12px;">git checkout TAP5-123</pre>
@@ -78,7 +91,7 @@
 20:22:11.439 [ERROR] [org.gradle.BuildExceptionReporter] A problem occurred 
evaluating root project 'tapestry-project-trunk'.
 20:22:11.440 [ERROR] [org.gradle.BuildExceptionReporter] Cause: Cannot get 
property 'plus' on null object
 </pre>
-</div></div><p><strong>Solution:</strong> Use the gradle wrapper (./gradlew 
build), not plain "gradle".</p><hr><p>&#160;</p><p><strong>Problem 2</strong>: 
Under Linux I get java.io.FileNotFoundException saying "Too many open 
files"</p><p><strong>Solution</strong>: You may have to increase the number of 
files your operating system allows you to have open at once. Try <code>ulimit 
-n</code> to see what the current value is, and if it is less than 2048, 
increase it to 2048 by editing your <code>/etc/security/limits.conf</code> 
file. See your operating system's documentation for 
details.</p><hr><p><strong><br clear="none"></strong></p><p><strong>Problem 
3:</strong> The gradle build opens a Firefox browser with a File Not Found 
error:</p><div class="code panel pdl" style="border-width: 1px;"><div 
class="codeContent panelContent pdl">
+</div></div><p><strong>Solution:</strong> Use the gradle wrapper (./gradlew 
build), not plain "gradle".</p><hr><p>&#160;</p><p><strong>Problem 2</strong>: 
Under Linux I get <a  class="external-link" href="http://java.io"; 
rel="nofollow">java.io</a>.FileNotFoundException saying "Too many open 
files"</p><p><strong>Solution</strong>: You may have to increase the number of 
files your operating system allows you to have open at once. Try <code>ulimit 
-n</code> to see what the current value is, and if it is less than 2048, 
increase it to 2048 by editing your <code>/etc/security/limits.conf</code> 
file. See your operating system's documentation for 
details.</p><hr><p><strong><br clear="none"></strong></p><p><strong>Problem 
3:</strong> The gradle build opens a Firefox browser with a File Not Found 
error:</p><div class="code panel pdl" style="border-width: 1px;"><div 
class="codeContent panelContent pdl">
 <pre class="brush: java; gutter: false; theme: Default" 
style="font-size:12px;">Firefox can't find the file at 
chrome://src/content/RemoteRunner.html
 ?sessionId=74c5c263747249739d82e4bee33fb4b6&amp;multiWindow=true&amp;baseUrl=
 
http://localhost:9090/&amp;debugMode=false&amp;driverUrl=http://localhost:4444/selenium-server/driver/.</pre>

Modified: websites/production/tapestry/content/cache/main.pageCache
==============================================================================
Binary files - no diff available.

Modified: websites/production/tapestry/content/component-cheat-sheet.html
==============================================================================
--- websites/production/tapestry/content/component-cheat-sheet.html (original)
+++ websites/production/tapestry/content/component-cheat-sheet.html Sat Feb  3 
18:21:36 2018
@@ -44,13 +44,26 @@
 
   <div class="wrapper bs">
 
-        <div id="navigation"><div class="nav"><ul class="alternate"><li><a  
href="index.html">Home</a></li><li><a  href="getting-started.html">Getting 
Started</a></li><li><a  href="documentation.html">Documentation</a></li><li><a  
href="download.html">Download</a></li><li><a  
href="about.html">About</a></li><li><a  class="external-link" 
href="http://www.apache.org/licenses/LICENSE-2.0";>License</a></li><li><a  
href="community.html">Community</a></li><li><a  class="external-link" 
href="http://www.apache.org/security/";>Security</a></li><li><a  
class="external-link" href="http://www.apache.org/";>Apache</a></li><li><a  
class="external-link" 
href="http://www.apache.org/foundation/sponsorship.html";>Sponsorship</a></li><li><a
  class="external-link" 
href="http://www.apache.org/foundation/thanks.html";>Thanks</a></li></ul></div></div>
+        <div id="navigation"><div class="nav"><ul class="alternate"><li><a  
href="index.html">Home</a></li><li><a  href="getting-started.html">Getting 
Started</a></li><li><a  href="documentation.html">Documentation</a></li><li><a  
href="download.html">Download</a></li><li><a  
href="about.html">About</a></li><li><a  class="external-link" 
href="http://www.apache.org/licenses/LICENSE-2.0";>License</a></li><li><a  
href="community.html">Community</a></li><li><a  class="external-link" 
href="http://www.apache.org/security/";>Security</a></li><li><a  
class="external-link" href="http://www.apache.org/";>Apache</a></li><li><a  
class="external-link" 
href="http://www.apache.org/foundation/sponsorship.html";>Sponsorship</a></li><li><a
  class="external-link" 
href="http://www.apache.org/foundation/thanks.html";>Thanks</a></li></ul></div>
+
+</div>
 
           <div id="top">
-            <div id="smallbanner"><div class="searchbox" 
style="float:right;margin: .3em 1em .1em 1em"><span style="color: #999; 
font-size: 90%">Tapestry docs, issues, wikis &amp; blogs:</span><form 
enctype="application/x-www-form-urlencoded" method="get" 
action="http://tapestry.apache.org/search.html";> 
- <input type="text" name="q"> 
- <input type="submit" value="Search"> 
-</form></div><div class="emblem" style="float:left"><p><a  
href="index.html"><span class="confluence-embedded-file-wrapper"><img 
class="confluence-embedded-image confluence-external-resource" 
src="http://tapestry.apache.org/images/tapestry_small.png"; 
data-image-src="http://tapestry.apache.org/images/tapestry_small.png";></span></a></p></div><div
 class="title" style="float:left; margin: 0 0 0 3em"><h1 
id="SmallBanner-PageTitle">Component Cheat Sheet</h1></div></div>
+            <div id="smallbanner"><div class="searchbox" 
style="float:right;margin: .3em 1em .1em 1em"><span style="color: #999; 
font-size: 90%">Tapestry docs, issues, wikis &amp; blogs:</span>
+<form enctype="application/x-www-form-urlencoded" method="get" 
action="http://tapestry.apache.org/search.html";>
+  <input type="text" name="q">
+  <input type="submit" value="Search">
+</form>
+
+</div>
+
+
+<div class="emblem" style="float:left"><p><a  href="index.html"><span 
class="confluence-embedded-file-wrapper"><img class="confluence-embedded-image 
confluence-external-resource" 
src="http://tapestry.apache.org/images/tapestry_small.png"; 
data-image-src="http://tapestry.apache.org/images/tapestry_small.png";></span></a></p></div>
+
+
+<div class="title" style="float:left; margin: 0 0 0 3em"><h1 
id="SmallBanner-PageTitle">Component Cheat Sheet</h1></div>
+
+</div>
       <div class="clearer"></div>
       </div>
 
@@ -62,55 +75,94 @@
       </div>
 
       <div id="content">
-                <div id="ConfluenceContent"><p>&#160;</p><p>This is a summary 
of the more common annotations and methods you can add to Tapestry pages and 
component classes.</p><div class="aui-label" style="float:right" title="Related 
Articles"><h3>Related Articles</h3><ul class="content-by-label"><li> 
-  <div> 
-   <span class="icon aui-icon aui-icon-small aui-iconfont-page-default" 
title="Page">Page:</span> 
-  </div> 
-  <div class="details"> 
-   <a  href="component-parameters.html">Component Parameters</a> 
-  </div> </li><li> 
-  <div> 
-   <span class="icon aui-icon aui-icon-small aui-iconfont-page-default" 
title="Page">Page:</span> 
-  </div> 
-  <div class="details"> 
-   <a  href="templating-and-markup-faq.html">Templating and Markup FAQ</a> 
-  </div> </li><li> 
-  <div> 
-   <span class="icon aui-icon aui-icon-small aui-iconfont-page-default" 
title="Page">Page:</span> 
-  </div> 
-  <div class="details"> 
-   <a  href="component-classes.html">Component Classes</a> 
-  </div> </li><li> 
-  <div> 
-   <span class="icon aui-icon aui-icon-small aui-iconfont-page-default" 
title="Page">Page:</span> 
-  </div> 
-  <div class="details"> 
-   <a  href="component-reference.html">Component Reference</a> 
-  </div> </li><li> 
-  <div> 
-   <span class="icon aui-icon aui-icon-small aui-iconfont-page-default" 
title="Page">Page:</span> 
-  </div> 
-  <div class="details"> 
-   <a  href="component-libraries.html">Component Libraries</a> 
-  </div> </li><li> 
-  <div> 
-   <span class="icon aui-icon aui-icon-small aui-iconfont-page-default" 
title="Page">Page:</span> 
-  </div> 
-  <div class="details"> 
-   <a  href="page-and-component-classes-faq.html">Page And Component Classes 
FAQ</a> 
-  </div> </li><li> 
-  <div> 
-   <span class="icon aui-icon aui-icon-small aui-iconfont-page-default" 
title="Page">Page:</span> 
-  </div> 
-  <div class="details"> 
-   <a  href="component-templates.html">Component Templates</a> 
-  </div> </li><li> 
-  <div> 
-   <span class="icon aui-icon aui-icon-small aui-iconfont-page-default" 
title="Page">Page:</span> 
-  </div> 
-  <div class="details"> 
-   <a  href="component-cheat-sheet.html">Component Cheat Sheet</a> 
-  </div> </li></ul></div><p>For an exhaustive list, see the <a  
href="annotations.html">annotations list</a>.</p><h2 
id="ComponentCheatSheet-FieldInjectionAnnotations">Field Injection 
Annotations</h2><p>Main articles: <a  href="component-classes.html">Component 
Classes</a>, <a  href="injection.html">Injection</a>, <a  
href="annotations.html">Annotations</a></p><h3 
id="ComponentCheatSheet-@Inject">@Inject</h3><p>@Inject is the Swiss Army knife 
of annotations; it's designed to connect your component to services, resources, 
and other objects. See <a  href="injection.html">Injection</a>.</p><h4 
id="ComponentCheatSheet-ServiceInjection">Service Injection</h4><p>In most 
cases, the injected value is a service; the service is located by type. If 
there are ambiguities, caused by multiple services implementing the same 
interface, you'll see injection exceptions. You can resolve those exceptions by 
adding marker annotations to select a specific service, or by adding @Service 
to specify the spe
 cific service ID you want.</p><div class="confluence-information-macro 
confluence-information-macro-note"><span class="aui-icon aui-icon-small 
aui-iconfont-warning confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>Use of @Service is discouraged. If 
marker annotations are available, that is preferred.</p></div></div><h3 
id="ComponentCheatSheet-@InjectComponent">@InjectComponent</h3><p>Injects a 
component from this component's template into this component's class. Injecting 
a component is based on the component's ID, which should match the field name. 
However, the value attribute of the @InjectComponent annotation can be 
specified as well, this takes precedence over the field name.</p><p>It is 
common to inject a component in order to obtain its client-side ID (used when 
generating client-side JavaScript).</p><h3 
id="ComponentCheatSheet-@InjectContainer">@InjectContainer</h3><p>Injects the 
container of a component or, when used in a mixin, inje
 cts the component the mixin is attached to.</p><h3 
id="ComponentCheatSheet-@InjectPage">@InjectPage</h3><p>Injects a page of the 
application. Normally, the page to inject is identified based on the field 
type. The value attribute can be specified, in which case the page to be 
injected is identified by name.</p><h3 
id="ComponentCheatSheet-@Environmental">@Environmental</h3><p>Injects an <a  
href="environmental-services.html">environmental object</a>; such objects are 
request scoped but may be overridden at any time using the methods of the 
Environment service. Environmental objects are used to allow outer components 
to communicate with components they enclose.</p><p>Most often, @Environmental 
is used with type JavaScriptSupport, which is used to add JavaScript code and 
libraries to the rendered page.</p><h2 
id="ComponentCheatSheet-FieldBehaviorAnnotations">Field Behavior 
Annotations</h2><p>Main articles: <a  href="component-classes.html">Component 
Classes</a>, <a  href="annotations.h
 tml">Annotations</a></p><h3 
id="ComponentCheatSheet-@PageActivationContext">@PageActivationContext</h3><p>This
 annotation is allowed on a <em>single</em> field; the value of the field will 
be included in URLs for the page as the page's activation context. This is an 
alternative to implementing event handler methods<br clear="none"> for the 
activate and passivate events directly.</p><h3 
id="ComponentCheatSheet-@Parameter">@Parameter</h3><p>Marks the field as a 
component parameter. Attributes of the annotation allow the parameter to be 
marked as required or optional. If the parameter value will typically be a 
literal string (for example, the title parameter to a Layout component), you 
should add <code>defaultPrefix=BindingConstants.LITERAL</code> to the 
annotation so that users of the component won't have to use the "literal:" 
binding prefix with the parameter. See <a  
href="component-parameters.html">Component Parameters</a></p><h3 
id="ComponentCheatSheet-@Persist">@Persist</h3><p>Ma
 rks the field as a persistent value, one that maintains its value between 
requests. The default <em>strategy</em> is to simply store the value in the 
session (which is created as needed). Other strategies can be specified by name 
as the value attribute. See <a  href="persistent-page-data.html">Persistent 
Page Data</a>.</p><h3 
id="ComponentCheatSheet-@Property">@Property</h3><p>Directs Tapestry to 
automatically generate a getter and a setter for the field, converting it to a 
JavaBeans property than can be referenced from the template.</p><h3 
id="ComponentCheatSheet-@SessionState">@SessionState</h3><p>Marks the field as 
a Session State Object (SSO). SSOs store global data, and can be injected into 
any page or component. The SSOs are stored in the session, using a key based on 
the Java type. SSOs are usually created on demand, but the <code>create</code> 
attribute can turn this off. See <a  href="session-storage.html">Session 
Storage</a></p><h3 id="ComponentCheatSheet-@SessionAttribute
 ">@SessionAttribute</h3><p>In Tapestry 5.2 and later, marks the field as a 
Session Attribute. Like Session State Objects (SSO), a Session Attribute is 
stored in the session, however Session Attributes are stored by using a name 
you choose rather than based on the Java type. See <a  
href="session-storage.html">Session Storage</a>.</p><h3 
id="ComponentCheatSheet-@ActivationRequestParameter">@ActivationRequestParameter</h3><p>Fields
 with this annotation will be encoded into URLs as query parameters, in much 
the same way as data is encoded into the URL path. The query parameter name 
matches the field name, unless the value attribute is specified.</p><h2 
id="ComponentCheatSheet-MethodAnnotations">Method Annotations</h2><p>Main 
articles: <a  href="component-classes.html">Component Classes</a>, <a  
href="annotations.html">Annotations</a></p><h3 
id="ComponentCheatSheet-@OnEvent">@OnEvent</h3><p>Marks a method as an event 
handler method. Such methods may have any visibility, and typically us
 e package private visibility (that is, no visibility keyword at all). By 
default, the method will handle the action event from any component; the value 
attribute controls the matched event, and the component annotation is used to 
limit the event source.</p><p>An event handler method may take parameters, 
corresponding the event context associated with the event, such as the page 
activation context for the activate event. The method will not be invoked if it 
defines more parameters than there are values in the context.</p><p>The 
@RequestParameter annotation can be used on parameters, in which case the 
parameters value comes from a request query parameter, and not from the event 
context.</p><p>Events fired on a component bubble up the component's container. 
Return a non-null value to cancel event bubbling. What values may be returned 
from an event handler method is dependent on the type of event.</p><p>You may 
also return true to indicate that the event is handled and bubbling should c
 ancel (even for events that do not permit a return value).</p><div 
class="confluence-information-macro confluence-information-macro-note"><span 
class="aui-icon aui-icon-small aui-iconfont-warning 
confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>An alternative to @OnEvent is the 
naming convention <code>on</code><em>EventName</em> or 
<code>on</code><em>EventName</em><code>From</code><em>ComponentId</em>.</p></div></div><h3
 id="ComponentCheatSheet-@Log">@Log</h3><p>Marks the method to be logged for 
debugging purposes: method entry (with parameters) and exit (with return value) 
will be logged at debug level, as will any thrown exception. This is primarily 
for debugging purposes. The Logger name will match the component classes' fully 
qualified class name.</p><h3 
id="ComponentCheatSheet-@CommitAfter">@CommitAfter</h3><div 
class="confluence-information-macro confluence-information-macro-note"><span 
class="aui-icon aui-icon-small aui-iconfont-warn
 ing confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>The support for this annotation 
comes from the <a  href="hibernate.html">tapestry-hibernate</a> module or 
tapestry-jpa module.</p></div></div><h3 
id="ComponentCheatSheet-@Cached">@Cached</h3><p>Used on methods that perform 
expensive operations, such as database queries. The first time such a method is 
invoked, the return value is cached. Future invocations of the same method 
return the cached value.</p><p>The result cache is per-request and is discarded 
at the end of the request.</p><p>@Cached only works on methods that take no 
parameters.</p><h2 id="ComponentCheatSheet-ParameterAnnotations">Parameter 
Annotations</h2><p>Main article: <a  href="component-parameters.html">Component 
Parameters</a></p><h3 
id="ComponentCheatSheet-@RequestParameter">@RequestParameter</h3><p>Used with 
event handler methods to get the value for the parameter from a request query 
parameter.</p><h2 id="ComponentChe
 atSheet-TypeAnnotations">Type Annotations</h2><h3 
id="ComponentCheatSheet-@Events">@Events</h3><p>Lists the names of events that 
may be fired from within this component; used for documentation purposes 
only.</p><h3 id="ComponentCheatSheet-@Import">@Import</h3><p>Allows JavaScript 
libraries and CSS stylesheet files to be included in the rendered page. Each 
such file is added to the page only once, in the order in which the page 
renders.</p><p>It is allowed to use symbol expansions (with the 
<code>${...</code>} syntax) inside a library or stylesheet path.</p><p>@Import 
may also be applied to individual methods, in which case the import operation 
only occurs when the method is invoked.</p><div 
class="confluence-information-macro confluence-information-macro-note"><span 
class="aui-icon aui-icon-small aui-iconfont-warning 
confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>When specifying a file to import, 
you'll often use the prefix <code>context:
 </code> to indicate that the file is stored in the web application context, 
and not on the classpath. Relative paths will be on the classpath, relative to 
the Java class.</p></div></div><h3 
id="ComponentCheatSheet-@SupportsInformalParameters">@SupportsInformalParameters</h3><p>Marks
 the component as allowing informal parameters (extra attributes in the 
template that do not match formally declared parameters). Normally, informal 
parameters are simply discarded.</p><p>The method 
ComponentResources.renderInformalParameters() can be used to include the 
informal parameters within the element rendered by your component.</p><h3 
id="ComponentCheatSheet-@Secure">@Secure</h3><p>Marks the page as accessible 
only via secure (HTTPs). Any attempt to access the page via standard HTTP will 
be redirected to the HTTPs version.</p><p>By default, the @Secure annotation is 
ignored in development mode and only active in production mode.</p><h2 
id="ComponentCheatSheet-RenderPhaseMethods">Render Phase Meth
 ods</h2><p>Main article: <a  href="component-rendering.html">Component 
Rendering</a></p><p>Render phase methods are close cousins to event handler 
methods; they are how Tapestry integrates your code into the overall rendering 
of the page. For each render phase, there's an annotation and corresponding 
naming convention to define a render phase method:</p><div 
class="table-wrap"><table class="confluenceTable"><tbody><tr><th colspan="1" 
rowspan="1" class="confluenceTh"><p>Annotation</p></th><th colspan="1" 
rowspan="1" class="confluenceTh"><p>Method Name</p></th><th colspan="1" 
rowspan="1" class="confluenceTh"><p>General Use</p></th></tr><tr><td 
colspan="1" rowspan="1" class="confluenceTd"><p>@SetupRender</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>setupRender()</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>Initializes the component 
before rendering</p></td></tr><tr><td colspan="1" rowspan="1" 
class="confluenceTd"><p>@BeginRender</p></td><td colspan="1" row
 span="1" class="confluenceTd"><p>beginRender()</p></td><td colspan="1" 
rowspan="1" class="confluenceTd"><p>Renders the element and primary attributes 
of the component</p></td></tr><tr><td colspan="1" rowspan="1" 
class="confluenceTd"><p>@AfterRender</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>afterRender()</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>Closes the element started in 
beginRender()</p></td></tr><tr><td colspan="1" rowspan="1" 
class="confluenceTd"><p>@CleanupRender</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>cleanupRender()</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>Performs cleanup after all rendering of the component 
finishes</p></td></tr></tbody></table></div><p>Render phase methods either take 
no parameters, or take a single parameter of type MarkupWriter.</p><p>Render 
phase methods may return <code>void</code>, a <code>boolean</code>, or a 
<em>renderable object</em>.</p><div class="confluence-information-
 macro confluence-information-macro-note"><span class="aui-icon aui-icon-small 
aui-iconfont-warning confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>Generally, a <code>renderable 
object</code> is a <a  class="external-link" 
href="http://tapestry.apache.org/5.4/apidocs/org/apache/tapestry5/Block.html";>Block</a>
 or a component. The object is pushed onto the stack of rendering operations, 
temporarily replacing the current component as the object to be 
rendered.</p></div></div><p>Returning true is the same as returning void; it 
means that the component should follow the typical 
flow:</p><ul><li>@SetupRender</li><li>@BeginRender</li><li>Render the 
component's template, if any</li><li>Render the component's 
body</li><li>@AfterRender</li><li>@CleanupRender</li></ul><p>If a component has 
a template, the component's body will only render if the template contains a 
&lt;t:body&gt; element. If a component has no template, then it will always 
render its 
 body (between @BeginRender and @AfterRender).</p><p>A render phase method may 
also return false, in which case the flow continues to an alternate render 
phase, as per the chart in the <a  href="component-rendering.html">Component 
Rendering</a> reference page.</p><p>The most common cases:</p><ul><li>return 
<code>false</code> from @BeginRender to skip the rendering of the component's 
template and/or body, and continue with @AfterRender</li><li>return 
<code>false</code> from @AfterRender to return to @BeginRender (this is used in 
component, such as <code>Loop</code>, that render themselves multiple 
times)</li></ul><h2 id="ComponentCheatSheet-PageLifeCycleMethods">Page Life 
Cycle Methods</h2><p>Main article: <a  href="page-life-cycle.html">Page Life 
Cycle</a></p><p>Pages have a life cycle and this is represented by a 
<em>third</em> set of annotations or method naming conventions. Life cycle 
methods may appear on a page or any component of a page.</p><div 
class="table-wrap"><table class=
 "confluenceTable"><tbody><tr><th colspan="1" rowspan="1" 
class="confluenceTh"><p>Annotation</p></th><th colspan="1" rowspan="1" 
class="confluenceTh"><p>Method Name</p></th><th colspan="1" rowspan="1" 
class="confluenceTh"><p>Description</p></th></tr><tr><td colspan="1" 
rowspan="1" class="confluenceTd"><p>@PageLoaded</p></td><td colspan="1" 
rowspan="1" class="confluenceTd"><p>pageLoaded()</p></td><td colspan="1" 
rowspan="1" class="confluenceTd"><p>The page instance has been loaded but not 
yet attached for the first time.</p></td></tr><tr><td colspan="1" rowspan="1" 
class="confluenceTd"><p>@PageAttached</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>pageAttached()</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>The page is being used within a particular request. 
This occurs before the activate event.</p></td></tr><tr><td colspan="1" 
rowspan="1" class="confluenceTd"><p>@PageReset</p></td><td colspan="1" 
rowspan="1" class="confluenceTd"><p>pageReset()</p></td><td
  colspan="1" rowspan="1" class="confluenceTd"><p>See notes 
below.</p></td></tr><tr><td colspan="1" rowspan="1" 
class="confluenceTd"><p>@PageDetached</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>pageDetached()</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>End of request 
notification.</p></td></tr></tbody></table></div><p>Page life cycle methods may 
be any visibility. They must take no parameters and return void.</p><p>Page 
life cycle methods are of lower importance starting in Tapestry 5.2, since page 
instances are now shared across threads, rather than pooled.</p><p>The 
@PageReset life cycle is new in Tapestry 5.2. It will be invoked on a page 
render request when linked to from some other page of the application. This is 
to allow the page to reset its state, if any, when a user returns to the page 
from some other part of the application.</p><h2 
id="ComponentCheatSheet-ConfiguringAnnotations">Configuring 
Annotations</h2><p>The SymbolProvider service has t
 wo interfaces : FactoryDefaults and ApplicationDefaults. Tapestry provides 2 
annotations in order to define which implementation you want to override in 
your AppModule :&#160;</p><ul><li><p>@FactoryDefaults</p><div class="code panel 
pdl" style="border-width: 1px;"><div class="codeHeader panelHeader pdl" 
style="border-bottom-width: 1px;"><b>AppModule with 
@FactoryDefaults</b></div><div class="codeContent panelContent pdl">
+                <div id="ConfluenceContent"><p>&#160;</p><p>This is a summary 
of the more common annotations and methods you can add to Tapestry pages and 
component classes.</p><div class="aui-label" style="float:right" title="Related 
Articles">
+
+
+
+
+
+
+
+
+<h3>Related Articles</h3>
+
+<ul class="content-by-label"><li>
+        <div>
+                <span class="icon aui-icon aui-icon-small 
aui-iconfont-page-default" title="Page">Page:</span>        </div>
+
+        <div class="details">
+                        <a  href="component-parameters.html">Component 
Parameters</a>
+                
+                        
+                    </div>
+    </li><li>
+        <div>
+                <span class="icon aui-icon aui-icon-small 
aui-iconfont-page-default" title="Page">Page:</span>        </div>
+
+        <div class="details">
+                        <a  href="component-reference.html">Component 
Reference</a>
+                
+                        
+                    </div>
+    </li><li>
+        <div>
+                <span class="icon aui-icon aui-icon-small 
aui-iconfont-page-default" title="Page">Page:</span>        </div>
+
+        <div class="details">
+                        <a  href="component-libraries.html">Component 
Libraries</a>
+                
+                        
+                    </div>
+    </li><li>
+        <div>
+                <span class="icon aui-icon aui-icon-small 
aui-iconfont-page-default" title="Page">Page:</span>        </div>
+
+        <div class="details">
+                        <a  href="templating-and-markup-faq.html">Templating 
and Markup FAQ</a>
+                
+                        
+                    </div>
+    </li><li>
+        <div>
+                <span class="icon aui-icon aui-icon-small 
aui-iconfont-page-default" title="Page">Page:</span>        </div>
+
+        <div class="details">
+                        <a  href="component-classes.html">Component Classes</a>
+                
+                        
+                    </div>
+    </li><li>
+        <div>
+                <span class="icon aui-icon aui-icon-small 
aui-iconfont-page-default" title="Page">Page:</span>        </div>
+
+        <div class="details">
+                        <a  href="page-and-component-classes-faq.html">Page 
And Component Classes FAQ</a>
+                
+                        
+                    </div>
+    </li><li>
+        <div>
+                <span class="icon aui-icon aui-icon-small 
aui-iconfont-page-default" title="Page">Page:</span>        </div>
+
+        <div class="details">
+                        <a  href="component-templates.html">Component 
Templates</a>
+                
+                        
+                    </div>
+    </li><li>
+        <div>
+                <span class="icon aui-icon aui-icon-small 
aui-iconfont-page-default" title="Page">Page:</span>        </div>
+
+        <div class="details">
+                        <a  href="component-cheat-sheet.html">Component Cheat 
Sheet</a>
+                
+                        
+                    </div>
+    </li></ul>
+</div>
+
+
+<p>For an exhaustive list, see the <a  
href="component-cheat-sheet.html">annotations list</a>.</p><h2 
id="ComponentCheatSheet-FieldInjectionAnnotations">Field Injection 
Annotations</h2><p>Main articles: <a  
href="component-cheat-sheet.html">Component Cheat Sheet</a>, <a  
href="component-cheat-sheet.html">Component Cheat Sheet</a>, <a  
href="component-cheat-sheet.html">Component Cheat Sheet</a></p><h3 
id="ComponentCheatSheet-@Inject">@Inject</h3><p>@Inject is the Swiss Army knife 
of annotations; it's designed to connect your component to services, resources, 
and other objects. See <a  href="component-cheat-sheet.html">Component Cheat 
Sheet</a>.</p><h4 id="ComponentCheatSheet-ServiceInjection">Service 
Injection</h4><p>In most cases, the injected value is a service; the service is 
located by type. If there are ambiguities, caused by multiple services 
implementing the same interface, you'll see injection exceptions. You can 
resolve those exceptions by adding marker annotations to select
  a specific service, or by adding @Service to specify the specific service ID 
you want.</p><div class="confluence-information-macro 
confluence-information-macro-note"><span class="aui-icon aui-icon-small 
aui-iconfont-warning confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>Use of @Service is discouraged. If 
marker annotations are available, that is preferred.</p></div></div><h3 
id="ComponentCheatSheet-@InjectComponent">@InjectComponent</h3><p>Injects a 
component from this component's template into this component's class. Injecting 
a component is based on the component's ID, which should match the field name. 
However, the value attribute of the @InjectComponent annotation can be 
specified as well, this takes precedence over the field name.</p><p>It is 
common to inject a component in order to obtain its client-side ID (used when 
generating client-side JavaScript).</p><h3 
id="ComponentCheatSheet-@InjectContainer">@InjectContainer</h3><p>Inject
 s the container of a component or, when used in a mixin, injects the component 
the mixin is attached to.</p><h3 
id="ComponentCheatSheet-@InjectPage">@InjectPage</h3><p>Injects a page of the 
application. Normally, the page to inject is identified based on the field 
type. The value attribute can be specified, in which case the page to be 
injected is identified by name.</p><h3 
id="ComponentCheatSheet-@Environmental">@Environmental</h3><p>Injects an <a  
href="component-cheat-sheet.html">environmental object</a>; such objects are 
request scoped but may be overridden at any time using the methods of the 
Environment service. Environmental objects are used to allow outer components 
to communicate with components they enclose.</p><p>Most often, @Environmental 
is used with type JavaScriptSupport, which is used to add JavaScript code and 
libraries to the rendered page.</p><h2 
id="ComponentCheatSheet-FieldBehaviorAnnotations">Field Behavior 
Annotations</h2><p>Main articles: <a  href="component-
 cheat-sheet.html">Component Cheat Sheet</a>, <a  
href="component-cheat-sheet.html">Component Cheat Sheet</a></p><h3 
id="ComponentCheatSheet-@PageActivationContext">@PageActivationContext</h3><p>This
 annotation is allowed on a <em>single</em> field; the value of the field will 
be included in URLs for the page as the page's activation context. This is an 
alternative to implementing event handler methods<br clear="none"> for the 
activate and passivate events directly.</p><h3 
id="ComponentCheatSheet-@Parameter">@Parameter</h3><p>Marks the field as a 
component parameter. Attributes of the annotation allow the parameter to be 
marked as required or optional. If the parameter value will typically be a 
literal string (for example, the title parameter to a Layout component), you 
should add <code>defaultPrefix=BindingConstants.LITERAL</code> to the 
annotation so that users of the component won't have to use the "literal:" 
binding prefix with the parameter. See <a  href="component-cheat-sheet.h
 tml">Component Cheat Sheet</a></p><h3 
id="ComponentCheatSheet-@Persist">@Persist</h3><p>Marks the field as a 
persistent value, one that maintains its value between requests. The default 
<em>strategy</em> is to simply store the value in the session (which is created 
as needed). Other strategies can be specified by name as the value attribute. 
See <a  href="component-cheat-sheet.html">Component Cheat Sheet</a>.</p><h3 
id="ComponentCheatSheet-@Property">@Property</h3><p>Directs Tapestry to 
automatically generate a getter and a setter for the field, converting it to a 
JavaBeans property than can be referenced from the template.</p><h3 
id="ComponentCheatSheet-@SessionState">@SessionState</h3><p>Marks the field as 
a Session State Object (SSO). SSOs store global data, and can be injected into 
any page or component. The SSOs are stored in the session, using a key based on 
the Java type. SSOs are usually created on demand, but the <code>create</code> 
attribute can turn this off. See <a  href
 ="component-cheat-sheet.html">Component Cheat Sheet</a></p><h3 
id="ComponentCheatSheet-@SessionAttribute">@SessionAttribute</h3><p>In Tapestry 
5.2 and later, marks the field as a Session Attribute. Like Session State 
Objects (SSO), a Session Attribute is stored in the session, however Session 
Attributes are stored by using a name you choose rather than based on the Java 
type. See <a  href="component-cheat-sheet.html">Component Cheat 
Sheet</a>.</p><h3 
id="ComponentCheatSheet-@ActivationRequestParameter">@ActivationRequestParameter</h3><p>Fields
 with this annotation will be encoded into URLs as query parameters, in much 
the same way as data is encoded into the URL path. The query parameter name 
matches the field name, unless the value attribute is specified.</p><h2 
id="ComponentCheatSheet-MethodAnnotations">Method Annotations</h2><p>Main 
articles: <a  href="component-cheat-sheet.html">Component Cheat Sheet</a>, <a  
href="component-cheat-sheet.html">Component Cheat Sheet</a></p><h3 id=
 "ComponentCheatSheet-@OnEvent">@OnEvent</h3><p>Marks a method as an event 
handler method. Such methods may have any visibility, and typically use package 
private visibility (that is, no visibility keyword at all). By default, the 
method will handle the action event from any component; the value attribute 
controls the matched event, and the component annotation is used to limit the 
event source.</p><p>An event handler method may take parameters, corresponding 
the event context associated with the event, such as the page activation 
context for the activate event. The method will not be invoked if it defines 
more parameters than there are values in the context.</p><p>The 
@RequestParameter annotation can be used on parameters, in which case the 
parameters value comes from a request query parameter, and not from the event 
context.</p><p>Events fired on a component bubble up the component's container. 
Return a non-null value to cancel event bubbling. What values may be returned 
from an ev
 ent handler method is dependent on the type of event.</p><p>You may also 
return true to indicate that the event is handled and bubbling should cancel 
(even for events that do not permit a return value).</p><div 
class="confluence-information-macro confluence-information-macro-note"><span 
class="aui-icon aui-icon-small aui-iconfont-warning 
confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>An alternative to @OnEvent is the 
naming convention <code>on</code><em>EventName</em> or 
<code>on</code><em>EventName</em><code>From</code><em>ComponentId</em>.</p></div></div><h3
 id="ComponentCheatSheet-@Log">@Log</h3><p>Marks the method to be logged for 
debugging purposes: method entry (with parameters) and exit (with return value) 
will be logged at debug level, as will any thrown exception. This is primarily 
for debugging purposes. The Logger name will match the component classes' fully 
qualified class name.</p><h3 id="ComponentCheatSheet-@CommitAfter">@Co
 mmitAfter</h3><div class="confluence-information-macro 
confluence-information-macro-note"><span class="aui-icon aui-icon-small 
aui-iconfont-warning confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>The support for this annotation 
comes from the <a  href="component-cheat-sheet.html">tapestry-hibernate</a> 
module or tapestry-jpa module.</p></div></div><h3 
id="ComponentCheatSheet-@Cached">@Cached</h3><p>Used on methods that perform 
expensive operations, such as database queries. The first time such a method is 
invoked, the return value is cached. Future invocations of the same method 
return the cached value.</p><p>The result cache is per-request and is discarded 
at the end of the request.</p><p>@Cached only works on methods that take no 
parameters.</p><h2 id="ComponentCheatSheet-ParameterAnnotations">Parameter 
Annotations</h2><p>Main article: <a  
href="component-cheat-sheet.html">Component Cheat Sheet</a></p><h3 
id="ComponentCheatSheet-@Request
 Parameter">@RequestParameter</h3><p>Used with event handler methods to get the 
value for the parameter from a request query parameter.</p><h2 
id="ComponentCheatSheet-TypeAnnotations">Type Annotations</h2><h3 
id="ComponentCheatSheet-@Events">@Events</h3><p>Lists the names of events that 
may be fired from within this component; used for documentation purposes 
only.</p><h3 id="ComponentCheatSheet-@Import">@Import</h3><p>Allows JavaScript 
libraries and CSS stylesheet files to be included in the rendered page. Each 
such file is added to the page only once, in the order in which the page 
renders.</p><p>It is allowed to use symbol expansions (with the 
<code>${...</code>} syntax) inside a library or stylesheet path.</p><p>@Import 
may also be applied to individual methods, in which case the import operation 
only occurs when the method is invoked.</p><div 
class="confluence-information-macro confluence-information-macro-note"><span 
class="aui-icon aui-icon-small aui-iconfont-warning confluence
 -information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>When specifying a file to import, 
you'll often use the prefix <code>context:</code> to indicate that the file is 
stored in the web application context, and not on the classpath. Relative paths 
will be on the classpath, relative to the Java class.</p></div></div><h3 
id="ComponentCheatSheet-@SupportsInformalParameters">@SupportsInformalParameters</h3><p>Marks
 the component as allowing informal parameters (extra attributes in the 
template that do not match formally declared parameters). Normally, informal 
parameters are simply discarded.</p><p>The method 
ComponentResources.renderInformalParameters() can be used to include the 
informal parameters within the element rendered by your component.</p><h3 
id="ComponentCheatSheet-@Secure">@Secure</h3><p>Marks the page as accessible 
only via secure (HTTPs). Any attempt to access the page via standard HTTP will 
be redirected to the HTTPs version.</p><p>By default, 
 the @Secure annotation is ignored in development mode and only active in 
production mode.</p><h2 id="ComponentCheatSheet-RenderPhaseMethods">Render 
Phase Methods</h2><p>Main article: <a  
href="component-cheat-sheet.html">Component Cheat Sheet</a></p><p>Render phase 
methods are close cousins to event handler methods; they are how Tapestry 
integrates your code into the overall rendering of the page. For each render 
phase, there's an annotation and corresponding naming convention to define a 
render phase method:</p><div class="table-wrap"><table 
class="confluenceTable"><tbody><tr><th colspan="1" rowspan="1" 
class="confluenceTh"><p>Annotation</p></th><th colspan="1" rowspan="1" 
class="confluenceTh"><p>Method Name</p></th><th colspan="1" rowspan="1" 
class="confluenceTh"><p>General Use</p></th></tr><tr><td colspan="1" 
rowspan="1" class="confluenceTd"><p>@SetupRender</p></td><td colspan="1" 
rowspan="1" class="confluenceTd"><p>setupRender()</p></td><td colspan="1" 
rowspan="1" class="conflue
 nceTd"><p>Initializes the component before rendering</p></td></tr><tr><td 
colspan="1" rowspan="1" class="confluenceTd"><p>@BeginRender</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>beginRender()</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>Renders the element and primary 
attributes of the component</p></td></tr><tr><td colspan="1" rowspan="1" 
class="confluenceTd"><p>@AfterRender</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>afterRender()</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>Closes the element started in 
beginRender()</p></td></tr><tr><td colspan="1" rowspan="1" 
class="confluenceTd"><p>@CleanupRender</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>cleanupRender()</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>Performs cleanup after all rendering of the component 
finishes</p></td></tr></tbody></table></div><p>Render phase methods either take 
no parameters, or take a single parameter of type Mark
 upWriter.</p><p>Render phase methods may return <code>void</code>, a 
<code>boolean</code>, or a <em>renderable object</em>.</p><div 
class="confluence-information-macro confluence-information-macro-note"><span 
class="aui-icon aui-icon-small aui-iconfont-warning 
confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body"><p>Generally, a <code>renderable 
object</code> is a <a  class="external-link" 
href="http://tapestry.apache.org/5.4/apidocs/org/apache/tapestry5/Block.html";>Block</a>
 or a component. The object is pushed onto the stack of rendering operations, 
temporarily replacing the current component as the object to be 
rendered.</p></div></div><p>Returning true is the same as returning void; it 
means that the component should follow the typical 
flow:</p><ul><li>@SetupRender</li><li>@BeginRender</li><li>Render the 
component's template, if any</li><li>Render the component's 
body</li><li>@AfterRender</li><li>@CleanupRender</li></ul><p>If a component has 
a 
 template, the component's body will only render if the template contains a 
&lt;t:body&gt; element. If a component has no template, then it will always 
render its body (between @BeginRender and @AfterRender).</p><p>A render phase 
method may also return false, in which case the flow continues to an alternate 
render phase, as per the chart in the <a  
href="component-cheat-sheet.html">Component Cheat Sheet</a> reference 
page.</p><p>The most common cases:</p><ul><li>return <code>false</code> from 
@BeginRender to skip the rendering of the component's template and/or body, and 
continue with @AfterRender</li><li>return <code>false</code> from @AfterRender 
to return to @BeginRender (this is used in component, such as 
<code>Loop</code>, that render themselves multiple times)</li></ul><h2 
id="ComponentCheatSheet-PageLifeCycleMethods">Page Life Cycle 
Methods</h2><p>Main article: <a  href="component-cheat-sheet.html">Component 
Cheat Sheet</a></p><p>Pages have a life cycle and this is represented
  by a <em>third</em> set of annotations or method naming conventions. Life 
cycle methods may appear on a page or any component of a page.</p><div 
class="table-wrap"><table class="confluenceTable"><tbody><tr><th colspan="1" 
rowspan="1" class="confluenceTh"><p>Annotation</p></th><th colspan="1" 
rowspan="1" class="confluenceTh"><p>Method Name</p></th><th colspan="1" 
rowspan="1" class="confluenceTh"><p>Description</p></th></tr><tr><td 
colspan="1" rowspan="1" class="confluenceTd"><p>@PageLoaded</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>pageLoaded()</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>The page instance has been 
loaded but not yet attached for the first time.</p></td></tr><tr><td 
colspan="1" rowspan="1" class="confluenceTd"><p>@PageAttached</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>pageAttached()</p></td><td 
colspan="1" rowspan="1" class="confluenceTd"><p>The page is being used within a 
particular request. This occurs before the a
 ctivate event.</p></td></tr><tr><td colspan="1" rowspan="1" 
class="confluenceTd"><p>@PageReset</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>pageReset()</p></td><td colspan="1" rowspan="1" 
class="confluenceTd"><p>See notes below.</p></td></tr><tr><td colspan="1" 
rowspan="1" class="confluenceTd"><p>@PageDetached</p></td><td colspan="1" 
rowspan="1" class="confluenceTd"><p>pageDetached()</p></td><td colspan="1" 
rowspan="1" class="confluenceTd"><p>End of request 
notification.</p></td></tr></tbody></table></div><p>Page life cycle methods may 
be any visibility. They must take no parameters and return void.</p><p>Page 
life cycle methods are of lower importance starting in Tapestry 5.2, since page 
instances are now shared across threads, rather than pooled.</p><p>The 
@PageReset life cycle is new in Tapestry 5.2. It will be invoked on a page 
render request when linked to from some other page of the application. This is 
to allow the page to reset its state, if any, when a user r
 eturns to the page from some other part of the application.</p><h2 
id="ComponentCheatSheet-ConfiguringAnnotations">Configuring 
Annotations</h2><p>The SymbolProvider service has two interfaces : 
FactoryDefaults and ApplicationDefaults. Tapestry provides 2 annotations in 
order to define which implementation you want to override in your AppModule 
:&#160;</p><ul><li><p>@FactoryDefaults</p><div class="code panel pdl" 
style="border-width: 1px;"><div class="codeHeader panelHeader pdl" 
style="border-bottom-width: 1px;"><b>AppModule with 
@FactoryDefaults</b></div><div class="codeContent panelContent pdl">
 <pre class="brush: java; gutter: false; theme: Default" 
style="font-size:12px;">@Contribute(SymbolProvider.class)
 @FactoryDefaults
 public void setParam(MappedConfiguration&lt; String, String&gt; configuration){

Modified: websites/production/tapestry/content/component-events-faq.html
==============================================================================
--- websites/production/tapestry/content/component-events-faq.html (original)
+++ websites/production/tapestry/content/component-events-faq.html Sat Feb  3 
18:21:36 2018
@@ -77,38 +77,19 @@
       </div>
 
       <div id="content">
-                <div id="ConfluenceContent"> 
+                <div id="ConfluenceContent"><h2 
id="ComponentEventsFAQ-ComponentEvents">Component Events</h2><h3 
id="ComponentEventsFAQ-WhydoesTapestrysendaredirectafteraformissubmitted?">Why 
does Tapestry send a redirect after a form is submitted?</h3><p>This is an 
extension of the <a  class="external-link" 
href="http://en.wikipedia.org/wiki/Post/Redirect/Get"; 
rel="nofollow">Post/Redirect/Get</a> approach. It ensures that after an 
operation that updates server-side state, such as a form submission, if the 
user resubmits the resulting page, the operation is <strong>not</strong> 
performed a second time; instead just the results of the operation, reflecting 
the changed server-side state, is re-rendered.</p><p>This has the unwanted 
requirement that any data needed to render the response must persist between 
the event request (the form submission) and the render request; this often 
means that fields must be annotated with @<a  class="external-link" 
href="http://tapestry.apache.org/curre
 nt/apidocs/org/apache/tapestry5/annotations/Persist.html">Persist</a>.
 
-<h2 id="ComponentEventsFAQ-ComponentEvents">Component Events </h2>
-
-<h3 
id="ComponentEventsFAQ-WhydoesTapestrysendaredirectafteraformissubmitted?">Why 
does Tapestry send a redirect after a form is submitted?</h3>
-
-<p>This is an extension of the <a  class="external-link" 
href="http://en.wikipedia.org/wiki/Post/Redirect/Get"; 
rel="nofollow">Post/Redirect/Get</a> approach. It ensures that after an 
operation that updates server-side state, such as a form submission, if the 
user resubmits the resulting page, the operation is <strong>not</strong> 
performed a second time; instead just the results of the operation, reflecting 
the changed server-side state, is re-rendered.</p>
-
-<p>This has the unwanted requirement that any data needed to render the 
response must persist between the event request (the form submission) and the 
render request; this often means that fields must be annotated with @<a  
class="external-link" 
href="http://tapestry.apache.org/current/apidocs/org/apache/tapestry5/annotations/Persist.html";>Persist</a>.</p>
-
-
-
-<div class="confluence-information-macro 
confluence-information-macro-information"><p class="title">Added in 
5.2</p><span class="aui-icon aui-icon-small aui-iconfont-info 
confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body">
+</p><div class="confluence-information-macro 
confluence-information-macro-information"><p class="title">Added in 
5.2</p><span class="aui-icon aui-icon-small aui-iconfont-info 
confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body">
 </div></div>
 <div class="error"><span class="error">Unknown macro: {div}</span> 
-
 <p>If you want to short-circuit this behavior and render a response directly, 
your component event handle method may return an instance of <a  
class="external-link" 
href="http://tapestry.apache.org/current/apidocs/org/apache/tapestry5/services/StreamPageContent.html";>StreamPageContent</a>.
 Tapestry will render the page as part of the event request and stream its 
content back to the client web browser, rather than sending the normal 
redirect.</p>
 </div>
 
-
-
 <div class="confluence-information-macro 
confluence-information-macro-information"><p class="title">Added in 
5.4</p><span class="aui-icon aui-icon-small aui-iconfont-info 
confluence-information-macro-icon"></span><div 
class="confluence-information-macro-body">
 </div></div>
 <div class="error"><span class="error">Unknown macro: {div}</span> 
-
 <p>Starting in release 5.4, Forms (by default) will NOT redirect after post if 
there are validation errors. This makes it possible to re-render the page, with 
error decorations, without requiring that the validation errors be stored in 
the session between requests ... and that means that the application can remain 
stateless much longer.</p>
-</div>
-
-<h3 
id="ComponentEventsFAQ-IspecifiedazoneinmyActionLink/EventLink,sowhydoesn'tmyeventfireviaajax(request.isXHR()isfalse)?">I
 specified a zone in my ActionLink/EventLink, so why doesn't my event fire via 
ajax (request.isXHR() is false)?</h3>
-
-<p>Check your browser's JavaScript console for errors. It's likely that a 
JavaScript error has prevented Tapestry from transforming your 
ActionLink/EventLink from a page render action to an ajax action.</p>
-</div>
+</div><h3 
id="ComponentEventsFAQ-IspecifiedazoneinmyActionLink/EventLink,sowhydoesn'tmyeventfireviaajax(request.isXHR()isfalse)?">I
 specified a zone in my ActionLink/EventLink, so why doesn't my event fire via 
ajax (request.isXHR() is false)?</h3><p>Check your browser's JavaScript console 
for errors. It's likely that a JavaScript error has prevented Tapestry from 
transforming your ActionLink/EventLink from a page render action to an ajax 
action.</p></div>
       </div>
 
       <div class="clearer"></div>


Reply via email to