Summary

Definitions

Overview

Illustration 1
   Page Template
   -Page Specification
   Page Class
   Application Specification
   web.xml

Illustration 2

Illustration 3

The Framework - a flyby

Conclusion

Biography

Resources

Page Specification
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE page-specification PUBLIC
    "-//Apache Software Foundation//Tapestry Specification 3.0//EN"
    "http://jakarta.apache.org/tapestry/dtd/Tapestry_3_0.dtd">

<page-specification class="demo.Home">
    <component id="user" type="Insert">
        <binding name="value" expression="userName"/>
    </component>
    
    <context-asset name="$template" path="Home.html"/>
</page-specification>
Listing 2. Home.page
The specification is the part that drives a component and ties its pieces together. It specifies, among a lot of things, the class that defines the behavior of the component under construction (called container or parent component – Home Page in our example), the template for the container component and the components to be plugged in place of the template's placeholder tags (called contained or child components). The defining class (also known as component class – demo.Home in our example) of the container component is specified using the class attribute of the specification root element – page-specification. The container component's template is specified using the context-asset element. A component can have any number of types of assets (images, stylesheets etc.) associated with it and the template is treated as one such type. The template asset is specified using the special name $template. The contained components are declared using the component element. Components thus declared are known as an "Explicit" or "Declared" components. The id attribute of the component element is like an Object reference in OO paradigm, and is the same as the jwcid attribute of the placeholder tag in the template. Thus the framework knows which component needs to be plugged into which placeholder tag. The type of component to be instantiated and plugged in is defined by the type attribute of the component tag. The component we use in our example is the Insert JWC that comes with Tapestry's core library. As mentioned before, every component serves a specific purpose and so is our Insert JWC. The Insert JWC, like the name suggests, inserts text (the user name in our example) in place of the placeholder tag in the template. The text to be inserted is provided to the JWC via a parameter defined by the component.
Parameters are the gateway to configure components in Tapestry. Component parameters are like method parameters, the difference being that component parameters can be two-way; i.e., component parameters can pass in a value and also spit out a value. Tapestry allows four different kinds of parameters - in, form, custom and auto. in parameters can only pass in a value to the component, while the other kinds can pass values in and out of a component. The value passed in to a component is stored in the JWC as a JavaBeans property (known as parameter-property) in the component class. The value passed out of a component is updated in the variable that was the source of the data that was passed in. This variable is usually an attribute of the container component class, although it can be any variable accessible from the container component class. In addition to the parameter property, the JWC houses another JavaBeans property called the binding-property. Every JWC parameter-property is accompanied by a binding-property. The name of the binding-property is the name of the parameter-property + the literal suffix Binding. The purpose of the binding-property, like the name suggests, is to bind a foreign object (unknown at the time of component definition) to the JWC parameter-property. This allows a JWC to be decoupled from the source of data for the parameter-property. This decoupling is achieved with the help of another incredible open source project – Object Graph Navigation Library, OGNL. The component class will use the parameter-property, via the JavaBeans-style get method, as needed in defining the component's behavior. The get<ParameterProperty> method in turn, will use the get<ParameterProperty>Binding method, which will retrieve the bound object at runtime, using OGNL, and make it available to the component class as shown in Figure 2. The parameter-property is specified in the JWC specification at the time of component definition and the binding-property is automatically created and provided by the framework at runtime. The actual binding of the foreign object, though, is specified at the time of component declaration in the container component's specification as shown in our Page specification (Listing 2).

Figure 2. Parameter mechanics
The binding is specified in the component declaration using the binding element, nested within the component element. The binding element has two attributes – name and expression. Attribute name specifies the name of the parameter and the expression attribute specifies the foreign object to bind. The foreign object is any object that can be accessed from within the container component class via a JavaBeans-style get method, or an object that is the result of an OGNL expression. The target foreign object can be a very distant object in the object graph and yet be accessed from right within the expression attribute. This object graph navigation is achieved via OGNL. Please see Resources for information on OGNL expressions.
The Insert JWC (user in our example) defines a parameter called value. This parameter is bound to the foreign object (userName in our example) via the binding element as shown in the example Page specification (Home.page). At runtime, the user instance JWC reads the value of userName attribute of demo.Home instance and updates the value parameter using OGNL. The user instance then uses the parameter value and inserts it into the template.
Page components are special JWCs, as already stated. Page components are root level components (can never be contained components) with special attributes and responsibilities. Page components cannot be used as building blocks to compose other components; that said, parameters are useless in Page components and so the framework forbids Pages from having parameters.
The naming convention for specifications is the name of the component with an extension of .page (for Page components) or .jwc (for non-Page components). And thus the specification for our Page component is named Home.page. Specifications are typically placed under the WEB-INF folder of the application context. So, if Welcome is the context of our Welcome application, Home.page will typically be placed under webapps/Welcome/WEB-INF.
<< Previous Next >>