Nuxeo Server

Module Extensibility

This page is scheduled for review and update. Check back soon for updated content!

The module defined here extends the module defined in Tutorial 4.

Module Definition

MANIFEST.MF

...
Nuxeo-WebModule: org.nuxeo.ecm.webengine.app.WebEngineModule;name=sample5;extends=sample4

JAX-RS Resources

Samples5.java

import javax.ws.rs.*;
import javax.ws.rs.core.*;
import org.nuxeo.ecm.core.rest.*;
import org.nuxeo.ecm.webengine.model.impl.*;
import org.nuxeo.ecm.webengine.model.*;
import org.nuxeo.ecm.webengine.model.exceptions.*;

/**
 * Web Module Extensibility.
 *
 * This sample is demonstrating how existing web modules can be extended.
 * To extend another module you should use the <code>base="BaseModule"</code> in the <code>@WebModule</code>
 * annotation. This way the new module will inherit all templates and resources defined in the base module.
 * You can thus create a chain of inherited web modules.
 *
<p>
 * Here is how template resolval will be impacted by the module inheritance:
 * <br>
 * <i>If a template T is not found in skin directory of derived module then search the template inside the base module and so on
 * until a template is found or no more base module exists.</i>
 * The view resolval is similar to the template one but it will use the WebObject inheritance too:
 * <br>
 * <i></i>
 * <br>
 * <b>Note</b> that only the <i>skin</i> directory is stacked over the one in the base module.
 * The other directories in the module are not inheritable.
 *
<p>
 * Also, resource types defined by the base module will become visible in the derived one.
 *
<p>
 * In this example you will also find a very useful feature of WebEngine: the builtin <b>view service adapter</b>.
 * This adapter can be used on any web object to locate any view declared on that object.
 * Let's say we define a view named <i>info</i> for the <i>Document</i> WebObject type.
 * And the following request path will point to a Document WebObject: <code>/my/doc</code>.
 * Then to display the <i>info</i> view we can use the builtin views adapter this way:
 * <code>/my/doc/@views/info</code>.
 *
<p>
 * Obviously, you can redefine the WebObject corresponding to your document type and add a new method that will dispatch
 * the view <info>info</info> using a pretty path like <code>/my/doc/info</code>. But this involves changing code.
 * If you don't want this then the views adapter will be your friend.
 *
 *
<p>
 *
<p>
 * This example will extend the module defined in sample5 and will reuse and add more templates.
 * Look into template files to see how base module templates are reused.
 *
 * @author <a href="mailto:[email protected]">Bogdan Stefanescu</a>
 */
@WebObject(type="sample5")
@Produces("text/html")
public class Sample5 extends Sample4 {

  /**
   * We are reusing bindings declared in the main class from sample5 and only a new one.
   */
  @Path("info")
  @GET
  public Object getInfo() {
    return "This is the 'info' segment added by the derived module";
  }

}

Object Views

skin/views/sample5/index.ftl

<#-- we are reusing the base template from the base module -->
<@extends src="base.ftl">

<#-- we are redefining only the title block -->
<@block name="title">Sample 5: Web Module Extensibility</@block>

<@block name="content">
Browse <a href="${This.path}/repository">repository</a>
</@block>

</@extends>

skin/views/Document/index.ftl

<#-- we reuse base.ftl from base module -->
<@extends src="base.ftl">

<@block name="content">

<h2>${Document.title}</h2>

<div>Document ID: ${Document.id}</div>

<div>Document path: ${Document.path}</div>

<div>Document name: ${Document.name}</div>

<div>Document type: ${Document.type}</div>

<p>
    <#-- we redefine the nested block info by adding a link to another view named 'info' on the document -->
    <@block name="info">
    <#-- look how the builtin view service adapter is used to locate the 'info' view -->
    <a href="${This.path}/@views/info">More Info</a>
    </@block>
  </p>

  <#if Document.isFolder>
    <hr/>

<div>
    Document children:

<ul>
    <#list Document.children as doc>

<li> <a href="${This.path}/${doc.name}">${doc.name}</a> </li>
    </#list>
    </ul>
    </div>
  </#if>

</@block>
</@extends>

skin/views/Document/info.ftl

<@extends src="base.ftl">

<#--
Here is an additional view on a document added by the derived  module.
You can display the view by using the builtin View Service adapter.
Example: /my/doc/@views/info
-->

<@block name="content">

<h2>More info on document ${Document.title}</h2>

<h3>Last modified: ${Document["dc:modified"]}</h3>

<div>
    Document schemas:

<ul>
    <#list Document.schemas as schema>

<li> ${schema} </li>
    </#list>
    </ul>
  </div>

<div>
    Document facets:

<ul>
    <#list Document.facets as facet>

<li> ${facet} </li>
    </#list>
    </ul>
  </div>
</@block>

</@extends>

2 months ago Loubna Benzaama Fix Showcase Content add-on doc
3 years ago Damien Metzler 6
7 years ago Solen Guitter 4
7 years ago Solen Guitter 5 | Migrated to Confluence 4.0
8 years ago Bogdan Stefanescu 3
8 years ago Bogdan Stefanescu 2
8 years ago Bogdan Stefanescu 1
History: Created by Bogdan Stefanescu

We'd love to hear your thoughts!

All fields required