Class ExtensionsFile

java.lang.Object
net.sf.basedb.util.extensions.manager.ExtensionsFile
All Implemented Interfaces:
Comparable<ExtensionsFile>

public class ExtensionsFile extends Object implements Comparable<ExtensionsFile>
Represents a file with extensions in it. The file is either an XML file or a JAR file. A JAR file is always a real file on the file system and can be accessed with getFile(). An XML file can be both a real file or an abstract stream of bytes and can be accessed by getXmlStream(). The latter method can also be used in the case of a JAR file and will then open the META-INF/extensions.xml file.
Since:
3.0
Author:
Nicklas
Last modified
$Date: 2017-01-20 10:35:05 +0100 (fr, 20 jan 2017) $
  • Field Details

    • log

      private static final Logger log
    • manager

      private final ExtensionsManager manager
    • file

      private final File file
    • uri

      private final URI uri
    • isJar

      private final boolean isJar
    • name

      private final String name
    • rwLock

      private final ReentrantReadWriteLock rwLock
    • allObjects

      private final Map<ObjectKey<?>,Object> allObjects
    • objectMetadata

      private final Map<ObjectKey<?>,Object> objectMetadata
    • isNew

      private boolean isNew
    • wasModified

      private boolean wasModified
    • lastModified

      private long lastModified
    • lastLength

      private long lastLength
    • jarLoader

      private JarClassLoader jarLoader
    • about

      private About about
    • hasError

      private boolean hasError
    • isValid

      private volatile boolean isValid
    • validationError

      private Throwable validationError
  • Constructor Details

    • ExtensionsFile

      ExtensionsFile(ExtensionsManager manager, File file)
      Create a new extensions file backed by a real file on the file system. If the file name ends with '.jar' it is assumed to be a JAR file, otherwise it must be an XML file containing extension definitions.
      Parameters:
      file - The file
    • ExtensionsFile

      ExtensionsFile(ExtensionsManager manager, File file, boolean isJar)
      Create a new extensions file backed by a real file on the file system. The file may be a JAR file or an XML file.
      Parameters:
      file - The file
      isJar - TRUE if it is a JAR file, FALSE if it is an XML file
    • ExtensionsFile

      ExtensionsFile(ExtensionsManager manager, URI uri)
      Create a new extension file backed by an URI. The URI must point to an XML file containing extension definitions.
      Parameters:
      uri - The URI
    • ExtensionsFile

      private ExtensionsFile(ExtensionsManager manager, File file, URI uri, String name, boolean isJar)
  • Method Details

    • compareTo

      public int compareTo(ExtensionsFile other)
      Specified by:
      compareTo in interface Comparable<ExtensionsFile>
    • hashCode

      public int hashCode()
      Overrides:
      hashCode in class Object
    • equals

      public boolean equals(Object o)
      Overrides:
      equals in class Object
    • toString

      public String toString()
      Overrides:
      toString in class Object
    • getName

      public String getName()
      Get the name of the file. The name may or may not correspond to a real file.
    • getFile

      public File getFile()
      Get the underlying file on the file system. Return null if the extension is defined by an URI.
    • getURI

      public URI getURI()
      Get an URI that points to the extensions file.
    • isJar

      public boolean isJar()
      If the file name ends with '.jar' the file is considered a JAR file. Otherwise it is considered an XML file. The file name check is case sensitive.
      Returns:
      TRUE if the file is a JAR file, false if it is an XML file
    • exists

      public boolean exists()
      Check if the file exists. For files that are only represented by an URI this method always return true. For other files the call is forwarded to File.exists() and File.isFile().
      Returns:
      See File.exists()
    • isNew

      public boolean isNew()
      If the file is a new file not previously processed by the extension system. Thew 'new' status is changed when ExtensionsFile.WriteableExtensionsFile.markAsProcessed() is called which usually happens when all extensions has been registered.
      Returns:
      TRUE if the file is a new file, FALSE otherwise
    • isInstalled

      public boolean isInstalled()
      Is this file installed into the system or not?
    • isIgnored

      public boolean isIgnored()
      Is this an extension file that should be ignored?
      Since:
      3.10
    • wasModified

      public boolean wasModified()
      Check if the file was modified when the last call to checkModified() was made. It is recommended that processor implementation use this method instead to avoid inconsistent behaviour if the file happens to be modified while a processor is running.
      Returns:
      TRUE if the file was modified, FALSE otherwise
    • checkModified

      public boolean checkModified()
      Check if the underlying file has been modified since it was last processed. Files that are new are always considered to be modified. Files that are only represented as an URI are considered to be unmodifiable. For other files, we check the File.lastModified() and File.length() of the underlying file and compare that to the last known timestamp and size. Files that are JAR files we also check with the class loader if any of the libraries it uses have changed.

      The result of this call is remembered until this method is called again or until the file is marked as processed.

      See Also:
    • isValid

      public boolean isValid()
      Is the file a valid extensions file according to the last performed validation. This means that the file must be either:
      • An extensions definition XML file
      • A JAR file with an extensions definition XML file at META-INF/extensions.xml.
      The result of the validation is remembered as long as the file is not modified. If checkModified() returns true, the return value of this method may be out of sync. Re-validation of modified files are usually performed by the extensions manager by calling ExtensionsManager.scanForChanges()

      NOTE! The validation will only verify that the XML file follows the rules defined by the schema definition. It will not check that actual classes, etc. exists and can be created. This usually happens later in the registration process, and can be checked by hasError().

      Returns:
      TRUE if the file is valid, FALSE otherwise
      See Also:
    • getValidationError

      public Throwable getValidationError()
      Get more information about the error that caused the validation to fail.
      Returns:
      An exception or null if the validation succeeded
      See Also:
    • getAbout

      public About getAbout()
      Get information about the extensions in this file.
      Returns:
      An About object or null if the file is not a valid extensions file
    • getXmlStream

      public InputStream getXmlStream() throws IOException
      Get an input stream for reading the XML file containing the extension definitions.
      Returns:
      An input stream
      Throws:
      IOException
    • getStream

      public InputStream getStream(String path) throws IOException
      Get an input stream for reading the resource specified by the given path
      Parameters:
      path - The path of the resource
      Returns:
      An input stream (or null if this extensions file is not a JAR file or if the given path is not found)
      Throws:
      IOException
    • validate

      boolean validate()
      Validate the XML file with the extension definitions.
    • hasError

      public boolean hasError()
      If there was an error when registering the extensions in this file. This property is only set if the file has been determined to be a valid extensions file by the isValid() method. Extensions that has an error are automatically disabled.
      Returns:
      TRUE if there was some error, FALSE if everything is ok
    • getAllObjects

      public List<Object> getAllObjects()
      Get a list of all objects defined in this extensions file. This list can contain any type of objects that have been registered by a processer, but typically this list contains ExtensionPoint:s and Extension:s. Use getObjectsOfClass(Class) to get a list with only one type of objects.
      Returns:
      A list with the objects
    • getObjectsOfClass

      public <T> List<T> getObjectsOfClass(Class<T> ofClass)
      Get a list of all objects defined in this extensions file that are of the specified class or interface. Note! The returned list may be empty if another thread is currently processing this file.
      Parameters:
      ofClass - The class/interface the objects must be an instance of
      Returns:
      A list with the objects, if no objects are found the list is empty
    • getObjectForKey

      public <O> O getObjectForKey(ObjectKey<O> key)
      Get the object that was registered for the given key.
      Parameters:
      key - An object key
      Returns:
      The object or null if no object was found
    • getMetadata

      public <M> M getMetadata(ObjectKey<M> key)
      Get metadata registered for a given given key.
      Parameters:
      key - An object key
      Returns:
      A metadata object, or null if no metadata was found
    • getMetadataKeysOfClass

      public <T> List<T> getMetadataKeysOfClass(Class<T> ofClass)
      Get a list of all metadata defined in this extensions file that are keyed with the specified class or interface. Note! The returned list may be empty if another thread is currently processing this file.
      Parameters:
      ofClass - The class/interface the metadata keys must be an instance of
      Returns:
      A list with the objects, if no objects are found the list is empty
    • getClassLoader

      public ClassLoader getClassLoader() throws IOException
      Get the class loader used to load classes for the extension. Only JAR files have class loaders so this method may return null. Once a class loader has been created it remains the same until a change has been detected with checkModified() which forces the creation of a new class loader when this method is called.
      Throws:
      IOException
    • getWriteableFile

      Get a writeable view for the current file. Note that the view is returned in read-only mode and to really be able to write information the method ExtensionsFile.WriteableExtensionsFile.open() must be called.
    • readLock

      boolean readLock()
      Try to aquire a read-lock. A read-lock is needed when reading information that may be corrupted if another thread is currently writing information to this file.
      Returns:
      TRUE if the read-lock could be aquired immediately, FALSE if not
    • writeLock

      boolean writeLock()
      Try to aquire a write-lock. A write-lock is needed by any thread that wants to update information about this file. The write-lock can only be held by a single thread at a time.
      Returns:
      TRUE if the write-lock could be aquired within 1 second, FALSE if not