Latest Posts

Archives [+]

Categories [+]

Authors [+]

Entries filed under 'atom'

    Posted by Michael Marth JAN 13, 2010

    Posted in atom, cmis, jcr, lotd, standards, wcm and webdav Add comment

    Following up on Jon Marks' post on standards relevant for content management Justin Cormack has put together a "Standards Diagram for Content Management" Prezi landscape. Nice work!


    The part "structuring" in Justin's presentation contains Docbook and DITA. Theresa compared these two standards a while ago:

    Posted by Michael Marth OCT 07, 2009

    Posted in atom, cmis, jackrabbit, jcr, rest and sling Add comment

    Justin Cormack has written a noteable blog post titled "RESTful daydream #4" (pun intended?) about RESTful content repositories. I disagree with some of what Justin writes about JCR and Sling. However, I completely share his vision about REST's role in content management and I am with him regarding the overall theme of his post.

    Essentially, Justin asks for a "web content repository":

    The odd thing is that a web content repository alone surely lends itself to a simple REST architecture. Content is after all lots of small resources with relations. [...] It takes content, relates it to other content, and serves it back, with authentication and versioning. Everything else is in other system layers, transforming it and so on. Not simple, but well defined; lower level than JCR + Sling say.

    Apache Sling provides a RESTful interface onto content, but being a web application framework it provides much more, especially scripting. So I can understand well why Justin dismisses Sling as being too powerful. However, I believe that Jackrabbit's native http layer is pretty much on the mark (Justin also dismisses it in the comments as being not RESTful. I do not know why.). As far as I know the Jackrabbit http remoting layer is quite work-in-progress so one might argue about the details regarding its RESTfulness, but overall it fits what I understand to be a RESTful web content repository.

    There is one aspect regarding a web content repository I would like to add to the discussion: I think it is crucial that the representations of resources and be consumed by browsers. HTML forms for writing and presenting resources in JSON should be part of the equation. Adding models or semantics on top of that will might do more harm than good.

    Do we need a formal standard for web content repositories? From my perspective: not yet. At the moment we still need to learn more, i.e. more repository implementations and users that have built a CMS on top of a web content repository.

    Posted by Michael Marth JAN 29, 2009

    Posted in atom, atompub, cmis and rest Comment 1

    David Nuescheler has published the slide deck he presented at the CMIS F2F in Redmond. Interesting bits about the relation of AtomPub and CMIS.

     

    Posted by Michael Marth DEC 16, 2008

    Posted in atom, atompub, crx and jcr Comment 1

    Apache Abdera is an Apache Software Foundation project to...

    build a functionally-complete, high-performance implementation of the IETF Atom Syndication Format (RFC 4287) and Atom Publishing Protocol (RFC 5023) specifications.

    (if reading RFCs is not your cup of tea: IBM developerworks has some good tutorials on AtomPub. Update: Julian Reschke pointed me to these HTML versions of the Publishing and Syndication spec which are quite a bit easier on the eyes).

    The project has recently graduated from the incubator and is now a top level project at the ASF. Congratulations!

    Since release 0.4 Abdera comes with a JCR adapter (JCR-loves-Atom, remember?). The JCR adapter allows you to run an Abdera AtomPub server and have a Jackrabbit repository be used for storage.

    Getting it to run is quite easy: do a checkout of the 0.4 release at http://svn.apache.org/repos/asf/abdera/java/tags/abdera-0.4.0-incubating/ and built with

    mvn clean install
    

    This command will also execute the test cases in adapters/jcr/src/test/java/org/apache/abdera/jcr. As part of the test cases a JCR-backed Atom server gets started and some JCR nodes are created through Atom. The main magic happens in the JcrCollectionProvider class that maps the AtomPub elements onto JCR nodes. For example, AtomPub's ID is mapped onto JCR's UUID:

    public String getId(Node entry) throws ResponseContextException {
     try {
      return "urn:" + entry.getUUID();
     } catch (RepositoryException e) {
      throw new ResponseContextException(500, e);
     }
    }
    

    Getting Abdera to interact with CRX

    The primary purpose of the JcrCollectionAdapter class is to equip a stand-alone Atom server with a JCR repository for storage. However, with a bit of tweaking the class can also be used to provide an Atom interface to an existing CRX repository: a simple way to get things running is to leave the existing CRX Quickstart untouched and connect to the repository through RMI. RMI is disabled by default, but on CRX's Knowledge Base is an article how to enable it.

    Abdera bundles Jetty which can be used to provide the http server for AtomPub. I have wrapped the JcrCollectionProvider in a little servlet and initialized Jetty with this servlet. The class looks like this:

    import org.apache.jackrabbit.rmi.client.ClientRepositoryFactory;
    import javax.jcr.Repository;
    import javax.jcr.Session;
    import javax.jcr.SimpleCredentials;
    import javax.servlet.http.HttpServlet;
    import org.apache.abdera.protocol.server.Provider;
    import org.apache.abdera.protocol.server.impl.DefaultProvider;
    import org.apache.abdera.protocol.server.impl.SimpleWorkspaceInfo;
    import org.apache.abdera.protocol.server.servlet.AbderaServlet;
    import org.mortbay.jetty.Server;
    import org.mortbay.jetty.servlet.Context;
    import org.mortbay.jetty.servlet.ServletHolder;
    
    public class AppServer {
    
     public static void main(String... args) throws Exception {
      int port = 9002;
      try {
       port = args.length > 0 ? Integer.parseInt(args[0]) : 9002;
      } catch (Exception e) {
      }
      Server server = new Server(port);
      Context context = new Context(server, "/", Context.SESSIONS);
      ServletHolder servletHolder = new ServletHolder(new
      JcrCollectionServlet());
      context.addServlet(servletHolder, "/*");
      server.start();
      server.join();
     }
    
     public static final class JcrCollectionServlet extends AbderaServlet {
      protected Provider createProvider() {
    
       DefaultProvider jcrProvider = new DefaultProvider();
    
       try {
    
        ClientRepositoryFactory factory = new ClientRepositoryFactory();
        Repository repository = factory.getRepository("//localhost:1234/crx");
    
        JcrCollectionAdapter cp = new JcrCollectionAdapter();
        cp.setTitle("My Entries");
        cp.setAuthor("Apache Abdera");
        cp.setCollectionNodePath("entries");
        cp.setRepository(repository);
        cp.setCredentials(new SimpleCredentials("admin", "admin".toCharArray()));
        cp.setHref("feed");
        cp.initialize();
    
        SimpleWorkspaceInfo wkspc = new SimpleWorkspaceInfo();
        wkspc.setTitle("JCR Workspace");
        wkspc.addCollection(cp);
        jcrProvider.addWorkspace(wkspc);
        jcrProvider.init(getAbdera(), getProperties(getServletConfig()));
       } catch (Exception e) {
        return null;
       }
       return jcrProvider;
      }
     }
    }
    

    Please note that the servlet just needs to acquire the JCR and pass a reference to it to the JcrCollectionProvider. Thus, this approach can be used with JNDI or other means of connection as well and is not specific to RMI. Before you run the server you will have to perform a little tweak in the JcrCollectionProvider: when the provider is started it will try to register a new node type. AFAIK this does not work via RMI (I might be wrong, though), so I commented this code in the initialize() method :

    //JackrabbitNodeTypeManager jntmgr = (JackrabbitNodeTypeManager) workspace.getNodeTypeManager();
    //if (!jntmgr.hasNodeType("abdera:entry")) {
     //InputStream in = getClass().getResourceAsStream("/org/apache/abdera/jcr/nodeTypes.xml");
     //try {
      //jntmgr.registerNodeTypes(in, JackrabbitNodeTypeManager.TEXT_XML);
     //} finally {
      //in.close();
     //}
    //}
    

    and manually added the the namespace abdera="http://abdera.apache.org" and the node type "abdera:entry" defined in adapters/jcr/src/main/resources/org/apache/abdera/jcr/nodeTypes.xml to CRX (find a link to the node type manager that provides a UI for registering namespaces and node types at http://localhost:7402/crx). The JcrCollectionProvider will use its specific node type abdera:entry to store and retrieve data.

    After you have defined abdera:entry run the AtomPub server main class from above and find your Atom interface at http://localhost:9002/feed (make sure to include the CRX RMI jars from crx-quickstart/server/runtime/0/_crx/WEB-INF/lib on your classpath). You create nodes via curl (see here for an example) or (more or less convenient, depending on your taste) via the AbderaClient class like this code below. It creates a new post with some example data:

    import java.util.Date;
    import javax.jcr.Repository;
    import org.apache.abdera.Abdera;
    import org.apache.abdera.factory.Factory;
    import org.apache.abdera.i18n.iri.IRI;
    import org.apache.abdera.model.Entry;
    import org.apache.abdera.protocol.client.AbderaClient;
    import org.apache.abdera.protocol.client.RequestOptions;
    import org.apache.abdera.protocol.server.impl.DefaultProvider;
    
    // this code is taken from Dan Diephous's
    // test classes for the JcrCollectionProvider 
    public class AppServerTest {
    
     private DefaultProvider jcrProvider;
     private Repository repository;
    
     public static void main(String... args) throws Exception {
      Abdera abdera = new Abdera();
      Factory factory = abdera.getFactory();
    
      AbderaClient client = new AbderaClient(abdera);
    
      String base = "http://localhost:9002/";
    
      // Testing of entry creation
      IRI colUri = new IRI(base).resolve("feed");
      Entry entry = factory.newEntry();
      entry.setTitle("Some Entry");
      entry.setUpdated(new Date());
      entry.addAuthor("Dan Diephouse"); // thanks, for the provider, Dan!
      entry.setId(factory.newUuidUri());
      entry.setSummary("This is my entry.");
      entry.setContent("This is my entry. It's swell.");
    
      RequestOptions opts = new RequestOptions();
      opts.setContentType("application/atom+xml;type=entry");
      ClientResponse res = client.post(colUri.toString(), entry, opts);
     }
    }
    

    (the example is taken from Dan Diephouse's test classes for the JcrCollectionProvider)

    This might be your first step if you want to offer an AtomPub interface to your CRX repository. However, it is likely that you will have to tweak the JcrCollectionProvider class a bit more: the crucial part is the mapping between JCR nodes and AtomPub elements. As discussed above the out-of-the-box JcrCollectionProvider can only deal with nodes of type abdera:entry. However, this will not suffice to Atom-enable an existing application, the mapping needs to fit to your specific application's node types.

    Somewhat related to AtomPub and JCR: Apache Jackrabbit is expected to support CMIS in the future (which includes an AtomPub binding). Work has started on this and there is some initial code in the sandbox.

    Posted by Michael Marth JUL 02, 2008

    Posted in atom, atompub and jcr Add comment

    Mule Galaxy 1.0 has been released 2 days ago. It is (in their own words)...

    an open source governance platform with an integrated registry/repository. It includes versioning, lifecycle management, dependency management and policy enforcement features which enable you to effectively govern your applications and services

    Galaxy uses JCR (Apache Jackrabbit) internally and Atom Publishing Protocol for custom integrations. As such it constitutes a nice example for JCR and APP complementing each other.

    Another comment that is only slightly related: I just came across Galaxy developer Dan Diephouse's presentations on Effective RESTful services and AtomPub. Excellent stuff (and slide 40 of the first one made me lol).