summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--desktop/inc/app.hxx1
-rw-r--r--desktop/source/app/app.cxx3
-rw-r--r--desktop/source/app/check_ext_deps.cxx235
-rw-r--r--desktop/source/deployment/dp_services.cxx13
-rw-r--r--desktop/source/deployment/gui/dp_gui_extensioncmdqueue.cxx20
-rw-r--r--desktop/source/deployment/inc/dp_descriptioninfoset.hxx15
-rw-r--r--desktop/source/deployment/inc/dp_misc.h21
-rw-r--r--desktop/source/deployment/inc/dp_version.hxx7
-rw-r--r--desktop/source/deployment/manager/dp_activepackages.cxx22
-rw-r--r--desktop/source/deployment/manager/dp_activepackages.hxx10
-rw-r--r--desktop/source/deployment/manager/dp_extensionmanager.cxx1301
-rw-r--r--desktop/source/deployment/manager/dp_extensionmanager.hxx287
-rw-r--r--desktop/source/deployment/manager/dp_manager.cxx696
-rw-r--r--desktop/source/deployment/manager/dp_manager.h53
-rw-r--r--desktop/source/deployment/manager/dp_managerfac.cxx4
-rw-r--r--desktop/source/deployment/manager/dp_tmprepocmdenv.cxx166
-rw-r--r--desktop/source/deployment/manager/dp_tmprepocmdenv.hxx84
-rw-r--r--desktop/source/deployment/manager/makefile.mk4
-rw-r--r--desktop/source/deployment/misc/dp_descriptioninfoset.cxx250
-rw-r--r--desktop/source/deployment/misc/dp_misc.cxx31
-rw-r--r--desktop/source/deployment/misc/dp_version.cxx6
-rw-r--r--desktop/source/deployment/misc/makefile.mk3
-rw-r--r--desktop/source/deployment/registry/component/dp_compbackenddb.cxx142
-rw-r--r--desktop/source/deployment/registry/component/dp_compbackenddb.hxx116
-rw-r--r--desktop/source/deployment/registry/component/dp_component.cxx171
-rw-r--r--desktop/source/deployment/registry/component/makefile.mk3
-rw-r--r--desktop/source/deployment/registry/configuration/dp_configuration.cxx13
-rw-r--r--desktop/source/deployment/registry/dp_backend.cxx81
-rw-r--r--desktop/source/deployment/registry/dp_backenddb.cxx332
-rw-r--r--desktop/source/deployment/registry/dp_registry.cxx27
-rw-r--r--desktop/source/deployment/registry/executable/dp_executable.cxx10
-rw-r--r--desktop/source/deployment/registry/help/dp_help.cxx13
-rw-r--r--desktop/source/deployment/registry/inc/dp_backend.h16
-rw-r--r--desktop/source/deployment/registry/inc/dp_backenddb.hxx121
-rw-r--r--desktop/source/deployment/registry/makefile.mk3
-rw-r--r--desktop/source/deployment/registry/package/dp_description.cxx205
-rw-r--r--desktop/source/deployment/registry/package/dp_description.hxx125
-rw-r--r--desktop/source/deployment/registry/package/dp_extbackenddb.cxx177
-rw-r--r--desktop/source/deployment/registry/package/dp_extbackenddb.hxx94
-rw-r--r--desktop/source/deployment/registry/package/dp_package.cxx282
-rw-r--r--desktop/source/deployment/registry/package/makefile.mk2
-rw-r--r--desktop/source/deployment/registry/script/dp_script.cxx19
-rw-r--r--desktop/source/deployment/registry/sfwk/dp_sfwk.cxx18
-rw-r--r--desktop/source/pkgchk/unopkg/unopkg_app.cxx80
-rw-r--r--desktop/source/pkgchk/unopkg/unopkg_cmdenv.cxx2
45 files changed, 4396 insertions, 888 deletions
diff --git a/desktop/inc/app.hxx b/desktop/inc/app.hxx
index 0ae632a6e968..4f5a3b176be3 100644
--- a/desktop/inc/app.hxx
+++ b/desktop/inc/app.hxx
@@ -132,6 +132,7 @@ class Desktop : public Application
static sal_Bool LicenseNeedsAcceptance();
static sal_Bool IsFirstStartWizardNeeded();
static sal_Bool CheckExtensionDependencies();
+ static void SynchronizeExtensionRepositories();
private:
// Bootstrap methods
diff --git a/desktop/source/app/app.cxx b/desktop/source/app/app.cxx
index efba60ca75b9..b82915871566 100644
--- a/desktop/source/app/app.cxx
+++ b/desktop/source/app/app.cxx
@@ -1395,6 +1395,9 @@ void Desktop::Main()
bool bAbort = CheckExtensionDependencies();
if ( bAbort )
return;
+ //Check if bundled or shared extensions were added /removed
+ //and process those extensions
+ SynchronizeExtensionRepositories();
// First Start Wizard allowed ?
if ( ! pCmdLineArgs->IsNoFirstStartWizard())
diff --git a/desktop/source/app/check_ext_deps.cxx b/desktop/source/app/check_ext_deps.cxx
index 8b73e0c2c525..17dc20e1a129 100644
--- a/desktop/source/app/check_ext_deps.cxx
+++ b/desktop/source/app/check_ext_deps.cxx
@@ -27,21 +27,27 @@
// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_desktop.hxx"
+#include <osl/file.hxx>
#include <rtl/bootstrap.hxx>
#include <rtl/ustring.hxx>
+#include <rtl/logfile.hxx>
+#include "cppuhelper/compbase3.hxx"
+
#include <unotools/configmgr.hxx>
#include <comphelper/processfactory.hxx>
#include <comphelper/sequence.hxx>
#include <cppuhelper/bootstrap.hxx>
-
+#include <com/sun/star/ucb/XCommandEnvironment.hpp>
#include <com/sun/star/beans/XPropertySet.hpp>
#include <com/sun/star/beans/NamedValue.hpp>
#include "com/sun/star/deployment/XPackage.hpp"
#include "com/sun/star/deployment/XPackageManager.hpp"
#include "com/sun/star/deployment/thePackageManagerFactory.hpp"
+#include "com/sun/star/deployment/ExtensionManager.hpp"
#include <com/sun/star/task/XJob.hpp>
#include <com/sun/star/task/XJobExecutor.hpp>
+#include <com/sun/star/task/XInteractionApprove.hpp>
#include <com/sun/star/ui/dialogs/XExecutableDialog.hpp>
#include <com/sun/star/util/XChangesBatch.hpp>
@@ -53,9 +59,91 @@ using namespace com::sun::star;
#define UNISTRING(s) rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(s))
+namespace
+{
+//For use with XExtensionManager.synchronize
+class SilentCommandEnv
+ : public ::cppu::WeakImplHelper3< ucb::XCommandEnvironment,
+ task::XInteractionHandler,
+ ucb::XProgressHandler >
+{
+public:
+ virtual ~SilentCommandEnv(){};
+ SilentCommandEnv(){};
+
+ // XCommandEnvironment
+ virtual uno::Reference<task::XInteractionHandler > SAL_CALL
+ getInteractionHandler() throw (uno::RuntimeException);
+ virtual uno::Reference<ucb::XProgressHandler >
+ SAL_CALL getProgressHandler() throw (uno::RuntimeException);
+
+ // XInteractionHandler
+ virtual void SAL_CALL handle(
+ uno::Reference<task::XInteractionRequest > const & xRequest )
+ throw (uno::RuntimeException);
+
+ // XProgressHandler
+ virtual void SAL_CALL push( uno::Any const & Status )
+ throw (uno::RuntimeException);
+ virtual void SAL_CALL update( uno::Any const & Status )
+ throw (uno::RuntimeException);
+ virtual void SAL_CALL pop() throw (uno::RuntimeException);
+};
+Reference<task::XInteractionHandler> SilentCommandEnv::getInteractionHandler()
+throw (uno::RuntimeException)
+{
+ return this;
+}
+
+Reference<ucb::XProgressHandler> SilentCommandEnv::getProgressHandler()
+throw (uno::RuntimeException)
+{
+ return this;
+}
+
+// XInteractionHandler
+void SilentCommandEnv::handle(
+ Reference< task::XInteractionRequest> const & xRequest )
+ throw (uno::RuntimeException)
+{
+ uno::Any request( xRequest->getRequest() );
+
+ // We approve everything here
+ uno::Sequence< Reference< task::XInteractionContinuation > > conts(
+ xRequest->getContinuations() );
+ Reference< task::XInteractionContinuation > const * pConts =
+ conts.getConstArray();
+ sal_Int32 len = conts.getLength();
+ for ( sal_Int32 pos = 0; pos < len; ++pos )
+ {
+
+ Reference< task::XInteractionApprove > xInteractionApprove(
+ pConts[ pos ], uno::UNO_QUERY );
+ if (xInteractionApprove.is()) {
+ xInteractionApprove->select();
+ }
+ }
+}
+
+// XProgressHandler
+void SilentCommandEnv::push( uno::Any const & /*Status*/ )
+throw (uno::RuntimeException)
+{
+}
+
+
+void SilentCommandEnv::update( uno::Any const & /*Status */)
+throw (uno::RuntimeException)
+{
+}
+
+void SilentCommandEnv::pop() throw (uno::RuntimeException)
+{
+}
+
+} // end namespace
static const OUString sConfigSrvc( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.configuration.ConfigurationProvider" ) );
static const OUString sAccessSrvc( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.configuration.ConfigurationUpdateAccess" ) );
-
//------------------------------------------------------------------------------
static sal_Int16 impl_showExtensionDialog( uno::Reference< uno::XComponentContext > &xContext )
{
@@ -254,3 +342,146 @@ sal_Bool Desktop::CheckExtensionDependencies()
return bAbort;
}
+//Returns true if the Folder was more recently modified then
+//the lastsynchronized file. That is the repository needs to
+//be synchronized.
+static bool compareExtensionFolderWithLastSynchronizedFile(
+ OUString const & folderURL, OUString const & fileURL)
+{
+ bool bNeedsSync = false;
+ ::osl::DirectoryItem itemExtFolder;
+ ::osl::File::RC err1 =
+ ::osl::DirectoryItem::get(folderURL, itemExtFolder);
+ //If it does not exist, then there is nothing to be done
+ if (err1 == ::osl::File::E_NOENT)
+ {
+ return false;
+ }
+ else if (err1 != ::osl::File::E_None)
+ {
+ OSL_ENSURE(0, "Cannot access extension folder");
+ return true; //sync just in case
+ }
+
+ //If last synchronized does not exist, then OOo is started for the first time
+ ::osl::DirectoryItem itemFile;
+ ::osl::File::RC err2 = ::osl::DirectoryItem::get(fileURL, itemFile);
+ if (err2 == ::osl::File::E_NOENT)
+ {
+ return true;
+
+ }
+ else if (err2 != ::osl::File::E_None)
+ {
+ OSL_ENSURE(0, "Cannot access file lastsynchronized");
+ return true; //sync just in case
+ }
+
+ //compare the modification time of the extension folder and the last
+ //modified file
+ ::osl::FileStatus statFolder(FileStatusMask_ModifyTime);
+ ::osl::FileStatus statFile(FileStatusMask_ModifyTime);
+ if (itemExtFolder.getFileStatus(statFolder) == ::osl::File::E_None)
+ {
+ if (itemFile.getFileStatus(statFile) == ::osl::File::E_None)
+ {
+ TimeValue timeFolder = statFolder.getModifyTime();
+ TimeValue timeFile = statFile.getModifyTime();
+
+ if (timeFile.Seconds < timeFolder.Seconds)
+ bNeedsSync = true;
+ }
+ else
+ {
+ OSL_ASSERT(0);
+ bNeedsSync = true;
+ }
+ }
+ else
+ {
+ OSL_ASSERT(0);
+ bNeedsSync = true;
+ }
+ return bNeedsSync;
+}
+
+static bool needToSyncRepostitory(OUString const & name)
+{
+ OUString folder;
+ OUString file;
+ if (name.equals(OUString(RTL_CONSTASCII_USTRINGPARAM("bundled"))))
+ {
+ folder = OUString(
+ RTL_CONSTASCII_USTRINGPARAM("$BUNDLED_EXTENSIONS"));
+ file = OUString (
+ RTL_CONSTASCII_USTRINGPARAM(
+ "$BUNDLED_EXTENSIONS_USER/lastsynchronized"));
+ }
+ else if (name.equals(OUString(RTL_CONSTASCII_USTRINGPARAM("shared"))))
+ {
+ folder = OUString(
+ RTL_CONSTASCII_USTRINGPARAM(
+ "$UNO_SHARED_PACKAGES_CACHE/uno_packages"));
+ file = OUString (
+ RTL_CONSTASCII_USTRINGPARAM(
+ "$SHARED_EXTENSIONS_USER/lastsynchronized"));
+ }
+ else
+ {
+ OSL_ASSERT(0);
+ return true;
+ }
+ ::rtl::Bootstrap::expandMacros(folder);
+ ::rtl::Bootstrap::expandMacros(file);
+ return compareExtensionFolderWithLastSynchronizedFile(
+ folder, file);
+}
+
+void Desktop::SynchronizeExtensionRepositories()
+{
+ RTL_LOGFILE_CONTEXT(aLog,"desktop (jl97489) ::Desktop::SynchronizeExtensionRepositories");
+ OUString sDisable;
+ ::rtl::Bootstrap::get(
+ OUString(RTL_CONSTASCII_USTRINGPARAM("DISABLE_SYNC_EXTENSIONS")),
+ sDisable,
+ OUString(RTL_CONSTASCII_USTRINGPARAM("")));
+ if (sDisable.getLength() > 0)
+ return;
+ Reference<deployment::XExtensionManager> xExtensionManager;
+ //synchronize shared before bundled otherewise there are
+ //more revoke and registration calls.
+ OUString sShared(RTL_CONSTASCII_USTRINGPARAM("shared"));
+ if (needToSyncRepostitory(sShared))
+ {
+ xExtensionManager =
+ deployment::ExtensionManager::get(
+ comphelper_getProcessComponentContext());
+ if (xExtensionManager.is())
+ {
+ Reference<ucb::XCommandEnvironment> cmdEnv(
+ new SilentCommandEnv());
+ xExtensionManager->synchronize(
+ sShared, Reference<task::XAbortChannel>(), cmdEnv);
+ }
+
+ }
+
+ OUString sBundled(RTL_CONSTASCII_USTRINGPARAM("bundled"));
+ if (needToSyncRepostitory( sBundled))
+ {
+ if (!xExtensionManager.is())
+ {
+ xExtensionManager =
+ deployment::ExtensionManager::get(
+ comphelper_getProcessComponentContext());
+ }
+ if (xExtensionManager.is())
+ {
+ Reference<ucb::XCommandEnvironment> cmdEnv(
+ new SilentCommandEnv());
+ xExtensionManager->synchronize(
+ sBundled, Reference<task::XAbortChannel>(), cmdEnv);
+
+ }
+ }
+}
diff --git a/desktop/source/deployment/dp_services.cxx b/desktop/source/deployment/dp_services.cxx
index c83a62bfd17e..05b9a2a1971a 100644
--- a/desktop/source/deployment/dp_services.cxx
+++ b/desktop/source/deployment/dp_services.cxx
@@ -28,7 +28,7 @@
// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_desktop.hxx"
-#define COMPHELPER_SERVICEDECL_COMPONENT_HELPER_MAX_ARGS 11
+#define COMPHELPER_SERVICEDECL_COMPONENT_HELPER_MAX_ARGS 12
#include "comphelper/servicedecl.hxx"
using namespace com::sun::star;
@@ -69,6 +69,8 @@ namespace factory {
extern sdecl::ServiceDecl const serviceDecl;
bool singleton_entries( uno::Reference<registry::XRegistryKey> const& );
}
+extern sdecl::ServiceDecl const serviceDecl;
+bool singleton_entries( uno::Reference<registry::XRegistryKey> const& );
}
namespace dp_log {
@@ -109,9 +111,11 @@ sal_Bool SAL_CALL component_writeInfo(
dp_manager::factory::serviceDecl,
dp_log::serviceDecl,
dp_migration::serviceDecl,
- dp_info::serviceDecl ) &&
+ dp_info::serviceDecl,
+ dp_manager::serviceDecl) &&
dp_manager::factory::singleton_entries( pRegistryKey ) &&
- dp_info::singleton_entries( pRegistryKey );
+ dp_info::singleton_entries( pRegistryKey ) &&
+ dp_manager::singleton_entries( pRegistryKey);
}
void * SAL_CALL component_getFactory(
@@ -130,7 +134,8 @@ void * SAL_CALL component_getFactory(
dp_manager::factory::serviceDecl,
dp_log::serviceDecl,
dp_migration::serviceDecl,
- dp_info::serviceDecl );
+ dp_info::serviceDecl,
+ dp_manager::serviceDecl);
}
} // extern "C"
diff --git a/desktop/source/deployment/gui/dp_gui_extensioncmdqueue.cxx b/desktop/source/deployment/gui/dp_gui_extensioncmdqueue.cxx
index 58a5ab1c19ea..89a5ae1e22c8 100644
--- a/desktop/source/deployment/gui/dp_gui_extensioncmdqueue.cxx
+++ b/desktop/source/deployment/gui/dp_gui_extensioncmdqueue.cxx
@@ -110,12 +110,15 @@ using ::rtl::OUString;
namespace {
-OUString getVersion( const uno::Reference< deployment::XPackage > &rPackage )
+OUString getVersion( OUString const & sVersion )
{
- OUString sVersion( rPackage->getVersion());
return ( sVersion.getLength() == 0 ) ? OUString( RTL_CONSTASCII_USTRINGPARAM( "0" ) ) : sVersion;
}
+OUString getVersion( const uno::Reference< deployment::XPackage > &rPackage )
+{
+ return getVersion( rPackage->getVersion());
+}
}
@@ -468,7 +471,8 @@ void ProgressCmdEnv::handle( uno::Reference< task::XInteractionRequest > const &
else if (request >>= verExc)
{
sal_uInt32 id;
- switch (dp_misc::comparePackageVersions( verExc.New, verExc.Deployed ))
+ switch (dp_misc::compareVersions(
+ verExc.NewVersion, verExc.Deployed->getVersion() ))
{
case dp_misc::LESS:
id = RID_WARNINGBOX_VERSION_LESS;
@@ -480,8 +484,8 @@ void ProgressCmdEnv::handle( uno::Reference< task::XInteractionRequest > const &
id = RID_WARNINGBOX_VERSION_GREATER;
break;
}
- OSL_ASSERT( verExc.New.is() && verExc.Deployed.is() );
- bool bEqualNames = verExc.New->getDisplayName().equals(
+ OSL_ASSERT( verExc.Deployed.is() );
+ bool bEqualNames = verExc.NewDisplayName.equals(
verExc.Deployed->getDisplayName());
{
vos::OGuard guard(Application::GetSolarMutex());
@@ -506,9 +510,9 @@ void ProgressCmdEnv::handle( uno::Reference< task::XInteractionRequest > const &
{
s = String(ResId(RID_STR_WARNINGBOX_VERSION_GREATER_DIFFERENT_NAMES, *DeploymentGuiResMgr::get()));
}
- s.SearchAndReplaceAllAscii( "$NAME", verExc.New->getDisplayName());
+ s.SearchAndReplaceAllAscii( "$NAME", verExc.NewDisplayName);
s.SearchAndReplaceAllAscii( "$OLDNAME", verExc.Deployed->getDisplayName());
- s.SearchAndReplaceAllAscii( "$NEW", getVersion(verExc.New) );
+ s.SearchAndReplaceAllAscii( "$NEW", getVersion(verExc.NewVersion) );
s.SearchAndReplaceAllAscii( "$DEPLOYED", getVersion(verExc.Deployed) );
box.SetMessText(s);
approve = box.Execute() == RET_OK;
@@ -527,7 +531,7 @@ void ProgressCmdEnv::handle( uno::Reference< task::XInteractionRequest > const &
{
vos::OGuard guard(Application::GetSolarMutex());
- approve = m_pDialogHelper->installExtensionWarn( instExc.New->getDisplayName() );
+ approve = m_pDialogHelper->installExtensionWarn( instExc.displayName );
}
else
approve = false;
diff --git a/desktop/source/deployment/inc/dp_descriptioninfoset.hxx b/desktop/source/deployment/inc/dp_descriptioninfoset.hxx
index 38a1870782ed..3d2d56cad00a 100644
--- a/desktop/source/deployment/inc/dp_descriptioninfoset.hxx
+++ b/desktop/source/deployment/inc/dp_descriptioninfoset.hxx
@@ -62,6 +62,7 @@ struct DESKTOP_DEPLOYMENTMISC_DLLPUBLIC SimpleLicenseAttributes
bool suppressIfRequired;
};
+
/**
Access to the content of an XML <code>description</code> element.
@@ -226,6 +227,8 @@ public:
::com::sun::star::uno::Reference< ::com::sun::star::xml::xpath::XXPathAPI >
getXpath() const;
+ bool hasDescription() const;
+
private:
SAL_DLLPRIVATE ::boost::optional< ::rtl::OUString > getOptionalValue(
::rtl::OUString const & expression) const;
@@ -289,6 +292,18 @@ private:
::com::sun::star::xml::xpath::XXPathAPI > m_xpath;
};
+inline bool DescriptionInfoset::hasDescription() const
+{
+ return m_element.is();
+}
+
+/** creates a DescriptionInfoset object.
+
+ The argument sExtensionFolderURL is a file URL to extension folder containing
+ the description.xml.
+ */
+DESKTOP_DEPLOYMENTMISC_DLLPUBLIC
+DescriptionInfoset getDescriptionInfoset(::rtl::OUString const & sExtensionFolderURL);
}
#endif
diff --git a/desktop/source/deployment/inc/dp_misc.h b/desktop/source/deployment/inc/dp_misc.h
index a717e7797c8a..ee5867a655d3 100644
--- a/desktop/source/deployment/inc/dp_misc.h
+++ b/desktop/source/deployment/inc/dp_misc.h
@@ -74,9 +74,25 @@ DESKTOP_DEPLOYMENTMISC_DLLPUBLIC
::rtl::OUString expandUnoRcUrl( ::rtl::OUString const & url );
//==============================================================================
+
+/** appends a relative path to a url.
+
+ The relative path must already be correctly encoded for use in an URL.
+ If the URL starts with vnd.sun.star.expand then the relative path will
+ be again encoded for use in an "expand" URL.
+ */
DESKTOP_DEPLOYMENTMISC_DLLPUBLIC ::rtl::OUString makeURL(
::rtl::OUString const & baseURL, ::rtl::OUString const & relPath );
+
+/** appends a relative path to a url.
+
+ This is the same as makeURL, but the relative Path must me a segment
+ of an system path.
+ */
+DESKTOP_DEPLOYMENTMISC_DLLPUBLIC ::rtl::OUString makeURLAppendSysPathSegment(
+ ::rtl::OUString const & baseURL, ::rtl::OUString const & relPath );
+
//==============================================================================
DESKTOP_DEPLOYMENTMISC_DLLPUBLIC ::rtl::OUString generateRandomPipeId();
@@ -151,6 +167,11 @@ DESKTOP_DEPLOYMENTMISC_DLLPUBLIC
void TRACE(::rtl::OUString const & sText);
DESKTOP_DEPLOYMENTMISC_DLLPUBLIC
void TRACE(::rtl::OString const & sText);
+
+DESKTOP_DEPLOYMENTMISC_DLLPUBLIC
+bool hasExtensionRepositoryChanged(::rtl::OUString const & repository);
+
+
}
#endif
diff --git a/desktop/source/deployment/inc/dp_version.hxx b/desktop/source/deployment/inc/dp_version.hxx
index 9808ebaab388..c459333f97a9 100644
--- a/desktop/source/deployment/inc/dp_version.hxx
+++ b/desktop/source/deployment/inc/dp_version.hxx
@@ -43,13 +43,6 @@ enum Order { LESS, EQUAL, GREATER };
DESKTOP_DEPLOYMENTMISC_DLLPUBLIC Order compareVersions(
::rtl::OUString const & version1, ::rtl::OUString const & version2);
-
-DESKTOP_DEPLOYMENTMISC_DLLPUBLIC Order comparePackageVersions(
- ::com::sun::star::uno::Reference< ::com::sun::star::deployment::XPackage >
- const & package1,
- ::com::sun::star::uno::Reference< ::com::sun::star::deployment::XPackage >
- const & package2);
-
}
#endif
diff --git a/desktop/source/deployment/manager/dp_activepackages.cxx b/desktop/source/deployment/manager/dp_activepackages.cxx
index 04dc22b77a77..bf9071682b2e 100644
--- a/desktop/source/deployment/manager/dp_activepackages.cxx
+++ b/desktop/source/deployment/manager/dp_activepackages.cxx
@@ -96,9 +96,23 @@ static char const legacyPrefix[] = "org.openoffice.legacy.";
OSL_ASSERT(i2 >= 0);
d.fileName = ::rtl::OUString(
value.getStr() + i1 + 1, i2 - i1 - 1, RTL_TEXTENCODING_UTF8);
- d.mediaType = ::rtl::OUString(
- value.getStr() + i2 + 1, value.getLength() - i2 - 1,
- RTL_TEXTENCODING_UTF8);
+ sal_Int32 i3 = value.indexOf(separator, i2 + 1);
+
+ if (i3 < 0)
+ {
+ //Before ActivePackages::Data::version was added
+ d.mediaType = ::rtl::OUString(
+ value.getStr() + i2 + 1, value.getLength() - i2 - 1,
+ RTL_TEXTENCODING_UTF8);
+ }
+ else
+ {
+ d.mediaType = ::rtl::OUString(
+ value.getStr() + i2 + 1, i3 - i2 -1, RTL_TEXTENCODING_UTF8);
+ d.version = ::rtl::OUString(
+ value.getStr() + i3 + 1, value.getLength() - i3 - 1,
+ RTL_TEXTENCODING_UTF8);
+ }
return d;
}
@@ -172,6 +186,8 @@ void ActivePackages::put(::rtl::OUString const & id, Data const & data) {
b.append(::rtl::OUStringToOString(data.fileName, RTL_TEXTENCODING_UTF8));
b.append(separator);
b.append(::rtl::OUStringToOString(data.mediaType, RTL_TEXTENCODING_UTF8));
+ b.append(separator);
+ b.append(::rtl::OUStringToOString(data.version, RTL_TEXTENCODING_UTF8));
m_map.put(newKey(id), b.makeStringAndClear());
}
diff --git a/desktop/source/deployment/manager/dp_activepackages.hxx b/desktop/source/deployment/manager/dp_activepackages.hxx
index 1c58f76be245..36060d26bd02 100644
--- a/desktop/source/deployment/manager/dp_activepackages.hxx
+++ b/desktop/source/deployment/manager/dp_activepackages.hxx
@@ -42,9 +42,19 @@ namespace dp_manager {
class ActivePackages {
public:
struct Data {
+ /* name of the temporary file (shared, user extension) or the name of
+ the folder of the bundled extension.
+ It does not contain the trailing '_' of the folder.
+ UTF-8 encoded
+ */
::rtl::OUString temporaryName;
+ /* The file name (shared, user) or the folder name (bundled)
+ If the key is the file name, then file name is not encoded.
+ If the key is the idendifier then the file name is UTF-8 encoded.
+ */
::rtl::OUString fileName;
::rtl::OUString mediaType;
+ ::rtl::OUString version;
};
typedef ::std::vector< ::std::pair< ::rtl::OUString, Data > > Entries;
diff --git a/desktop/source/deployment/manager/dp_extensionmanager.cxx b/desktop/source/deployment/manager/dp_extensionmanager.cxx
new file mode 100644
index 000000000000..469245bef340
--- /dev/null
+++ b/desktop/source/deployment/manager/dp_extensionmanager.cxx
@@ -0,0 +1,1301 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_desktop.hxx"
+
+#include <cppuhelper/implbase1.hxx>
+
+#include "comphelper/servicedecl.hxx"
+#include "cppuhelper/exc_hlp.hxx"
+#include "rtl/bootstrap.hxx"
+#include "com/sun/star/deployment/ExtensionManager.hpp"
+#include "com/sun/star/deployment/XExtensionManager.hpp"
+#include "com/sun/star/deployment/thePackageManagerFactory.hpp"
+#include "com/sun/star/deployment/XPackageManager.hpp"
+#include "com/sun/star/deployment/XPackageManagerFactory.hpp"
+#include "com/sun/star/deployment/XPackage.hpp"
+#include "com/sun/star/deployment/InstallException.hpp"
+#include "com/sun/star/deployment/VersionException.hpp"
+#include "com/sun/star/deployment/LicenseException.hpp"
+#include "com/sun/star/lang/XServiceInfo.hpp"
+#include "com/sun/star/registry/XRegistryKey.hpp"
+#include "com/sun/star/beans/Optional.hpp"
+#include "com/sun/star/task/XInteractionApprove.hpp"
+#include "com/sun/star/beans/Ambiguous.hpp"
+#include "com/sun/star/uno/XComponentContext.hpp"
+#include "com/sun/star/io/XInputStream.hpp"
+#include "comphelper/sequence.hxx"
+#include "xmlscript/xml_helper.hxx"
+#include "osl/diagnose.h"
+#include "dp_interact.h"
+#include "dp_resource.h"
+#include "dp_ucb.h"
+#include "dp_identifier.hxx"
+
+#include "dp_extensionmanager.hxx"
+#include "dp_tmprepocmdenv.hxx"
+#include <list>
+#include <hash_map>
+#include <algorithm>
+
+namespace deploy = com::sun::star::deployment;
+namespace lang = com::sun::star::lang;
+namespace registry = com::sun::star::registry;
+namespace task = com::sun::star::task;
+namespace ucb = com::sun::star::ucb;
+namespace uno = com::sun::star::uno;
+namespace beans = com::sun::star::beans;
+namespace css = com::sun::star;
+
+//#define OUSTR(s) rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(s))
+
+using ::com::sun::star::uno::Reference;
+using ::rtl::OUString;
+
+namespace {
+
+struct CompIdentifiers
+{
+ bool operator() (::std::vector<Reference<deploy::XPackage> > const & a,
+ ::std::vector<Reference<deploy::XPackage> > const & b)
+ {
+
+ if (getName(a).compareTo(getName(b)) < 0)
+ return true;
+ return false;
+ }
+
+ OUString getName(::std::vector<Reference<deploy::XPackage> > const & a);
+};
+
+OUString CompIdentifiers::getName(::std::vector<Reference<deploy::XPackage> > const & a)
+{
+ OSL_ASSERT(a.size() == 3);
+ //get the first non-null reference
+ Reference<deploy::XPackage> extension;
+ ::std::vector<Reference<deploy::XPackage> >::const_iterator it = a.begin();
+ for (; it != a.end(); it++)
+ {
+ if (it->is())
+ {
+ extension = *it;
+ break;
+ }
+ }
+ OSL_ASSERT(extension.is());
+ return extension->getDisplayName();
+}
+} //end namespace
+
+namespace dp_manager {
+
+
+
+//------------------------------------------------------------------------------
+
+//ToDo: bundled extension
+ExtensionManager::ExtensionManager( Reference< uno::XComponentContext > const& xContext) :
+ m_xContext( xContext )
+{
+ Reference<deploy::XPackageManagerFactory> xPackageManagerFactory(
+ deploy::thePackageManagerFactory::get(m_xContext));
+ m_userRepository = xPackageManagerFactory->getPackageManager(OUSTR("user"));
+ m_sharedRepository = xPackageManagerFactory->getPackageManager(OUSTR("shared"));
+ m_bundledRepository = xPackageManagerFactory->getPackageManager(OUSTR("bundled"));
+ m_tmpRepository = xPackageManagerFactory->getPackageManager(OUSTR("tmp"));
+
+ m_repositoryNames.push_back(OUSTR("user"));
+ m_repositoryNames.push_back(OUSTR("shared"));
+ m_repositoryNames.push_back(OUSTR("bundled"));
+}
+
+//------------------------------------------------------------------------------
+
+ExtensionManager::~ExtensionManager()
+{
+}
+
+Reference<task::XAbortChannel> ExtensionManager::createAbortChannel()
+ throw (uno::RuntimeException)
+{
+ return new dp_misc::AbortChannel;
+}
+
+/*
+ Enters the XPackage objects into a map. They must be all from the
+ same repository. The value type of the map is a vector, where each vector
+ represents an extension with a particular identifier. The first member
+ is represents the user extension, the second the shared extension and the
+ third the bundled extension.
+ */
+void ExtensionManager::addExtensionsToMap(
+ id2extensions & mapExt,
+ uno::Sequence<Reference<deploy::XPackage> > const & seqExt,
+ OUString const & repository)
+{
+ //Determine the index in the vector where these extensions are to be
+ //added.
+ ::std::list<OUString>::const_iterator citNames =
+ m_repositoryNames.begin();
+ int index = 0;
+ for (;citNames != m_repositoryNames.end(); citNames++, index++)
+ {
+ if (citNames->equals(repository))
+ break;
+ }
+
+ for (int i = 0; i < seqExt.getLength(); i++)
+ {
+ Reference<deploy::XPackage> const & xExtension = seqExt[i];
+ OUString id = dp_misc::getIdentifier(xExtension);
+ id2extensions::iterator ivec = mapExt.find(id);
+ if (ivec == mapExt.end())
+ {
+ ::std::vector<Reference<deploy::XPackage> > vec(3);
+ vec[index] = xExtension;
+ mapExt[id] = vec;
+ }
+ else
+ {
+ ivec->second[index] = xExtension;
+ }
+ }
+}
+
+/*
+ returns a list containing extensions with the same identifier from
+ all repositories (user, shared, bundled) If one repository does not
+ have this extension, then the list contains an empty Referenc. The list
+ is ordered according to the priority of the repostories:
+ 1. user
+ 2. shared
+ 3. bundled
+
+ The number of elements is always three, unless the number of repository
+ changes.
+ */
+::std::list<Reference<deploy::XPackage> >
+ ExtensionManager::getExtensionsWithSameId(
+ OUString const & identifier, OUString const & fileName)
+
+{
+ ::std::list<Reference<deploy::XPackage> > extensionList;
+ try
+ { //will throw an exception if the extension does not exist
+ extensionList.push_back(m_userRepository->getDeployedPackage(
+ identifier, fileName, Reference<ucb::XCommandEnvironment>()));
+ } catch(lang::IllegalArgumentException &)
+ {
+ extensionList.push_back(Reference<deploy::XPackage>());
+ }
+ try
+ {
+ extensionList.push_back(m_sharedRepository->getDeployedPackage(
+ identifier, fileName, Reference<ucb::XCommandEnvironment>()));
+ } catch (lang::IllegalArgumentException &)
+ {
+ extensionList.push_back(Reference<deploy::XPackage>());
+ }
+ try
+ {
+ extensionList.push_back(m_bundledRepository->getDeployedPackage(
+ identifier, fileName, Reference<ucb::XCommandEnvironment>()));
+ } catch (lang::IllegalArgumentException &)
+ {
+ extensionList.push_back(Reference<deploy::XPackage>());
+ }
+ OSL_ASSERT(extensionList.size() == 3);
+ return extensionList;
+}
+
+
+/*
+
+*/
+Reference<deploy::XPackage> ExtensionManager::getExtensionAndStatus(
+ ::rtl::OUString const & identifier,
+ ::rtl::OUString const & fileName,
+ ::rtl::OUString const & repository,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv,
+ bool & out_bWasRegistered)
+{
+ Reference<deploy::XPackage> theExtension;
+ ::std::list<Reference<deploy::XPackage> > listExtensions =
+ getExtensionsWithSameId(identifier, fileName);
+ OSL_ASSERT(listExtensions.size() == m_repositoryNames.size());
+ Reference<deploy::XPackage> xActiveExtension;
+ ::std::list<OUString>::const_iterator
+ inames = m_repositoryNames.begin();
+ ::std::list<Reference<deploy::XPackage> >::const_iterator
+ iext = listExtensions.begin();
+ for (; inames != m_repositoryNames.end(); inames++, iext++)
+ {
+ if (repository.equals(*inames))
+ {
+ theExtension = *iext;
+ if (iext->is())
+ {
+ beans::Optional<beans::Ambiguous<sal_Bool> > optRegistered =
+ (*iext)->isRegistered(xAbortChannel, xCmdEnv);
+ OSL_ENSURE(! optRegistered.Value.IsAmbiguous,
+ "Extension is not properly registered");
+ //IsAmbiguous = true: only partly registered, but we assume
+ //that this is the active extension, and something went wrong when registering it
+ //previously.
+ if (optRegistered.IsPresent
+ && (optRegistered.Value.Value || optRegistered.Value.IsAmbiguous))
+ out_bWasRegistered = true;
+ }
+ break;
+ }
+ }
+ return theExtension;
+}
+
+/*
+ Determines if the user extension was disabled by the user. Currently a user
+ cannot disable extensions from other repositories. If an extension does not
+ contain any items which need to be registered then the extension cannot
+ actually be disabled (because it cannot be registered). In this case false is
+ returned. If there is no user extension then also false is returned.
+
+ A user extension is regarded as disabled if there is an extension in a
+ repository with a lower priority that is registered.
+ */
+bool ExtensionManager::isUserExtensionDisabled(
+ OUString const & identifier, OUString const & fileName,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+
+{
+ bool bDisabled = false;
+ ::std::list<Reference<deploy::XPackage> > listExtensions =
+ getExtensionsWithSameId(identifier, fileName);
+ ::std::list<Reference<deploy::XPackage> >::const_iterator
+ iext = listExtensions.begin();
+ bool bCheckOptional = false;
+ Reference<deploy::XPackage> xActive;
+ for (; iext != listExtensions.end(); iext++)
+ {
+ if (iext->is())
+ {
+ if (!(*iext)->isRegistered(xAbortChannel, xCmdEnv).IsPresent)
+ {
+ // IsPresent must be the same for all extnesions
+ OSL_ASSERT(!bCheckOptional);
+ break;
+ }
+ else
+ {
+ bCheckOptional = true;
+ if ((*iext)->isRegistered(xAbortChannel, xCmdEnv).Value.Value)
+ {
+ xActive = *iext;
+ break;
+ }
+ }
+ }
+ Reference<deploy::XPackage> const & xUser = listExtensions.front();
+ if (xUser.is()
+ && xActive.is()
+ && xUser != xActive)
+ bDisabled = true;
+ }
+ return bDisabled;
+}
+/*
+ This method determines the active extension (XPackage.registerPackage) with a
+ particular identifier.
+
+ The parameter bUserDisabled determines if the user extension is disabled.
+
+ When the user repository contains an extension with the given identifier and
+ it is not disabled by the user, then it is always registered. Otherwise an
+ extension is only registered when there is no registered extension in one of
+ the repositories with a higher priority. That is, if the extension is from
+ the shared repository and an active extension with the same identifer is in
+ the user repository, then the extension is not registered. Similarly a
+ bundled extension is not registered if there is an active extension with the
+ same identifier in the shared or user repository.
+*/
+void ExtensionManager::activateExtension(
+ OUString const & identifier, OUString const & fileName,
+ bool bUserDisabled,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+{
+ ::std::list<Reference<deploy::XPackage> > listExtensions =
+ getExtensionsWithSameId(identifier, fileName);
+ OSL_ASSERT(listExtensions.size() == 3);
+ ::std::list<Reference<deploy::XPackage> >::const_iterator
+ iext = listExtensions.begin();
+ //skip disabled user extension
+ if (listExtensions.front().is() && bUserDisabled)
+ iext++;
+ bool bActive = false;
+ for (; iext != listExtensions.end(); iext++)
+ {
+ if (iext->is())
+ {
+ //get the registration value of the current iteration
+ beans::Optional<beans::Ambiguous<sal_Bool> > optReg =
+ (*iext)->isRegistered(xAbortChannel, xCmdEnv);
+ //If nothing can be registered then break
+ if (!optReg.IsPresent)
+ break;
+
+ //If we have already determined an active extension then we must
+ //make sure to unregister all extensions with the same id in
+ //repositories with a lower priority
+ if (bActive)
+ {
+ (*iext)->revokePackage(xAbortChannel, xCmdEnv);
+ }
+ else
+ {
+ //This is the first extension in the ordered list, which becomes
+ //the active extension
+ bActive = true;
+ //Register if not already done.
+ //reregister if the value is ambiguous, which indicates that
+ //something went wrong during last registration.
+ (*iext)->registerPackage(xAbortChannel, xCmdEnv);
+ }
+ }
+ }
+}
+
+Reference<deploy::XPackage> ExtensionManager::backupExtension(
+ OUString const & identifier, OUString const & fileName,
+ Reference<deploy::XPackageManager> const & xPackageManager,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+{
+ Reference<deploy::XPackage> xBackup;
+ Reference<ucb::XCommandEnvironment> tmpCmdEnv(
+ new TmpRepositoryCommandEnv(xCmdEnv->getInteractionHandler()));
+ Reference<deploy::XPackage> xOldExtension;
+ xOldExtension = xPackageManager->getDeployedPackage(
+ identifier, fileName, tmpCmdEnv);
+
+ if (xOldExtension.is())
+ {
+ xBackup = m_tmpRepository->addPackage(
+ xOldExtension->getURL(), OUString(),
+ Reference<task::XAbortChannel>(), tmpCmdEnv);
+
+ OSL_ENSURE(xBackup.is(), "Failed to backup extension");
+ }
+ return xBackup;
+}
+
+uno::Sequence< Reference<deploy::XPackageTypeInfo> >
+ExtensionManager::getSupportedPackageTypes(OUString const & repository)
+ throw (uno::RuntimeException)
+{
+ if (repository.equals(OUSTR("user")))
+ return m_userRepository->getSupportedPackageTypes();
+ else if (repository.equals(OUSTR("shared")))
+ return m_sharedRepository->getSupportedPackageTypes();
+ else
+ return uno::Sequence< Reference<deploy::XPackageTypeInfo> >();
+}
+
+// Only add to shared and user repository
+Reference<deploy::XPackage> ExtensionManager::addExtension(
+ OUString const & url, OUString const & repository,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (deploy::DeploymentException,
+ ucb::CommandFailedException,
+ ucb::CommandAbortedException,
+ lang::IllegalArgumentException,
+ uno::RuntimeException)
+{
+ Reference<deploy::XPackage> xNewExtension;
+ //Determine the repository to use
+ Reference<deploy::XPackageManager> xPackageManager;
+ if (repository.equals(OUSTR("user")))
+ xPackageManager = m_userRepository;
+ else if (repository.equals(OUSTR("shared")))
+ xPackageManager = m_sharedRepository;
+ else
+ throw lang::IllegalArgumentException(
+ OUSTR("No valid repository name provided."),
+ static_cast<cppu::OWeakObject*>(this), 0);
+
+ ::osl::MutexGuard guard(m_mutex);
+ Reference<deploy::XPackage> xTmpExtension =
+ getTempExtension(url, xAbortChannel, xCmdEnv);
+ const OUString sIdentifier = dp_misc::getIdentifier(xTmpExtension);
+ const OUString sFileName = xTmpExtension->getName();
+ const OUString sDisplayName = xTmpExtension->getDisplayName();
+ const OUString sVersion = xTmpExtension->getVersion();
+
+ Reference<deploy::XPackage> xOldExtension;
+ bool bUserDisabled = false;
+ Reference<deploy::XPackage> xExtensionBackup;
+
+ uno::Any excOccurred1;
+ uno::Any excOccurred2;
+
+ try
+ {
+ //If we add a user extension and there is already one which was
+ //disabled by a user, then the newly installed one is enabled. If we
+ //add to another repository then the user extension remains
+ //disabled.
+ if (! repository.equals(OUSTR("user")))
+ bUserDisabled = isUserExtensionDisabled(
+ sIdentifier, sFileName, xAbortChannel, xCmdEnv);
+
+ bool bWasRegistered = false;
+ xOldExtension = getExtensionAndStatus(
+ sIdentifier, sFileName, repository, xAbortChannel,
+ xCmdEnv, bWasRegistered);
+ bool bCanInstall = false;
+ try
+ {
+ if (xOldExtension.is())
+ {
+ //throws a CommandFailedException if the user cancels
+ //the action.
+ checkUpdate(sVersion, sDisplayName,xOldExtension, xCmdEnv);
+ }
+ else
+ {
+ //throws a CommandFailedException if the user cancels
+ //the action.
+ checkInstall(sDisplayName, xCmdEnv);
+ }
+
+ bCanInstall = xTmpExtension->checkPrerequisites(
+ xAbortChannel, xCmdEnv, xOldExtension.is(), repository);
+ }
+ catch (deploy::DeploymentException& ) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (ucb::CommandFailedException & ) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (ucb::CommandAbortedException & ) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (lang::IllegalArgumentException &) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (uno::RuntimeException &) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (...) {
+ excOccurred1 = ::cppu::getCaughtException();
+ deploy::DeploymentException exc(
+ OUSTR("Extension Manager: exception during addExtension, url: ")
+ + url, static_cast<OWeakObject*>(this), excOccurred1);
+ excOccurred1 <<= exc;
+ }
+
+ if (bCanInstall)
+ {
+ if (xOldExtension.is())
+ {
+ if (bWasRegistered)
+ xOldExtension->revokePackage(xAbortChannel, xCmdEnv);
+ //save the old user extension in case the user aborts
+ //store the extension in the tmp repository, this will overwrite
+ //xTmpPackage (same identifier). Do not let the user abort or
+ //interact
+ Reference<ucb::XCommandEnvironment> tmpCmdEnv(
+ new TmpRepositoryCommandEnv(xCmdEnv->getInteractionHandler()));
+ //importing the old extension in the tmp repository will remove
+ //the xTmpExtension
+ xTmpExtension = 0;
+ xExtensionBackup = m_tmpRepository->importExtension(
+ xOldExtension, Reference<task::XAbortChannel>(),
+ tmpCmdEnv);
+ }
+
+ xNewExtension = xPackageManager->addPackage(
+ url, OUString(), xAbortChannel, xCmdEnv);
+ activateExtension(
+ dp_misc::getIdentifier(xNewExtension),
+ xNewExtension->getName(), bUserDisabled,
+ xAbortChannel, xCmdEnv);
+ }
+ }
+ catch (deploy::DeploymentException& ) {
+ excOccurred2 = ::cppu::getCaughtException();
+ } catch (ucb::CommandFailedException & ) {
+ excOccurred2 = ::cppu::getCaughtException();
+ } catch (ucb::CommandAbortedException & ) {
+ excOccurred2 = ::cppu::getCaughtException();
+ } catch (lang::IllegalArgumentException &) {
+ excOccurred2 = ::cppu::getCaughtException();
+ } catch (uno::RuntimeException &) {
+ excOccurred2 = ::cppu::getCaughtException();
+ } catch (...) {
+ excOccurred2 = ::cppu::getCaughtException();
+ deploy::DeploymentException exc(
+ OUSTR("Extension Manager: exception during addExtension, url: ")
+ + url, static_cast<OWeakObject*>(this), excOccurred2);
+ excOccurred2 <<= exc;
+ }
+
+ if (excOccurred2.hasValue())
+ {
+ //It does not matter what exception is thrown. We try to
+ //recover the original status.
+ //If the user aborted installation then a ucb::CommandAbortedException
+ //is thrown.
+ //Use a private AbortChannel so the user cannot interrupt.
+ try
+ {
+ Reference<ucb::XCommandEnvironment> tmpCmdEnv(
+ new TmpRepositoryCommandEnv(xCmdEnv->getInteractionHandler()));
+ if (xExtensionBackup.is())
+ {
+ Reference<deploy::XPackage> xRestored =
+ xPackageManager->importExtension(
+ xExtensionBackup, Reference<task::XAbortChannel>(),
+ tmpCmdEnv);
+ }
+ activateExtension(
+ sIdentifier, sFileName, bUserDisabled,
+ Reference<task::XAbortChannel>(), tmpCmdEnv);
+ if (xTmpExtension.is() || xExtensionBackup.is())
+ m_tmpRepository->removePackage(
+ sIdentifier, OUString(), xAbortChannel, xCmdEnv);
+ }
+ catch (...)
+ {
+ }
+ ::cppu::throwException(excOccurred2);
+ }
+ if (xTmpExtension.is() || xExtensionBackup.is())
+ m_tmpRepository->removePackage(
+ sIdentifier,OUString(), xAbortChannel, xCmdEnv);
+
+ if (excOccurred1.hasValue())
+ ::cppu::throwException(excOccurred1);
+
+ return xNewExtension;
+}
+
+void ExtensionManager::removeExtension(
+ OUString const & identifier, OUString const & fileName,
+ OUString const & repository,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (deploy::DeploymentException,
+ ucb::CommandFailedException,
+ ucb::CommandAbortedException,
+ lang::IllegalArgumentException,
+ uno::RuntimeException)
+{
+ uno::Any excOccurred1;
+ Reference<deploy::XPackage> xExtensionBackup;
+ Reference<deploy::XPackageManager> xPackageManager;
+ bool bUserDisabled = false;
+ try
+ {
+//Determine the repository to use
+ if (repository.equals(OUSTR("user")))
+ xPackageManager = m_userRepository;
+ else if (repository.equals(OUSTR("shared")))
+ xPackageManager = m_sharedRepository;
+ else
+ throw lang::IllegalArgumentException(
+ OUSTR("No valid repository name provided."),
+ static_cast<cppu::OWeakObject*>(this), 0);
+
+ ::osl::MutexGuard guard(m_mutex);
+ //Backup the extension, in case the user cancels the action
+
+ bUserDisabled = isUserExtensionDisabled(
+ identifier, fileName, xAbortChannel, xCmdEnv);
+ //Backup the extension, in case the user cancels the action
+ xExtensionBackup = backupExtension(
+ identifier, fileName, xPackageManager, xCmdEnv);
+
+ //revoke the extension if it is active
+ Reference<deploy::XPackage> xOldExtension =
+ xPackageManager->getDeployedPackage(
+ identifier, fileName, xCmdEnv);
+ xOldExtension->revokePackage(xAbortChannel, xCmdEnv);
+
+ xPackageManager->removePackage(
+ identifier, fileName, xAbortChannel, xCmdEnv);
+ activateExtension(identifier, fileName, bUserDisabled,
+ xAbortChannel, xCmdEnv);
+ }
+ catch (deploy::DeploymentException& ) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (ucb::CommandFailedException & ) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (ucb::CommandAbortedException & ) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (lang::IllegalArgumentException &) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (uno::RuntimeException &) {
+ excOccurred1 = ::cppu::getCaughtException();
+ } catch (...) {
+ excOccurred1 = ::cppu::getCaughtException();
+ deploy::DeploymentException exc(
+ OUSTR("Extension Manager: exception during removeEtension"),
+ static_cast<OWeakObject*>(this), excOccurred1);
+ excOccurred1 <<= exc;
+ }
+
+ if (excOccurred1.hasValue())
+ {
+ //User aborted installation, restore the previous situation.
+ //Use a private AbortChannel so the user cannot interrupt.
+ try
+ {
+ Reference<ucb::XCommandEnvironment> tmpCmdEnv(
+ new TmpRepositoryCommandEnv(xCmdEnv->getInteractionHandler()));
+ if (xExtensionBackup.is())
+ {
+ Reference<deploy::XPackage> xRestored =
+ xPackageManager->importExtension(
+ xExtensionBackup, Reference<task::XAbortChannel>(),
+ tmpCmdEnv);
+ activateExtension(
+ identifier, fileName, bUserDisabled, Reference<task::XAbortChannel>(),
+ tmpCmdEnv);
+
+ m_tmpRepository->removePackage(
+ dp_misc::getIdentifier(xExtensionBackup),
+ xExtensionBackup->getName(), xAbortChannel, xCmdEnv);
+ }
+ }
+ catch (...)
+ {
+ }
+ ::cppu::throwException(excOccurred1);
+ }
+
+ if (xExtensionBackup.is())
+ m_tmpRepository->removePackage(
+ dp_misc::getIdentifier(xExtensionBackup),
+ xExtensionBackup->getName(), xAbortChannel, xCmdEnv);
+}
+
+// Only enable extensions from shared and user repository
+void ExtensionManager::enableExtension(
+ Reference<deploy::XPackage> const & extension,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv)
+ throw (deploy::DeploymentException,
+ ucb::CommandFailedException,
+ ucb::CommandAbortedException,
+ lang::IllegalArgumentException,
+ uno::RuntimeException)
+{
+ try
+ {
+ if (!extension.is())
+ return;
+
+ OUString repository = extension->getRepositoryName();
+ if (!repository.equals(OUSTR("user")))
+ throw lang::IllegalArgumentException(
+ OUSTR("No valid repository name provided."),
+ static_cast<cppu::OWeakObject*>(this), 0);
+ ::osl::MutexGuard guard(m_mutex);
+
+ //if it is already registered or if it cannot be registered
+ //because it does not contain any files which need to be processed
+ //then there is nothing to do here
+ beans::Optional<beans::Ambiguous<sal_Bool> > reg =
+ extension->isRegistered(xAbortChannel, xCmdEnv);
+ if (!reg.IsPresent
+ || (!reg.Value.IsAmbiguous && reg.Value.Value))
+ return;
+ }
+ catch (deploy::DeploymentException& ) {
+ throw;
+ } catch (ucb::CommandFailedException & ) {
+ throw;
+ } catch (ucb::CommandAbortedException & ) {
+ throw;
+ } catch (lang::IllegalArgumentException &) {
+ throw;
+ } catch (uno::RuntimeException &) {
+ throw;
+ } catch (...) {
+ uno::Any exc = ::cppu::getCaughtException();
+ throw deploy::DeploymentException(
+ OUSTR("Extension Manager: exception during enableExtension"),
+ static_cast<OWeakObject*>(this), exc);
+ }
+
+ uno::Any excOccurred;
+ try
+ {
+ activateExtension(dp_misc::getIdentifier(extension),
+ extension->getName(),
+ false, xAbortChannel, xCmdEnv);
+ }
+ catch (deploy::DeploymentException& ) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (ucb::CommandFailedException & ) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (ucb::CommandAbortedException & ) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (lang::IllegalArgumentException &) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (uno::RuntimeException &) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (...) {
+ excOccurred = ::cppu::getCaughtException();
+ deploy::DeploymentException exc(
+ OUSTR("Extension Manager: exception during enableExtension"),
+ static_cast<OWeakObject*>(this), excOccurred);
+ excOccurred <<= exc;
+ }
+
+ if (excOccurred.hasValue())
+ {
+ try
+ {
+ extension->revokePackage(Reference<task::XAbortChannel>(), xCmdEnv);
+ activateExtension(dp_misc::getIdentifier(extension),
+ extension->getName(),
+ true, xAbortChannel, xCmdEnv);
+ }
+ catch (...)
+ {
+ }
+ ::cppu::throwException(excOccurred);
+ }
+}
+
+void ExtensionManager::disableExtension(
+ Reference<deploy::XPackage> const & extension,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (deploy::DeploymentException,
+ ucb::CommandFailedException,
+ ucb::CommandAbortedException,
+ lang::IllegalArgumentException,
+ uno::RuntimeException)
+{
+ uno::Any excOccurred;
+ try
+ {
+ if (!extension.is())
+ return;
+
+ ::osl::MutexGuard guard(m_mutex);
+ OUString repository = extension->getRepositoryName();
+ if (!repository.equals(OUSTR("user")))
+ throw lang::IllegalArgumentException(
+ OUSTR("No valid repository name provided."),
+ static_cast<cppu::OWeakObject*>(this), 0);
+
+ //if it is already registered or if it cannot be registered
+ //because it does not contain any files which need to be processed
+ //then there is nothing to do here
+ beans::Optional<beans::Ambiguous<sal_Bool> > reg =
+ extension->isRegistered(xAbortChannel, xCmdEnv);
+ if (!reg.IsPresent
+ || (!reg.Value.IsAmbiguous && !reg.Value.Value))
+ return;
+
+ extension->revokePackage(xAbortChannel, xCmdEnv);
+ activateExtension(dp_misc::getIdentifier(extension),
+ extension->getName(),
+ true, xAbortChannel, xCmdEnv);
+ }
+ catch (deploy::DeploymentException& ) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (ucb::CommandFailedException & ) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (ucb::CommandAbortedException & ) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (lang::IllegalArgumentException &) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (uno::RuntimeException &) {
+ excOccurred = ::cppu::getCaughtException();
+ } catch (...) {
+ excOccurred = ::cppu::getCaughtException();
+ deploy::DeploymentException exc(
+ OUSTR("Extension Manager: exception during disableExtension"),
+ static_cast<OWeakObject*>(this), excOccurred);
+ excOccurred <<= exc;
+ }
+
+ if (excOccurred.hasValue())
+ {
+ try
+ {
+ activateExtension(dp_misc::getIdentifier(extension),
+ extension->getName(),
+ false, xAbortChannel, xCmdEnv);
+ }
+ catch (...)
+ {
+ }
+ ::cppu::throwException(excOccurred);
+ }
+}
+
+uno::Sequence< Reference<deploy::XPackage> >
+ ExtensionManager::getDeployedExtensions(
+ OUString const & repository,
+ Reference<task::XAbortChannel> const &xAbort,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (deploy::DeploymentException,
+ ucb::CommandFailedException,
+ ucb::CommandAbortedException,
+ lang::IllegalArgumentException,
+ uno::RuntimeException)
+{
+ if (repository.equals(OUSTR("user")))
+ {
+ return m_userRepository->getDeployedPackages(
+ xAbort, xCmdEnv);
+ }
+ else if (repository.equals(OUSTR("shared")))
+ {
+ return m_sharedRepository->getDeployedPackages(
+ xAbort, xCmdEnv);
+ }
+ else if (repository.equals(OUSTR("bundled")))
+ {
+ return m_bundledRepository->getDeployedPackages(
+ xAbort, xCmdEnv);
+ }
+ else
+ throw lang::IllegalArgumentException(
+ OUSTR("No valid repository name provided."),
+ static_cast<cppu::OWeakObject*>(this), 0);
+
+}
+
+Reference<deploy::XPackage>
+ ExtensionManager::getDeployedExtension(
+ OUString const & repository,
+ OUString const & identifier,
+ OUString const & filename,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (deploy::DeploymentException,
+ ucb::CommandFailedException,
+ lang::IllegalArgumentException,
+ uno::RuntimeException)
+{
+ if (repository.equals(OUSTR("user")))
+ {
+ return m_userRepository->getDeployedPackage(
+ identifier, filename, xCmdEnv);
+ }
+ else if (repository.equals(OUSTR("shared")))
+ {
+ return m_sharedRepository->getDeployedPackage(
+ identifier, filename, xCmdEnv);
+ }
+ else if (repository.equals(OUSTR("bundled")))
+ {
+ return m_bundledRepository->getDeployedPackage(
+ identifier, filename, xCmdEnv);
+ }
+ else
+ throw lang::IllegalArgumentException(
+ OUSTR("No valid repository name provided."),
+ static_cast<cppu::OWeakObject*>(this), 0);
+}
+
+uno::Sequence< uno::Sequence<Reference<deploy::XPackage> > >
+ ExtensionManager::getAllExtensions(
+ Reference<task::XAbortChannel> const & xAbort,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (deploy::DeploymentException,
+ ucb::CommandFailedException,
+ ucb::CommandAbortedException,
+ lang::IllegalArgumentException,
+ uno::RuntimeException)
+{
+ uno::Sequence< uno::Sequence<Reference<deploy::XPackage> > > seqSeq;
+ try
+ {
+ id2extensions mapExt;
+
+ uno::Sequence<Reference<deploy::XPackage> > userExt =
+ m_userRepository->getDeployedPackages(xAbort, xCmdEnv);
+ addExtensionsToMap(mapExt, userExt, OUSTR("user"));
+ uno::Sequence<Reference<deploy::XPackage> > sharedExt =
+ m_sharedRepository->getDeployedPackages(xAbort, xCmdEnv);
+ addExtensionsToMap(mapExt, sharedExt, OUSTR("shared"));
+ uno::Sequence<Reference<deploy::XPackage> > bundledExt =
+ m_bundledRepository->getDeployedPackages(xAbort, xCmdEnv);
+ addExtensionsToMap(mapExt, bundledExt, OUSTR("bundled"));
+
+ //copy the values of the map to a vector for sorting
+ ::std::vector< ::std::vector<Reference<deploy::XPackage> > >
+ vecExtensions;
+ id2extensions::const_iterator mapIt = mapExt.begin();
+ for (;mapIt != mapExt.end(); mapIt++)
+ vecExtensions.push_back(mapIt->second);
+
+ //sort the element according to the identifier
+ ::std::sort(vecExtensions.begin(), vecExtensions.end(), CompIdentifiers());
+
+ ::std::vector< ::std::vector<Reference<deploy::XPackage> > >::const_iterator
+ citVecVec = vecExtensions.begin();
+ sal_Int32 j = 0;
+ for (;citVecVec != vecExtensions.end(); citVecVec++, j++)
+ {
+ seqSeq[j] = comphelper::containerToSequence(*citVecVec);
+ }
+ } catch (deploy::DeploymentException& ) {
+ throw;
+ } catch (ucb::CommandFailedException & ) {
+ throw;
+ } catch (ucb::CommandAbortedException & ) {
+ throw;
+ } catch (lang::IllegalArgumentException &) {
+ throw;
+ } catch (uno::RuntimeException &) {
+ throw;
+ } catch (...) {
+ uno::Any exc = ::cppu::getCaughtException();
+ throw deploy::DeploymentException(
+ OUSTR("Extension Manager: exception during enableExtension"),
+ static_cast<OWeakObject*>(this), exc);
+ }
+
+ return seqSeq;
+}
+
+void ExtensionManager::reinstallDeployedExtensions(
+ OUString const & repository,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (deploy::DeploymentException,
+ ucb::CommandFailedException, ucb::CommandAbortedException,
+ lang::IllegalArgumentException, uno::RuntimeException)
+{
+ try
+ {
+ Reference<deploy::XPackageManager> xPackageManager;
+ if (repository.equals(OUSTR("user")))
+ xPackageManager = m_userRepository;
+ else if (repository.equals(OUSTR("shared")))
+ xPackageManager = m_sharedRepository;
+ else if (repository.equals(OUSTR("bundled")))
+ xPackageManager = m_bundledRepository;
+ else
+ throw lang::IllegalArgumentException(
+ OUSTR("No valid repository name provided."),
+ static_cast<cppu::OWeakObject*>(this), 0);
+
+ ::osl::MutexGuard guard(m_mutex);
+ xPackageManager->reinstallDeployedPackages(xAbortChannel, xCmdEnv);
+ const uno::Sequence< Reference<deploy::XPackage> > extensions(
+ xPackageManager->getDeployedPackages(xAbortChannel, xCmdEnv));
+
+ for ( sal_Int32 pos = 0; pos < extensions.getLength(); ++pos )
+ {
+ try
+ {
+ const OUString id = dp_misc::getIdentifier(extensions[ pos ]);
+ const OUString fileName = extensions[ pos ]->getName();
+ OSL_ASSERT(id.getLength());
+ activateExtension(
+ id, fileName,
+ isUserExtensionDisabled(id, fileName, xAbortChannel, xCmdEnv),
+ xAbortChannel, xCmdEnv );
+ }
+ catch (lang::DisposedException &)
+ {
+ }
+ }
+ } catch (deploy::DeploymentException& ) {
+ throw;
+ } catch (ucb::CommandFailedException & ) {
+ throw;
+ } catch (ucb::CommandAbortedException & ) {
+ throw;
+ } catch (lang::IllegalArgumentException &) {
+ throw;
+ } catch (uno::RuntimeException &) {
+ throw;
+ } catch (...) {
+ uno::Any exc = ::cppu::getCaughtException();
+ throw deploy::DeploymentException(
+ OUSTR("Extension Manager: exception during enableExtension"),
+ static_cast<OWeakObject*>(this), exc);
+ }
+}
+
+void ExtensionManager::synchronize(
+ OUString const & repository,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (deploy::DeploymentException,
+ ucb::CommandFailedException,
+ ucb::CommandAbortedException,
+ lang::IllegalArgumentException,
+ uno::RuntimeException)
+{
+ try
+ {
+ Reference<deploy::XPackageManager> xPackageManager;
+ OUString file;
+ if (repository.equals(OUSTR("user")))
+ {
+ xPackageManager = m_userRepository;
+ }
+ else if (repository.equals(OUSTR("shared")))
+ {
+ xPackageManager = m_sharedRepository;
+ file = OUString (
+ RTL_CONSTASCII_USTRINGPARAM(
+ "$SHARED_EXTENSIONS_USER/lastsynchronized"));
+ }
+ else if (repository.equals(OUSTR("bundled")))
+ {
+ xPackageManager = m_bundledRepository;
+ file = OUString (
+ RTL_CONSTASCII_USTRINGPARAM(
+ "$BUNDLED_EXTENSIONS_USER/lastsynchronized"));
+ }
+ else
+ throw lang::IllegalArgumentException(
+ OUSTR("No valid repository name provided."),
+ static_cast<cppu::OWeakObject*>(this), 0);
+
+ ::osl::MutexGuard guard(m_mutex);
+ uno::Sequence<Reference<deploy::XPackage> > seqAddedExtensions;
+ uno::Sequence<Reference<deploy::XPackage> > seqRemovedExtensions;
+ xPackageManager->synchronize(seqAddedExtensions, seqRemovedExtensions,
+ xAbortChannel, xCmdEnv);
+
+ //ToDo: optimize, only call activateExtension once per id.
+ //Determine which of the extensions was disabled by the user
+ //iterate of both sequences and add the ids of the user disabled
+ //to a map
+ for (sal_Int32 i = 0; i < seqRemovedExtensions.getLength(); i++)
+ {
+ try
+ {
+ Reference<deploy::XPackage> const & xExtension = seqRemovedExtensions[i];
+ OSL_ASSERT(xExtension.is());
+ const OUString id = dp_misc::getIdentifier(xExtension);
+ const OUString fileName = xExtension->getName();
+
+ bool bUserDisabled = isUserExtensionDisabled(
+ id, xExtension->getName(), xAbortChannel, xCmdEnv);
+ xExtension->revokePackage(xAbortChannel, xCmdEnv);
+ xPackageManager->removePackage(
+ id, fileName, xAbortChannel, xCmdEnv);
+ activateExtension(
+ id, fileName, bUserDisabled, xAbortChannel, xCmdEnv);
+ }
+ catch (...)
+ {
+ OSL_ENSURE(0, "Extensions Manager: synchronize");
+ }
+ }
+
+ for (sal_Int32 i = 0; i < seqAddedExtensions.getLength(); i++)
+ {
+ try
+ {
+ Reference<deploy::XPackage> const & xExtension = seqAddedExtensions[i];
+ OSL_ASSERT(xExtension.is());
+ const OUString id = dp_misc::getIdentifier(xExtension);
+ const OUString fileName = xExtension->getName();
+ bool bUserDisabled = isUserExtensionDisabled(
+ id, fileName, xAbortChannel, xCmdEnv);
+ activateExtension(
+ id, fileName, bUserDisabled, xAbortChannel, xCmdEnv);
+ }
+ catch (...)
+ {
+ OSL_ENSURE(0, "Extensions Manager: synchronize");
+ }
+ }
+
+ //Write the lastmodified file
+ try {
+ ::rtl::Bootstrap::expandMacros(file);
+ ::ucbhelper::Content ucbStamp(file, xCmdEnv );
+ dp_misc::erase_path( file, xCmdEnv );
+ ::rtl::OString stamp("1" );
+ Reference<css::io::XInputStream> xData(
+ ::xmlscript::createInputStream(
+ ::rtl::ByteSequence(
+ reinterpret_cast<sal_Int8 const *>(stamp.getStr()),
+ stamp.getLength() ) ) );
+ ucbStamp.writeStream( xData, true /* replace existing */ );
+ }
+ catch(...)
+ {
+ uno::Any exc(::cppu::getCaughtException());
+ throw deploy::DeploymentException(
+ OUSTR("Failed to update") + file,
+ static_cast<OWeakObject*>(this), exc);
+
+ }
+ } catch (deploy::DeploymentException& ) {
+ throw;
+ } catch (ucb::CommandFailedException & ) {
+ throw;
+ } catch (ucb::CommandAbortedException & ) {
+ throw;
+ } catch (lang::IllegalArgumentException &) {
+ throw;
+ } catch (uno::RuntimeException &) {
+ throw;
+ } catch (...) {
+ uno::Any exc = ::cppu::getCaughtException();
+ throw deploy::DeploymentException(
+ OUSTR("Extension Manager: exception during enableExtension"),
+ static_cast<OWeakObject*>(this), exc);
+ }
+}
+
+// Notify the user when a new extension is to be installed. This is only the
+// case when one uses the system integration to install an extension (double
+// clicking on .oxt file etc.)). The function must only be called if there is no
+// extension with the same identifier already deployed. Then the checkUpdate
+// function will inform the user that the extension is about to be installed In
+// case the user cancels the installation a CommandFailed exception is
+// thrown.
+void ExtensionManager::checkInstall(
+ OUString const & displayName,
+ Reference<ucb::XCommandEnvironment> const & cmdEnv)
+{
+ uno::Any request(
+ deploy::InstallException(
+ OUSTR("Extension ") + displayName +
+ OUSTR(" is about to be installed."),
+ static_cast<OWeakObject *>(this), displayName));
+ bool approve = false, abort = false;
+ if (! dp_misc::interactContinuation(
+ request, task::XInteractionApprove::static_type(),
+ cmdEnv, &approve, &abort ))
+ {
+ OSL_ASSERT( !approve && !abort );
+ throw deploy::DeploymentException(
+ dp_misc::getResourceString(RID_STR_ERROR_WHILE_ADDING) + displayName,
+ static_cast<OWeakObject *>(this), request );
+ }
+ if (abort || !approve)
+ throw ucb::CommandFailedException(
+ dp_misc::getResourceString(RID_STR_ERROR_WHILE_ADDING) + displayName,
+ static_cast<OWeakObject *>(this), request );
+}
+
+/* The function will make the user interaction in case there is an extension
+installed with the same id. This function may only be called if there is already
+an extension.
+*/
+void ExtensionManager::checkUpdate(
+ OUString const & newVersion,
+ OUString const & newDisplayName,
+ Reference<deploy::XPackage> const & oldExtension,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv )
+{
+ // package already deployed, interact --force:
+ uno::Any request(
+ (deploy::VersionException(
+ dp_misc::getResourceString(
+ RID_STR_PACKAGE_ALREADY_ADDED ) + newDisplayName,
+ static_cast<OWeakObject *>(this), newVersion, newDisplayName,
+ oldExtension ) ) );
+ bool replace = false, abort = false;
+ if (! dp_misc::interactContinuation(
+ request, task::XInteractionApprove::static_type(),
+ xCmdEnv, &replace, &abort )) {
+ OSL_ASSERT( !replace && !abort );
+ throw deploy::DeploymentException(
+ dp_misc::getResourceString(
+ RID_STR_ERROR_WHILE_ADDING) + newDisplayName,
+ static_cast<OWeakObject *>(this), request );
+ }
+ if (abort || !replace)
+ throw ucb::CommandFailedException(
+ dp_misc::getResourceString(
+ RID_STR_PACKAGE_ALREADY_ADDED) + newDisplayName,
+ static_cast<OWeakObject *>(this), request );
+}
+
+Reference<deploy::XPackage> ExtensionManager::getTempExtension(
+ OUString const & url,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<ucb::XCommandEnvironment> const & /*xCmdEnv*/)
+
+{
+ Reference<ucb::XCommandEnvironment> tmpCmdEnvA(new TmpRepositoryCommandEnv());
+ Reference<deploy::XPackage> xTmpPackage = m_tmpRepository->addPackage(
+ url, OUString(), xAbortChannel, tmpCmdEnvA);
+
+ if (!xTmpPackage.is())
+ {
+ throw deploy::DeploymentException(
+ OUSTR("Extension Manager: Failed to create temporary XPackage for url: ") + url,
+ static_cast<OWeakObject*>(this), uno::Any());
+
+ }
+ return xTmpPackage;
+}
+//------------------------------------------------------------------------------
+//------------------------------------------------------------------------------
+//------------------------------------------------------------------------------
+
+namespace sdecl = comphelper::service_decl;
+sdecl::class_<ExtensionManager> servicePIP;
+extern sdecl::ServiceDecl const serviceDecl(
+ servicePIP,
+ // a private one:
+ "com.sun.star.comp.deployment.ExtensionManager",
+ "com.sun.star.comp.deployment.ExtensionManager");
+
+//------------------------------------------------------------------------------
+bool singleton_entries(
+ uno::Reference< registry::XRegistryKey > const & xRegistryKey )
+{
+ try {
+ uno::Reference< registry::XRegistryKey > xKey(
+ xRegistryKey->createKey(
+ serviceDecl.getImplementationName() +
+ // xxx todo: use future generated function to get singleton name
+ OUSTR("/UNO/SINGLETONS/"
+ "com.sun.star.deployment.ExtensionManager") ) );
+ xKey->setStringValue( serviceDecl.getSupportedServiceNames()[0] );
+ return true;
+ }
+ catch (registry::InvalidRegistryException & exc) {
+ (void) exc; // avoid warnings
+ OSL_ENSURE( 0, ::rtl::OUStringToOString(
+ exc.Message, RTL_TEXTENCODING_UTF8 ).getStr() );
+ return false;
+ }
+}
+
+} // namespace dp_manager
+
+
diff --git a/desktop/source/deployment/manager/dp_extensionmanager.hxx b/desktop/source/deployment/manager/dp_extensionmanager.hxx
new file mode 100644
index 000000000000..386e2a7ceffd
--- /dev/null
+++ b/desktop/source/deployment/manager/dp_extensionmanager.hxx
@@ -0,0 +1,287 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+
+#if ! defined INCLUDED_DP_EXTENSIONMANAGER_H
+#define INCLUDED_DP_EXTENSIONMANAGER_H
+
+#include "dp_manager.hrc"
+#include "dp_misc.h"
+#include "dp_interact.h"
+#include "dp_activepackages.hxx"
+#include "rtl/ref.hxx"
+#include "cppuhelper/compbase1.hxx"
+//#include "cppuhelper/implbase2.hxx"
+#include "ucbhelper/content.hxx"
+#include "com/sun/star/deployment/XPackageRegistry.hpp"
+#include "com/sun/star/deployment/XPackageManager.hpp"
+//#include <memory>
+#include "osl/mutex.hxx"
+#include <list>
+
+
+namespace css = ::com::sun::star;
+
+namespace dp_manager {
+
+typedef ::std::hash_map<
+ ::rtl::OUString,
+ ::std::vector<css::uno::Reference<css::deployment::XPackage> >,
+ ::rtl::OUStringHash > id2extensions;
+
+class ExtensionManager :
+ public ::cppu::WeakImplHelper1< css::deployment::XExtensionManager >
+
+{
+private:
+ ::osl::Mutex m_mutex;
+
+ public:
+ ExtensionManager( css::uno::Reference< css::uno::XComponentContext >const& xContext);
+ virtual ~ExtensionManager();
+
+ static css::uno::Sequence< ::rtl::OUString > getServiceNames();
+ static ::rtl::OUString getImplName();
+
+// // XInteractionHandler
+// virtual void SAL_CALL handle( const uno::Reference< task::XInteractionRequest >& Request )
+// throw( uno::RuntimeException );
+// // XCommandEnvironment
+// virtual uno::Reference< task::XInteractionHandler > SAL_CALL getInteractionHandler()
+// throw ( uno::RuntimeException ) { return static_cast<task::XInteractionHandler*>(this); };
+
+// virtual uno::Reference< css_ucb::XProgressHandler > SAL_CALL getProgressHandler()
+// throw ( uno::RuntimeException ) { return uno::Reference< css_ucb::XProgressHandler >(); };
+public:
+ // XComponent
+ //virtual void SAL_CALL dispose() throw (css::uno::RuntimeException);
+ //virtual void SAL_CALL addEventListener(
+ // css::uno::Reference<css::lang::XEventListener> const & xListener )
+ // throw (css::uno::RuntimeException);
+ //virtual void SAL_CALL removeEventListener(
+ // css::uno::Reference<css::lang::XEventListener> const & xListener )
+ // throw (css::uno::RuntimeException);
+ //
+ //// XModifyBroadcaster
+ //virtual void SAL_CALL addModifyListener(
+ // css::uno::Reference<css::util::XModifyListener> const & xListener )
+ // throw (css::uno::RuntimeException);
+ //virtual void SAL_CALL removeModifyListener(
+ // css::uno::Reference<css::util::XModifyListener> const & xListener )
+ // throw (css::uno::RuntimeException);
+
+ // XPackageManager
+// virtual ::rtl::OUString SAL_CALL getContext()
+// throw (css::uno::RuntimeException);
+ virtual css::uno::Sequence<
+ css::uno::Reference<css::deployment::XPackageTypeInfo> > SAL_CALL
+ getSupportedPackageTypes(::rtl::OUString const & repository)
+ throw (css::uno::RuntimeException);
+
+ virtual css::uno::Reference<css::task::XAbortChannel> SAL_CALL
+ createAbortChannel() throw (css::uno::RuntimeException);
+
+ virtual css::uno::Reference<css::deployment::XPackage> SAL_CALL addExtension(
+ ::rtl::OUString const & url, ::rtl::OUString const & repository,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
+
+ virtual void SAL_CALL removeExtension(
+ ::rtl::OUString const & identifier,
+ ::rtl::OUString const & filename,
+ ::rtl::OUString const & repository,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
+
+ virtual void SAL_CALL enableExtension(
+ css::uno::Reference<css::deployment::XPackage> const & extension,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
+
+ virtual void SAL_CALL disableExtension(
+ css::uno::Reference<css::deployment::XPackage> const & extension,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
+
+ virtual css::uno::Sequence< css::uno::Reference<css::deployment::XPackage> >
+ SAL_CALL getDeployedExtensions(
+ ::rtl::OUString const & repository,
+ css::uno::Reference<css::task::XAbortChannel> const &,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
+
+ virtual css::uno::Reference< css::deployment::XPackage>
+ SAL_CALL getDeployedExtension(
+ ::rtl::OUString const & repository,
+ ::rtl::OUString const & identifier,
+ ::rtl::OUString const & filename,
+ css::uno::Reference< css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (
+ css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
+
+ virtual css::uno::Sequence< css::uno::Sequence<css::uno::Reference<css::deployment::XPackage> > >
+ SAL_CALL getAllExtensions(
+ css::uno::Reference<css::task::XAbortChannel> const &,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
+
+
+ virtual void SAL_CALL reinstallDeployedExtensions(
+ ::rtl::OUString const & repository,
+ css::uno::Reference< css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference< css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (
+ css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
+
+ virtual void SAL_CALL synchronize(
+ ::rtl::OUString const & repository,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
+
+private:
+
+ struct ExtensionInfos
+ {
+ ::rtl::OUString identifier;
+ ::rtl::OUString fileName;
+ ::rtl::OUString displayName;
+ ::rtl::OUString version;
+ };
+
+ css::uno::Reference< css::uno::XComponentContext> m_xContext;
+
+ css::uno::Reference<css::deployment::XPackageManager> m_userRepository;
+ css::uno::Reference<css::deployment::XPackageManager> m_sharedRepository;
+ css::uno::Reference<css::deployment::XPackageManager> m_bundledRepository;
+ css::uno::Reference<css::deployment::XPackageManager> m_tmpRepository;
+
+ /* contains the names of all repositories (except tmp) in order of there
+ priority. That is, the first element is "user" follod by "shared" and
+ then "bundled"
+ */
+ ::std::list< ::rtl::OUString > m_repositoryNames;
+
+ css::uno::Reference<css::deployment::XPackage> getExtensionAndStatus(
+ ::rtl::OUString const & identifier,
+ ::rtl::OUString const & fileName,
+ ::rtl::OUString const & repository,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv,
+ bool & out_bWasRegistered);
+
+ bool isUserExtensionDisabled(
+ ::rtl::OUString const & identifier,
+ ::rtl::OUString const & fileName,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv);
+
+ void activateExtension(
+ ::rtl::OUString const & identifier,
+ ::rtl::OUString const & fileName,
+ bool bUserDisabled,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv);
+
+
+ ::std::list<css::uno::Reference<css::deployment::XPackage> >
+ getExtensionsWithSameId(::rtl::OUString const & identifier,
+ ::rtl::OUString const & fileName);
+
+ css::uno::Reference<css::deployment::XPackage> backupExtension(
+ ::rtl::OUString const & identifier, ::rtl::OUString const & fileName,
+ css::uno::Reference<css::deployment::XPackageManager> const & xPackageManager,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv);
+
+ void checkInstall(
+ ::rtl::OUString const & displayName,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & cmdEnv);
+
+ void checkUpdate(
+ ::rtl::OUString const & newVersion,
+ ::rtl::OUString const & newDisplayName,
+ css::uno::Reference<css::deployment::XPackage> const & oldExtension,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv);
+
+ css::uno::Reference<css::deployment::XPackage> getTempExtension(
+ ::rtl::OUString const & url,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv);
+
+
+ void addExtensionsToMap(
+ id2extensions & mapExt,
+ css::uno::Sequence<css::uno::Reference<css::deployment::XPackage> > const & seqExt,
+ ::rtl::OUString const & repository);
+};
+
+}
+
+
+
+
+#endif
+
diff --git a/desktop/source/deployment/manager/dp_manager.cxx b/desktop/source/deployment/manager/dp_manager.cxx
index 3f13cb021aae..59e9f2049722 100644
--- a/desktop/source/deployment/manager/dp_manager.cxx
+++ b/desktop/source/deployment/manager/dp_manager.cxx
@@ -60,7 +60,12 @@
#include "com/sun/star/task/XInteractionApprove.hpp"
#include "com/sun/star/ucb/UnsupportedCommandException.hpp"
#include "boost/bind.hpp"
+#include "tools/urlobj.hxx"
+
+#include "osl/file.hxx"
#include <vector>
+#include <list>
+#include "dp_descriptioninfoset.hxx"
using namespace ::dp_misc;
@@ -91,6 +96,58 @@ struct MatchTempDir
}
};
+struct MatchExtension
+{
+ const ActivePackages::Data m_data;
+ MatchExtension(ActivePackages::Data const & data ) : m_data(data) {}
+ bool operator () ( OUString const & temporaryName ) const;
+};
+
+bool MatchExtension::operator () (OUString const & temporaryName) const
+{
+ //case 1: The temporary file and thus the extension folder are already
+ //removed.
+ return m_data.temporaryName.equals(temporaryName);
+}
+
+namespace {
+OUString getExtensionFolder(OUString const & parentFolder,
+ Reference<ucb::XCommandEnvironment> const & xCmdEnv)
+{
+ ::ucbhelper::Content tempFolder(
+ parentFolder, xCmdEnv );
+ Reference<sdbc::XResultSet> xResultSet(
+ tempFolder.createCursor(
+ Sequence<OUString>( &StrTitle::get(), 1 ),
+ ::ucbhelper::INCLUDE_FOLDERS_ONLY ) );
+
+ OUString title;
+ while (xResultSet->next())
+ {
+ title = Reference<sdbc::XRow>(
+ xResultSet, UNO_QUERY_THROW )->getString(1 /* Title */ ) ;
+ break;
+ }
+ return title;
+}
+/* adds an unencoded segment to the URL.
+
+ Throws an com.sun.star.uno.Exception if this failed.
+*/
+OUString appendURLSegement(OUString const & baseURL, OUString const & segment)
+{
+ OUString url;
+ INetURLObject inet(baseURL);
+ if (inet.insertName(
+ segment, false, INetURLObject::LAST_SEGMENT, true,
+ INetURLObject::ENCODE_ALL))
+ url = inet.GetMainURL(INetURLObject::NO_DECODE);
+ else
+ throw Exception(
+ OUSTR("ExtensionManager: failed to add segment to URL"), 0);
+ return url;
+}
+}
//______________________________________________________________________________
void PackageManagerImpl::initActivationLayer(
Reference<XCommandEnvironment> const & xCmdEnv )
@@ -151,12 +208,23 @@ void PackageManagerImpl::initActivationLayer(
// user|share:
OSL_ASSERT( m_activePackages.getLength() > 0 );
m_activePackages_expanded = expandUnoRcUrl( m_activePackages );
- create_folder( 0, m_activePackages_expanded, xCmdEnv, !m_readOnly );
+ m_registrationData_expanded = expandUnoRcUrl(m_registrationData);
+ create_folder( 0, m_activePackages_expanded, xCmdEnv, true);
+
+ OUString dbName;
+ if (m_context.equals(OUSTR("user")))
+ dbName = m_activePackages_expanded + OUSTR(".db");
+ else
+ {
+ //Create the extension data base in the user installation
+ create_folder( 0, m_registrationData_expanded, xCmdEnv, true);
+ dbName = m_registrationData_expanded + OUSTR("/extensions.db");
+ }
+ //The data base can always be written because it it always in the user installation
m_activePackagesDB.reset(
- new ActivePackages(
- m_activePackages_expanded + OUSTR(".db"), m_readOnly ) );
+ new ActivePackages( dbName, false ) );
- if (! m_readOnly)
+ if (! m_readOnly && ! m_context.equals(OUSTR("bundled")))
{
// clean up activation layer, scan for zombie temp dirs:
ActivePackages::Entries id2temp( m_activePackagesDB->getEntries() );
@@ -169,11 +237,17 @@ void PackageManagerImpl::initActivationLayer(
::ucbhelper::INCLUDE_DOCUMENTS_ONLY ) );
// get all temp directories:
::std::vector<OUString> tempEntries;
- while (xResultSet->next()) {
+ while (xResultSet->next())
+ {
OUString title(
Reference<sdbc::XRow>(
xResultSet, UNO_QUERY_THROW )->getString(
1 /* Title */ ) );
+ const char extensionRemoved[] = ".tmpremoved";
+ if (title.endsWithAsciiL(
+ extensionRemoved, sizeof(extensionRemoved) - 1))
+ continue;
+
tempEntries.push_back( ::rtl::Uri::encode(
title, rtl_UriCharClassPchar,
rtl_UriEncodeIgnoreEscapes,
@@ -195,6 +269,9 @@ void PackageManagerImpl::initActivationLayer(
false /* no throw: ignore errors */ );
erase_path( url, Reference<XCommandEnvironment>(),
false /* no throw: ignore errors */ );
+ //delete the xxx.tmpremoved file
+ erase_path(url + OUSTR("removed"),
+ Reference<XCommandEnvironment>(), false);
}
}
}
@@ -206,9 +283,9 @@ void PackageManagerImpl::initRegistryBackends()
{
if (m_registryCache.getLength() > 0)
create_folder( 0, m_registryCache,
- Reference<XCommandEnvironment>(), !m_readOnly );
+ Reference<XCommandEnvironment>(), false);
m_xRegistry.set( ::dp_registry::create(
- m_context, m_registryCache, m_readOnly,
+ m_context, m_registryCache, false,
m_xComponentContext ) );
}
@@ -223,12 +300,14 @@ Reference<deployment::XPackageManager> PackageManagerImpl::create(
OUString packages, logFile, stampURL;
if (context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("user") )) {
- that->m_activePackages = OUSTR("vnd.sun.star.expand:$UNO_"
- "USER_PACKAGES_CACHE/uno_packages");
- that->m_registryCache = OUSTR("vnd.sun.star.expand:$UNO_"
- "USER_PACKAGES_CACHE/registry");
- logFile = OUSTR("vnd.sun.star.expand:$UNO_"
- "USER_PACKAGES_CACHE/log.txt");
+ that->m_activePackages = OUSTR(
+ "vnd.sun.star.expand:$UNO_USER_PACKAGES_CACHE/uno_packages");
+ that->m_registrationData = OUSTR(
+ "vnd.sun.star.expand:$UNO_USER_PACKAGES_CACHE");
+ that->m_registryCache = OUSTR(
+ "vnd.sun.star.expand:$UNO_USER_PACKAGES_CACHE/registry");
+ logFile = OUSTR(
+ "vnd.sun.star.expand:$UNO_USER_PACKAGES_CACHE/log.txt");
//We use the extension .sys for the file because on Windows Vista a sys
//(as well as exe and dll) file
//will not be written in the VirtualStore. For example if the process has no
@@ -240,25 +319,42 @@ Reference<deployment::XPackageManager> PackageManagerImpl::create(
//using virtualization it appears that he/she can. Then a shared extension can
//be installed but is only visible for the user (because the extension is in
//the virtual store).
- stampURL = OUSTR("vnd.sun.star.expand:$UNO_"
- "USER_PACKAGES_CACHE/stamp.sys");
+ stampURL = OUSTR(
+ "vnd.sun.star.expand:$UNO_USER_PACKAGES_CACHE/stamp.sys");
}
else if (context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("shared") )) {
- that->m_activePackages = OUSTR("vnd.sun.star.expand:$UNO_"
- "SHARED_PACKAGES_CACHE/uno_packages");
- that->m_registryCache = OUSTR("vnd.sun.star.expand:$UNO_"
- "SHARED_PACKAGES_CACHE/registry");
-// The current logging implementation does not work for shared, because it requires
-// write access to the logfile. When two users run OOo at the same time on the same machine
-// then the
-// second will fail because it does not get write access. One cannot write into the
-// user's home, because then people may complain that when installing shared extension
-// stuff is written in their home.
-// logFile = OUSTR("vnd.sun.star.expand:$UNO_"
-// "SHARED_PACKAGES_CACHE/log.txt");
- //See description for stampURL for user packages.
- stampURL = OUSTR("vnd.sun.star.expand:$UNO_"
- "SHARED_PACKAGES_CACHE/stamp.sys");
+ that->m_activePackages = OUSTR(
+ "vnd.sun.star.expand:$UNO_SHARED_PACKAGES_CACHE/uno_packages");
+ that->m_registrationData = OUSTR(
+ "vnd.sun.star.expand:$SHARED_EXTENSIONS_USER");
+ that->m_registryCache = OUSTR(
+ "vnd.sun.star.expand:$SHARED_EXTENSIONS_USER/registry");
+ logFile = OUSTR(
+ "vnd.sun.star.expand:$SHARED_EXTENSIONS_USER/log.txt");
+ stampURL = OUSTR(
+ "vnd.sun.star.expand:$UNO_SHARED_PACKAGES_CACHE/stamp.sys");
+ }
+ else if (context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("bundled") )) {
+ that->m_activePackages = OUSTR(
+ "vnd.sun.star.expand:$BUNDLED_EXTENSIONS");
+ that->m_registrationData = OUSTR(
+ "vnd.sun.star.expand:$BUNDLED_EXTENSIONS_USER");
+ that->m_registryCache = OUSTR(
+ "vnd.sun.star.expand:$BUNDLED_EXTENSIONS_USER/registry");
+ logFile = OUSTR(
+ "vnd.sun.star.expand:$BUNDLED_EXTENSIONS_USER/log.txt");
+ //No stamp file. We assume that bundled is always readonly. It must not be
+ //modified from ExtensionManager but only by the installer
+ }
+ else if (context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("tmp") )) {
+ that->m_activePackages = OUSTR(
+ "vnd.sun.star.expand:$TMP_EXTENSIONS/extensions");
+ that->m_registrationData = OUSTR(
+ "vnd.sun.star.expand:$TMP_EXTENSIONS");
+ that->m_registryCache = OUSTR(
+ "vnd.sun.star.expand:$TMP_EXTENSIONS/registry");
+ stampURL = OUSTR(
+ "vnd.sun.star.expand:$TMP_EXTENSIONS/stamp.sys");
}
else if (! context.matchAsciiL(
RTL_CONSTASCII_STRINGPARAM("vnd.sun.star.tdoc:/") )) {
@@ -270,29 +366,15 @@ Reference<deployment::XPackageManager> PackageManagerImpl::create(
Reference<XCommandEnvironment> xCmdEnv;
try {
- bool renewal = false;
-
+ //There is no stampURL for the bundled folder
if (stampURL.getLength() > 0)
{
- // currently no automatic renewal possible, because quickstarter
- // already hinders from deleting registry directory...
-
#define CURRENT_STAMP "1"
-// renewal = true;
-// {
-// ::ucbhelper::Content ucbStamp;
-// if (create_ucb_content(
-// &ucbStamp, stampURL, xCmdEnv, false /* no throw */ ))
-// {
-// OUString line;
-// renewal = !readLine( &line, OUSTR(CURRENT_STAMP), ucbStamp,
-// RTL_TEXTENCODING_ASCII_US );
-// }
-// }
-
try {
+ //The osl file API does not allow to find out if one can write
+ //into a folder. Therefore we try to write a file. Then we delete
+ //it, so that it does not hinder uninstallation of OOo
// probe writing:
- erase_path( stampURL, xCmdEnv );
::ucbhelper::Content ucbStamp( stampURL, xCmdEnv );
::rtl::OString stamp(
RTL_CONSTASCII_STRINGPARAM(CURRENT_STAMP) );
@@ -302,8 +384,15 @@ Reference<deployment::XPackageManager> PackageManagerImpl::create(
reinterpret_cast<sal_Int8 const *>(stamp.getStr()),
stamp.getLength() ) ) );
ucbStamp.writeStream( xData, true /* replace existing */ );
+ that->m_readOnly = false;
+ erase_path( stampURL, xCmdEnv );
}
catch (RuntimeException &) {
+ try {
+ erase_path( stampURL, xCmdEnv );
+ } catch (...)
+ {
+ }
throw;
}
catch (Exception &) {
@@ -324,12 +413,6 @@ Reference<deployment::XPackageManager> PackageManagerImpl::create(
xCmdEnv.set( new CmdEnvWrapperImpl( xCmdEnv, that->m_xLogFile ) );
}
- OSL_ENSURE( !that->m_readOnly || !renewal,
- "### ought to reinstall all packages, but cannot write!" );
- if (!that->m_readOnly && renewal) // try to reinstall
- that->reinstallDeployedPackages(
- Reference<task::XAbortChannel>(), xCmdEnv );
-
that->initRegistryBackends();
that->initActivationLayer( xCmdEnv );
@@ -484,7 +567,7 @@ OUString PackageManagerImpl::detectMediaType(
try {
Reference<deployment::XPackage> xPackage(
m_xRegistry->bindPackage(
- url, OUString(), ucbContent.getCommandEnvironment() ) );
+ url, OUString(), false, ucbContent.getCommandEnvironment() ) );
const Reference<deployment::XPackageTypeInfo> xPackageType(
xPackage->getPackageType() );
OSL_ASSERT( xPackageType.is() );
@@ -564,10 +647,18 @@ OUString PackageManagerImpl::insertToActivationLayer(
title, NameClash::OVERWRITE ))
throw RuntimeException( OUSTR("UCB transferContent() failed!"), 0 );
+
// write to DB:
+ //bundled extensions should only be added by the synchronizeAddedExtensions
+ //functions. Moreover, there is no "temporary folder" for bundled extensions.
+ OSL_ASSERT(!m_context.equals(OUSTR("bundled")));
+ DescriptionInfoset info =
+ dp_misc::getDescriptionInfoset(
+ appendURLSegement(destFolderContent.getURL(), title));
dbData->temporaryName = tempEntry;
dbData->fileName = title;
dbData->mediaType = mediaType;
+ dbData->version = info.getVersion();
return destFolder;
}
@@ -582,79 +673,35 @@ void PackageManagerImpl::insertToActivationLayerDB(
/* The function returns true if there is an extension with the same id already
installed which needs to be uninstalled, before the new extension can be installed.
*/
-bool PackageManagerImpl::checkUpdate(
- Reference<deployment::XPackage> const & package,
- Reference<XCommandEnvironment> const & origCmdEnv,
- Reference<XCommandEnvironment> const & wrappedCmdEnv )
+bool PackageManagerImpl::isInstalled(
+ Reference<deployment::XPackage> const & package)
{
OUString id(dp_misc::getIdentifier(package));
OUString fn(package->getName());
- bool removeExisting = false;
+ bool bInstalled = false;
if (m_activePackagesDB->has( id, fn ))
{
- // package already deployed, interact --force:
- Any request(
- (deployment::VersionException(
- getResourceString( RID_STR_PACKAGE_ALREADY_ADDED ) + id,
- static_cast<OWeakObject *>(this), package,
- getDeployedPackage_( id, fn, origCmdEnv ) ) ) );
- bool replace = false, abort = false;
- if (! interactContinuation(
- request, task::XInteractionApprove::static_type(),
- wrappedCmdEnv, &replace, &abort )) {
- OSL_ASSERT( !replace && !abort );
- throw deployment::DeploymentException(
- getResourceString(RID_STR_ERROR_WHILE_ADDING) + id,
- static_cast<OWeakObject *>(this), request );
- }
- if (abort || !replace)
- throw CommandFailedException(
- getResourceString(RID_STR_PACKAGE_ALREADY_ADDED) + id,
- static_cast<OWeakObject *>(this), request );
-
- // remove clashing package before registering new version:
- removeExisting = true;
+ bInstalled = true;
}
- return removeExisting;
+ return bInstalled;
}
+
+// XPackageManager
//______________________________________________________________________________
-// Notify the user when a new extension is to be installed. This is only the case
-//when unopkg gui extension1 is used (used by system integration (double click on .oxt
-// file etc.)). In case there is already this extension then the function returns
-//true.
-//ToDo: Function always returns true or throws an exception
-bool PackageManagerImpl::checkInstall(
- Reference<deployment::XPackage> const & package,
- Reference<XCommandEnvironment> const & cmdEnv)
+Reference<deployment::XPackage> PackageManagerImpl::importExtension(
+ Reference<deployment::XPackage> const & extension,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<XCommandEnvironment> const & xCmdEnv_ )
+ throw (deployment::DeploymentException, CommandFailedException,
+ CommandAbortedException, lang::IllegalArgumentException,
+ RuntimeException)
{
- OUString id(dp_misc::getIdentifier(package));
- if ( ! m_activePackagesDB->has( id, package->getName() ))
- {
- Any request(
- deployment::InstallException(
- OUSTR("Extension ") + id + OUSTR(" is about to be installed."),
- static_cast<OWeakObject *>(this), package));
- bool approve = false, abort = false;
- if (! interactContinuation(
- request, task::XInteractionApprove::static_type(),
- cmdEnv, &approve, &abort ))
- {
- OSL_ASSERT( !approve && !abort );
- throw deployment::DeploymentException(
- getResourceString(RID_STR_ERROR_WHILE_ADDING) + id,
- static_cast<OWeakObject *>(this), request );
- }
- if (abort || !approve)
- throw CommandFailedException(
- getResourceString(RID_STR_ERROR_WHILE_ADDING) + id,
- static_cast<OWeakObject *>(this), request );
-
- }
- return true;
+ return addPackage(extension->getURL(), OUString(), xAbortChannel, xCmdEnv_);
}
-// XPackageManager
-//______________________________________________________________________________
+/* The function adds an extension but does not register it!!!
+ It may not do any user interaction. This is done in XExtensionManager::addExtension
+*/
Reference<deployment::XPackage> PackageManagerImpl::addPackage(
OUString const & url, OUString const & mediaType_,
Reference<task::XAbortChannel> const & xAbortChannel,
@@ -733,80 +780,39 @@ Reference<deployment::XPackage> PackageManagerImpl::addPackage(
// bind activation package:
- //Because every extension will be unpacked in a folder, which was created with a unique name
- //we will always have two different XPackage objects, even if the second extension is the same.
+ //Because every shared/user extension will be unpacked in a folder,
+ //which was created with a unique name we will always have two different
+ //XPackage objects, even if the second extension is the same.
//Therefore bindPackage does not need a guard here.
xPackage = m_xRegistry->bindPackage(
- makeURL( destFolder, title_enc ), mediaType, xCmdEnv );
+ makeURL( destFolder, title_enc ), mediaType, false, xCmdEnv );
OSL_ASSERT( xPackage.is() );
if (xPackage.is())
{
bool install = false;
- OUString id;
-
try
{
- id = dp_misc::getIdentifier( xPackage );
- //checkInstall throws an exception if the user denies the installation
- checkInstall(xPackage, xCmdEnv);
- //checkUpdate throws an exception if the user cancels the interaction.
- //For example, he may be asked if he wants to replace the older version
- //with the new version.
- //checkUpdates must be called before checkPrerequisites
- bool bAlreadyInstalled = checkUpdate(
- xPackage, xCmdEnv_, xCmdEnv );
-
- if (xPackage->checkPrerequisites(xAbortChannel, xCmdEnv, bAlreadyInstalled, m_context))
+ OUString const id = dp_misc::getIdentifier( xPackage );
+ //This guard is used to prevent that an extension is
+ //installed twice. Do not use it in other functions.
+ //Imagine addPackage is called two times by different
+ //threads for the same extension quickly after each other.
+ //The second call would calculate "bAlreadyInstalled =
+ //false" if the first thread has not yet reached
+ //insertToActivationLayerDB.
+ ::osl::MutexGuard g(m_addMutex);
+ if (isInstalled(xPackage))
{
- //This guard is used to prevent that an extension is installed twice. Do not use it in other
- //functions.
- //Imagine addPackage is called two times by different threads for the same extension quickly
- //after each other.
- //The second call would calculate "bAlreadyInstalled = false" if the first thread has not yet reached
- //insertToActivationLayerDB.
- ::osl::MutexGuard g(m_addMutex);
-
- //Holds the database data of the old extension, in case we need to roll back.
- ActivePackages::Data oldDbData;
- if (bAlreadyInstalled)
- {
- // Remove extension which is already installed. It is not removed from disk, only
- // the different contents are being unregisterd. We remember the databas information
- // in case we need to roll back this operation.
- // When the user canceled the operation (CommandAbortedException) than the package is still
- // fully functional.
- // Do not guard the complete function with the getMutex
- removePackage_(id, xPackage->getName(), xAbortChannel,
- xCmdEnv, & oldDbData);
- }
- install = true;
- const ::osl::MutexGuard guard( getMutex() );
- try
- {
- //throws CommandAbortedException if the user cancelled the installation.
- xPackage->registerPackage(xAbortChannel, xCmdEnv);
- }
- catch(CommandAbortedException & )
- { //ToDo: Interaction so that the gui can display an appropriate string.
- //See also removePackage_
- //User aborted installation, restore the previous situation.
- //Use a private AbortChannel so the user cannot interrupt.
- xPackage->revokePackage(new AbortChannel(), xCmdEnv);
- if (bAlreadyInstalled)
- {
- OUString instFolder = makeURL( m_activePackages, oldDbData.temporaryName)
- + OUSTR("_");
- Reference<deployment::XPackage> xOldPgk = m_xRegistry->bindPackage(
- makeURL( instFolder, oldDbData.fileName ), oldDbData.mediaType, xCmdEnv );
- xOldPgk->registerPackage(new AbortChannel(), xCmdEnv);
- insertToActivationLayerDB(dp_misc::getIdentifier( xOldPgk ), oldDbData);
- }
- throw;
- }
- //access to the database must be guarded. See removePackage_
- insertToActivationLayerDB(id, dbData);
+ //Do not guard the complete function with the getMutex
+ removePackage(id, xPackage->getName(), xAbortChannel,
+ xCmdEnv);
}
+ install = true;
+ const ::osl::MutexGuard guard( getMutex() );
+ //access to the database must be guarded. See removePackage_
+ insertToActivationLayerDB(id, dbData);
+
}
catch (...)
{
@@ -817,6 +823,7 @@ Reference<deployment::XPackage> PackageManagerImpl::addPackage(
{
deletePackageFromCache( xPackage, destFolder );
}
+ //ToDo: We should notify only if the extension is registered
fireModified();
}
return xPackage;
@@ -861,41 +868,9 @@ void PackageManagerImpl::deletePackageFromCache(
}
//______________________________________________________________________________
-void PackageManagerImpl::removePackage_(
- OUString const & id, OUString const & fileName,
- Reference<task::XAbortChannel> const & xAbortChannel,
- Reference<XCommandEnvironment> const & xCmdEnv,
- ActivePackages::Data * out_dbData)
-{
- Reference<deployment::XPackage> xPackage;
- {
- try {
- const ::osl::MutexGuard guard(getMutex());
- xPackage = getDeployedPackage_(id, fileName, xCmdEnv );
- m_activePackagesDB->get(out_dbData, id, fileName);
- beans::Optional< beans::Ambiguous<sal_Bool> > option(
- xPackage->isRegistered( Reference<task::XAbortChannel>(),
- xCmdEnv ) );
- if (!option.IsPresent || option.Value.IsAmbiguous || option.Value.Value)
- xPackage->revokePackage( xAbortChannel, xCmdEnv );
- m_activePackagesDB->erase( id, fileName ); // to be removed upon next start
- }
- catch (CommandAbortedException &)
- {
- //ToDo: interaction, so that gui can show an appropriate string
- //reregister the package
- //Create our own XAbortChannel, so the user cannot interrupt the registration.
- xPackage->registerPackage(new AbortChannel(), xCmdEnv);
- throw;
- }
- }
- try_dispose( xPackage );
-}
-
-//______________________________________________________________________________
void PackageManagerImpl::removePackage(
OUString const & id, ::rtl::OUString const & fileName,
- Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<task::XAbortChannel> const & /*xAbortChannel*/,
Reference<XCommandEnvironment> const & xCmdEnv_ )
throw (deployment::DeploymentException, CommandFailedException,
CommandAbortedException, lang::IllegalArgumentException,
@@ -920,7 +895,39 @@ void PackageManagerImpl::removePackage(
xCmdEnv.set( xCmdEnv_ );
try {
- removePackage_( id, fileName, xAbortChannel, xCmdEnv, NULL);
+ Reference<deployment::XPackage> xPackage;
+ {
+ const ::osl::MutexGuard guard(getMutex());
+ //Check if this extension exist and throw an IllegalArgumentException
+ //if it does not
+ xPackage = getDeployedPackage_(id, fileName, xCmdEnv );
+ //Because the extension is only removed the next time the extension
+ //manager runs after restarting OOo, we need to indicate that a
+ //shared extension was "deleted". When a user starts OOo, then it
+ //will check if something changed in the shared repository. Based on
+ //the flag file it will then recognize, that the extension was
+ //deleted and can then update the extnesion database of the shared
+ //extensions in the user installation.
+ if (m_context.equals(OUSTR("shared")))
+ {
+ ActivePackages::Data val;
+ m_activePackagesDB->get( & val, id, fileName);
+ OSL_ASSERT(val.temporaryName.getLength());
+ OUString url(makeURL(m_activePackages_expanded,
+ val.temporaryName + OUSTR("removed")));
+ ::ucbhelper::Content contentRemoved(url, xCmdEnv );
+ ::rtl::OString stamp("1");
+ Reference<css::io::XInputStream> xData(
+ ::xmlscript::createInputStream(
+ ::rtl::ByteSequence(
+ reinterpret_cast<sal_Int8 const *>(stamp.getStr()),
+ stamp.getLength() ) ) );
+ contentRemoved.writeStream( xData, true /* replace existing */ );
+ }
+ m_activePackagesDB->erase( id, fileName ); // to be removed upon next start
+ }
+ try_dispose( xPackage );
+
fireModified();
}
catch (RuntimeException &) {
@@ -955,10 +962,16 @@ OUString PackageManagerImpl::getDeployPath( ActivePackages::Data const & data )
{
::rtl::OUStringBuffer buf;
buf.append( data.temporaryName );
- buf.appendAscii( RTL_CONSTASCII_STRINGPARAM("_/") );
- buf.append( ::rtl::Uri::encode( data.fileName, rtl_UriCharClassPchar,
+ //The bundled extensions are not contained in an additional folder
+ //with a unique name. data.temporaryName contains already the
+ //UTF8 encoded folder name. See PackageManagerImpl::synchronize
+ if (!m_context.equals(OUSTR("bundled")))
+ {
+ buf.appendAscii( RTL_CONSTASCII_STRINGPARAM("_/") );
+ buf.append( ::rtl::Uri::encode( data.fileName, rtl_UriCharClassPchar,
rtl_UriEncodeIgnoreEscapes,
RTL_TEXTENCODING_UTF8 ) );
+ }
return makeURL( m_activePackages, buf.makeStringAndClear() );
}
@@ -998,7 +1011,7 @@ Reference<deployment::XPackage> PackageManagerImpl::getDeployedPackage_(
}
}
return m_xRegistry->bindPackage(
- getDeployPath( data ), data.mediaType, xCmdEnv );
+ getDeployPath( data ), data.mediaType, false, xCmdEnv );
}
//______________________________________________________________________________
@@ -1124,8 +1137,12 @@ PackageManagerImpl::getDeployedPackages(
}
//______________________________________________________________________________
+
+
+//ToDo: the function must not call registerPackage, do this in
+//XExtensionManager.reinstallDeployedExtensions
void PackageManagerImpl::reinstallDeployedPackages(
- Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<task::XAbortChannel> const & /*xAbortChannel*/,
Reference<XCommandEnvironment> const & xCmdEnv_ )
throw (deployment::DeploymentException,
CommandFailedException, CommandAbortedException,
@@ -1167,12 +1184,7 @@ void PackageManagerImpl::reinstallDeployedPackages(
if (xUpdatable.is())
xUpdatable->update();
- // reregister all:
- const ::osl::MutexGuard guard( getMutex() );
- const Sequence< Reference<deployment::XPackage> > packages(
- getDeployedPackages_( xCmdEnv ) );
- for ( sal_Int32 pos = 0; pos < packages.getLength(); ++pos )
- packages[ pos ]->registerPackage( xAbortChannel, xCmdEnv );
+ //registering is done by the ExtensionManager service.
}
catch (RuntimeException &) {
throw;
@@ -1205,6 +1217,242 @@ void PackageManagerImpl::reinstallDeployedPackages(
{
return m_readOnly;
}
+void PackageManagerImpl::synchronizeRemovedExtensions(
+ Sequence<Reference<deployment::XPackage> > & out_removedExtensions,
+ Reference<task::XAbortChannel> const & /*xAbortChannel*/,
+ Reference<css::ucb::XCommandEnvironment> const & xCmdEnv)
+{
+
+ //find all which are in the extension data base but which
+ //are removed already.
+ OSL_ASSERT(!m_context.equals(OUSTR("user")));
+ ActivePackages::Entries id2temp( m_activePackagesDB->getEntries() );
+
+ //Iterate over the contents of the extension folder and gather the
+ //temp file names (shared) or the folder names of the bundled extension.
+ ::ucbhelper::ResultSetInclude includeType = ::ucbhelper::INCLUDE_DOCUMENTS_ONLY;
+ if (m_context.equals(OUSTR("bundled")))
+ includeType = ::ucbhelper::INCLUDE_FOLDERS_ONLY;
+ ::ucbhelper::Content tempFolder(
+ m_activePackages_expanded, xCmdEnv );
+ Reference<sdbc::XResultSet> xResultSet(
+ tempFolder.createCursor(
+ Sequence<OUString>( &StrTitle::get(), 1 ), includeType) );
+ // get all temp directories:
+ ::std::vector<OUString> tempEntries;
+ while (xResultSet->next()) {
+ OUString title(
+ Reference<sdbc::XRow>(
+ xResultSet, UNO_QUERY_THROW )->getString(
+ 1 /* Title */ ) );
+ //also add the xxx.tmpremoved files for remove shared extensions
+ //this does not matter
+ tempEntries.push_back( ::rtl::Uri::encode(
+ title, rtl_UriCharClassPchar,
+ rtl_UriEncodeIgnoreEscapes,
+ RTL_TEXTENCODING_UTF8 ) );
+ }
+
+ typedef ActivePackages::Entries::const_iterator ITActive;
+ bool bShared = m_context.equals(OUSTR("shared"));
+ ::std::vector<Reference<deployment::XPackage> > removedExtensions;
+ for (ITActive i = id2temp.begin(); i != id2temp.end(); i++)
+ {
+ //Get the URL to the extensions folder, first make the url for the
+ //shared repository including the temporary name
+// OUString url(m_activePackages_expanded + OUSTR("/")
+// + i->second.temporaryName);
+// if (bShared)
+// url = appendURLSegement(m_activePackages_expanded + OUSTR("/")
+// + i->second.temporaryName + OUSTR("_"),
+// i->second.fileName);
+ OUString url = makeURL(m_activePackages, i->second.temporaryName);
+ if (bShared)
+ url = makeURLAppendSysPathSegment( url + OUSTR("_"), i->second.fileName);
+
+ const MatchExtension match(i->second);
+ bool bRemoved = false;
+ if (::std::find_if(tempEntries.begin(), tempEntries.end(), match) ==
+ tempEntries.end())
+ {
+ //The the URL from the data base entry does not exist anymore. That is the
+ //folder was removed.
+ bRemoved = true;
+ }
+ else
+ {
+ //The folder is in the extension database, but it can still be deleted.
+ //look for the xxx.tmpremoved file
+ if (bShared)
+ {
+ ::ucbhelper::Content contentRemoved;
+ if (create_ucb_content(
+ &contentRemoved,
+ m_activePackages_expanded + OUSTR("/") +
+ i->second.temporaryName + OUSTR("removed"),
+ Reference<XCommandEnvironment>(), false))
+ {
+ bRemoved = true;
+ }
+ }
+ if (!bRemoved)
+ {
+ //There may be another extensions at the same place
+ dp_misc::DescriptionInfoset infoset =
+ dp_misc::getDescriptionInfoset(url);
+ OSL_ENSURE(infoset.hasDescription(),
+ "Extension Manager: bundled and shared extensions "
+ "must have an identifer and a version");
+ if ( ! i->first.equals(*(infoset.getIdentifier()))
+ || ! i->second.version.equals(infoset.getVersion()))
+ {
+ bRemoved = true;
+ }
+ }
+ }
+ if (bRemoved)
+ {
+ Reference<deployment::XPackage> xPackage = m_xRegistry->bindPackage(
+ url, i->second.mediaType, true, xCmdEnv );
+ OSL_ASSERT(xPackage.is()); //Even if the files are removed, we must get the object.
+ removedExtensions.push_back(xPackage);
+ }
+ }
+ out_removedExtensions = ::comphelper::containerToSequence(removedExtensions);
+}
+
+void PackageManagerImpl::synchronizeAddedExtensions(
+ Sequence<Reference<deployment::XPackage> > & out_addedExtensions,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<css::ucb::XCommandEnvironment> const & xCmdEnv)
+{
+ // clean up activation layer, scan for zombie temp dirs:
+ ActivePackages::Entries id2temp( m_activePackagesDB->getEntries() );
+
+ ::ucbhelper::Content tempFolder(
+ m_activePackages_expanded, xCmdEnv );
+ Reference<sdbc::XResultSet> xResultSet(
+ tempFolder.createCursor(
+ Sequence<OUString>( &StrTitle::get(), 1 ),
+ ::ucbhelper::INCLUDE_FOLDERS_ONLY ) );
+
+
+ ::std::vector<Reference<deployment::XPackage> > addedExtensions;
+ while (xResultSet->next())
+ {
+ OUString title(
+ Reference<sdbc::XRow>(
+ xResultSet, UNO_QUERY_THROW )->getString(
+ 1 /* Title */ ) );
+ //The temporary folders of user and shared have an '_' at then end.
+ //But the name in ActivePackages.temporaryName is saved without.
+ OUString title2 = title;
+ bool bNotBundled = !m_context.equals(OUSTR("bundled"));
+ if (bNotBundled)
+ {
+ OSL_ASSERT(title2[title2.getLength() -1] == '_');
+ title2 = title2.copy(0, title2.getLength() -1);
+ }
+ OUString titleEncoded = ::rtl::Uri::encode(
+ title2, rtl_UriCharClassPchar,
+ rtl_UriEncodeIgnoreEscapes,
+ RTL_TEXTENCODING_UTF8);
+
+ const MatchTempDir match(titleEncoded);
+ if (::std::find_if( id2temp.begin(), id2temp.end(), match ) ==
+ id2temp.end())
+ {
+
+ // The folder was not found in the data base, so it must be
+ // an added extension
+ OUString url(m_activePackages_expanded + OUSTR("/") + titleEncoded);
+ OUString sExtFolder;
+ if (bNotBundled) //that is, shared
+ {
+ //Check if the extension was not "deleted" already which is indicated
+ //by a xxx.tmpremoved file
+ ::ucbhelper::Content contentRemoved;
+ if (create_ucb_content(&contentRemoved, url + OUSTR("removed"),
+ Reference<XCommandEnvironment>(), false))
+ continue;
+ sExtFolder = getExtensionFolder(
+ m_activePackages_expanded +
+ OUString(OUSTR("/")) + titleEncoded + OUSTR("_"), xCmdEnv);
+ url = appendURLSegement(m_activePackages_expanded, title);
+ url = appendURLSegement(url, sExtFolder);
+ }
+ Reference<deployment::XPackage> xPackage = m_xRegistry->bindPackage(
+ url, OUString(), false, xCmdEnv );
+ if (xPackage.is())
+ {
+ try
+ {
+ //ToDo: We need to prevent that removed shared extensions are
+ //added again. This can happen if there is still the folder of the
+ //extension. However, there is the "removed" flag file which indicates
+ //that the extension was removed.
+ //Prepare the database entry
+ ActivePackages::Data dbData;
+ //There is no temporary folder for bundled extensions. It is therefore
+ //an empty string.
+ dbData.temporaryName = titleEncoded;
+ if (bNotBundled)
+ dbData.fileName = sExtFolder;
+ else
+ dbData.fileName = title;
+ dbData.mediaType = xPackage->getPackageType()->getMediaType();
+ dbData.version = xPackage->getVersion();
+ OSL_ENSURE(dbData.version.getLength() > 0,
+ "Extension Manager: bundled and shared extensions must have "
+ "an identifier and a version");
+
+ OUString id = dp_misc::getIdentifier( xPackage );
+ sal_Bool bAlreadyInstalled = sal_False;
+ if (xPackage->checkPrerequisites(
+ xAbortChannel, xCmdEnv, bAlreadyInstalled, m_context))
+ {
+ const ::osl::MutexGuard guard( getMutex() );
+ //access to the database must be guarded. See removePackage_
+ insertToActivationLayerDB(id, dbData);
+ }
+ else
+ {
+ //ToDo: Remember that this failed. For example, the user
+ //could have declined the license. Then the next time the
+ //extension folder is investigated we do not want to
+ //try to install the extension again.
+ }
+ addedExtensions.push_back(xPackage);
+ }
+ catch (...)
+ {
+ }
+ }
+ }
+ }
+ out_addedExtensions = ::comphelper::containerToSequence(addedExtensions);
+}
+
+void PackageManagerImpl::synchronize(
+ Sequence<Reference<deployment::XPackage> > & out_addedExtensions,
+ Sequence<Reference<deployment::XPackage> > & out_removedExtensions,
+ Reference<task::XAbortChannel> const & xAbortChannel,
+ Reference<css::ucb::XCommandEnvironment> const & xCmdEnv)
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::uno::RuntimeException)
+{
+
+ check();
+ if (m_context.equals(OUSTR("user")))
+ return;
+ synchronizeRemovedExtensions(
+ out_removedExtensions, xAbortChannel, xCmdEnv);
+ synchronizeAddedExtensions(
+ out_addedExtensions, xAbortChannel, xCmdEnv);
+}
+
//##############################################################################
diff --git a/desktop/source/deployment/manager/dp_manager.h b/desktop/source/deployment/manager/dp_manager.h
index ffa7252d7883..1249fe7e29d4 100644
--- a/desktop/source/deployment/manager/dp_manager.h
+++ b/desktop/source/deployment/manager/dp_manager.h
@@ -53,6 +53,8 @@ class PackageManagerImpl : private ::dp_misc::MutexHolder, public t_pm_helper
{
css::uno::Reference<css::uno::XComponentContext> m_xComponentContext;
::rtl::OUString m_context;
+ ::rtl::OUString m_registrationData;
+ ::rtl::OUString m_registrationData_expanded;
::rtl::OUString m_registryCache;
bool m_readOnly;
@@ -83,16 +85,20 @@ class PackageManagerImpl : private ::dp_misc::MutexHolder, public t_pm_helper
css::uno::Reference<css::deployment::XPackage> const & xPackage,
::rtl::OUString const & destFolder );
- bool checkUpdate(
- css::uno::Reference<css::deployment::XPackage> const & package,
- css::uno::Reference<css::ucb::XCommandEnvironment> const & origCmdEnv,
- css::uno::Reference<css::ucb::XCommandEnvironment> const &
- wrappedCmdEnv );
+ bool isInstalled(
+ css::uno::Reference<css::deployment::XPackage> const & package);
- bool checkInstall(
- css::uno::Reference<css::deployment::XPackage> const & package,
- css::uno::Reference<css::ucb::XCommandEnvironment> const & cmdEnv);
+ void synchronizeRemovedExtensions(
+ css::uno::Sequence<css::uno::Reference<css::deployment::XPackage> > &
+ out_removedExtensions,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv);
+ void synchronizeAddedExtensions(
+ css::uno::Sequence<css::uno::Reference<css::deployment::XPackage> > &
+ out_AddedExtensions,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv);
class CmdEnvWrapperImpl
: public ::cppu::WeakImplHelper2< css::ucb::XCommandEnvironment,
@@ -135,7 +141,7 @@ protected:
: t_pm_helper( getMutex() ),
m_xComponentContext( xComponentContext ),
m_context( context ),
- m_readOnly( false )
+ m_readOnly( true )
{}
public:
@@ -180,17 +186,15 @@ public:
css::lang::IllegalArgumentException,
css::uno::RuntimeException);
- /* Unregisters the package but does not remove it from disk.
- When the operation is canceled by the user, a CommandAbortedException
- is thrown. Then the package is still fully functional.
- @param out_oldData
- can be NULL
- */
- void removePackage_(
- ::rtl::OUString const & id, ::rtl::OUString const & fileName,
+ virtual css::uno::Reference<css::deployment::XPackage> SAL_CALL importExtension(
+ css::uno::Reference<css::deployment::XPackage> const & extension,
css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
- css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv,
- ActivePackages::Data * out_oldData);
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::lang::IllegalArgumentException,
+ css::uno::RuntimeException);
virtual void SAL_CALL removePackage(
::rtl::OUString const & id, ::rtl::OUString const & fileName,
@@ -242,6 +246,17 @@ public:
virtual ::sal_Bool SAL_CALL isReadOnly( )
throw (::com::sun::star::uno::RuntimeException);
+
+ virtual void SAL_CALL synchronize(
+ css::uno::Sequence<css::uno::Reference<css::deployment::XPackage> > & out_xAddedExtensions,
+ css::uno::Sequence<css::uno::Reference<css::deployment::XPackage> > & out_xRemovedExtensions,
+ css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
+ css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
+ throw (css::deployment::DeploymentException,
+ css::ucb::CommandFailedException,
+ css::ucb::CommandAbortedException,
+ css::uno::RuntimeException);
+
};
//______________________________________________________________________________
diff --git a/desktop/source/deployment/manager/dp_managerfac.cxx b/desktop/source/deployment/manager/dp_managerfac.cxx
index d4c9df1d57af..f6fde6b07d60 100644
--- a/desktop/source/deployment/manager/dp_managerfac.cxx
+++ b/desktop/source/deployment/manager/dp_managerfac.cxx
@@ -53,6 +53,7 @@ class PackageManagerFactoryImpl : private MutexHolder, public t_pmfac_helper
Reference<deployment::XPackageManager> m_xUserMgr;
Reference<deployment::XPackageManager> m_xSharedMgr;
+ Reference<deployment::XPackageManager> m_xBundledMgr;
typedef ::std::hash_map<
OUString, WeakReference<deployment::XPackageManager>,
::rtl::OUStringHash > t_string2weakref;
@@ -141,6 +142,7 @@ void PackageManagerFactoryImpl::disposing()
// the below are already disposed:
m_xUserMgr.clear();
m_xSharedMgr.clear();
+ m_xBundledMgr.clear();
}
// XPackageManagerFactory
@@ -172,6 +174,8 @@ PackageManagerFactoryImpl::getPackageManager( OUString const & context )
m_xUserMgr = xRet;
else if (context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("shared") ))
m_xSharedMgr = xRet;
+ else if (context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("bundled") ))
+ m_xBundledMgr = xRet;
}
else
{
diff --git a/desktop/source/deployment/manager/dp_tmprepocmdenv.cxx b/desktop/source/deployment/manager/dp_tmprepocmdenv.cxx
new file mode 100644
index 000000000000..3a4a6f1d2b72
--- /dev/null
+++ b/desktop/source/deployment/manager/dp_tmprepocmdenv.cxx
@@ -0,0 +1,166 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_desktop.hxx"
+
+#include "com/sun/star/deployment/VersionException.hpp"
+#include "com/sun/star/deployment/LicenseIndividualAgreementException.hpp"
+#include "com/sun/star/deployment/LicenseException.hpp"
+#include "com/sun/star/deployment/InstallException.hpp"
+#include "com/sun/star/task/XInteractionApprove.hpp"
+#include "com/sun/star/task/XInteractionAbort.hpp"
+#include "com/sun/star/ucb/XCommandEnvironment.hpp"
+#include "com/sun/star/uno/XComponentContext.hpp"
+#include "dp_tmprepocmdenv.hxx"
+
+namespace deployment = com::sun::star::deployment;
+namespace lang = com::sun::star::lang;
+namespace task = com::sun::star::task;
+namespace ucb = com::sun::star::ucb;
+namespace uno = com::sun::star::uno;
+namespace css = com::sun::star;
+
+#define OUSTR(s) rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(s))
+
+using ::com::sun::star::uno::Reference;
+using ::rtl::OUString;
+
+namespace dp_manager {
+
+TmpRepositoryCommandEnv::TmpRepositoryCommandEnv()
+{
+}
+
+TmpRepositoryCommandEnv::TmpRepositoryCommandEnv(
+ Reference< css::task::XInteractionHandler> const & handler)
+ : m_forwardHandler(handler)
+{
+}
+
+TmpRepositoryCommandEnv::~TmpRepositoryCommandEnv()
+{
+}
+// XCommandEnvironment
+//______________________________________________________________________________
+Reference<task::XInteractionHandler> TmpRepositoryCommandEnv::getInteractionHandler()
+throw (uno::RuntimeException)
+{
+ return this;
+}
+
+//______________________________________________________________________________
+Reference<ucb::XProgressHandler> TmpRepositoryCommandEnv::getProgressHandler()
+throw (uno::RuntimeException)
+{
+ return this;
+}
+
+// XInteractionHandler
+void TmpRepositoryCommandEnv::handle(
+ Reference< task::XInteractionRequest> const & xRequest )
+ throw (uno::RuntimeException)
+{
+ uno::Any request( xRequest->getRequest() );
+ OSL_ASSERT( request.getValueTypeClass() == uno::TypeClass_EXCEPTION );
+
+ deployment::VersionException verExc;
+ deployment::LicenseException licExc;
+ deployment::InstallException instExc;
+ deployment::LicenseIndividualAgreementException licAgreementExc;
+
+
+ bool approve = false;
+ bool abort = false;
+
+ if ((request >>= verExc)
+ || (request >>= licExc)
+ || (request >>= instExc)
+ || (request >>= licAgreementExc))
+ {
+ approve = true;
+ }
+
+ if (approve == false && abort == false)
+ {
+ if (m_forwardHandler.is())
+ m_forwardHandler->handle(xRequest);
+ else
+ approve = true;
+ }
+ else
+ {
+ // select:
+ uno::Sequence< Reference< task::XInteractionContinuation > > conts(
+ xRequest->getContinuations() );
+ Reference< task::XInteractionContinuation > const * pConts =
+ conts.getConstArray();
+ sal_Int32 len = conts.getLength();
+ for ( sal_Int32 pos = 0; pos < len; ++pos )
+ {
+ if (approve) {
+ Reference< task::XInteractionApprove > xInteractionApprove(
+ pConts[ pos ], uno::UNO_QUERY );
+ if (xInteractionApprove.is()) {
+ xInteractionApprove->select();
+ // don't query again for ongoing continuations:
+ approve = false;
+ }
+ }
+ else if (abort) {
+ Reference< task::XInteractionAbort > xInteractionAbort(
+ pConts[ pos ], uno::UNO_QUERY );
+ if (xInteractionAbort.is()) {
+ xInteractionAbort->select();
+ // don't query again for ongoing continuations:
+ abort = false;
+ }
+ }
+ }
+ }
+}
+
+// XProgressHandler
+void TmpRepositoryCommandEnv::push( uno::Any const & /*Status*/ )
+throw (uno::RuntimeException)
+{
+}
+
+
+void TmpRepositoryCommandEnv::update( uno::Any const & /*Status */)
+throw (uno::RuntimeException)
+{
+}
+
+void TmpRepositoryCommandEnv::pop() throw (uno::RuntimeException)
+{
+}
+
+
+} // namespace dp_manager
+
+
diff --git a/desktop/source/deployment/manager/dp_tmprepocmdenv.hxx b/desktop/source/deployment/manager/dp_tmprepocmdenv.hxx
new file mode 100644
index 000000000000..22111bc1e081
--- /dev/null
+++ b/desktop/source/deployment/manager/dp_tmprepocmdenv.hxx
@@ -0,0 +1,84 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+#if ! defined INCLUDED_DP_TMPREPOSITORYCOMMANDENVIRONMENT_HXX
+#define INCLUDED_DP_TMPREPOSITORYCOMMANDENVIRONMENT_HXX
+
+
+#include "cppuhelper/compbase3.hxx"
+//#include "cppuhelper/implbase2.hxx"
+#include "ucbhelper/content.hxx"
+
+
+
+namespace css = ::com::sun::star;
+
+namespace dp_manager {
+
+/**
+ This command environment is to be used when an extension is temporarily
+ stored in the "tmp" repository. It prevents all kind of user interaction.
+ */
+class TmpRepositoryCommandEnv
+ : public ::cppu::WeakImplHelper3< css::ucb::XCommandEnvironment,
+ css::task::XInteractionHandler,
+ css::ucb::XProgressHandler >
+{
+ css::uno::Reference< css::uno::XComponentContext > m_xContext;
+ css::uno::Reference< css::task::XInteractionHandler> m_forwardHandler;
+public:
+ virtual ~TmpRepositoryCommandEnv();
+ TmpRepositoryCommandEnv();
+ TmpRepositoryCommandEnv(
+ css::uno::Reference< css::task::XInteractionHandler> const & handler);
+
+ // XCommandEnvironment
+ virtual css::uno::Reference<css::task::XInteractionHandler > SAL_CALL
+ getInteractionHandler() throw (css::uno::RuntimeException);
+ virtual css::uno::Reference<css::ucb::XProgressHandler >
+ SAL_CALL getProgressHandler() throw (css::uno::RuntimeException);
+
+ // XInteractionHandler
+ virtual void SAL_CALL handle(
+ css::uno::Reference<css::task::XInteractionRequest > const & xRequest )
+ throw (css::uno::RuntimeException);
+
+ // XProgressHandler
+ virtual void SAL_CALL push( css::uno::Any const & Status )
+ throw (css::uno::RuntimeException);
+ virtual void SAL_CALL update( css::uno::Any const & Status )
+ throw (css::uno::RuntimeException);
+ virtual void SAL_CALL pop() throw (css::uno::RuntimeException);
+};
+
+}
+
+
+
+
+#endif
+
diff --git a/desktop/source/deployment/manager/makefile.mk b/desktop/source/deployment/manager/makefile.mk
index a9ff47881fc3..cb99325bde52 100644
--- a/desktop/source/deployment/manager/makefile.mk
+++ b/desktop/source/deployment/manager/makefile.mk
@@ -45,7 +45,9 @@ SLOFILES = \
$(SLO)$/dp_activepackages.obj \
$(SLO)$/dp_manager.obj \
$(SLO)$/dp_managerfac.obj \
- $(SLO)$/dp_informationprovider.obj
+ $(SLO)$/dp_informationprovider.obj \
+ $(SLO)$/dp_extensionmanager.obj \
+ $(SLO)$/dp_tmprepocmdenv.obj
.INCLUDE : ..$/target.pmk
.INCLUDE : target.mk
diff --git a/desktop/source/deployment/misc/dp_descriptioninfoset.cxx b/desktop/source/deployment/misc/dp_descriptioninfoset.cxx
index 28f45918e9e2..d97b400f4609 100644
--- a/desktop/source/deployment/misc/dp_descriptioninfoset.cxx
+++ b/desktop/source/deployment/misc/dp_descriptioninfoset.cxx
@@ -35,6 +35,7 @@
#include "comphelper/sequence.hxx"
#include "comphelper/makesequence.hxx"
+#include "comphelper/processfactory.hxx"
#include "boost/optional.hpp"
#include "com/sun/star/beans/Optional.hpp"
#include "com/sun/star/lang/XMultiComponentFactory.hpp"
@@ -47,17 +48,23 @@
#include "com/sun/star/xml/dom/DOMException.hpp"
#include "com/sun/star/xml/dom/XNode.hpp"
#include "com/sun/star/xml/dom/XNodeList.hpp"
+#include "com/sun/star/xml/dom/XDocumentBuilder.hpp"
#include "com/sun/star/xml/xpath/XXPathAPI.hpp"
+#include "com/sun/star/ucb/InteractiveAugmentedIOException.hpp"
#include "cppuhelper/implbase1.hxx"
+#include "cppuhelper/implbase2.hxx"
#include "cppuhelper/weak.hxx"
+#include "cppuhelper/exc_hlp.hxx"
#include "rtl/ustring.h"
#include "rtl/ustring.hxx"
#include "sal/types.h"
-
+#include "ucbhelper/content.hxx"
namespace {
namespace css = ::com::sun::star;
+using css::uno::Reference;
+using ::rtl::OUString;
class EmptyNodeList: public ::cppu::WeakImplHelper1< css::xml::dom::XNodeList >
{
@@ -110,10 +117,251 @@ css::uno::Reference< css::xml::dom::XNode > EmptyNodeList::item(::sal_Int32)
}
}
+/**The class uses the UCB to access the description.xml file in an
+ extension. The UCB must have been initialized already. It also
+ requires that the extension has already be unzipped to a particular
+ location.
+ */
+class ExtensionDescription
+{
+public:
+ /**throws an exception if the description.xml is not
+ available, cannot be read, does not contain the expected data,
+ or any other error occured. Therefore it shoult only be used with
+ new extensions.
+
+ Throws com::sun::star::uno::RuntimeException,
+ com::sun::star::deployment::DeploymentException,
+ dp_registry::backend::bundle::NoDescriptionException.
+ */
+ ExtensionDescription(
+ const css::uno::Reference<css::uno::XComponentContext>& xContext,
+ const ::rtl::OUString& installDir,
+ const css::uno::Reference< css::ucb::XCommandEnvironment >& xCmdEnv);
+
+ ~ExtensionDescription();
+
+ css::uno::Reference<css::xml::dom::XNode> getRootElement() const
+ {
+ return m_xRoot;
+ }
+
+ ::rtl::OUString getExtensionRootUrl() const
+ {
+ return m_sExtensionRootUrl;
+ }
+
+
+private:
+ css::uno::Reference<css::xml::dom::XNode> m_xRoot;
+ ::rtl::OUString m_sExtensionRootUrl;
+};
+
+class NoDescriptionException
+{
+};
+
+class FileDoesNotExistFilter
+ : public ::cppu::WeakImplHelper2< css::ucb::XCommandEnvironment,
+ css::task::XInteractionHandler >
+
+{
+ //css::uno::Reference<css::task::XInteractionHandler> m_xHandler;
+ bool m_bExist;
+ css::uno::Reference< css::ucb::XCommandEnvironment > m_xCommandEnv;
+
+public:
+ virtual ~FileDoesNotExistFilter();
+ FileDoesNotExistFilter(
+ const css::uno::Reference< css::ucb::XCommandEnvironment >& xCmdEnv);
+
+ bool exist();
+ // XCommandEnvironment
+ virtual css::uno::Reference<css::task::XInteractionHandler > SAL_CALL
+ getInteractionHandler() throw (css::uno::RuntimeException);
+ virtual css::uno::Reference<css::ucb::XProgressHandler >
+ SAL_CALL getProgressHandler() throw (css::uno::RuntimeException);
+
+ // XInteractionHandler
+ virtual void SAL_CALL handle(
+ css::uno::Reference<css::task::XInteractionRequest > const & xRequest )
+ throw (css::uno::RuntimeException);
+};
+
+ExtensionDescription::ExtensionDescription(
+ const Reference<css::uno::XComponentContext>& xContext,
+ const OUString& installDir,
+ const Reference< css::ucb::XCommandEnvironment >& xCmdEnv)
+{
+ try {
+ m_sExtensionRootUrl = installDir;
+ //may throw ::com::sun::star::ucb::ContentCreationException
+ //If there is no description.xml then ucb will start an interaction which
+ //brings up a dialog.We want to prevent this. Therefore we wrap the xCmdEnv
+ //and filter the respective exception out.
+ OUString sDescriptionUri(installDir + OUSTR("/description.xml"));
+ Reference<css::ucb::XCommandEnvironment> xFilter =
+ static_cast<css::ucb::XCommandEnvironment*>(
+ new FileDoesNotExistFilter(xCmdEnv));
+ ::ucbhelper::Content descContent(sDescriptionUri, xFilter);
+
+ //throws an com::sun::star::uno::Exception if the file is not available
+ Reference<css::io::XInputStream> xIn;
+ try
+ { //throws com.sun.star.ucb.InteractiveAugmentedIOException
+ xIn = descContent.openStream();
+ }
+ catch (css::uno::Exception& )
+ {
+ if ( ! static_cast<FileDoesNotExistFilter*>(xFilter.get())->exist())
+ throw NoDescriptionException();
+ throw;
+ }
+ if (!xIn.is())
+ {
+ throw css::uno::Exception(
+ OUSTR("Could not get XInputStream for description.xml of extension ") +
+ sDescriptionUri, 0);
+ }
+
+ //get root node of description.xml
+ Reference<css::xml::dom::XDocumentBuilder> xDocBuilder(
+ xContext->getServiceManager()->createInstanceWithContext(
+ OUSTR("com.sun.star.xml.dom.DocumentBuilder"),
+ xContext ), css::uno::UNO_QUERY);
+ if (!xDocBuilder.is())
+ throw css::uno::Exception(OUSTR(" Could not create service com.sun.star.xml.dom.DocumentBuilder"), 0);
+
+ if (xDocBuilder->isNamespaceAware() == sal_False)
+ {
+ throw css::uno::Exception(
+ OUSTR("Service com.sun.star.xml.dom.DocumentBuilder is not namespace aware."), 0);
+ }
+
+ Reference<css::xml::dom::XDocument> xDoc = xDocBuilder->parse(xIn);
+ if (!xDoc.is())
+ {
+ throw css::uno::Exception(sDescriptionUri + OUSTR(" contains data which cannot be parsed. "), 0);
+ }
+
+ //check for proper root element and namespace
+ Reference<css::xml::dom::XElement> xRoot = xDoc->getDocumentElement();
+ if (!xRoot.is())
+ {
+ throw css::uno::Exception(
+ sDescriptionUri + OUSTR(" contains no root element."), 0);
+ }
+
+ if ( ! xRoot->getTagName().equals(OUSTR("description")))
+ {
+ throw css::uno::Exception(
+ sDescriptionUri + OUSTR(" does not contain the root element <description>."), 0);
+ }
+
+ m_xRoot = Reference<css::xml::dom::XNode>(
+ xRoot, css::uno::UNO_QUERY_THROW);
+ OUString nsDescription = xRoot->getNamespaceURI();
+
+ //check if this namespace is supported
+ if ( ! nsDescription.equals(OUSTR("http://openoffice.org/extensions/description/2006")))
+ {
+ throw css::uno::Exception(sDescriptionUri + OUSTR(" contains a root element with an unsupported namespace. "), 0);
+ }
+ } catch (css::uno::RuntimeException &) {
+ throw;
+ } catch (css::deployment::DeploymentException &) {
+ throw;
+ } catch (css::uno::Exception & e) {
+ css::uno::Any a(cppu::getCaughtException());
+ throw css::deployment::DeploymentException(
+ e.Message, Reference< css::uno::XInterface >(), a);
+ }
+}
+
+ExtensionDescription::~ExtensionDescription()
+{
+}
+
+//======================================================================
+FileDoesNotExistFilter::FileDoesNotExistFilter(
+ const Reference< css::ucb::XCommandEnvironment >& xCmdEnv):
+ m_bExist(true), m_xCommandEnv(xCmdEnv)
+{}
+
+FileDoesNotExistFilter::~FileDoesNotExistFilter()
+{
+};
+
+bool FileDoesNotExistFilter::exist()
+{
+ return m_bExist;
+}
+ // XCommandEnvironment
+Reference<css::task::XInteractionHandler >
+ FileDoesNotExistFilter::getInteractionHandler() throw (css::uno::RuntimeException)
+{
+ return static_cast<css::task::XInteractionHandler*>(this);
+}
+
+Reference<css::ucb::XProgressHandler >
+ FileDoesNotExistFilter::getProgressHandler() throw (css::uno::RuntimeException)
+{
+ return m_xCommandEnv.is()
+ ? m_xCommandEnv->getProgressHandler()
+ : Reference<css::ucb::XProgressHandler>();
+}
+
+// XInteractionHandler
+//If the interaction was caused by a non-existing file which is specified in the ctor
+//of FileDoesNotExistFilter, then we do nothing
+void FileDoesNotExistFilter::handle(
+ Reference<css::task::XInteractionRequest > const & xRequest )
+ throw (css::uno::RuntimeException)
+{
+ css::uno::Any request( xRequest->getRequest() );
+
+ css::ucb::InteractiveAugmentedIOException ioexc;
+ if ((request>>= ioexc) && ioexc.Code == css::ucb::IOErrorCode_NOT_EXISTING )
+ {
+ m_bExist = false;
+ return;
+ }
+ Reference<css::task::XInteractionHandler> xInteraction;
+ if (m_xCommandEnv.is()) {
+ xInteraction = m_xCommandEnv->getInteractionHandler();
+ }
+ if (xInteraction.is()) {
+ xInteraction->handle(xRequest);
+ }
+}
+
}
namespace dp_misc {
+DescriptionInfoset getDescriptionInfoset(OUString const & sExtensionFolderURL)
+{
+ Reference< css::xml::dom::XNode > root;
+ Reference<css::uno::XComponentContext> context =
+ comphelper_getProcessComponentContext();
+ OSL_ASSERT(context.is());
+ try {
+ root =
+ ExtensionDescription(
+ context, sExtensionFolderURL,
+ Reference< css::ucb::XCommandEnvironment >()).
+ getRootElement();
+ } catch (NoDescriptionException &) {
+ } catch (css::deployment::DeploymentException & e) {
+ throw css::uno::RuntimeException(
+ (OUString(
+ RTL_CONSTASCII_USTRINGPARAM(
+ "com.sun.star.deployment.DeploymentException: ")) +
+ e.Message), 0);
+ }
+ return DescriptionInfoset(context, root);
+}
+
DescriptionInfoset::DescriptionInfoset(
css::uno::Reference< css::uno::XComponentContext > const & context,
css::uno::Reference< css::xml::dom::XNode > const & element):
diff --git a/desktop/source/deployment/misc/dp_misc.cxx b/desktop/source/deployment/misc/dp_misc.cxx
index 3ed2d554b59f..1f1fde7ca7bf 100644
--- a/desktop/source/deployment/misc/dp_misc.cxx
+++ b/desktop/source/deployment/misc/dp_misc.cxx
@@ -197,6 +197,19 @@ OUString makeURL( OUString const & baseURL, OUString const & relPath_ )
return buf.makeStringAndClear();
}
+OUString makeURLAppendSysPathSegment( OUString const & baseURL, OUString const & relPath_ )
+{
+ OUString segment = relPath_;
+ OSL_ASSERT(segment.indexOf(static_cast<sal_Unicode>('/')) == -1);
+
+ ::rtl::Uri::encode(
+ segment, rtl_UriCharClassPchar, rtl_UriEncodeIgnoreEscapes,
+ RTL_TEXTENCODING_UTF8);
+ return makeURL(baseURL, segment);
+}
+
+
+
//==============================================================================
OUString expandUnoRcTerm( OUString const & term_ )
{
@@ -467,4 +480,22 @@ void TRACE(::rtl::OString const & sText)
#endif
}
+bool hasExtensionRepositoryChanged(::rtl::OUString const & repository)
+{
+ if (repository.equals(OUSTR("shared")))
+ {
+ //get the extensions folder
+ OUString folder(RTL_CONSTASCII_USTRINGPARAM("BUNDLED_EXTENSIONS"));
+ ::rtl::Bootstrap::expandMacros(folder);
+ }
+ else if (repository.equals(OUSTR("bundled")))
+ {
+ }
+ else
+ throw lang::IllegalArgumentException(
+ OUSTR("Invalid repository name."), 0, 0);
+
+ return false;
+}
+
}
diff --git a/desktop/source/deployment/misc/dp_version.cxx b/desktop/source/deployment/misc/dp_version.cxx
index 1668ebe4a0b7..c0da0533b54c 100644
--- a/desktop/source/deployment/misc/dp_version.cxx
+++ b/desktop/source/deployment/misc/dp_version.cxx
@@ -70,11 +70,5 @@ namespace dp_misc {
return ::dp_misc::EQUAL;
}
-::dp_misc::Order comparePackageVersions(
- css::uno::Reference< css::deployment::XPackage > const & package1,
- css::uno::Reference< css::deployment::XPackage > const & package2)
-{
- return compareVersions(package1->getVersion(), package2->getVersion());
-}
}
diff --git a/desktop/source/deployment/misc/makefile.mk b/desktop/source/deployment/misc/makefile.mk
index e191169202fd..9a7f1d62e001 100644
--- a/desktop/source/deployment/misc/makefile.mk
+++ b/desktop/source/deployment/misc/makefile.mk
@@ -75,7 +75,8 @@ SHL1STDLIBS = \
$(TOOLSLIB) \
$(UCBHELPERLIB) \
$(UNOTOOLSLIB) \
- $(XMLSCRIPTLIB)
+ $(XMLSCRIPTLIB) \
+ $(COMPHELPERLIB)
.IF "$(GUI)"=="OS2"
SHL1IMPLIB = ideploymentmisc$(DLLPOSTFIX)
LIB1TARGET = $(SLB)$/_deplmisc.lib
diff --git a/desktop/source/deployment/registry/component/dp_compbackenddb.cxx b/desktop/source/deployment/registry/component/dp_compbackenddb.cxx
new file mode 100644
index 000000000000..edaf642a2ab1
--- /dev/null
+++ b/desktop/source/deployment/registry/component/dp_compbackenddb.cxx
@@ -0,0 +1,142 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_desktop.hxx"
+
+#include "rtl/string.h"
+#include "rtl/bootstrap.hxx"
+#include "cppuhelper/exc_hlp.hxx"
+#include "com/sun/star/uno/XComponentContext.hpp"
+#include "com/sun/star/xml/dom/XDocumentBuilder.hpp"
+#include "com/sun/star/xml/xpath/XXPathAPI.hpp"
+#include "dp_misc.h"
+
+#include "dp_compbackenddb.hxx"
+
+
+namespace css = ::com::sun::star;
+using namespace ::com::sun::star::uno;
+using ::rtl::OUString;
+
+#define EXTENSION_REG_NS "http://openoffice.org/extensionmanager/component-registry/2010"
+#define ROOT_ELEMENT_NAME "component-backend-db"
+
+namespace dp_registry {
+namespace backend {
+namespace component {
+
+ComponentBackendDb::ComponentBackendDb(
+ Reference<XComponentContext> const & xContext,
+ ::rtl::OUString const & url):BackendDb(xContext, url)
+{
+
+}
+
+OUString ComponentBackendDb::getDbNSName()
+{
+ return OUSTR(EXTENSION_REG_NS);
+}
+
+OUString ComponentBackendDb::getRootElementName()
+{
+ return OUSTR(ROOT_ELEMENT_NAME);
+}
+
+void ComponentBackendDb::addEntry(::rtl::OUString const & url, Data const & data)
+{
+ try{
+
+ Reference<css::xml::dom::XDocument> doc = getDocument();
+ Reference<css::xml::dom::XNode> root = doc->getFirstChild();
+
+#if OSL_DEBUG_LEVEL > 0
+ //There must not be yet an entry with the same url
+ OUString sExpression(
+ OUSTR("reg:component[@url = \"") + url + OUSTR("\"]"));
+ Reference<css::xml::dom::XNode> _extensionNode =
+ getXPathAPI()->selectSingleNode(root, sExpression);
+ OSL_ASSERT(! _extensionNode.is());
+#endif
+ Reference<css::xml::dom::XElement> componentElement(
+ doc->createElement(OUSTR("component")));
+
+ componentElement->setAttribute(OUSTR("url"), url);
+
+ Reference<css::xml::dom::XNode> componentNode(
+ componentElement, UNO_QUERY_THROW);
+
+ root->appendChild(componentNode);
+
+ Reference<css::xml::dom::XNode> javaTypeLibNode(
+ doc->createElement(OUSTR("java-type-library")), UNO_QUERY_THROW);
+
+ componentNode->appendChild(javaTypeLibNode);
+
+ Reference<css::xml::dom::XNode> javaTypeLibValueNode(
+ doc->createTextNode(OUString::valueOf((sal_Bool) data.javaTypeLibrary)),
+ UNO_QUERY_THROW);
+ javaTypeLibNode->appendChild(javaTypeLibValueNode);
+
+ writeSimpleList(
+ data.implementationNames,
+ OUSTR("implementation-names"),
+ OUSTR("name"),
+ componentNode);
+
+ writeVectorOfPair(
+ data.singletons,
+ OUSTR("singletons"),
+ OUSTR("item"),
+ OUSTR("key"),
+ OUSTR("value"),
+ componentNode);
+
+ save();
+ }
+ catch(css::uno::Exception &)
+ {
+ Any exc( ::cppu::getCaughtException() );
+ throw css::deployment::DeploymentException(
+ OUSTR("Extension Manager: failed to write data entry in backend db: ") +
+ m_urlDb, 0, exc);
+ }
+}
+
+void ComponentBackendDb::removeEntry(::rtl::OUString const & url)
+{
+ OUString sExpression(
+ OUSTR("reg:component[@url = \"") + url + OUSTR("\"]"));
+ removeElement(sExpression);
+}
+
+
+
+} // namespace bundle
+} // namespace backend
+} // namespace dp_registry
+
diff --git a/desktop/source/deployment/registry/component/dp_compbackenddb.hxx b/desktop/source/deployment/registry/component/dp_compbackenddb.hxx
new file mode 100644
index 000000000000..0dde24beed3f
--- /dev/null
+++ b/desktop/source/deployment/registry/component/dp_compbackenddb.hxx
@@ -0,0 +1,116 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+#if ! defined INCLUDED_DP_COMPBACKENDDB_HXX
+#define INCLUDED_DP_COMPBACKENDDB_HXX
+
+#include "rtl/ustring.hxx"
+#include "rtl/string.hxx"
+#include <vector>
+#include <list>
+#include "dp_backenddb.hxx"
+
+namespace css = ::com::sun::star;
+
+namespace com { namespace sun { namespace star {
+ namespace uno {
+ class XComponentContext;
+ }
+ namespace xml { namespace dom {
+ class XDocument;
+ class XNode;
+ }}
+ namespace xml { namespace xpath {
+ class XXPathAPI;
+ }}
+}}}
+
+namespace dp_registry {
+namespace backend {
+namespace component {
+
+/* The XML file stores the extensions which are currently registered.
+ They will be removed when they are revoked.
+ The format looks like this:
+
+<?xml version="1.0"?>
+<component-backend-db xmlns="http://openoffice.org/extensionmanager/component-registry/2010">
+ <component url="vnd.sun.star.expand:$UNO_USER_PACKAGES_CACHE/uno_packages/5CD5.tmp_/leaves1.oxt/extensionoptions.jar">
+ <java-type-library>true</java-type-library>
+ <implementation-names>
+ <name>com.sun.star.comp.extensionoptions.OptionsEventHandler$_OptionsEventHandler</name>
+ ...
+ </implementation-names>
+ <singletons>
+ <item>
+ <key>com.sun.star.java.theJavaVirtualMachine</key>
+ <value>com.sun.star.java.JavaVirtualMachine</value>
+ </item>
+ ...
+ </singletons>
+ </component>
+
+ <component ...>
+ ...
+</component-backend-db>
+ */
+class ComponentBackendDb: public dp_registry::backend::BackendDb
+{
+public:
+ struct Data
+ {
+ Data(): javaTypeLibrary(false) {};
+
+ ::std::list< ::rtl::OUString> implementationNames;
+ /* every singleton has a key and a value
+ */
+ ::std::vector< ::std::pair< ::rtl::OUString, ::rtl::OUString> >singletons;
+ bool javaTypeLibrary;
+ };
+
+public:
+
+ ComponentBackendDb( css::uno::Reference<css::uno::XComponentContext> const & xContext,
+ ::rtl::OUString const & url);
+
+ void addEntry(::rtl::OUString const & url, Data const & data);
+ void removeEntry(::rtl::OUString const & url);
+
+ virtual ::rtl::OUString getDbNSName();
+
+ virtual ::rtl::OUString getRootElementName();
+
+
+};
+
+
+
+}
+}
+}
+#endif
+
diff --git a/desktop/source/deployment/registry/component/dp_component.cxx b/desktop/source/deployment/registry/component/dp_component.cxx
index e6781e2a1746..e4e5efff9e81 100644
--- a/desktop/source/deployment/registry/component/dp_component.cxx
+++ b/desktop/source/deployment/registry/component/dp_component.cxx
@@ -58,7 +58,7 @@
#include <vector>
#include <memory>
#include <algorithm>
-
+#include "dp_compbackenddb.hxx"
using namespace ::dp_misc;
using namespace ::com::sun::star;
@@ -74,6 +74,9 @@ namespace {
typedef ::std::list<OUString> t_stringlist;
typedef ::std::vector< ::std::pair<OUString, OUString> > t_stringpairvec;
+#define IMPLEMENTATION_NAME "com.sun.star.comp.deployment.component.PackageRegistryBackend"
+inline OUString makeRcTerm( OUString const & url );
+
/** return a vector of bootstrap variables which have been provided
as command arguments.
*/
@@ -153,9 +156,9 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
::rtl::Reference<PackageRegistryBackend> const & myBackend,
OUString const & url, OUString const & name,
Reference<deployment::XPackageTypeInfo> const & xPackageType,
- OUString const & loader )
+ OUString const & loader, bool bUseDb )
: Package( myBackend, url, name, name /* display-name */,
- xPackageType ),
+ xPackageType, bUseDb ),
m_loader( loader ),
m_registered( REG_UNINIT )
{}
@@ -187,9 +190,9 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
::rtl::Reference<PackageRegistryBackend> const & myBackend,
OUString const & url, OUString const & name,
Reference<deployment::XPackageTypeInfo> const & xPackageType,
- bool jarFile )
+ bool jarFile, bool bUseDb )
: Package( myBackend, url, name, name /* display-name */,
- xPackageType ),
+ xPackageType, bUseDb),
m_jarFile( jarFile )
{}
};
@@ -212,6 +215,7 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
// PackageRegistryBackend
virtual Reference<deployment::XPackage> bindPackage_(
OUString const & url, OUString const & mediaType,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv );
virtual void SAL_CALL disposing();
@@ -230,6 +234,12 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
OUString m_commonRDB_RO;
OUString m_nativeRDB_RO;
+ std::auto_ptr<ComponentBackendDb> m_backendDb;
+
+ void addDataToDb(OUString const & url, ComponentBackendDb::Data const & data);
+ void deleteDataFromDb(OUString const & url);
+
+
//These rdbs are for writing new service entries. The rdb files are copies
//which are created when services are added or removed.
Reference<registry::XSimpleRegistry> m_xCommonRDB;
@@ -371,59 +381,59 @@ void BackendImpl::disposing()
}
}
+
void BackendImpl::initServiceRdbFiles()
{
const Reference<XCommandEnvironment> xCmdEnv;
- if (! m_readOnly)
+
+ ::ucbhelper::Content cacheDir( getCachePath(), xCmdEnv );
+ ::ucbhelper::Content oldRDB;
+ // switch common rdb:
+ if (m_commonRDB_RO.getLength() > 0)
{
- ::ucbhelper::Content cacheDir( getCachePath(), xCmdEnv );
- ::ucbhelper::Content oldRDB;
- // switch common rdb:
- if (m_commonRDB_RO.getLength() > 0)
- {
- create_ucb_content(
- &oldRDB, makeURL( getCachePath(), m_commonRDB_RO),
- xCmdEnv, false /* no throw */ );
- }
- m_commonRDB = m_commonRDB_RO.equalsAsciiL(
- RTL_CONSTASCII_STRINGPARAM("common.rdb") )
- ? OUSTR("common_.rdb") : OUSTR("common.rdb");
- if (oldRDB.get().is())
- {
- if (! cacheDir.transferContent(
+ create_ucb_content(
+ &oldRDB, makeURL( getCachePath(), m_commonRDB_RO),
+ xCmdEnv, false /* no throw */ );
+ }
+ m_commonRDB = m_commonRDB_RO.equalsAsciiL(
+ RTL_CONSTASCII_STRINGPARAM("common.rdb") )
+ ? OUSTR("common_.rdb") : OUSTR("common.rdb");
+ if (oldRDB.get().is())
+ {
+ if (! cacheDir.transferContent(
oldRDB, ::ucbhelper::InsertOperation_COPY,
m_commonRDB, NameClash::OVERWRITE ))
- {
-
- throw RuntimeException(
- OUSTR("UCB transferContent() failed!"), 0 );
- }
- oldRDB = ::ucbhelper::Content();
- }
- // switch native rdb:
- if (m_nativeRDB_RO.getLength() > 0)
{
- create_ucb_content(
- &oldRDB, makeURL(getCachePath(), m_nativeRDB_RO),
- xCmdEnv, false /* no throw */ );
+
+ throw RuntimeException(
+ OUSTR("UCB transferContent() failed!"), 0 );
}
- const OUString plt_rdb( getPlatformString() + OUSTR(".rdb") );
- const OUString plt_rdb_( getPlatformString() + OUSTR("_.rdb") );
- m_nativeRDB = m_nativeRDB_RO.equals( plt_rdb ) ? plt_rdb_ : plt_rdb;
- if (oldRDB.get().is())
- {
- if (! cacheDir.transferContent(
+ oldRDB = ::ucbhelper::Content();
+ }
+ // switch native rdb:
+ if (m_nativeRDB_RO.getLength() > 0)
+ {
+ create_ucb_content(
+ &oldRDB, makeURL(getCachePath(), m_nativeRDB_RO),
+ xCmdEnv, false /* no throw */ );
+ }
+ const OUString plt_rdb( getPlatformString() + OUSTR(".rdb") );
+ const OUString plt_rdb_( getPlatformString() + OUSTR("_.rdb") );
+ m_nativeRDB = m_nativeRDB_RO.equals( plt_rdb ) ? plt_rdb_ : plt_rdb;
+ if (oldRDB.get().is())
+ {
+ if (! cacheDir.transferContent(
oldRDB, ::ucbhelper::InsertOperation_COPY,
m_nativeRDB, NameClash::OVERWRITE ))
- throw RuntimeException(
+ throw RuntimeException(
OUSTR("UCB transferContent() failed!"), 0 );
- }
-
- // UNO is bootstrapped, flush for next process start:
- m_unorc_modified = true;
- unorc_flush( Reference<XCommandEnvironment>() );
}
+ // UNO is bootstrapped, flush for next process start:
+ m_unorc_modified = true;
+ unorc_flush( Reference<XCommandEnvironment>() );
+
+
// common rdb for java, native rdb for shared lib components
if (m_commonRDB.getLength() > 0) {
m_xCommonRDB.set(
@@ -433,7 +443,8 @@ void BackendImpl::initServiceRdbFiles()
m_xComponentContext ), UNO_QUERY_THROW );
m_xCommonRDB->open(
makeURL( expandUnoRcUrl(getCachePath()), m_commonRDB ),
- m_readOnly, !m_readOnly );
+// m_readOnly, !m_readOnly );
+ false, true);
}
if (m_nativeRDB.getLength() > 0) {
m_xNativeRDB.set(
@@ -443,7 +454,8 @@ void BackendImpl::initServiceRdbFiles()
m_xComponentContext ), UNO_QUERY_THROW );
m_xNativeRDB->open(
makeURL( expandUnoRcUrl(getCachePath()), m_nativeRDB ),
- m_readOnly, !m_readOnly );
+// m_readOnly, !m_readOnly );
+ false, true);
}
}
@@ -562,9 +574,25 @@ BackendImpl::BackendImpl(
initServiceRdbFiles_RO();
+ OUString dbFile = makeURL(getCachePath(), OUSTR("backenddb.xml"));
+ m_backendDb.reset(
+ new ComponentBackendDb(getComponentContext(), dbFile));
}
}
+void BackendImpl::addDataToDb(
+ OUString const & url, ComponentBackendDb::Data const & data)
+{
+ if (m_backendDb.get())
+ m_backendDb->addEntry(url, data);
+}
+
+void BackendImpl::deleteDataFromDb(OUString const & url)
+{
+ if (m_backendDb.get())
+ m_backendDb->removeEntry(url);
+}
+
// XPackageRegistry
//______________________________________________________________________________
Sequence< Reference<deployment::XPackageTypeInfo> >
@@ -577,6 +605,7 @@ BackendImpl::getSupportedPackageTypes() throw (RuntimeException)
//______________________________________________________________________________
Reference<deployment::XPackage> BackendImpl::bindPackage_(
OUString const & url, OUString const & mediaType_,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv )
{
OUString mediaType(mediaType_);
@@ -649,17 +678,20 @@ Reference<deployment::XPackage> BackendImpl::bindPackage_(
if (value.EqualsIgnoreCaseAscii("native")) {
return new BackendImpl::ComponentPackageImpl(
this, url, name, m_xDynComponentTypeInfo,
- OUSTR("com.sun.star.loader.SharedLibrary") );
+ OUSTR("com.sun.star.loader.SharedLibrary"),
+ bNoFileAccess );
}
if (value.EqualsIgnoreCaseAscii("Java")) {
return new BackendImpl::ComponentPackageImpl(
this, url, name, m_xJavaComponentTypeInfo,
- OUSTR("com.sun.star.loader.Java2") );
+ OUSTR("com.sun.star.loader.Java2"),
+ bNoFileAccess );
}
if (value.EqualsIgnoreCaseAscii("Python")) {
return new BackendImpl::ComponentPackageImpl(
this, url, name, m_xPythonComponentTypeInfo,
- OUSTR("com.sun.star.loader.Python") );
+ OUSTR("com.sun.star.loader.Python"),
+ bNoFileAccess);
}
}
}
@@ -675,12 +707,12 @@ Reference<deployment::XPackage> BackendImpl::bindPackage_(
{
return new BackendImpl::TypelibraryPackageImpl(
this, url, name, m_xRDBTypelibTypeInfo,
- false /* rdb */ );
+ false /* rdb */, bNoFileAccess);
}
if (value.EqualsIgnoreCaseAscii("Java")) {
return new BackendImpl::TypelibraryPackageImpl(
this, url, name, m_xJavaTypelibTypeInfo,
- true /* jar */ );
+ true /* jar */, bNoFileAccess);
}
}
}
@@ -785,18 +817,11 @@ void BackendImpl::unorc_flush( Reference<XCommandEnvironment> const & xCmdEnv )
return;
::rtl::OStringBuffer buf;
- // UNO_USER_PACKAGES_CACHE, UNO_SHARED_PACKAGES_CACHE have to be resolved
- // locally:
- if (m_eContext == CONTEXT_USER) {
- buf.append( RTL_CONSTASCII_STRINGPARAM(
- "UNO_USER_PACKAGES_CACHE=$ORIGIN/../..") );
- }
- else if (m_eContext == CONTEXT_SHARED) {
- buf.append( RTL_CONSTASCII_STRINGPARAM(
- "UNO_SHARED_PACKAGES_CACHE=$ORIGIN/../..") );
- }
- else
- OSL_ASSERT(0);
+
+ buf.append(RTL_CONSTASCII_STRINGPARAM("ORIGIN="));
+ OUString sOrigin = makeRcTerm(m_cachePath);
+ ::rtl::OString osOrigin = ::rtl::OUStringToOString(sOrigin, RTL_TEXTENCODING_UTF8);
+ buf.append(osOrigin);
buf.append(LF);
if (! m_jar_typelibs.empty())
@@ -852,6 +877,9 @@ void BackendImpl::unorc_flush( Reference<XCommandEnvironment> const & xCmdEnv )
// write native rc:
::rtl::OStringBuffer buf2;
+ buf2.append(RTL_CONSTASCII_STRINGPARAM("ORIGIN="));
+ buf2.append(osOrigin);
+ buf2.append(LF);
buf2.append( RTL_CONSTASCII_STRINGPARAM("UNO_SERVICES=?$ORIGIN/") );
buf2.append( ::rtl::OUStringToOString(
sNativeRDB, RTL_TEXTENCODING_ASCII_US ) );
@@ -886,7 +914,7 @@ void BackendImpl::unorc_flush( Reference<XCommandEnvironment> const & xCmdEnv )
inline OUString makeRcTerm( OUString const & url )
{
OSL_ASSERT( url.matchAsciiL( RTL_CONSTASCII_STRINGPARAM(
- "vnd.sun.star.expand:") ) );
+ "vnd.sun.star.expand:") ) );
if (url.matchAsciiL( RTL_CONSTASCII_STRINGPARAM("vnd.sun.star.expand:") )) {
// cut protocol:
OUString rcterm( url.copy( sizeof ("vnd.sun.star.expand:") - 1 ) );
@@ -1186,6 +1214,8 @@ void BackendImpl::ComponentPackageImpl::processPackage_(
bool isJavaTypelib = java &&
!jarManifestHeaderPresent( url, OUSTR("UNO-Type-Path"), xCmdEnv );
+ ComponentBackendDb::Data data;
+ data.javaTypeLibrary = isJavaTypelib;
if (doRegisterPackage)
{
if (! m_xRemoteContext.is()) {
@@ -1210,12 +1240,17 @@ void BackendImpl::ComponentPackageImpl::processPackage_(
//only write to unorc if registration was successful.
//It may fail if there is no suitable java.
if (isJavaTypelib)
+ {
that->addToUnoRc( java, url, xCmdEnv );
+ data.javaTypeLibrary = true;
+ }
t_stringlist implNames;
t_stringpairvec singletons;
- const Reference<loader::XImplementationLoader> xLoader(
+ const Reference<loader::XImplementationLoader> xLoader(
getComponentInfo( &implNames, &singletons, m_xRemoteContext ) );
+ data.implementationNames = implNames;
+ data.singletons = singletons;
// factories live insertion:
const Reference<container::XSet> xSet(
@@ -1280,6 +1315,7 @@ void BackendImpl::ComponentPackageImpl::processPackage_(
}
m_registered = REG_REGISTERED;
+ getMyBackend()->addDataToDb(url, data);
}
else // revokePackage()
{
@@ -1364,6 +1400,7 @@ void BackendImpl::ComponentPackageImpl::processPackage_(
}
m_registered = REG_NOT_REGISTERED;
+ getMyBackend()->deleteDataFromDb(url);
}
}
@@ -1490,7 +1527,7 @@ namespace sdecl = comphelper::service_decl;
sdecl::class_<BackendImpl, sdecl::with_args<true> > serviceBI;
extern sdecl::ServiceDecl const serviceDecl(
serviceBI,
- "com.sun.star.comp.deployment.component.PackageRegistryBackend",
+ IMPLEMENTATION_NAME,
BACKEND_SERVICE_NAME );
} // namespace component
diff --git a/desktop/source/deployment/registry/component/makefile.mk b/desktop/source/deployment/registry/component/makefile.mk
index 4c4016f9bf6c..b7ee5c203cd5 100644
--- a/desktop/source/deployment/registry/component/makefile.mk
+++ b/desktop/source/deployment/registry/component/makefile.mk
@@ -40,7 +40,8 @@ SRC1FILES = \
INCPRE += ..$/..$/inc
SLOFILES = \
- $(SLO)$/dp_component.obj
+ $(SLO)$/dp_component.obj \
+ $(SLO)$/dp_compbackenddb.obj
.INCLUDE : ..$/..$/target.pmk
.INCLUDE : target.mk
diff --git a/desktop/source/deployment/registry/configuration/dp_configuration.cxx b/desktop/source/deployment/registry/configuration/dp_configuration.cxx
index 460ba5e9fed0..7118e6d1b2d5 100644
--- a/desktop/source/deployment/registry/configuration/dp_configuration.cxx
+++ b/desktop/source/deployment/registry/configuration/dp_configuration.cxx
@@ -94,9 +94,9 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
::rtl::Reference<PackageRegistryBackend> const & myBackend,
OUString const & url, OUString const & name,
Reference<deployment::XPackageTypeInfo> const & xPackageType,
- bool isSchema )
+ bool isSchema, bool bUseDb)
: Package( myBackend, url, name, name /* display-name */,
- xPackageType ),
+ xPackageType, bUseDb),
m_isSchema( isSchema )
{}
};
@@ -113,7 +113,7 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
// PackageRegistryBackend
virtual Reference<deployment::XPackage> bindPackage_(
- OUString const & url, OUString const & mediaType,
+ OUString const & url, OUString const & mediaType, sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv );
::std::auto_ptr<PersistentMap> m_registeredPackages;
@@ -199,7 +199,7 @@ BackendImpl::BackendImpl(
m_registeredPackages.reset(
new PersistentMap(
makeURL( getCachePath(), OUSTR("registered_packages.db") ),
- m_readOnly ) );
+ false ) );
}
}
@@ -215,6 +215,7 @@ BackendImpl::getSupportedPackageTypes() throw (RuntimeException)
//______________________________________________________________________________
Reference<deployment::XPackage> BackendImpl::bindPackage_(
OUString const & url, OUString const & mediaType_,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv )
{
OUString mediaType( mediaType_ );
@@ -255,14 +256,14 @@ Reference<deployment::XPackage> BackendImpl::bindPackage_(
return new PackageImpl(
this, url, ucbContent.getPropertyValue(
StrTitle::get() ).get<OUString>(),
- m_xConfDataTypeInfo, false /* data file */ );
+ m_xConfDataTypeInfo, false /* data file */, bNoFileAccess);
}
else if (subType.EqualsIgnoreCaseAscii(
"vnd.sun.star.configuration-schema")) {
return new PackageImpl(
this, url, ucbContent.getPropertyValue(
StrTitle::get() ).get<OUString>(),
- m_xConfSchemaTypeInfo, true /* schema file */ );
+ m_xConfSchemaTypeInfo, true /* schema file */, bNoFileAccess);
}
}
}
diff --git a/desktop/source/deployment/registry/dp_backend.cxx b/desktop/source/deployment/registry/dp_backend.cxx
index c06b30be1669..31bb30de7315 100644
--- a/desktop/source/deployment/registry/dp_backend.cxx
+++ b/desktop/source/deployment/registry/dp_backend.cxx
@@ -88,6 +88,10 @@ PackageRegistryBackend::PackageRegistryBackend(
m_eContext = CONTEXT_USER;
else if (m_context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("shared") ))
m_eContext = CONTEXT_SHARED;
+ else if (m_context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("bundled") ))
+ m_eContext = CONTEXT_BUNDLED;
+ else if (m_context.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("tmp") ))
+ m_eContext = CONTEXT_TMP;
else if (m_context.matchIgnoreAsciiCaseAsciiL(
RTL_CONSTASCII_STRINGPARAM("vnd.sun.star.tdoc:/") ))
m_eContext = CONTEXT_DOCUMENT;
@@ -127,24 +131,29 @@ void PackageRegistryBackend::disposing()
// XPackageRegistry
//______________________________________________________________________________
Reference<deployment::XPackage> PackageRegistryBackend::bindPackage(
- OUString const & url, OUString const & mediaType,
+ OUString const & url, OUString const & mediaType, sal_Bool bNoFileAccess ,
Reference<XCommandEnvironment> const & xCmdEnv )
throw (deployment::DeploymentException, CommandFailedException,
lang::IllegalArgumentException, RuntimeException)
{
::osl::ResettableMutexGuard guard( getMutex() );
check();
- t_string2ref::const_iterator const iFind( m_bound.find( url ) );
- if (iFind != m_bound.end()) {
- Reference<deployment::XPackage> xPackage( iFind->second );
- if (xPackage.is())
- return xPackage;
+ if (!bNoFileAccess)
+ {
+ //We only save those object which were created with bNoFileAccess = false
+ t_string2ref::const_iterator const iFind( m_bound.find( url ) );
+ if (iFind != m_bound.end())
+ {
+ Reference<deployment::XPackage> xPackage( iFind->second );
+ if (xPackage.is())
+ return xPackage;
+ }
}
guard.clear();
Reference<deployment::XPackage> xNewPackage;
try {
- xNewPackage = bindPackage_( url, mediaType, xCmdEnv );
+ xNewPackage = bindPackage_( url, mediaType, bNoFileAccess, xCmdEnv );
}
catch (RuntimeException &) {
throw;
@@ -166,19 +175,23 @@ Reference<deployment::XPackage> PackageRegistryBackend::bindPackage(
}
guard.reset();
- ::std::pair< t_string2ref::iterator, bool > insertion(
- m_bound.insert( t_string2ref::value_type( url, xNewPackage ) ) );
- if (insertion.second)
- { // first insertion
- OSL_ASSERT( Reference<XInterface>(insertion.first->second)
- == xNewPackage );
- }
- else
- { // found existing entry
- Reference<deployment::XPackage> xPackage( insertion.first->second );
- if (xPackage.is())
- return xPackage;
- insertion.first->second = xNewPackage;
+ if (!bNoFileAccess)
+ {
+ //We only save those object which were created with bNoFileAccess = false
+ ::std::pair< t_string2ref::iterator, bool > insertion(
+ m_bound.insert( t_string2ref::value_type( url, xNewPackage ) ) );
+ if (insertion.second)
+ { // first insertion
+ OSL_ASSERT( Reference<XInterface>(insertion.first->second)
+ == xNewPackage );
+ }
+ else
+ { // found existing entry
+ Reference<deployment::XPackage> xPackage( insertion.first->second );
+ if (xPackage.is())
+ return xPackage;
+ insertion.first->second = xNewPackage;
+ }
}
guard.clear();
xNewPackage->addEventListener( this ); // listen for disposing events
@@ -197,13 +210,15 @@ Package::Package( ::rtl::Reference<PackageRegistryBackend> const & myBackend,
OUString const & url,
OUString const & name,
OUString const & displayName,
- Reference<deployment::XPackageTypeInfo> const & xPackageType )
+ Reference<deployment::XPackageTypeInfo> const & xPackageType,
+ bool bUseDb)
: t_PackageBase( getMutex() ),
m_myBackend( myBackend ),
m_url( url ),
m_name( name ),
m_displayName( displayName ),
- m_xPackageType( xPackageType )
+ m_xPackageType( xPackageType ),
+ m_bUseDb(bUseDb)
{
}
@@ -542,7 +557,29 @@ void Package::revokePackage(
lang::IllegalArgumentException, RuntimeException)
{
processPackage_impl( false /* revoke */, xAbortChannel, xCmdEnv );
+
+}
+
+PackageRegistryBackend * Package::getMyBackend() const
+{
+ PackageRegistryBackend * pBackend = m_myBackend.get();
+ if (NULL == pBackend)
+ {
+ //May throw a DisposedException
+ check();
+ //We should never get here...
+ throw RuntimeException(
+ OUSTR("Failed to get the BackendImpl"),
+ static_cast<OWeakObject*>(const_cast<Package *>(this)));
+ }
+ return pBackend;
}
+OUString Package::getRepositoryName()
+ throw (RuntimeException)
+{
+ PackageRegistryBackend * backEnd = getMyBackend();
+ return backEnd->getContext();
+ }
//##############################################################################
diff --git a/desktop/source/deployment/registry/dp_backenddb.cxx b/desktop/source/deployment/registry/dp_backenddb.cxx
new file mode 100644
index 000000000000..fb0b99c3363c
--- /dev/null
+++ b/desktop/source/deployment/registry/dp_backenddb.cxx
@@ -0,0 +1,332 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_desktop.hxx"
+
+#include "rtl/string.h"
+#include "rtl/strbuf.hxx"
+#include "rtl/bootstrap.hxx"
+#include "cppuhelper/exc_hlp.hxx"
+#include "osl/file.hxx"
+#include "com/sun/star/uno/XComponentContext.hpp"
+#include "com/sun/star/xml/dom/XDocumentBuilder.hpp"
+#include "com/sun/star/xml/xpath/XXPathAPI.hpp"
+#include "com/sun/star/io/XActiveDataSource.hpp"
+#include "com/sun/star/io/XActiveDataControl.hpp"
+#include "dp_ucb.h"
+#include "dp_misc.h"
+#include "ucbhelper/content.hxx"
+#include "xmlscript/xml_helper.hxx"
+#include "dp_backenddb.hxx"
+
+
+namespace css = ::com::sun::star;
+using namespace ::com::sun::star::uno;
+using ::rtl::OUString;
+
+
+namespace dp_registry {
+namespace backend {
+
+BackendDb::BackendDb(
+ Reference<css::uno::XComponentContext> const & xContext,
+ ::rtl::OUString const & url):
+ m_xContext(xContext)
+{
+ m_urlDb = dp_misc::expandUnoRcUrl(url);
+}
+
+void BackendDb::save()
+{
+ Reference<css::io::XActiveDataSource> xDataSource(m_doc,css::uno::UNO_QUERY_THROW);
+ ::rtl::ByteSequence bytes;
+ xDataSource->setOutputStream(::xmlscript::createOutputStream(&bytes));
+ Reference<css::io::XActiveDataControl> xDataControl(m_doc,css::uno::UNO_QUERY_THROW);
+ xDataControl->start();
+
+ Reference<css::io::XInputStream> xData(
+ ::xmlscript::createInputStream(bytes));
+ ::ucbhelper::Content ucbDb(m_urlDb, 0);
+ ucbDb.writeStream(xData, true /*replace existing*/);
+}
+
+css::uno::Reference<css::xml::dom::XDocument> BackendDb::getDocument()
+{
+ if (!m_doc.is())
+ {
+ Reference<css::xml::dom::XDocumentBuilder> xDocBuilder(
+ m_xContext->getServiceManager()->createInstanceWithContext(
+ OUSTR("com.sun.star.xml.dom.DocumentBuilder"),
+ m_xContext ), css::uno::UNO_QUERY);
+ if (!xDocBuilder.is())
+ throw css::uno::RuntimeException(
+ OUSTR(" Could not create service com.sun.star.xml.dom.DocumentBuilder"), 0);
+
+ ::osl::DirectoryItem item;
+ ::osl::File::RC err = ::osl::DirectoryItem::get(m_urlDb, item);
+ if (err == ::osl::File::E_None)
+ {
+ m_doc = xDocBuilder->parseURI(m_urlDb);
+ }
+ else if (err == ::osl::File::E_NOENT)
+ {
+ //Create a new document and insert some basic stuff
+ m_doc = xDocBuilder->newDocument();
+ Reference<css::xml::dom::XElement> rootNode =
+ m_doc->createElement(getRootElementName());
+ rootNode->setAttribute(
+ OUSTR("xmlns"), getDbNSName());
+ m_doc->appendChild(Reference<css::xml::dom::XNode>(
+ rootNode, UNO_QUERY_THROW));
+ save();
+ }
+ else
+ throw css::uno::RuntimeException(
+ OUSTR("Extension manager could not access database file:" )
+ + m_urlDb, 0);
+
+ if (!m_doc.is())
+ throw css::uno::RuntimeException(
+ OUSTR("Extension manager could not get root node of data base file: ")
+ + m_urlDb, 0);
+ }
+
+ return m_doc;
+}
+
+Reference<css::xml::xpath::XXPathAPI> BackendDb::getXPathAPI()
+{
+ if (!m_xpathApi.is())
+ {
+ m_xpathApi = Reference< css::xml::xpath::XXPathAPI >(
+ m_xContext->getServiceManager()->createInstanceWithContext(
+ OUSTR("com.sun.star.xml.xpath.XPathAPI"),
+ m_xContext), css::uno::UNO_QUERY);
+
+ if (!m_xpathApi.is())
+ throw css::uno::RuntimeException(
+ OUSTR(" Could not create service com.sun.star.xml.xpath.XPathAPI"), 0);
+
+ m_xpathApi->registerNS(
+ OUSTR("reg"), getDbNSName());
+ }
+
+ return m_xpathApi;
+}
+
+// OUString BackendDb::getDbNSName()
+// {
+// return OUString();
+// }
+
+
+// OUString BackendDb::getRootElementName()
+// {
+// return OUString();
+// }
+
+void BackendDb::removeElement(::rtl::OUString const & sXPathExpression)
+{
+ try
+ {
+ Reference<css::xml::dom::XDocument> doc = getDocument();
+ Reference<css::xml::dom::XNode> root = doc->getFirstChild();
+ Reference<css::xml::xpath::XXPathAPI> xpathApi = getXPathAPI();
+ //find the extension element that is to be removed
+ Reference<css::xml::dom::XNode> aNode =
+ xpathApi->selectSingleNode(root, sXPathExpression);
+ OSL_ASSERT(aNode.is());
+ if (aNode.is())
+ {
+ root->removeChild(aNode);
+ save();
+ }
+
+#if OSL_DEBUG_LEVEL > 0
+ //There must not be any other entry with the same url
+ Reference<css::xml::dom::XNode> nextNode =
+ xpathApi->selectSingleNode(root, sXPathExpression);
+ OSL_ASSERT(! nextNode.is());
+#endif
+ }
+ catch(css::uno::Exception &)
+ {
+ Any exc( ::cppu::getCaughtException() );
+ throw css::deployment::DeploymentException(
+ OUSTR("Extension Manager: failed to write data entry in backend db: ") +
+ m_urlDb, 0, exc);
+ }
+
+}
+
+void BackendDb::writeVectorOfPair(
+ ::std::vector< ::std::pair< ::rtl::OUString, ::rtl::OUString > > const & vecPairs,
+ OUString const & sVectorTagName,
+ OUString const & sPairTagName,
+ OUString const & sFirstTagName,
+ OUString const & sSecondTagName,
+ css::uno::Reference<css::xml::dom::XNode> const & xParent)
+{
+ try{
+
+ Reference<css::xml::dom::XDocument> doc = getDocument();
+ Reference<css::xml::dom::XNode> root = doc->getFirstChild();
+
+ Reference<css::xml::dom::XElement> vectorNode(
+ doc->createElement(sVectorTagName));
+
+ xParent->appendChild(
+ Reference<css::xml::dom::XNode>(
+ vectorNode, css::uno::UNO_QUERY_THROW));
+ typedef ::std::vector< ::std::pair< OUString, OUString > >::const_iterator CIT;
+ for (CIT i = vecPairs.begin(); i != vecPairs.end(); i++)
+ {
+ Reference<css::xml::dom::XElement> pairNode(
+ doc->createElement(sPairTagName));
+
+ vectorNode->appendChild(
+ Reference<css::xml::dom::XNode>(
+ pairNode, css::uno::UNO_QUERY_THROW));
+
+ Reference<css::xml::dom::XElement> firstNode(
+ doc->createElement(sFirstTagName));
+
+ pairNode->appendChild(
+ Reference<css::xml::dom::XNode>(
+ firstNode, css::uno::UNO_QUERY_THROW));
+
+ Reference<css::xml::dom::XText> firstTextNode(
+ doc->createTextNode( i->first));
+
+ firstNode->appendChild(
+ Reference<css::xml::dom::XNode>(
+ firstTextNode, css::uno::UNO_QUERY_THROW));
+
+ Reference<css::xml::dom::XElement> secondNode(
+ doc->createElement(sSecondTagName));
+
+ pairNode->appendChild(
+ Reference<css::xml::dom::XNode>(
+ secondNode, css::uno::UNO_QUERY_THROW));
+
+ Reference<css::xml::dom::XText> secondTextNode(
+ doc->createTextNode( i->second));
+
+ secondNode->appendChild(
+ Reference<css::xml::dom::XNode>(
+ secondTextNode, css::uno::UNO_QUERY_THROW));
+ }
+ }
+ catch(css::uno::Exception &)
+ {
+ Any exc( ::cppu::getCaughtException() );
+ throw css::deployment::DeploymentException(
+ OUSTR("Extension Manager: failed to write data entry in backend db: ") +
+ m_urlDb, 0, exc);
+ }
+}
+
+::std::vector< ::std::pair< OUString, OUString > >
+BackendDb::readVectorOfPair(
+ Reference<css::xml::dom::XNode> const & parent,
+ OUString const & sListTagName,
+ OUString const & sPairTagName,
+ OUString const & sFirstTagName,
+ OUString const & sSecondTagName)
+{
+ OSL_ASSERT(parent.is());
+ Reference<css::xml::xpath::XXPathAPI> xpathApi = getXPathAPI();
+ OUString sExprPairs(
+ sListTagName + OUSTR("/") + sPairTagName);
+ Reference<css::xml::dom::XNodeList> listPairs =
+ xpathApi->selectNodeList(parent, sExprPairs);
+
+ ::std::vector< ::std::pair< OUString, OUString > > retVector;
+ sal_Int32 length = listPairs->getLength();
+ for (sal_Int32 i = 0; i < length; i++)
+ {
+ Reference<css::xml::dom::XNode> aPair = listPairs->item(i);
+ OUString sExprFirst(sFirstTagName + OUSTR("/text()"));
+ Reference<css::xml::dom::XNode> first =
+ xpathApi->selectSingleNode(aPair, sExprFirst);
+
+ OUString sExprSecond(sSecondTagName + OUSTR("/text()"));
+ Reference<css::xml::dom::XNode> second =
+ xpathApi->selectSingleNode(aPair, sExprSecond);
+ OSL_ASSERT(first.is() && second.is());
+
+ retVector.push_back(::std::make_pair(
+ first->getNodeValue(), second->getNodeValue()));
+ }
+ return retVector;
+}
+
+void BackendDb::writeSimpleList(
+ ::std::list< ::rtl::OUString> const & list,
+ OUString const & sListTagName,
+ OUString const & sMemberTagName,
+ Reference<css::xml::dom::XNode> const & xParent)
+{
+ try
+ {
+ Reference<css::xml::dom::XDocument> doc = getDocument();
+
+ Reference<css::xml::dom::XElement> listNode(
+ doc->createElement(sListTagName));
+
+ xParent->appendChild(
+ Reference<css::xml::dom::XNode>(
+ listNode, css::uno::UNO_QUERY_THROW));
+
+ typedef ::std::list<OUString>::const_iterator ITC_ITEMS;
+ for (ITC_ITEMS i = list.begin(); i != list.end(); i++)
+ {
+ Reference<css::xml::dom::XNode> memberNode(
+ doc->createElement(sMemberTagName), css::uno::UNO_QUERY_THROW);
+
+ listNode->appendChild(memberNode);
+
+ Reference<css::xml::dom::XNode> textNode(
+ doc->createTextNode( *i), css::uno::UNO_QUERY_THROW);
+
+ memberNode->appendChild(textNode);
+ }
+ }
+ catch(css::uno::Exception &)
+ {
+ Any exc( ::cppu::getCaughtException() );
+ throw css::deployment::DeploymentException(
+ OUSTR("Extension Manager: failed to write data entry in backend db: ") +
+ m_urlDb, 0, exc);
+ }
+
+}
+
+} // namespace backend
+} // namespace dp_registry
+
diff --git a/desktop/source/deployment/registry/dp_registry.cxx b/desktop/source/deployment/registry/dp_registry.cxx
index c56131a1015c..9ea13ad2c91f 100644
--- a/desktop/source/deployment/registry/dp_registry.cxx
+++ b/desktop/source/deployment/registry/dp_registry.cxx
@@ -126,7 +126,7 @@ public:
// XPackageRegistry
virtual Reference<deployment::XPackage> SAL_CALL bindPackage(
- OUString const & url, OUString const & mediaType,
+ OUString const & url, OUString const & mediaType, sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv )
throw (deployment::DeploymentException, CommandFailedException,
lang::IllegalArgumentException, RuntimeException);
@@ -361,9 +361,24 @@ Reference<deployment::XPackageRegistry> PackageRegistryImpl::create(
// Always register as last, because we want to add extensions also as folders
// and as a default we accept every folder, which was not recognized by the other
// backends.
- that->insertBackend(
+ Reference<deployment::XPackageRegistry> extensionBackend =
::dp_registry::backend::bundle::create(
- that, context, cachePath, readOnly, xComponentContext ) );
+ that, context, cachePath, readOnly, xComponentContext);
+ that->insertBackend(extensionBackend);
+
+ Reference<lang::XServiceInfo> xServiceInfo(
+ extensionBackend, UNO_QUERY_THROW );
+
+ OSL_ASSERT(xServiceInfo.is());
+ OUString registryCachePath(
+ makeURL( cachePath,
+ ::rtl::Uri::encode(
+ xServiceInfo->getImplementationName(),
+ rtl_UriCharClassPchar,
+ rtl_UriEncodeIgnoreEscapes,
+ RTL_TEXTENCODING_UTF8 ) ) );
+ create_folder( 0, registryCachePath, Reference<XCommandEnvironment>());
+
#if OSL_DEBUG_LEVEL > 1
// dump tables:
@@ -443,7 +458,7 @@ void PackageRegistryImpl::update() throw (RuntimeException)
// XPackageRegistry
//______________________________________________________________________________
Reference<deployment::XPackage> PackageRegistryImpl::bindPackage(
- OUString const & url, OUString const & mediaType_,
+ OUString const & url, OUString const & mediaType_, sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv )
throw (deployment::DeploymentException, CommandFailedException,
lang::IllegalArgumentException, RuntimeException)
@@ -482,7 +497,7 @@ Reference<deployment::XPackage> PackageRegistryImpl::bindPackage(
for ( ; iPos != iEnd; ++iPos )
{
try {
- return (*iPos)->bindPackage( url, mediaType, xCmdEnv );
+ return (*iPos)->bindPackage( url, mediaType, bNoFileAccess, xCmdEnv );
}
catch (lang::IllegalArgumentException &) {
}
@@ -511,7 +526,7 @@ Reference<deployment::XPackage> PackageRegistryImpl::bindPackage(
getResourceString(RID_STR_UNSUPPORTED_MEDIA_TYPE) + mediaType,
static_cast<OWeakObject *>(this), static_cast<sal_Int16>(-1) );
}
- return iFind->second->bindPackage( url, mediaType, xCmdEnv );
+ return iFind->second->bindPackage( url, mediaType, bNoFileAccess, xCmdEnv );
}
}
diff --git a/desktop/source/deployment/registry/executable/dp_executable.cxx b/desktop/source/deployment/registry/executable/dp_executable.cxx
index 8c95d5874b4c..a5fe1b99746f 100644
--- a/desktop/source/deployment/registry/executable/dp_executable.cxx
+++ b/desktop/source/deployment/registry/executable/dp_executable.cxx
@@ -72,9 +72,9 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
inline ExecutablePackageImpl(
::rtl::Reference<PackageRegistryBackend> const & myBackend,
OUString const & url, OUString const & name,
- Reference<deployment::XPackageTypeInfo> const & xPackageType)
+ Reference<deployment::XPackageTypeInfo> const & xPackageType, bool bUseDb)
: Package( myBackend, url, name, name /* display-name */,
- xPackageType ) //,
+ xPackageType, bUseDb) //,
{}
};
friend class ExecutablePackageImpl;
@@ -84,7 +84,7 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
// PackageRegistryBackend
virtual Reference<deployment::XPackage> bindPackage_(
- OUString const & url, OUString const & mediaType,
+ OUString const & url, OUString const & mediaType, sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv );
Reference<deployment::XPackageTypeInfo> m_xExecutableTypeInfo;
@@ -125,7 +125,7 @@ BackendImpl::getSupportedPackageTypes() throw (RuntimeException)
// PackageRegistryBackend
Reference<deployment::XPackage> BackendImpl::bindPackage_(
- OUString const & url, OUString const & mediaType,
+ OUString const & url, OUString const & mediaType, sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv )
{
if (mediaType.getLength() == 0)
@@ -147,7 +147,7 @@ Reference<deployment::XPackage> BackendImpl::bindPackage_(
if (subType.EqualsIgnoreCaseAscii("vnd.sun.star.executable"))
{
return new BackendImpl::ExecutablePackageImpl(
- this, url, name, m_xExecutableTypeInfo);
+ this, url, name, m_xExecutableTypeInfo, bNoFileAccess);
}
}
}
diff --git a/desktop/source/deployment/registry/help/dp_help.cxx b/desktop/source/deployment/registry/help/dp_help.cxx
index 2b0d91250e4a..05ff8dda0e01 100644
--- a/desktop/source/deployment/registry/help/dp_help.cxx
+++ b/desktop/source/deployment/registry/help/dp_help.cxx
@@ -78,8 +78,9 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
inline PackageImpl(
::rtl::Reference<PackageRegistryBackend> const & myBackend,
OUString const & url, OUString const & name,
- Reference<deployment::XPackageTypeInfo> const & xPackageType )
- : Package( myBackend, url, name, name, xPackageType )
+ Reference<deployment::XPackageTypeInfo> const & xPackageType,
+ bool bUseDb)
+ : Package( myBackend, url, name, name, xPackageType, bUseDb)
{}
};
friend class PackageImpl;
@@ -87,6 +88,7 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
// PackageRegistryBackend
virtual Reference<deployment::XPackage> bindPackage_(
OUString const & url, OUString const & mediaType,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv );
void implProcessHelp( Reference< deployment::XPackage > xPackage, bool doRegisterPackage );
@@ -138,6 +140,7 @@ BackendImpl::getSupportedPackageTypes() throw (RuntimeException)
//______________________________________________________________________________
Reference<deployment::XPackage> BackendImpl::bindPackage_(
OUString const & url, OUString const & mediaType_,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv )
{
// we don't support auto detection:
@@ -156,8 +159,10 @@ Reference<deployment::XPackage> BackendImpl::bindPackage_(
if (subType.EqualsIgnoreCaseAscii(
"vnd.sun.star.help"))
{
- return new PackageImpl( this, url,
- ucbContent.getPropertyValue( StrTitle::get() ).get<OUString>(), m_xHelpTypeInfo );
+ return new PackageImpl(
+ this, url,
+ ucbContent.getPropertyValue( StrTitle::get() ).get<OUString>(),
+ m_xHelpTypeInfo, bNoFileAccess);
}
}
}
diff --git a/desktop/source/deployment/registry/inc/dp_backend.h b/desktop/source/deployment/registry/inc/dp_backend.h
index fe52c8ffc7e3..09b25caedc2b 100644
--- a/desktop/source/deployment/registry/inc/dp_backend.h
+++ b/desktop/source/deployment/registry/inc/dp_backend.h
@@ -62,6 +62,7 @@ typedef ::cppu::WeakComponentImplHelper1<
//==============================================================================
class Package : protected ::dp_misc::MutexHolder, public t_PackageBase
{
+ PackageRegistryBackend * getMyBackend() const;
void processPackage_impl(
bool registerPackage,
css::uno::Reference<css::task::XAbortChannel> const & xAbortChannel,
@@ -73,6 +74,7 @@ protected:
::rtl::OUString m_name;
::rtl::OUString m_displayName;
const css::uno::Reference<css::deployment::XPackageTypeInfo> m_xPackageType;
+ const bool m_bUseDb;
void check() const;
void fireModified();
@@ -101,7 +103,8 @@ protected:
::rtl::OUString const & name,
::rtl::OUString const & displayName,
css::uno::Reference<css::deployment::XPackageTypeInfo> const &
- xPackageType );
+ xPackageType,
+ bool bUseDb);
public:
@@ -233,6 +236,9 @@ public:
css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
throw (css::ucb::CommandFailedException,
css::ucb::CommandAbortedException, css::uno::RuntimeException);
+
+ virtual ::rtl::OUString SAL_CALL getRepositoryName()
+ throw (css::uno::RuntimeException);
};
typedef ::cppu::WeakComponentImplHelper2<
@@ -243,7 +249,6 @@ typedef ::cppu::WeakComponentImplHelper2<
class PackageRegistryBackend
: protected ::dp_misc::MutexHolder, public t_BackendBase
{
- ::rtl::OUString m_cachePath;
//The map held originally WeakReferences. The map entries are removed in the disposing
//function, which is called when the XPackages are destructed or they are
//explicitely disposed. The latter happens, for example, when a extension is
@@ -257,13 +262,14 @@ class PackageRegistryBackend
t_string2ref m_bound;
protected:
+ ::rtl::OUString m_cachePath;
css::uno::Reference<css::uno::XComponentContext> m_xComponentContext;
::rtl::OUString m_context;
// currently only for library containers:
enum context {
CONTEXT_UNKNOWN,
- CONTEXT_USER, CONTEXT_SHARED,
+ CONTEXT_USER, CONTEXT_SHARED,CONTEXT_BUNDLED, CONTEXT_TMP,
CONTEXT_DOCUMENT
} m_eContext;
bool m_readOnly;
@@ -276,6 +282,7 @@ protected:
// @@@ to be implemented by specific backend:
virtual css::uno::Reference<css::deployment::XPackage> bindPackage_(
::rtl::OUString const & url, ::rtl::OUString const & mediaType,
+ sal_Bool bNoFileAccess,
css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
= 0;
@@ -299,6 +306,8 @@ public:
inline ::rtl::OUString const & getCachePath() const { return m_cachePath; }
inline bool transientMode() const { return m_cachePath.getLength() == 0; }
+ inline ::rtl::OUString getContext() const {return m_context; }
+
// XEventListener
virtual void SAL_CALL disposing( css::lang::EventObject const & evt )
throw (css::uno::RuntimeException);
@@ -306,6 +315,7 @@ public:
// XPackageRegistry
virtual css::uno::Reference<css::deployment::XPackage> SAL_CALL bindPackage(
::rtl::OUString const & url, ::rtl::OUString const & mediaType,
+ sal_Bool bNoFileAccess,
css::uno::Reference<css::ucb::XCommandEnvironment> const & xCmdEnv )
throw (css::deployment::DeploymentException,
css::ucb::CommandFailedException,
diff --git a/desktop/source/deployment/registry/inc/dp_backenddb.hxx b/desktop/source/deployment/registry/inc/dp_backenddb.hxx
new file mode 100644
index 000000000000..3005ffcafb5b
--- /dev/null
+++ b/desktop/source/deployment/registry/inc/dp_backenddb.hxx
@@ -0,0 +1,121 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+#if ! defined INCLUDED_DP_BACKENDDB_HXX
+#define INCLUDED_DP_BACKENDDB_HXX
+
+#include "rtl/ustring.hxx"
+#include <list>
+
+namespace css = ::com::sun::star;
+
+namespace com { namespace sun { namespace star {
+ namespace uno {
+ class XComponentContext;
+ }
+ namespace xml { namespace dom {
+ class XDocument;
+ class XNode;
+ }}
+ namespace xml { namespace xpath {
+ class XXPathAPI;
+ }}
+}}}
+
+namespace dp_registry {
+namespace backend {
+
+class BackendDb
+{
+private:
+
+ css::uno::Reference<css::xml::dom::XDocument> m_doc;
+ css::uno::Reference<css::xml::xpath::XXPathAPI> m_xpathApi;
+
+ BackendDb(BackendDb const &);
+ BackendDb & operator = (BackendDb const &);
+
+protected:
+ const css::uno::Reference<css::uno::XComponentContext> m_xContext;
+ ::rtl::OUString m_urlDb;
+
+protected:
+
+ /* caller must make sure that only one thread accesses the function
+ */
+ css::uno::Reference<css::xml::dom::XDocument> getDocument();
+
+ /* the namespace prefix is "reg" (without quotes)
+ */
+ css::uno::Reference<css::xml::xpath::XXPathAPI> getXPathAPI();
+ void save();
+ void removeElement(::rtl::OUString const & sXPathExpression);
+
+ void writeSimpleList(
+ ::std::list< ::rtl::OUString> const & list,
+ ::rtl::OUString const & sListTagName,
+ ::rtl::OUString const & sMemberTagName,
+ css::uno::Reference<css::xml::dom::XNode> const & xParent);
+
+ void writeVectorOfPair(
+ ::std::vector< ::std::pair< ::rtl::OUString, ::rtl::OUString > > const & vecPairs,
+ ::rtl::OUString const & sVectorTagName,
+ ::rtl::OUString const & sPairTagName,
+ ::rtl::OUString const & sFirstTagName,
+ ::rtl::OUString const & sSecondTagName,
+ css::uno::Reference<css::xml::dom::XNode> const & xParent);
+
+ ::std::vector< ::std::pair< ::rtl::OUString, ::rtl::OUString > >
+ readVectorOfPair(
+ css::uno::Reference<css::xml::dom::XNode> const & parent,
+ ::rtl::OUString const & sListTagName,
+ ::rtl::OUString const & sPairTagName,
+ ::rtl::OUString const & sFirstTagName,
+ ::rtl::OUString const & sSecondTagName);
+
+
+
+ /* returns the namespace which is to be written as xmlns attribute
+ into the root element.
+ */
+ virtual ::rtl::OUString getDbNSName()=0;
+ /* returns the name of the root element without any namespace prefix.
+ */
+ virtual ::rtl::OUString getRootElementName()=0;
+
+
+public:
+ BackendDb(css::uno::Reference<css::uno::XComponentContext> const & xContext,
+ ::rtl::OUString const & url);
+ virtual ~BackendDb() {};
+
+};
+
+}
+}
+#endif
+
diff --git a/desktop/source/deployment/registry/makefile.mk b/desktop/source/deployment/registry/makefile.mk
index de0e943654d9..e45cec272ca7 100644
--- a/desktop/source/deployment/registry/makefile.mk
+++ b/desktop/source/deployment/registry/makefile.mk
@@ -41,7 +41,8 @@ INCPRE += inc
SLOFILES = \
$(SLO)$/dp_backend.obj \
- $(SLO)$/dp_registry.obj
+ $(SLO)$/dp_registry.obj \
+ $(SLO)$/dp_backenddb.obj
.INCLUDE : ..$/target.pmk
.INCLUDE : target.mk
diff --git a/desktop/source/deployment/registry/package/dp_description.cxx b/desktop/source/deployment/registry/package/dp_description.cxx
deleted file mode 100644
index 7c05bfd90a5b..000000000000
--- a/desktop/source/deployment/registry/package/dp_description.cxx
+++ /dev/null
@@ -1,205 +0,0 @@
-/*************************************************************************
- *
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * Copyright 2000, 2010 Oracle and/or its affiliates.
- *
- * OpenOffice.org - a multi-platform office productivity suite
- *
- * This file is part of OpenOffice.org.
- *
- * OpenOffice.org is free software: you can redistribute it and/or modify
- * it under the terms of the GNU Lesser General Public License version 3
- * only, as published by the Free Software Foundation.
- *
- * OpenOffice.org is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU Lesser General Public License version 3 for more details
- * (a copy is included in the LICENSE file that accompanied this code).
- *
- * You should have received a copy of the GNU Lesser General Public License
- * version 3 along with OpenOffice.org. If not, see
- * <http://www.openoffice.org/license.html>
- * for a copy of the LGPLv3 License.
- *
- ************************************************************************/
-
-// MARKER(update_precomp.py): autogen include statement, do not remove
-#include "precompiled_desktop.hxx"
-
-#include "dp_description.hxx"
-
-#include "cppuhelper/exc_hlp.hxx"
-#include "ucbhelper/content.hxx"
-#include "com/sun/star/deployment/DeploymentException.hpp"
-#include "com/sun/star/xml/dom/XDocumentBuilder.hpp"
-#include "com/sun/star/uno/XComponentContext.hpp"
-#include "com/sun/star/ucb/CommandFailedException.hpp"
-#include "com/sun/star/ucb/InteractiveAugmentedIOException.hpp"
-#include "com/sun/star/ucb/IOErrorCode.hpp"
-
-#include "com/sun/star/beans/PropertyValue.hpp"
-
-
-#define OUSTR(x) ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM(x) )
-
-namespace css = com::sun::star;
-namespace cssu = com::sun::star::uno;
-
-namespace dp_registry {
-namespace backend {
-namespace bundle {
-
-ExtensionDescription::ExtensionDescription(
- const cssu::Reference<cssu::XComponentContext>& xContext,
- const ::rtl::OUString& installDir,
- const cssu::Reference< css::ucb::XCommandEnvironment >& xCmdEnv)
-{
- try {
- m_sExtensionRootUrl = installDir;
- //may throw ::com::sun::star::ucb::ContentCreationException
- //If there is no description.xml then ucb will start an interaction which
- //brings up a dialog.We want to prevent this. Therefore we wrap the xCmdEnv
- //and filter the respective exception out.
- ::rtl::OUString sDescriptionUri(installDir + OUSTR("/description.xml"));
- cssu::Reference<css::ucb::XCommandEnvironment> xFilter =
- static_cast<css::ucb::XCommandEnvironment*>(
- new FileDoesNotExistFilter(xCmdEnv));
- ::ucbhelper::Content descContent(sDescriptionUri, xFilter);
-
- //throws an com::sun::star::uno::Exception if the file is not available
- cssu::Reference<css::io::XInputStream> xIn;
- try
- { //throws com.sun.star.ucb.InteractiveAugmentedIOException
- xIn = descContent.openStream();
- }
- catch (cssu::Exception& )
- {
- if ( ! static_cast<FileDoesNotExistFilter*>(xFilter.get())->exist())
- throw NoDescriptionException();
- throw;
- }
- if (!xIn.is())
- {
- throw cssu::Exception(
- OUSTR("Could not get XInputStream for description.xml of extension ") +
- sDescriptionUri, 0);
- }
-
- //get root node of description.xml
- cssu::Reference<css::xml::dom::XDocumentBuilder> xDocBuilder(
- xContext->getServiceManager()->createInstanceWithContext(
- OUSTR("com.sun.star.xml.dom.DocumentBuilder"),
- xContext ), cssu::UNO_QUERY);
- if (!xDocBuilder.is())
- throw css::uno::Exception(OUSTR(" Could not create service com.sun.star.xml.dom.DocumentBuilder"), 0);
-
- if (xDocBuilder->isNamespaceAware() == sal_False)
- {
- throw cssu::Exception(
- OUSTR("Service com.sun.star.xml.dom.DocumentBuilder is not namespace aware."), 0);
- }
-
- cssu::Reference<css::xml::dom::XDocument> xDoc = xDocBuilder->parse(xIn);
- if (!xDoc.is())
- {
- throw cssu::Exception(sDescriptionUri + OUSTR(" contains data which cannot be parsed. "), 0);
- }
-
- //check for proper root element and namespace
- cssu::Reference<css::xml::dom::XElement> xRoot = xDoc->getDocumentElement();
- if (!xRoot.is())
- {
- throw cssu::Exception(
- sDescriptionUri + OUSTR(" contains no root element."), 0);
- }
-
- if ( ! xRoot->getTagName().equals(OUSTR("description")))
- {
- throw cssu::Exception(
- sDescriptionUri + OUSTR(" does not contain the root element <description>."), 0);
- }
-
- m_xRoot = cssu::Reference<css::xml::dom::XNode>(
- xRoot, cssu::UNO_QUERY_THROW);
- ::rtl::OUString nsDescription = xRoot->getNamespaceURI();
-
- //check if this namespace is supported
- if ( ! nsDescription.equals(OUSTR("http://openoffice.org/extensions/description/2006")))
- {
- throw cssu::Exception(sDescriptionUri + OUSTR(" contains a root element with an unsupported namespace. "), 0);
- }
- } catch (css::uno::RuntimeException &) {
- throw;
- } catch (css::deployment::DeploymentException &) {
- throw;
- } catch (css::uno::Exception & e) {
- css::uno::Any a(cppu::getCaughtException());
- throw css::deployment::DeploymentException(
- e.Message, css::uno::Reference< css::uno::XInterface >(), a);
- }
-}
-
-ExtensionDescription::~ExtensionDescription()
-{
-}
-
-//======================================================================
-FileDoesNotExistFilter::FileDoesNotExistFilter(
- const css::uno::Reference< css::ucb::XCommandEnvironment >& xCmdEnv):
- m_bExist(true), m_xCommandEnv(xCmdEnv)
-{}
-
-FileDoesNotExistFilter::~FileDoesNotExistFilter()
-{
-};
-
-bool FileDoesNotExistFilter::exist()
-{
- return m_bExist;
-}
- // XCommandEnvironment
-cssu::Reference<css::task::XInteractionHandler >
- FileDoesNotExistFilter::getInteractionHandler() throw (css::uno::RuntimeException)
-{
- return static_cast<css::task::XInteractionHandler*>(this);
-}
-
-cssu::Reference<css::ucb::XProgressHandler >
- FileDoesNotExistFilter::getProgressHandler() throw (css::uno::RuntimeException)
-{
- return m_xCommandEnv.is()
- ? m_xCommandEnv->getProgressHandler()
- : cssu::Reference<css::ucb::XProgressHandler>();
-}
-
-// XInteractionHandler
-//If the interaction was caused by a non-existing file which is specified in the ctor
-//of FileDoesNotExistFilter, then we do nothing
-void FileDoesNotExistFilter::handle(
- cssu::Reference<css::task::XInteractionRequest > const & xRequest )
- throw (css::uno::RuntimeException)
-{
- cssu::Any request( xRequest->getRequest() );
-
- css::ucb::InteractiveAugmentedIOException ioexc;
- if ((request>>= ioexc) && ioexc.Code == css::ucb::IOErrorCode_NOT_EXISTING )
- {
- m_bExist = false;
- return;
- }
- css::uno::Reference<css::task::XInteractionHandler> xInteraction;
- if (m_xCommandEnv.is()) {
- xInteraction = m_xCommandEnv->getInteractionHandler();
- }
- if (xInteraction.is()) {
- xInteraction->handle(xRequest);
- }
-}
-
-
-} // namespace bundle
-} // namespace backend
-} // namespace dp_registry
-
diff --git a/desktop/source/deployment/registry/package/dp_description.hxx b/desktop/source/deployment/registry/package/dp_description.hxx
deleted file mode 100644
index eb74c454af75..000000000000
--- a/desktop/source/deployment/registry/package/dp_description.hxx
+++ /dev/null
@@ -1,125 +0,0 @@
-/*************************************************************************
- *
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * Copyright 2000, 2010 Oracle and/or its affiliates.
- *
- * OpenOffice.org - a multi-platform office productivity suite
- *
- * This file is part of OpenOffice.org.
- *
- * OpenOffice.org is free software: you can redistribute it and/or modify
- * it under the terms of the GNU Lesser General Public License version 3
- * only, as published by the Free Software Foundation.
- *
- * OpenOffice.org is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU Lesser General Public License version 3 for more details
- * (a copy is included in the LICENSE file that accompanied this code).
- *
- * You should have received a copy of the GNU Lesser General Public License
- * version 3 along with OpenOffice.org. If not, see
- * <http://www.openoffice.org/license.html>
- * for a copy of the LGPLv3 License.
- *
- ************************************************************************/
-
-#if !defined INCLUDED_DESKTOP_EXTENSION_DESCRIPTION_HXX
-#define INCLUDED_DESKTOP_EXTENSION_DESCRIPTION_HXX
-
-
-
-#include "com/sun/star/uno/Reference.hxx"
-
-#include "com/sun/star/ucb/XCommandEnvironment.hpp"
-#include "com/sun/star/uno/XComponentContext.hpp"
-#include "com/sun/star/xml/dom/XNode.hpp"
-#include "com/sun/star/task/XInteractionHandler.hpp"
-#include "cppuhelper/implbase2.hxx"
-
-
-namespace css = ::com::sun::star;
-
-namespace dp_registry {
-namespace backend {
-namespace bundle {
-
-/**The class uses the UCB to access the description.xml file in an
- extension. The UCB must have been initialized already. It also
- requires that the extension has already be unzipped to a particular
- location.
- */
-class ExtensionDescription
-{
-public:
- /**throws an exception if the description.xml is not
- available, cannot be read, does not contain the expected data,
- or any other error occured. Therefore it shoult only be used with
- new extensions.
-
- Throws com::sun::star::uno::RuntimeException,
- com::sun::star::deployment::DeploymentException,
- dp_registry::backend::bundle::NoDescriptionException.
- */
- ExtensionDescription(
- const css::uno::Reference<css::uno::XComponentContext>& xContext,
- const ::rtl::OUString& installDir,
- const css::uno::Reference< css::ucb::XCommandEnvironment >& xCmdEnv);
-
- ~ExtensionDescription();
-
- css::uno::Reference<css::xml::dom::XNode> getRootElement() const
- {
- return m_xRoot;
- }
-
- ::rtl::OUString getExtensionRootUrl() const
- {
- return m_sExtensionRootUrl;
- }
-
-
-private:
- css::uno::Reference<css::xml::dom::XNode> m_xRoot;
- ::rtl::OUString m_sExtensionRootUrl;
-};
-
-class NoDescriptionException
-{
-};
-
-class FileDoesNotExistFilter
- : public ::cppu::WeakImplHelper2< css::ucb::XCommandEnvironment,
- css::task::XInteractionHandler >
-
-{
- //css::uno::Reference<css::task::XInteractionHandler> m_xHandler;
- bool m_bExist;
- css::uno::Reference< css::ucb::XCommandEnvironment > m_xCommandEnv;
-
-public:
- virtual ~FileDoesNotExistFilter();
- FileDoesNotExistFilter(
- const css::uno::Reference< css::ucb::XCommandEnvironment >& xCmdEnv);
-
- bool exist();
- // XCommandEnvironment
- virtual css::uno::Reference<css::task::XInteractionHandler > SAL_CALL
- getInteractionHandler() throw (css::uno::RuntimeException);
- virtual css::uno::Reference<css::ucb::XProgressHandler >
- SAL_CALL getProgressHandler() throw (css::uno::RuntimeException);
-
- // XInteractionHandler
- virtual void SAL_CALL handle(
- css::uno::Reference<css::task::XInteractionRequest > const & xRequest )
- throw (css::uno::RuntimeException);
-};
-
-
-} // namespace bundle
-} // namespace backend
-} // namespace dp_registry
-
-
-#endif // INCLUDED_DESKTOP_LICENSE_INTERACT_HXX
diff --git a/desktop/source/deployment/registry/package/dp_extbackenddb.cxx b/desktop/source/deployment/registry/package/dp_extbackenddb.cxx
new file mode 100644
index 000000000000..97cfc136049c
--- /dev/null
+++ b/desktop/source/deployment/registry/package/dp_extbackenddb.cxx
@@ -0,0 +1,177 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_desktop.hxx"
+
+#include "rtl/string.h"
+#include "rtl/bootstrap.hxx"
+#include "cppuhelper/exc_hlp.hxx"
+#include "com/sun/star/uno/XComponentContext.hpp"
+#include "com/sun/star/xml/dom/XDocumentBuilder.hpp"
+#include "com/sun/star/xml/xpath/XXPathAPI.hpp"
+#include "dp_misc.h"
+
+#include "dp_extbackenddb.hxx"
+
+
+namespace css = ::com::sun::star;
+using namespace ::com::sun::star::uno;
+using ::rtl::OUString;
+
+#define EXTENSION_REG_NS "http://openoffice.org/extensionmanager/extension-registry/2010"
+#define ROOT_ELEMENT_NAME "extension-backend-db"
+
+// /extension-backend-db/extension
+#define EXTENSION_ELEMENT "extension"
+
+// /extension-backend-db/extension/extension-items
+#define EXTENSION_ITEMS "extension-items"
+
+// /extension-backend-db/extension/extension-items/item
+#define EXTENSION_ITEMS_ITEM "item"
+
+// /extension-backend-db/extension/extension-items/item/url
+#define ITEM_URL "url"
+
+// /extension-backend-db/extension/extension-items/item/media-type
+#define ITEM_MEDIA_TYP "media-type"
+
+
+namespace dp_registry {
+namespace backend {
+namespace bundle {
+
+ExtensionBackendDb::ExtensionBackendDb(
+ Reference<XComponentContext> const & xContext,
+ ::rtl::OUString const & url):BackendDb(xContext, url)
+{
+
+}
+
+OUString ExtensionBackendDb::getDbNSName()
+{
+ return OUSTR(EXTENSION_REG_NS);
+}
+
+OUString ExtensionBackendDb::getRootElementName()
+{
+ return OUSTR(ROOT_ELEMENT_NAME);
+}
+
+void ExtensionBackendDb::addEntry(::rtl::OUString const & url, Data const & data)
+{
+ try{
+
+ Reference<css::xml::dom::XDocument> doc = getDocument();
+ Reference<css::xml::dom::XNode> root = doc->getFirstChild();
+
+#if OSL_DEBUG_LEVEL > 0
+ //There must not be yet an entry with the same url
+ OUString sExpression(
+ OUSTR("reg:extension[@url = \"") + url + OUSTR("\"]"));
+ Reference<css::xml::dom::XNode> _extensionNode =
+ getXPathAPI()->selectSingleNode(root, sExpression);
+ OSL_ASSERT(! _extensionNode.is());
+#endif
+ // <extension url="file:///...">
+ Reference<css::xml::dom::XElement> extensionNode(
+ doc->createElement(OUSTR("extension")));
+
+ extensionNode->setAttribute(OUSTR("url"), url);
+
+ Reference<css::xml::dom::XNode> extensionNodeNode(
+ extensionNode, css::uno::UNO_QUERY_THROW);
+ root->appendChild(extensionNodeNode);
+
+ // <identifier>...</identifier>
+ Reference<css::xml::dom::XNode> identifierNode(
+ doc->createElement(OUSTR("identifier")), UNO_QUERY_THROW);
+ extensionNodeNode->appendChild(identifierNode);
+
+ Reference<css::xml::dom::XNode> identifierValue(
+ doc->createTextNode(data.identifier), UNO_QUERY_THROW);
+ identifierNode->appendChild(identifierValue);
+
+
+ writeVectorOfPair(
+ data.items,
+ OUSTR("extension-items"),
+ OUSTR("item"),
+ OUSTR("url"),
+ OUSTR("media-type"),
+ extensionNodeNode);
+ save();
+ }
+ catch(css::uno::Exception &)
+ {
+ Any exc( ::cppu::getCaughtException() );
+ throw css::deployment::DeploymentException(
+ OUSTR("Extension Manager: failed to write data entry in backend db: ") +
+ m_urlDb, 0, exc);
+ }
+}
+
+void ExtensionBackendDb::removeEntry(::rtl::OUString const & url)
+{
+ OUString sExpression(
+ OUSTR("reg:extension[@url = \"") + url + OUSTR("\"]"));
+ removeElement(sExpression);
+}
+
+ExtensionBackendDb::Data ExtensionBackendDb::getEntry(::rtl::OUString const & url)
+{
+ ExtensionBackendDb::Data retData;
+ const OUString sExpression(
+ OUSTR("reg:extension[@url = \"") + url + OUSTR("\"]"));
+ Reference<css::xml::dom::XDocument> doc = getDocument();
+ Reference<css::xml::dom::XNode> root = doc->getFirstChild();
+
+ Reference<css::xml::xpath::XXPathAPI> xpathApi = getXPathAPI();
+ //find the extension element that is to be removed
+ Reference<css::xml::dom::XNode> aNode =
+ xpathApi->selectSingleNode(root, sExpression);
+ OSL_ASSERT(aNode.is());
+
+ const OUString sExprIdentifier(OUSTR("reg:identifier/text()"));
+
+ Reference<css::xml::dom::XNode> idValueNode =
+ xpathApi->selectSingleNode(aNode, sExprIdentifier);
+ retData.identifier = idValueNode->getNodeValue();
+
+ retData.items =
+ readVectorOfPair(
+ aNode,
+ OUSTR("reg:extension-items"),
+ OUSTR("reg:item"), OUSTR("reg:url"), OUSTR("reg:media-type"));
+ return retData;
+}
+
+} // namespace bundle
+} // namespace backend
+} // namespace dp_registry
+
diff --git a/desktop/source/deployment/registry/package/dp_extbackenddb.hxx b/desktop/source/deployment/registry/package/dp_extbackenddb.hxx
new file mode 100644
index 000000000000..156e34155040
--- /dev/null
+++ b/desktop/source/deployment/registry/package/dp_extbackenddb.hxx
@@ -0,0 +1,94 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+
+#if ! defined INCLUDED_DP_EXTBACKENDDB_HXX
+#define INCLUDED_DP_EXTBACKENDDB_HXX
+
+#include "rtl/ustring.hxx"
+#include "rtl/string.hxx"
+#include <vector>
+#include "dp_backenddb.hxx"
+
+namespace css = ::com::sun::star;
+
+namespace com { namespace sun { namespace star {
+ namespace uno {
+ class XComponentContext;
+ }
+ namespace xml { namespace dom {
+ class XDocument;
+ class XNode;
+ }}
+ namespace xml { namespace xpath {
+ class XXPathAPI;
+ }}
+}}}
+
+namespace dp_registry {
+namespace backend {
+namespace bundle {
+
+/* The XML file stores the extensions which are currently registered.
+ They will be removed when they are revoked.
+ */
+class ExtensionBackendDb: public dp_registry::backend::BackendDb
+{
+public:
+ struct Data
+ {
+ ::rtl::OUString identifier;
+ /* every element consists of a pair of the url to the item (jar,rdb, etc)
+ and the media type
+ */
+ ::std::vector< ::std::pair< ::rtl::OUString, ::rtl::OUString> > items;
+ typedef ::std::vector<
+ ::std::pair< ::rtl::OUString, ::rtl::OUString> >::const_iterator ITC_ITEMS;
+
+ };
+
+public:
+
+ ExtensionBackendDb( css::uno::Reference<css::uno::XComponentContext> const & xContext,
+ ::rtl::OUString const & url);
+
+ void addEntry(::rtl::OUString const & url, Data const & data);
+ void removeEntry(::rtl::OUString const & url);
+ Data getEntry(::rtl::OUString const & url);
+
+ virtual ::rtl::OUString getDbNSName();
+
+ virtual ::rtl::OUString getRootElementName();
+};
+
+
+
+}
+}
+}
+#endif
+
diff --git a/desktop/source/deployment/registry/package/dp_package.cxx b/desktop/source/deployment/registry/package/dp_package.cxx
index b0b4a918c7a3..8fe7874f247f 100644
--- a/desktop/source/deployment/registry/package/dp_package.cxx
+++ b/desktop/source/deployment/registry/package/dp_package.cxx
@@ -34,7 +34,6 @@
#include "dp_interact.h"
#include "dp_dependencies.hxx"
#include "dp_platform.hxx"
-#include "dp_description.hxx"
#include "dp_descriptioninfoset.hxx"
#include "dp_identifier.hxx"
#include "rtl/uri.hxx"
@@ -74,7 +73,7 @@
#include <vector>
#include <stdio.h>
-
+#include "dp_extbackenddb.hxx"
using namespace ::dp_misc;
using namespace ::com::sun::star;
using namespace ::com::sun::star::uno;
@@ -106,6 +105,8 @@ class BackendImpl : public ImplBaseT
Sequence< Reference<deployment::XPackage> > m_bundle;
Sequence< Reference<deployment::XPackage> > * m_pBundle;
+ ExtensionBackendDb::Data m_data;
+
Reference<deployment::XPackage> bindBundleItem(
OUString const & url, OUString const & mediaType,
Reference<XCommandEnvironment> const & xCmdEnv,
@@ -122,20 +123,20 @@ class BackendImpl : public ImplBaseT
::rtl::Reference<AbortChannel> const & abortChannel,
Reference<XCommandEnvironment> const & xCmdEnv,
bool skip_registration = false );
-
+ ::std::vector<Reference<deployment::XPackage> > getPackagesFromDb();
bool checkPlatform(
css::uno::Reference< css::ucb::XCommandEnvironment > const & environment);
bool checkDependencies(
css::uno::Reference< css::ucb::XCommandEnvironment > const &
environment,
- ExtensionDescription const & description);
+ DescriptionInfoset const & description);
// throws css::uno::RuntimeException,
// css::deployment::DeploymentException
::sal_Bool checkLicense(
css::uno::Reference< css::ucb::XCommandEnvironment > const & xCmdEnv,
- ExtensionDescription const& description, bool bInstalled,
+ DescriptionInfoset const & description, bool bInstalled,
OUString const & aContextName )
throw (css::deployment::DeploymentException,
css::ucb::CommandFailedException,
@@ -169,13 +170,8 @@ class BackendImpl : public ImplBaseT
OUString const & url,
OUString const & name,
Reference<deployment::XPackageTypeInfo> const & xPackageType,
- bool legacyBundle )
- : Package( myBackend, url, name, name /* display-name */,
- xPackageType ),
- m_url_expanded( expandUnoRcUrl( url ) ),
- m_legacyBundle( legacyBundle ),
- m_pBundle( 0 )
- {}
+ bool legacyBundle,
+ bool useDb);
// XPackage
virtual sal_Bool SAL_CALL isBundle() throw (RuntimeException);
@@ -228,9 +224,16 @@ class BackendImpl : public ImplBaseT
const Reference<deployment::XPackageTypeInfo> m_xLegacyBundleTypeInfo;
Sequence< Reference<deployment::XPackageTypeInfo> > m_typeInfos;
+ std::auto_ptr<ExtensionBackendDb> m_backendDb;
+
+ void addDataToDb(OUString const & url, ExtensionBackendDb::Data const & data);
+ ExtensionBackendDb::Data readDataFromDb(OUString const & url);
+ void deleteDataFromDb(OUString const & url);
+
// PackageRegistryBackend
virtual Reference<deployment::XPackage> bindPackage_(
OUString const & url, OUString const & mediaType,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv );
virtual void SAL_CALL disposing();
@@ -291,6 +294,14 @@ BackendImpl::BackendImpl(
{
m_typeInfos[ 0 ] = m_xBundleTypeInfo;
m_typeInfos[ 1 ] = m_xLegacyBundleTypeInfo;
+
+ if (!transientMode())
+ {
+ OUString dbFile = makeURL(getCachePath(), getImplementationName());
+ dbFile = makeURL(dbFile, OUSTR("backenddb.xml"));
+ m_backendDb.reset(
+ new ExtensionBackendDb(getComponentContext(), dbFile));
+ }
}
//______________________________________________________________________________
@@ -333,6 +344,7 @@ BackendImpl::getSupportedPackageTypes() throw (RuntimeException)
//______________________________________________________________________________
Reference<deployment::XPackage> BackendImpl::bindPackage_(
OUString const & url, OUString const & mediaType_,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv )
{
OUString mediaType( mediaType_ );
@@ -381,19 +393,21 @@ Reference<deployment::XPackage> BackendImpl::bindPackage_(
{
if (type.EqualsIgnoreCaseAscii("application"))
{
- ::ucbhelper::Content ucbContent( url, xCmdEnv );
+ ::ucbhelper::Content ucbContent;
+ OUString name;
+ //In case a XPackage is created for a removed extension, we cannot
+ //obtain the name
+ if (create_ucb_content(&ucbContent, url, xCmdEnv, false ))
+ name = ucbContent.getPropertyValue(
+ StrTitle::get() ).get<OUString>();
if (subType.EqualsIgnoreCaseAscii("vnd.sun.star.package-bundle")) {
return new PackageImpl(
- this, url, ucbContent.getPropertyValue(
- StrTitle::get() ).get<OUString>(),
- m_xBundleTypeInfo, false );
+ this, url, name, m_xBundleTypeInfo, false, bNoFileAccess);
}
else if (subType.EqualsIgnoreCaseAscii(
"vnd.sun.star.legacy-package-bundle")) {
return new PackageImpl(
- this, url, ucbContent.getPropertyValue(
- StrTitle::get() ).get<OUString>(),
- m_xLegacyBundleTypeInfo, true );
+ this, url, name, m_xLegacyBundleTypeInfo, true, bNoFileAccess);
}
}
}
@@ -403,8 +417,48 @@ Reference<deployment::XPackage> BackendImpl::bindPackage_(
static_cast<sal_Int16>(-1) );
}
+void BackendImpl::addDataToDb(
+ OUString const & url, ExtensionBackendDb::Data const & data)
+{
+ if (m_backendDb.get())
+ m_backendDb->addEntry(url, data);
+}
+
+ExtensionBackendDb::Data BackendImpl::readDataFromDb(
+ OUString const & url)
+{
+ ExtensionBackendDb::Data data;
+ if (m_backendDb.get())
+ data = m_backendDb->getEntry(url);
+ return data;
+}
+
+void BackendImpl::deleteDataFromDb(OUString const & url)
+{
+ if (m_backendDb.get())
+ m_backendDb->removeEntry(url);
+}
+
+
//##############################################################################
+BackendImpl::PackageImpl::PackageImpl(
+ ::rtl::Reference<PackageRegistryBackend> const & myBackend,
+ OUString const & url,
+ OUString const & name,
+ Reference<deployment::XPackageTypeInfo> const & xPackageType,
+ bool legacyBundle,
+ bool useDb)
+ : Package( myBackend, url, name, name /* display-name */,
+ xPackageType, useDb ),
+ m_url_expanded( expandUnoRcUrl( url ) ),
+ m_legacyBundle( legacyBundle ),
+ m_pBundle( 0 )
+{
+ if (useDb)
+ m_data = getMyBackend()->readDataFromDb(url);
+}
+
BackendImpl * BackendImpl::PackageImpl::getMyBackend() const
{
BackendImpl * pBackend = static_cast<BackendImpl *>(m_myBackend.get());
@@ -510,23 +564,7 @@ OUString BackendImpl::PackageImpl::getTextFromURL(
DescriptionInfoset BackendImpl::PackageImpl::getDescriptionInfoset()
{
- css::uno::Reference< css::xml::dom::XNode > root;
- try {
- root =
- ExtensionDescription(
- getMyBackend()->getComponentContext(), m_url_expanded,
- css::uno::Reference< css::ucb::XCommandEnvironment >()).
- getRootElement();
- } catch (NoDescriptionException &) {
- } catch (css::deployment::DeploymentException & e) {
- throw RuntimeException(
- (OUString(
- RTL_CONSTASCII_USTRINGPARAM(
- "com.sun.star.deployment.DeploymentException: ")) +
- e.Message),
- static_cast< OWeakObject * >(this));
- }
- return DescriptionInfoset(getMyBackend()->getComponentContext(), root);
+ return dp_misc::getDescriptionInfoset(m_url_expanded);
}
bool BackendImpl::PackageImpl::checkPlatform(
@@ -561,14 +599,11 @@ bool BackendImpl::PackageImpl::checkPlatform(
bool BackendImpl::PackageImpl::checkDependencies(
css::uno::Reference< css::ucb::XCommandEnvironment > const & environment,
- ExtensionDescription const & description)
+ DescriptionInfoset const & description)
{
css::uno::Sequence< css::uno::Reference< css::xml::dom::XElement > >
- unsatisfied(
- dp_misc::Dependencies::check(
- DescriptionInfoset(
- getMyBackend()->getComponentContext(),
- description.getRootElement())));
+ unsatisfied(dp_misc::Dependencies::check(description));
+
if (unsatisfied.getLength() == 0) {
return true;
} else {
@@ -590,7 +625,7 @@ bool BackendImpl::PackageImpl::checkDependencies(
::sal_Bool BackendImpl::PackageImpl::checkLicense(
css::uno::Reference< css::ucb::XCommandEnvironment > const & xCmdEnv,
- ExtensionDescription const & desc, bool bInstalled, OUString const & aContextName)
+ DescriptionInfoset const & info, bool bInstalled, OUString const & aContextName)
throw (css::deployment::DeploymentException,
css::ucb::CommandFailedException,
css::ucb::CommandAbortedException,
@@ -598,7 +633,6 @@ bool BackendImpl::PackageImpl::checkDependencies(
{
try
{
- DescriptionInfoset info = getDescriptionInfoset();
::boost::optional<SimpleLicenseAttributes> simplLicAttr
= info.getSimpleLicenseAttributes();
if (! simplLicAttr)
@@ -610,7 +644,7 @@ bool BackendImpl::PackageImpl::checkDependencies(
if (sLic.getLength() == 0)
throw css::deployment::DeploymentException(
OUSTR("Could not obtain path to license. Possible error in description.xml"), 0, Any());
- OUString sHref = desc.getExtensionRootUrl() + OUSTR("/") + sLic;
+ OUString sHref = m_url_expanded + OUSTR("/") + sLic;
OUString sLicense = getTextFromURL(xCmdEnv, sHref);
////determine who has to agree to the license
//check correct value for attribute
@@ -693,19 +727,13 @@ bool BackendImpl::PackageImpl::checkDependencies(
css::ucb::CommandAbortedException,
css::uno::RuntimeException)
{
- std::auto_ptr<ExtensionDescription> spDescription;
- try {
- spDescription.reset(
- new ExtensionDescription(
- getMyBackend()->getComponentContext(),
- m_url_expanded,
- xCmdEnv));
- } catch (NoDescriptionException& ) {
+ DescriptionInfoset info = getDescriptionInfoset();
+ if (!info.hasDescription())
return sal_True;
- }
+
return checkPlatform(xCmdEnv)
- && checkDependencies(xCmdEnv, *spDescription)
- && checkLicense(xCmdEnv, *spDescription, bInstalled, aContextName);
+ && checkDependencies(xCmdEnv, info)
+ && checkLicense(xCmdEnv, info, bInstalled, aContextName);
}
::sal_Bool BackendImpl::PackageImpl::checkDependencies(
@@ -714,23 +742,25 @@ bool BackendImpl::PackageImpl::checkDependencies(
css::ucb::CommandFailedException,
css::uno::RuntimeException)
{
- std::auto_ptr<ExtensionDescription> spDescription;
- try {
- spDescription.reset(
- new ExtensionDescription( getMyBackend()->getComponentContext(), m_url_expanded, xCmdEnv ));
- } catch (NoDescriptionException& ) {
+ DescriptionInfoset info = getDescriptionInfoset();
+ if (!info.hasDescription())
return sal_True;
- }
- return checkDependencies(xCmdEnv, *spDescription);
+
+ return checkDependencies(xCmdEnv, info);
}
beans::Optional<OUString> BackendImpl::PackageImpl::getIdentifier()
throw (RuntimeException)
{
+ OUString identifier;
+ if (m_bUseDb)
+ identifier = m_data.identifier;
+ else
+ identifier = dp_misc::generateIdentifier(
+ getDescriptionInfoset().getIdentifier(), m_name);
+
return beans::Optional<OUString>(
- true,
- dp_misc::generateIdentifier(
- getDescriptionInfoset().getIdentifier(), m_name));
+ true, identifier);
}
OUString BackendImpl::PackageImpl::getVersion() throw (RuntimeException)
@@ -793,6 +823,7 @@ void BackendImpl::PackageImpl::processPackage_(
if (doRegisterPackage)
{
+ ExtensionBackendDb::Data data;
const sal_Int32 len = bundle.getLength();
for ( sal_Int32 pos = 0; pos < len; ++pos )
{
@@ -870,7 +901,12 @@ void BackendImpl::PackageImpl::processPackage_(
::cppu::throwException(exc);
}
}
+ data.items.push_back(
+ ::std::make_pair(xPackage->getURL(),
+ xPackage->getPackageType()->getMediaType()));
}
+ data.identifier = getIdentifier().Value;
+ getMyBackend()->addDataToDb(getURL(), data);
}
else
{
@@ -914,6 +950,7 @@ void BackendImpl::PackageImpl::processPackage_(
// selected
}
}
+ getMyBackend()->deleteDataFromDb(getURL());
}
}
@@ -1139,58 +1176,66 @@ Sequence< Reference<deployment::XPackage> > BackendImpl::PackageImpl::getBundle(
if (pBundle == 0)
{
t_packagevec bundle;
- try {
- if (m_legacyBundle)
- {
- // .zip legacy packages allow script.xlb, dialog.xlb in bundle
- // root folder:
- OUString mediaType;
- // probe for script.xlb:
- if (create_ucb_content(
- 0, makeURL( m_url_expanded, OUSTR("script.xlb") ),
- xCmdEnv, false /* no throw */ )) {
- mediaType = OUSTR("application/vnd.sun.star.basic-library");
+ if (m_bUseDb)
+ {
+ bundle = getPackagesFromDb();
+ }
+ else
+ {
+ try {
+ if (m_legacyBundle)
+ {
+ // .zip legacy packages allow script.xlb, dialog.xlb in bundle
+ // root folder:
+ OUString mediaType;
+ // probe for script.xlb:
+ if (create_ucb_content(
+ 0, makeURL( m_url_expanded, OUSTR("script.xlb") ),
+ xCmdEnv, false /* no throw */ )) {
+ mediaType = OUSTR("application/vnd.sun.star.basic-library");
+ }
+ // probe for dialog.xlb:
+ else if (create_ucb_content(
+ 0, makeURL( m_url_expanded, OUSTR("dialog.xlb") ),
+ xCmdEnv, false /* no throw */ ))
+ mediaType = OUSTR("application/vnd.sun.star."
+ "dialog-library");
+
+ if (mediaType.getLength() > 0) {
+ const Reference<deployment::XPackage> xPackage(
+ bindBundleItem( getURL(), mediaType, xCmdEnv ) );
+ if (xPackage.is())
+ bundle.push_back( xPackage );
+ // continue scanning:
+ }
+ scanLegacyBundle( bundle, getURL(),
+ AbortChannel::get(xAbortChannel), xCmdEnv );
}
- // probe for dialog.xlb:
- else if (create_ucb_content(
- 0, makeURL( m_url_expanded, OUSTR("dialog.xlb") ),
- xCmdEnv, false /* no throw */ ))
- mediaType = OUSTR("application/vnd.sun.star."
- "dialog-library");
-
- if (mediaType.getLength() > 0) {
- const Reference<deployment::XPackage> xPackage(
- bindBundleItem( getURL(), mediaType, xCmdEnv ) );
- if (xPackage.is())
- bundle.push_back( xPackage );
- // continue scanning:
+ else
+ {
+ // .oxt:
+ scanBundle( bundle, AbortChannel::get(xAbortChannel), xCmdEnv );
}
- scanLegacyBundle( bundle, getURL(),
- AbortChannel::get(xAbortChannel), xCmdEnv );
+
}
- else
- {
- // .oxt:
- scanBundle( bundle, AbortChannel::get(xAbortChannel), xCmdEnv );
+ catch (RuntimeException &) {
+ throw;
+ }
+ catch (CommandFailedException &) {
+ throw;
+ }
+ catch (CommandAbortedException &) {
+ throw;
+ }
+ catch (deployment::DeploymentException &) {
+ throw;
+ }
+ catch (Exception &) {
+ Any exc( ::cppu::getCaughtException() );
+ throw deployment::DeploymentException(
+ OUSTR("error scanning bundle: ") + getURL(),
+ static_cast<OWeakObject *>(this), exc );
}
- }
- catch (RuntimeException &) {
- throw;
- }
- catch (CommandFailedException &) {
- throw;
- }
- catch (CommandAbortedException &) {
- throw;
- }
- catch (deployment::DeploymentException &) {
- throw;
- }
- catch (Exception &) {
- Any exc( ::cppu::getCaughtException() );
- throw deployment::DeploymentException(
- OUSTR("error scanning bundle: ") + getURL(),
- static_cast<OWeakObject *>(this), exc );
}
// sort: schema before config data, typelibs before components:
@@ -1267,7 +1312,7 @@ Reference<deployment::XPackage> BackendImpl::PackageImpl::bindBundleItem(
Reference<deployment::XPackage>xPackage;
try {
xPackage.set( getMyBackend()->m_xRootRegistry->bindPackage(
- url, mediaType, xCmdEnv ) );
+ url, mediaType, false, xCmdEnv ) );
OSL_ASSERT( xPackage.is() );
}
catch (RuntimeException &) {
@@ -1523,6 +1568,13 @@ OUString BackendImpl::PackageImpl::getDisplayName() throw (RuntimeException)
return sName;
}
+::std::vector<Reference<deployment::XPackage> > BackendImpl::PackageImpl::getPackagesFromDb()
+{
+ //get the data base entry for this extension
+
+ return ::std::vector<Reference<deployment::XPackage> >();
+}
+
} // anon namespace
//==============================================================================
diff --git a/desktop/source/deployment/registry/package/makefile.mk b/desktop/source/deployment/registry/package/makefile.mk
index ccadc2070301..203ce176d289 100644
--- a/desktop/source/deployment/registry/package/makefile.mk
+++ b/desktop/source/deployment/registry/package/makefile.mk
@@ -41,7 +41,7 @@ INCPRE += ..$/..$/inc
SLOFILES = \
$(SLO)$/dp_package.obj \
- $(SLO)$/dp_description.obj
+ $(SLO)$/dp_extbackenddb.obj
.INCLUDE : ..$/..$/target.pmk
.INCLUDE : target.mk
diff --git a/desktop/source/deployment/registry/script/dp_script.cxx b/desktop/source/deployment/registry/script/dp_script.cxx
index 4af0cbb84130..6d503d33d51d 100644
--- a/desktop/source/deployment/registry/script/dp_script.cxx
+++ b/desktop/source/deployment/registry/script/dp_script.cxx
@@ -88,13 +88,15 @@ class BackendImpl : public t_helper
::rtl::Reference<BackendImpl> const & myBackend,
OUString const & url,
Reference<XCommandEnvironment> const &xCmdEnv,
- OUString const & scriptURL, OUString const & dialogURL );
+ OUString const & scriptURL, OUString const & dialogURL,
+ bool bUseDb);
};
friend class PackageImpl;
// PackageRegistryBackend
virtual Reference<deployment::XPackage> bindPackage_(
OUString const & url, OUString const & mediaType,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv );
rtl::OUString getRegisteredFlagFileURL( Reference< deployment::XPackage > xPackage );
@@ -123,11 +125,11 @@ BackendImpl::PackageImpl::PackageImpl(
::rtl::Reference<BackendImpl> const & myBackend,
OUString const & url,
Reference<XCommandEnvironment> const &xCmdEnv,
- OUString const & scriptURL, OUString const & dialogURL )
+ OUString const & scriptURL, OUString const & dialogURL, bool bUseDb )
: Package( myBackend.get(), url,
OUString(), OUString(), // will be late-initialized
scriptURL.getLength() > 0 ? myBackend->m_xBasicLibTypeInfo
- : myBackend->m_xDialogLibTypeInfo ),
+ : myBackend->m_xDialogLibTypeInfo, bUseDb),
m_scriptURL( scriptURL ),
m_dialogURL( dialogURL )
{
@@ -189,6 +191,7 @@ BackendImpl::getSupportedPackageTypes() throw (RuntimeException)
//______________________________________________________________________________
Reference<deployment::XPackage> BackendImpl::bindPackage_(
OUString const & url, OUString const & mediaType_,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv )
{
OUString mediaType( mediaType_ );
@@ -231,13 +234,15 @@ Reference<deployment::XPackage> BackendImpl::bindPackage_(
}
return new PackageImpl( this, url, xCmdEnv,
makeURL( url, OUSTR("script.xlb") ),
- dialogURL );
+ dialogURL, bNoFileAccess);
}
else if (subType.EqualsIgnoreCaseAscii(
"vnd.sun.star.dialog-library")) {
- return new PackageImpl( this, url, xCmdEnv,
- OUString() /* no script lib */,
- makeURL( url, OUSTR("dialog.xlb") ) );
+ return new PackageImpl(
+ this, url, xCmdEnv,
+ OUString() /* no script lib */,
+ makeURL( url, OUSTR("dialog.xlb") ),
+ bNoFileAccess);
}
}
}
diff --git a/desktop/source/deployment/registry/sfwk/dp_sfwk.cxx b/desktop/source/deployment/registry/sfwk/dp_sfwk.cxx
index 52ced6908bd8..47b6430f1a1e 100644
--- a/desktop/source/deployment/registry/sfwk/dp_sfwk.cxx
+++ b/desktop/source/deployment/registry/sfwk/dp_sfwk.cxx
@@ -81,8 +81,9 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
Reference<XCommandEnvironment> const & xCmdEnv );
public:
- PackageImpl( ::rtl::Reference<BackendImpl> const & myBackend,
- OUString const & url, OUString const & libType );
+ PackageImpl(
+ ::rtl::Reference<BackendImpl> const & myBackend,
+ OUString const & url, OUString const & libType, bool bUseDb);
// XPackage
virtual OUString SAL_CALL getDescription() throw (RuntimeException);
};
@@ -91,6 +92,7 @@ class BackendImpl : public ::dp_registry::backend::PackageRegistryBackend
// PackageRegistryBackend
virtual Reference<deployment::XPackage> bindPackage_(
OUString const & url, OUString const & mediaType,
+ sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv );
const Reference<deployment::XPackageTypeInfo> m_xTypeInfo;
@@ -131,9 +133,9 @@ OUString BackendImpl::PackageImpl::getDescription() throw (RuntimeException)
//______________________________________________________________________________
BackendImpl::PackageImpl::PackageImpl(
::rtl::Reference<BackendImpl> const & myBackend,
- OUString const & url, OUString const & libType )
+ OUString const & url, OUString const & libType, bool bUseDb)
: Package( myBackend.get(), url, OUString(), OUString(),
- myBackend->m_xTypeInfo ),
+ myBackend->m_xTypeInfo, bUseDb ),
m_descr(libType)
{
initPackageHandler();
@@ -217,7 +219,7 @@ BackendImpl::getSupportedPackageTypes() throw (RuntimeException)
// PackageRegistryBackend
//______________________________________________________________________________
Reference<deployment::XPackage> BackendImpl::bindPackage_(
- OUString const & url, OUString const & mediaType_,
+ OUString const & url, OUString const & mediaType_, sal_Bool bNoFileAccess,
Reference<XCommandEnvironment> const & xCmdEnv )
{
OUString mediaType( mediaType_ );
@@ -294,7 +296,7 @@ Reference<deployment::XPackage> BackendImpl::bindPackage_(
dp_misc::TRACE(OUSTR(" BackEnd detected lang = ") + lang + OUSTR("\n"));
dp_misc::TRACE(OUSTR(" for url ") + sParcelDescURL + OUSTR("\n") );
dp_misc::TRACE("******************************\n");
- return new PackageImpl( this, url, sfwkLibType );
+ return new PackageImpl( this, url, sfwkLibType, bNoFileAccess);
}
}
}
@@ -322,6 +324,10 @@ void BackendImpl::PackageImpl:: initPackageHandler()
{
aContext <<= OUSTR("share");
}
+ else if ( that->m_eContext == CONTEXT_BUNDLED )
+ {
+ aContext <<= OUSTR("bundled");
+ }
else
{
OSL_ASSERT( 0 );
diff --git a/desktop/source/pkgchk/unopkg/unopkg_app.cxx b/desktop/source/pkgchk/unopkg/unopkg_app.cxx
index 2acd4f79a781..807260fe4663 100644
--- a/desktop/source/pkgchk/unopkg/unopkg_app.cxx
+++ b/desktop/source/pkgchk/unopkg/unopkg_app.cxx
@@ -41,7 +41,8 @@
#include "cppuhelper/implbase1.hxx"
#include "cppuhelper/exc_hlp.hxx"
#include "comphelper/anytostring.hxx"
-#include "com/sun/star/deployment/thePackageManagerFactory.hpp"
+#include "com/sun/star/deployment/ExtensionManager.hpp"
+
#include "com/sun/star/deployment/ui/PackageManagerDialog.hpp"
#include "com/sun/star/ui/dialogs/XExecutableDialog.hpp"
#include "com/sun/star/lang/DisposedException.hpp"
@@ -149,12 +150,13 @@ void DialogClosedListenerImpl::dialogClosed(
// installed with OOo 2.2 or later could not normally be found via its file
// name.
Reference<deployment::XPackage> findPackage(
- Reference<deployment::XPackageManager> const & manager,
+ OUString const & repository,
+ Reference<deployment::XExtensionManager> const & manager,
Reference<ucb::XCommandEnvironment > const & environment,
OUString const & idOrFileName )
{
Sequence< Reference<deployment::XPackage> > ps(
- manager->getDeployedPackages(
+ manager->getDeployedExtensions(repository,
Reference<task::XAbortChannel>(), environment ) );
for ( sal_Int32 i = 0; i < ps.getLength(); ++i )
if ( dp_misc::getIdentifier( ps[i] ) == idOrFileName )
@@ -214,7 +216,7 @@ extern "C" int unopkg_main()
bool subcmd_add = false;
bool subcmd_gui = false;
OUString logFile;
- OUString deploymentContext;
+ OUString repository;
OUString cmdArg;
::std::vector<OUString> cmdPackages;
@@ -279,7 +281,7 @@ extern "C" int unopkg_main()
!readOption( &option_force, info_force, &nPos ) &&
!readOption( &option_bundled, info_bundled, &nPos ) &&
!readOption( &option_suppressLicense, info_suppressLicense, &nPos ) &&
- !readArgument( &deploymentContext, info_context, &nPos ) &&
+ !readArgument( &repository, info_context, &nPos ) &&
!isBootstrapVariable(&nPos))
{
osl_getCommandArg( nPos, &cmdArg.pData );
@@ -313,24 +315,30 @@ extern "C" int unopkg_main()
}
//make sure the bundled option was provided together with shared
- if (option_bundled && !option_shared)
- {
- dp_misc::writeConsoleError(
- "\nERROR: option --bundled can only be used together with --shared!");
- return 1;
- }
+// if (option_bundled && !option_shared)
+// {
+// dp_misc::writeConsoleError(
+// "\nERROR: option --bundled can only be used together with --shared!");
+// return 1;
+// }
xComponentContext = getUNO(
disposeGuard, option_verbose, option_shared, subcmd_gui,
xLocalComponentContext );
- if (deploymentContext.getLength() == 0) {
- deploymentContext = option_shared ? OUSTR("shared") : OUSTR("user");
+ if (repository.getLength() == 0)
+ {
+ if (option_shared)
+ repository = OUSTR("shared");
+ else if (option_bundled)
+ repository = OUSTR("bundled");
+ else
+ repository = OUSTR("user");
}
else
{
- if (deploymentContext.equalsAsciiL(
+ if (repository.equalsAsciiL(
RTL_CONSTASCII_STRINGPARAM("shared") )) {
option_shared = true;
}
@@ -343,10 +351,9 @@ extern "C" int unopkg_main()
}
}
- Reference<deployment::XPackageManagerFactory> xPackageManagerFactory(
- deployment::thePackageManagerFactory::get( xComponentContext ) );
- Reference<deployment::XPackageManager> xPackageManager(
- xPackageManagerFactory->getPackageManager( deploymentContext ) );
+
+ Reference<deployment::XExtensionManager> xExtensionManager(
+ deployment::ExtensionManager::get( xComponentContext ) );
Reference< ::com::sun::star::ucb::XCommandEnvironment > xCmdEnv(
createCmdEnv( xComponentContext, logFile,
@@ -362,25 +369,23 @@ extern "C" int unopkg_main()
OUString const & cmdPackage = cmdPackages[ pos ];
if (subcmd_add)
{
- Reference<deployment::XPackage> xPackage(
- xPackageManager->addPackage(
- cmdPackage, OUString() /* to be detected */,
- Reference<task::XAbortChannel>(), xCmdEnv ) );
- OSL_ASSERT( xPackage.is() );
+ xExtensionManager->addExtension(
+ cmdPackage, repository,
+ Reference<task::XAbortChannel>(), xCmdEnv);
}
else
{
try
{
- xPackageManager->removePackage(
- cmdPackage, cmdPackage,
+ xExtensionManager->removeExtension(
+ cmdPackage, cmdPackage, repository,
Reference<task::XAbortChannel>(), xCmdEnv );
}
catch (lang::IllegalArgumentException &)
{
Reference<deployment::XPackage> p(
- findPackage(
- xPackageManager, xCmdEnv, cmdPackage ) );
+ findPackage(repository,
+ xExtensionManager, xCmdEnv, cmdPackage ) );
//Todo. temporary preventing exception in bundled case.
//In case of a bundled extension, remove would be called as a result of
//uninstalling a rpm. Then we do not want to show an error when the
@@ -389,8 +394,9 @@ extern "C" int unopkg_main()
if ( !p.is() && !option_bundled)
throw;
else if (p.is())
- xPackageManager->removePackage(
+ xExtensionManager->removeExtension(
::dp_misc::getIdentifier(p), p->getName(),
+ repository,
Reference<task::XAbortChannel>(), xCmdEnv );
}
}
@@ -399,18 +405,18 @@ extern "C" int unopkg_main()
else if (subCommand.equalsAsciiL(
RTL_CONSTASCII_STRINGPARAM("reinstall") ))
{
- xPackageManager->reinstallDeployedPackages(
- Reference<task::XAbortChannel>(), xCmdEnv );
+ xExtensionManager->reinstallDeployedExtensions(
+ repository, Reference<task::XAbortChannel>(), xCmdEnv);
}
else if (subCommand.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("list") ))
{
Sequence< Reference<deployment::XPackage> > packages;
if (cmdPackages.empty())
{
- packages = xPackageManager->getDeployedPackages(
- Reference<task::XAbortChannel>(), xCmdEnv );
+ packages = xExtensionManager->getDeployedExtensions(
+ repository, Reference<task::XAbortChannel>(), xCmdEnv );
dp_misc::writeConsole(
- OUSTR("all deployed ") + deploymentContext + OUSTR(" packages:\n"));
+ OUSTR("all deployed ") + repository + OUSTR(" packages:\n"));
}
else
{
@@ -418,13 +424,13 @@ extern "C" int unopkg_main()
for ( ::std::size_t pos = 0; pos < cmdPackages.size(); ++pos )
try
{
- packages[ pos ] = xPackageManager->getDeployedPackage(
- cmdPackages[ pos ], cmdPackages[ pos ], xCmdEnv );
+ packages[ pos ] = xExtensionManager->getDeployedExtension(
+ repository, cmdPackages[ pos ], cmdPackages[ pos ], xCmdEnv );
}
catch (lang::IllegalArgumentException &)
{
- packages[ pos ] = findPackage(
- xPackageManager, xCmdEnv, cmdPackages[ pos ] );
+ packages[ pos ] = findPackage(repository,
+ xExtensionManager, xCmdEnv, cmdPackages[ pos ] );
if ( !packages[ pos ].is() )
throw;
}
diff --git a/desktop/source/pkgchk/unopkg/unopkg_cmdenv.cxx b/desktop/source/pkgchk/unopkg/unopkg_cmdenv.cxx
index e4a503d98732..d23dcbf9577d 100644
--- a/desktop/source/pkgchk/unopkg/unopkg_cmdenv.cxx
+++ b/desktop/source/pkgchk/unopkg/unopkg_cmdenv.cxx
@@ -320,7 +320,7 @@ void CommandEnvironmentImpl::handle(
deployment::VersionException nc_exc;
if (request >>= nc_exc) {
approve = m_option_force_overwrite ||
- (::dp_misc::comparePackageVersions(nc_exc.New, nc_exc.Deployed)
+ (::dp_misc::compareVersions(nc_exc.NewVersion, nc_exc.Deployed->getVersion())
== ::dp_misc::GREATER);
abort = !approve;
}