Resource Management
Introduction
The kernel of the jptools library is the resource management (ResourceManager
).
The idea is to provide a simple interface to load and store files (objects) from respective to a
resource. All actions of the resource management are transparent. An application which
use this management has not care about from which path, database or what ever a resource
will be loaded or stored to.
Design
The file manager (FileManager
)
The FileManager
interface defines the general access methods to a file:
The concrete implementation class is the class FileCacheManager
. It implements
the FileManager
and additionaly a simple cache which can be enabled or disabled.
The subclasses PropertiesManager
and the XMLManager
implements
the file handling to special files like properties or xml files. The
FileCacheManager
can also be used to read or store a file. It reads the whole
file and give it back in a String
representation.
The BootManager
is a special FileManager
. It is used to load
a configuration like the jptools.properties
. The BootManager run through the following
steps if it tries to load a resource:
It test first if an alias exist (see more in the chapter The resource mapping).
After resolving the alias, it tries to load the searched file with the
FileResourceHandler
(see more in the chapter The resource handler).If it can not found by the
FileResourceHandler
it tries to load the resource with theClasspathResourceHandler
but only if the flagresource.bootmanager.enableClasspathLoader
in the configutation is set totrue
(see more in the chapter The resource handler).
The default settings are:
############################################################################## # resource configuration ############################################################################## resource.propertiesDescritption = resource.enableSystemKeyValueFileLoader = true resource.bootmanager.enableClasspathLoader = true resource.classPathLoaderPrefix = $ # resource handlers resource.handlerMapper1.jptools.resource.ClasspathResourceHandler = ^\\$.* resource.handlerMapper2.jptools.resource.GZIPResourceHandler = .*\\.gz resource.handlerMapper3.jptools.resource.FileResourceHandler = .*
The resource manager (ResourceManager
)
All implementation of the FileManager
are working with simple streams like
InputStream
and OutputStream
. The ResourceManager
builds the kernel of the resource management. It gets a caller for a given resource name
a stream back. This can be either an InputStream
or neither an OutpuStream
.
The ResourceManager
has a ResourceHandlerMap
attribute which defines
which resource with which resource handler (ResourceHandler
) works. The
ResourceManager
also contains a ResourceConfig
and a Map
.
In the next chapters the resource handler and the resource mapping are more explained.
The configuration (ResourceConfig
) defines the settings for the map and the resource
handler.
The resource handler (ResourceHandler
)
A ResourceHandler
implements the concrete access to a resource. The following handlers are
currently realized:
FileResourceHandler
: This class implements the access of a file. The file can be accessed with absolult or realtiv path.ClasspathResourceHandler
: This handler implements the access of files which are placed in the classpath. Only read operations are supported.TODO:
JDBCResourceHandler
: This class implements the access to a database over JDBC.
In the ResourceConfig
which is hold by the ResourceManager
is defined which
resource will be loaded with which resource handler. There are two different ways to define or manipulate
this definition:
- Rules are defined in the
jptools.properties
file. The entries starts withresource.handlerMapper
and follows by a number. This number defines the sort order of the resource handler rule. After the sort order number the resource handler name follows. The value of the properties defines the rule to which resource the resource handler will be used. The rule is a regular expression:resource.handlerMapper1.jptools.resource.ClasspathResourceHandler = ^\\$.* resource.handlerMapper2.jptools.resource.FileResourceHandler = .*
This example defines that each resource which starts with a
$
character will loaded with the classjptools.resource.ClasspathResourceHandler
. All other files are loaded with the classjptools.resource.FileResourceHandler
.Each time when a resource should accessed by the
ResourceManager
the resource handler rules run through in the sort order which are defined by the described initialisation.
- The second way to modify the resource handler rules is to use the
ResourceManager
methods likegetResourceHandlerMapper
andsetResourceHandlerMapper
:public class Demo { public static void main (String[] args) throws Exception { ResourceHandlerMapper mapper = ResourceManager.getResourceHandlerMapper(); try { mappper.clear(); mapper.add( "^\\$.*", "jptools.resource.ClasspathResourceHandler" ); mapper.add( ".*", "jptools.resource.DefaultResourceHandler" ); } catch( RESyntaxException e ) { log.error( "Wrong initialisation", e ); } ResourceManager.setResourceHandlerMapper( mapper ); } }
The resource mapping (alias for a resource name)
The resource mapping maps as example a single resource name to another one. In other words it supports to set an alias for a resource. Recursive mappings (aliases) are supported!
Example:
If the resource TestResourceName as example should be loaded than the resource management searches a mapping for it. In this case no mapping is found. After searching and resolving the mapping the resource manager searches a
ResourceHandler
to load the resource. If no handler is found than theFileResourceHandler
will be used.If the following mapping is defined:
- TestResourceName1 = TestResourceName2
- TestResourceName2 = TestResourceName
If the resource TestResourceName should be loaded than the resource management finds firstly a mapping to TestResourceName2. Afterwards the framework finds also a mapping of the resource TestResourceName2 to TestResourceName1. In this example will the resource TestResourceName1 loaded if the resource TestResourceName should be accessed.
There are different ways to set a resource mapping:
- The general way to set an alias is to use the
jptools.properties
file and add some entries in there like:resource.alias1.testfiles.conf = conf/testfiles.conf resource.alias2.conf/demo.xml = testcase/demo.xml
- Additional the method
getResourceMapper()
of the classResourceManager
could be used to receive the current mapping (HashMap
). Add a new mapping by using the put method. The methodsetResourceMapper
sets a mapping:public class Demo { public static void main (String[] args) throws Exception { Map fileMapper = ResourceManager.getResourceMapper(); fileMapper.put( "logconfig.properties", "/conf/log.config" ); fileMapper.put( "mail.conf", "conf/mail.conf" ); fileMapper.put( "conf/mail.conf", "/conf/mail.conf" ); ResourceManager.setResourceMapper( fileMapper ); } }
- The way over system properties is also supported. But only if in the configuration the property
resource.enableSystemKeyValueFileLoader
is set totrue
. The system property key defines the resource name to map to another name and the value is the alias of the resource:java -Djptools.properties=config/jptools.properties ...
Examples
Reading an ASCII file
public class Demo { public static void main (String[] args) throws Exception { FileCacheManager fileManager = new FileCacheManager(); Object obj=fileManager.getFile( args[0] ); } }
Reading a property file
public class Demo { public static void main (String[] args) throws Exception { PropertiesManager propertiesManager = new PropertiesManager(); /* the cast is necessary!!! */ Properties prop = (Properties)propertiesManager.getFile( args[0] ); } }
Reading a xml file
public class Demo { public static void main (String[] args) throws Exception { XMLManager xmlManager = new XMLManager(); /* the cast is necessary!!! */ org.w3c.dom.Document doc = (org.w3c.dom.Document)xmlManager.getFile( args[0] ); } }
Get a resource mapping of a file
public class Demo { public static void main (String[] args) throws Exception { String fileName = ResourceManager.getInstance().getMappedResourceName( args[0] ); File theFile = new File( fileName ); } }