JBoss.orgCommunity Documentation

Chapter 13. File System Connector

This connector exposes an area of the local file system as a graph of "nt:file" and "nt:folder" nodes. The connector can be configured so that the workspace name is either a path to the directory on the file system that represents the root of that workspace or the name of subdirectory within a root directory (see the workspaceRootPath property below). Each connector can define whether it allows new workspaces to be created. If the directory for a workspace does not exist, this connector will attempt to create the directory (and any missing parent directories).

Note

The file nodes returned by this connector will have a primary type of nt:file and a child node named jcr:content. The jcr:content node will have a primary type of mode:resource. The mode:resource node type is equivalent to the built-in nt:resource node type in all ways except one: it does not extend mix:referenceable. This is because ModeShape cannot assign a persistent UUID to the files in the file system or guarantee that no other process will move or delete the files outside of ModeShape. The mix:referenceable node type cannot be implemented if either of these conditions cannot be met. Additional properties (including mixin types) can be added by setting the customPropertiesFactory property to point to an implementation of the CustomPropertiesFactory interface.

The FileSystemSource class provides a number of JavaBean properties that control its behavior:

Table 13.1. FileSystemSource properties

PropertyDescription
cachePolicyOptional property that, if used, defines the cache policy for this repository source. When not used, this source will not define a specific duration for caching information.
creatingWorkspaceAllowedOptional property that defines whether clients can create additional workspaces. The default value is "true".
customPropertiesFactory Specifies the CustomPropertiesFactory implementation that should be used to augment the default properties available on each node. This property can be set either from an object that implements the CustomPropertiesFactory interface or from the name of a class with a public, no-argument constructor that implements the CustomPropertiesFactory interface. In the latter case, a the named class will be instantiated and used as the custom properties factory implementation.
defaultWorkspaceNameOptional property that is initialized to "default" and which defines the name for the workspace that will be used by default if none is specified.
exclusionPattern

Specifies a regular expression that is used to determine which files and folders in the underlying file system should be exposed through this connector. Files and folders with a name that matches the provided regular expression will not be exposed by this source. Setting this property to null has the effect of removing the exclusion pattern.

This property is mutually incompatible with the filenameFilter property. Setting this property to a non-null value will automatically set the filenameFilter property to null.

filenameFilter

Specifies the FilenameFilter that is used to determine which files and folders in the underlying file system should be exposed through this connector. Only files and folders that the filter accepts will be accessible through this source.

This property can be set either from an object that implements the FilenameFilter interface or from the name of a class with a public, no-argument constructor that implements the FilenameFilter interface. In the latter case, a the named class will be instantiated and used as the filename filter implementation. Setting this property to null has the effect of clearing the filter.

This property is mutually incompatible with the exclusionPattern property. Setting this property to a non-null value will automatically set the exclusionPattern property to null.

nameThe name of the repository source, which is used by the RepositoryService when obtaining a RepositoryConnection by name.
predefinedWorkspaceNamesOptional property that, if used, defines names of the workspaces that are predefined and need not be created before being used. This can be coupled with a "false" value for the "creatingWorkspaceAllowed" property to allow only the use of only predefined workspaces.
rootNodeUuidOptional property that, if used, specifies the UUID that should be used for the root node of each workspace. If no value is specified, a default UUID is used.
retryLimitOptional property that, if used, defines the number of times that any single operation on a RepositoryConnection to this source should be retried following a communication failure. The default value is '0'.
updatesAllowedDetermines whether the content in the file system can be updated ("true"), or if the content may only be read ("false"). The default value is "false" to avoid unintentional security vulnerabilities.
workspaceRootPath

Optional property that, if used, specifies a path on the local file system to the root of all workspaces. The source will will use the name of the workspace as a relative path from the workspaceRootPath to determine the path for a particular workspace. If no value (or a null value) is specified, the source will use the name of the workspace as a relative path from the current working directory of this virtual machine (as defined by new File(".").

As an example for a workspace named "default/foo", the source will use new File(workspaceRootPath, "default/foo") as the source directory for the connector if workspaceRootPath is set to a non-null value, or new File(".", "default/foo") as the source directory for the connector if workspaceRootPath is set to null.


One way to configure the file system connector is to create JcrConfiguration instance with a repository source that uses the FileSystemSource class. For example:



JcrConfiguration config = ...
config.repositorySource("FS Store")
      .usingClass(FileSystemSource.class)
      .setDescription("The repository for our content")
      .setProperty("workspaceRootPath", "/home/content/someApp")
      .setProperty("defaultWorkspaceName", "prod")
      .setProperty("predefinedWorkspaceNames", new String[] { "staging", "dev"})
      .setProperty("rootNodeUuid", UUID.fromString("fd129c12-81a8-42ed-aa4b-820dba49e6f0")
      .setProperty("updatesAllowed", "true")
      .setProperty("creatingWorkspaceAllowed", "false");
 

Another way to configure the file system connector is to create JcrConfiguration instance and load an XML configuration file that contains a repository source that uses the FileSystemSource class. For example a file named configRepository.xml can be created with these contents:



<?xml version="1.0" encoding="UTF-8"?>
<configuration xmlns:mode="http://www.modeshape.org/1.0" xmlns:jcr="http://www.jcp.org/jcr/1.0">
    <!-- 
    Define the sources for the content.  These sources are directly accessible using the 
    ModeShape-specific Graph API. In fact, this is how the ModeShape JCR implementation works.  You can 
    think of these as being similar to JDBC DataSource objects, except that they expose graph 
    content via the Graph API instead of records via SQL or JDBC. 
    -->
    <mode:sources jcr:primaryType="nt:unstructured">
        <!-- 
        The 'FS Store' repository is a file system source with a three predefined workspaces 
        ("prod", "staging", and "dev").
        -->
        <mode:source jcr:name="FS Store" 
            mode:classname="org.modeshape.connector.filesystem.FileSystemSource"
            mode:description="The repository for our content"
            mode:workspaceRootPath="/home/content/someApp"
            mode:defaultWorkspaceName="prod"
            mode:creatingWorkspacesAllowed="false"
            mode:rootNodeUuid="fd129c12-81a8-42ed-aa4b-820dba49e6f0"
            mode:updatesAllowed="true" >
            <mode:predefinedWorkspaceNames>staging</mode:predefinedWorkspaceNames>
            <mode:predefinedWorkspaceNames>dev</mode:predefinedWorkspaceNames>
            <!-- 
            If desired, specify a cache policy that caches items in memory for 5 minutes (300000 ms).
            This fragment can be left out if the connector should not cache any content.
            -->
            <mode:cachePolicy jcr:name="cachePolicy" 
              mode:classname="org.modeshape.graph.connector.path.cache.InMemoryWorkspaceCache$InMemoryCachePolicy"
              mode:timeToLiveInMilliseconds="300000" />
        </mode:source>    
    </mode:sources>

    <!-- MIME type detectors and JCR repositories would be defined below --> 
</configuration>
 

The configuration can then be loaded from Java like this:



JcrConfiguration config = new JcrConfiguration().loadFrom("/configRepository.xml");