소스 검색

Added plugin specific data storage support.

Sascha Zelzer 14 년 전
부모
커밋
c94d269aaf

+ 24 - 20
Libs/PluginFramework/ctkPlugin.cpp

@@ -21,6 +21,7 @@
 
 #include "ctkPlugin.h"
 
+#include "ctkPluginFrameworkUtil_p.h"
 #include "ctkPluginPrivate_p.h"
 #include "ctkPluginArchive_p.h"
 #include "ctkPluginFrameworkContext_p.h"
@@ -226,26 +227,29 @@ void ctkPlugin::uninstall()
     d->fwCtx->plugins->remove(d->location);
     d->pluginActivator = 0;
 
-    //TODO: delete plugin specific storage area
-//    if (d->pluginDir != null)
-//    {
-//      if (!d->pluginDir.delete())
-//      {
-//        // Plugin dir is not deleted completely, make sure we mark
-//        // it as uninstalled for next framework restart
-//        if (null!=archive) {
-//          try {
-//            archive.setStartLevel(-2); // Mark as uninstalled
-//          } catch (Exception e) {
-//            // NYI! Generate FrameworkError if dir still exists!?
-//            fwCtx.debug.println("Failed to mark bundle " + id +
-//                                " as uninstalled, " + bundleDir +
-//                                " must be deleted manually: " + e);
-//          }
-//        }
-//      }
-//      bundleDir = null;
-//    }
+    if (d->pluginDir.exists())
+    {
+      if (!ctkPluginFrameworkUtil::removeDir(d->pluginDir.absolutePath()))
+      {
+        // Plugin dir is not deleted completely, make sure we mark
+        // it as uninstalled for next framework restart
+        if (d->archive)
+        {
+          try
+          {
+            d->archive->setStartLevel(-2); // Mark as uninstalled
+          }
+          catch (const std::exception& e)
+          {
+            // NYI! Generate FrameworkError if dir still exists!?
+            qDebug() << "Failed to mark plugin" <<  d->id
+                     << "as uninstalled," << d->pluginDir.absoluteFilePath()
+                     << "must be deleted manually:" << e.what();
+          }
+        }
+      }
+      d->pluginDir.setFile("");
+    }
     if (d->archive)
     {
       d->archive->purge();

+ 16 - 0
Libs/PluginFramework/ctkPluginContext.cpp

@@ -93,6 +93,22 @@ QSharedPointer<ctkPlugin> ctkPluginContext::installPlugin(const QUrl& location,
   return d->plugin->fwCtx->plugins->install(location, in);
 }
 
+QFileInfo ctkPluginContext::getDataFile(const QString& filename)
+{
+  Q_D(ctkPluginContext);
+  d->isPluginContextValid();
+  QDir dataRoot(d->plugin->getDataRoot().absolutePath());
+  if (!dataRoot.exists())
+  {
+    if (!dataRoot.mkpath(dataRoot.absolutePath()))
+    {
+      qWarning() << "Could not create persistent storage area:" << dataRoot.absolutePath();
+    }
+  }
+
+  return QFileInfo(dataRoot, filename);
+}
+
 ctkServiceRegistration* ctkPluginContext::registerService(const QStringList& clazzes, QObject* service, const ServiceProperties& properties)
 {
   Q_D(ctkPluginContext);

+ 25 - 0
Libs/PluginFramework/ctkPluginContext.h

@@ -27,6 +27,7 @@
 #include <QVariant>
 #include <QUrl>
 #include <QSharedPointer>
+#include <QFileInfo>
 
 #include "ctkPluginFramework_global.h"
 
@@ -391,6 +392,30 @@ public:
   bool ungetService(const ctkServiceReference& reference);
 
   /**
+   * Creates a <code>QFileInfo</code> object for a file or directoryin the
+   * persistent storage area provided for the plugin by the Framework.
+   *
+   * <p>
+   * A <code>QFileInfo</code> object for the base directory of the persistent
+   * storage area provided for the context plugin by the Framework can be
+   * obtained by calling this method with an empty string as
+   * <code>filename</code>.
+   *
+   * <p>
+   * If the permissions are enabled, the Framework will
+   * ensure that the plugin has the <code>ctkFilePermission</code> with
+   * actions <code>read</code>,<code>write</code>,<code>delete</code>
+   * for all files (recursively) in the persistent storage area provided for
+   * the context plugin.
+   *
+   * @param filename A relative name to the file or directory to be accessed.
+   * @return A <code>QFileInfo</code> object that represents the requested file
+   *         or directory.
+   * @throws std::logic_error If this ctkPluginContext is no longer valid.
+   */
+  QFileInfo getDataFile(const QString& filename);
+
+  /**
    * Installs a plugin from the specified <code>QIODevice</code> object.
    *
    * <p>

+ 6 - 0
Libs/PluginFramework/ctkPluginFrameworkContext.cpp

@@ -76,6 +76,7 @@ void ctkPluginFrameworkContext::init()
   systemPluginPrivate->initSystemPlugin();
 
   storage = new ctkPluginStorage(this);
+  dataStorage = ctkPluginFrameworkUtil::getFileStorage(this, "data");
   services = new ctkServices(this);
   plugins = new ctkPlugins(this);
 
@@ -123,6 +124,11 @@ int ctkPluginFrameworkContext::getId() const
   return id;
 }
 
+QFileInfo ctkPluginFrameworkContext::getDataStorage(long id)
+{
+  return QFileInfo(dataStorage, QString::number(id));
+}
+
 void ctkPluginFrameworkContext::checkOurPlugin(ctkPlugin* plugin) const
 {
   ctkPluginPrivate* pp = plugin->d_func();

+ 9 - 0
Libs/PluginFramework/ctkPluginFrameworkContext_p.h

@@ -67,6 +67,11 @@ public:
   ctkPluginStorage* storage;
 
   /**
+   * Private Plugin data storage
+   */
+  QDir dataStorage;
+
+  /**
    * First framework init
    */
   bool firstInit;
@@ -116,6 +121,10 @@ public:
    */
   int getId() const;
 
+  /**
+   * Get private plugin data storage file handle
+   */
+  QFileInfo getDataStorage(long id);
 
   /**
    * Check that the plugin belongs to this framework instance.

+ 34 - 1
Libs/PluginFramework/ctkPluginPrivate.cpp

@@ -50,6 +50,34 @@ ctkPluginPrivate::ctkPluginPrivate(
 
   checkManifestHeaders();
 
+  pluginDir = fwCtx->getDataStorage(id);
+//  int oldStartLevel = archive->getStartLevel();
+  try
+  {
+    //TODO: StartLevel Service
+    //if (fwCtx->startLevelController == 0)
+    //{
+      archive->setStartLevel(0);
+    //}
+//    else
+//    {
+//      if (oldStartLevel == -1)
+//      {
+//        archive->setStartLevel(fwCtx->startLevelController->getInitialPluginStartLevel());
+//      }
+//    }
+  }
+  catch (const std::exception& e)
+  {
+    qDebug() << "Failed to set start level on #" << id << ":" << e.what();
+  }
+
+  lastModified = archive->getLastModified();
+  if (lastModified.isNull())
+  {
+    modified();
+  }
+
   // fill require list
   QString requireString = archive->getAttribute(ctkPluginConstants::REQUIRE_PLUGIN);
   QList<QMap<QString, QStringList> > requireList = ctkPluginFrameworkUtil::parseEntries(ctkPluginConstants::REQUIRE_PLUGIN,
@@ -75,7 +103,7 @@ ctkPluginPrivate::ctkPluginPrivate(QWeakPointer<ctkPlugin> qq,
                                      pluginActivator(0), eagerActivation(false), activating(false),
                                      deactivating(false)
 {
-
+  modified();
 }
 
 ctkPluginPrivate::~ctkPluginPrivate()
@@ -108,6 +136,11 @@ ctkPlugin::State ctkPluginPrivate::getUpdatedState()
   return state;
 }
 
+QFileInfo ctkPluginPrivate::getDataRoot()
+{
+  return pluginDir;
+}
+
 void ctkPluginPrivate::setAutostartSetting(const ctkPlugin::StartOptions& setting) {
   try
   {

+ 13 - 0
Libs/PluginFramework/ctkPluginPrivate_p.h

@@ -29,6 +29,7 @@
 #include <QHash>
 #include <QPluginLoader>
 #include <QDateTime>
+#include <QFileInfo>
 
 
 class ctkPluginActivator;
@@ -83,6 +84,13 @@ public:
   ctkPlugin::State getUpdatedState();
 
   /**
+   * Get root for persistent storage area for this plugin.
+   *
+   * @return A QDir object representing the data root.
+   */
+  QFileInfo getDataRoot();
+
+  /**
    * Save the autostart setting to the persistent plugin storage.
    *
    * @param setting The autostart options to save.
@@ -141,6 +149,11 @@ public:
   ctkPluginArchive* archive;
 
   /**
+   * Directory for plugin data
+   */
+  QFileInfo pluginDir;
+
+  /**
    * ctkPluginContext for the plugin
    */
   QScopedPointer<ctkPluginContext> pluginContext;