Mapping Address Spaces
XRL is implemented, in part, by the
mapper
accessor.
The principle function of the mapper service is to map a public address space
(the address space presented by a module) and the module's
inner private address space.
The mapping from public to private address spaces is defined in
an XML links document.
To see how this mapping is implemented, examine a portion of the module.xml file used
for the workbench area itself:
<rewrite>
<!---->
<rule>
<match>(ffcpl:/workbench/xrldemo/.*)</match>
<to>active:mapper+operator@ffcpl:/xrldemo/links.xml+operand@$1</to>
</rule>
</rewrite>
This rewrite rule directs all requests matching "ffcpl:/workbench/xrldemo/.*"
to the mapper accessor and specifies the links document located at
ffcpl:/xrldemo/links.xml.
A links document that supports only one mapping (extracted from the workbench's
links.xml document) would be:
<links basepath="ffcpl:/workbench/xrldemo/">
<!---->
<link>
<name>index0</name>
<ext>/part0/index</ext>
<int>ffcpl:/xrldemo/part0/template.xml</int>
</link>
</links>
In this example, all requests in the public address space for
ffcpl:/workbench/xrldemo/part0/index
will be mapped to the private internal address
ffcpl:/xrldemo/part0/template.xml
.
Let's see how this works.
The request in the public address space, "ffcpl:/workbench/xrldemo/part0/index",
is presented to the module.
Subsequently:
-
The rewrite rule regular expression "(ffcpl:/workbench/xrldemo/.*)" matches the address.
-
The whole address, "ffcpl:/workbench/xrldemo/part0/index", is passed
as the operand to the mapper service through the request:
active:mapper+operator@ffcpl:/xrldemo/links.xml+operand@$1
.
-
The mapper finds the mapping in the links.xml file and
substitutes the private address "ffcpl:/xrldemo/part0/template.xml"
for the public one and sends the request to the module.
-
The specified resource is located within the module and returned to the client.
Since the workbench module is registered with the front-end fulcrum, you can
activate the first example by clicking this external URL:
http://localhost:8080/workbench/xrldemo/part0/index
.
You should see a small XHTML document which, you'll have guessed,
is actually the static module resource
ffcpl:/xrldemo/part0/template.xml
.
Here's what just happened tracing from the browser request to the
browser display of the result...
-
The HTTP request for
http://localhost:8080/workbench/xrldemo/part0/index
arrived in the front-end-fulcrum module as a request
for the internal resource ffcpl:/workbench/xrldemo/part0/index
.
-
Because the workbench module is imported into the front-end fulcrum,
the workbench captured the request since it matches
ffcpl:/workbench/.*
.
-
Inside the workbench module the request was rewritten to
active:mapper+operator@ffcpl:/xrldemo/links.xml+operand@ffcpl:/workbench/xrldemo/part0/index
.
-
The mapper captures this rewritten request.
-
The mapper used the concatenation of the basepath and the
<ext>
tag entry to find a match for the operand argument's URI.
-
The mapper found that the index0 link matches the operand URI.
-
The mapper issued a subrequest for the internal URI which was is provided in the
<int>
tag of the index0 link.
-
The result of the sub-request was returned as the response of the mapper,
which was written to the HTTP response which you saw as the response in
your browser.
This seems like quite an elaborate sequence of events to serve a single static file!
But we have walked through the full step-by-step sequence in order
to show how the public interface of a module can be delegated to the XRL mapper.
In practice we do not have to consider this again. After establishing the routing to
the mapper, all we ever have to think about is the links document and the implementations
for internal requests - as we shall see, the external address
space takes care of itself.
xrl: references
We have one more trick up our sleeve before we can move on to templating and widgets.
XRL will attempt to resolve any URI with the scheme xrl:
to the corresponding named link in the links.xml document.
Here is the previous example re-written to use two links.
<links basepath="ffcpl:/workbench/xrldemo/">
<!---->
<link>
<name>index1</name>
<ext>/part1/index</ext>
<int>xrl:part1-content</int>
<args>links</args>
</link>
<link>
<name>part1-content</name>
<int>ffcpl:/xrldemo/part1/content.xml</int>
</link>
</links>
The first link named index1 is similar to the first example except the
<int>
tag now has a URI referencing an XRL widget (xrl:part1-content
).
The
second link named part1-content simply provides a reference to
a static internal resource.
You can probably tell what's going to happen when you click this URL:
http://localhost:8080/workbench/xrldemo/part1/index
.
That's right, the mapper resolved the URL to the link named index1 and then continued with a second
resolution of the xrl: URI to locate the link named part1-content.
Finally, the internal resource referenced by that link's <int>
tag
was returned to your browser.
As we will see later, any included resource may use the xrl:
address space and rely on the XRL system to resolve that reference to
an internal address.
As you will see, this provides a great deal of flexibility.