Basic Concepts
TrueZIP is a Java based plug-in framework for virtual file systems (VFS) which provides transparent access to archive files as if they were just plain directories.
Overall Architecture
TrueZIP applies the (in)famous three-tier architecture pattern:
- The Access Tier is a facade for the Kernel Tier which provides convenient-to-use client APIs for TrueZIP applications. No file system state is managed by this tier, which enables a TrueZIP application to work with any client API concurrently. This tier consists of the modules TrueZIP File* and TrueZIP Path (since TrueZIP 7.2). In addition to the canonical term access module, each of these may also get referred to by the term client API module for better comprehensibility.
- The Kernel Tier manages all virtual file system state. It also provides multiplexing, caching and buffering for multithreaded environments so that the driver tier does not need to take care of this. This tier solely consists of the module TrueZIP Kernel.
- The Driver Tier implements the I/O operations for their respective (federated) file system type. This tier consists of all file system driver modules, e.g. TrueZIP Driver FILE, TrueZIP Driver ZIP et al.
Design Paradigms
The TrueZIP project employs several high level design paradigms which have proven to be beneficial. However, these are only guidelines - not rules - so they should get applied with some care.
Convention Over Configuration
The decomposition of this framework into separate modules enables users to easily configure the initial setup of the application's archive detection by simply putting the JARs of the required file system driver modules on the run time class path. This will cause the application to automatically detect the canonical file extension for the archive files supported by the respective file system driver modules - no configuration file editing is required.
The application can simply accept this initial setup of the archive detection in its current configuration or it can explicitly override it. Check the FAQ for the TrueZIP File* API for a discussion of some options to adapt the archive detection to your needs.
Service Location
As an implication of the Convention Over Configuration design paradigm, the TrueZIP Kernel module provides service locator singletons for the file system manager, the file system drivers and the temporary I/O buffer pool.
File system drivers may add additional service locators singletons. For example, the TrueZIP Driver ZIP.RAES (TZP) module adds another service locator singleton for the key manager which obtains passwords or key files required to encrypt and decrypt RAES encrypted ZIP files.
Dependency Injection
Although the service locator singletons are provided by the TrueZIP Kernel module, it does not actually use them. To the contrary, the TrueZIP Kernel module fully relies on the Dependency Injection design paradigm. This enables TrueVFS modules and TrueVFS applications to inject custom implementations or simply the service locator singletons as a dependency into the TrueVFS Kernel.
For example, the file system manager service locator singleton and the file system driver service locator singleton are used by the APIs of the TrueZIP File* and TrueZIP Path modules in order to implement the Convention Over Configuration design paradigm. Likewise, the temporary I/O entry pool service locator singleton is used by the file system driver modules.
No Dependency Injection framework is used in order to reduce TrueZIP's dependency on third party projects.
Constructor injection is favored wherever possible in order to enable immutable objects.
Immutable Classes
Immutable classes are favored wherever possible because they inherently provide support for multithreading, which is a key requirement for most TrueZIP Kernel classes.
For example, the classes FsPath, FsMountPoint and FsEntryName are immutable so that their instances can get safely shared among many objects and threads.
Loose Coupling
Programming against interfaces or abstract classes is preferred over implementation classes in order to ease exchanging implementation classes.
For example, the abstract classes FsModel and FsController participate in a variant of the MVC design pattern which is known as the Front Controller design pattern. The numerous implementation classes participate in the different file system driver modules in order to accommodate to the different contexts of non-federated and federated file system types and implement their specific behavior.
Open For Extension, Closed For Modification
Abstract classes are favored over interfaces wherever the future addition of more methods is anticipated in order to enable binary backwards compatibility.
Wherever reasonable, classes, methods and fields are declared (package) private and/or final in order to inhibit undesirable inheritance, enhance maintainability and/or enable true immutability.
For example, the abstract classes FsModel and FsController provide final implementations for Object.equals(Object), Object.hashCode() and Object.toString() because there is exactly only one reasonable implementation for any implementation class.
Separation Of Concerns
The design of interfaces and abstract classes aims for strong cohesion in order to ease implementation classes and enhance their extensibility and reusability. Where conflicts arise, the Law Of Demeter is sacrificed for strong cohesion.
The set of overridable public methods of abstract classes and interfaces is reduced as much as reasonable in order to ease implementation classes.
For example, the abstract class FsDriver consists of only one abstract method FsDriver.newController(FsModel, FsController) which needs to get implemented in any file system driver module.