Skip to main content
summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDJ Houghton2010-01-19 20:30:34 +0000
committerDJ Houghton2010-01-19 20:30:34 +0000
commite4eb90e7667876c2a0d280d59404bdf805743054 (patch)
tree1677d419c5d13bb5d6b6334d96eb96eb0e5f8606
parentcdcaf976b5399762363680438d906aabaf8f1507 (diff)
downloadrt.equinox.p2-e4eb90e7667876c2a0d280d59404bdf805743054.tar.gz
rt.equinox.p2-e4eb90e7667876c2a0d280d59404bdf805743054.tar.xz
rt.equinox.p2-e4eb90e7667876c2a0d280d59404bdf805743054.zip
Bug 299544 - Links in dropins directory are never rescannedv20100201-1055R34x_v20100119
-rw-r--r--bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Activator.java185
-rw-r--r--bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/DropinsRepositoryListener.java37
-rw-r--r--bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Messages.java5
-rw-r--r--bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/messages.properties6
4 files changed, 144 insertions, 89 deletions
diff --git a/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Activator.java b/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Activator.java
index 1d61916c2..dac8868ba 100644
--- a/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Activator.java
+++ b/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Activator.java
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2007, 2009 IBM Corporation and others. All rights reserved.
+ * Copyright (c) 2007, 2010 IBM Corporation and others. All rights reserved.
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v1.0 which accompanies this distribution,
* and is available at http://www.eclipse.org/legal/epl-v10.html
@@ -42,11 +42,16 @@ public class Activator implements BundleActivator {
private static final String CONFIG_INI = "config.ini"; //$NON-NLS-1$
private static final String PLATFORM_CFG = "org.eclipse.update/platform.xml"; //$NON-NLS-1$
private static final String CACHE_FILENAME = "cache.timestamps"; //$NON-NLS-1$
+ private static final String DIR_ECLIPSE = "eclipse"; //$NON-NLS-1$
+ private static final String DIR_PLUGINS = "plugins"; //$NON-NLS-1$
+ private static final String DIR_FEATURES = "features"; //$NON-NLS-1$
+ private static final String EXT_LINK = ".link"; //$NON-NLS-1$
private static PackageAdmin packageAdmin;
private static BundleContext bundleContext;
private ServiceReference packageAdminRef;
private List watchers = new ArrayList();
private final static Set repositories = new HashSet();
+ private Collection filesToCheck = null;
/**
* Helper method to create an extension location metadata repository at the given URL.
@@ -136,8 +141,11 @@ public class Activator implements BundleActivator {
// check to see if there is really any work to do. Do this after setting the context, and
// doing other initialization in case others call our public methods later.
- if (isUpToDate())
+ if (isUpToDate()) {
+ // clear the cache
+ filesToCheck = null;
return;
+ }
if (!startEarly("org.eclipse.equinox.p2.exemplarysetup")) //$NON-NLS-1$
return;
@@ -166,6 +174,7 @@ public class Activator implements BundleActivator {
// see Bug 223422
// for now explicitly nulling out these repos to allow GC to occur
repositories.clear();
+ filesToCheck = null;
}
private void checkConfigIni() {
@@ -214,55 +223,127 @@ public class Activator implements BundleActivator {
if (timestamps.isEmpty())
return false;
- // check platform.xml
+ // gather the list of files/folders that we need to check
+ Collection files = getFilesToCheck();
+ for (Iterator iter = files.iterator(); iter.hasNext();) {
+ File file = (File) iter.next();
+ String key = file.getAbsolutePath();
+ String timestamp = timestamps.getProperty(key);
+ if (timestamp == null)
+ return false;
+ if (!Long.toString(file.lastModified()).equals(timestamp))
+ return false;
+ timestamps.remove(key);
+ }
+
+ // if we had some extra timestamps in the file, then signal that something has
+ // changed and we need to reconcile
+ return timestamps.isEmpty();
+ }
+
+ /*
+ * Return a collection of files which are interesting to us when we want to record timestamps
+ * to figure out if something has changed and perhaps avoid an unnecessary reconcilation.
+ */
+ private Collection getFilesToCheck() {
+ if (filesToCheck != null)
+ return filesToCheck;
+
+ Set result = new HashSet();
+
+ // configuration/org.eclipse.update/platform.xml, configuration/../plugins, configuration/../features
File configuration = getConfigurationLocation();
if (configuration != null) {
- File platformXML = new File(configuration, PLATFORM_CFG);
- if (!Long.toString(platformXML.lastModified()).equals(timestamps.getProperty(platformXML.getAbsolutePath())))
- return false;
- // the plugins and features directories are always siblings to the configuration directory
+ result.add(new File(configuration, PLATFORM_CFG));
File parent = configuration.getParentFile();
if (parent != null) {
File plugins = new File(parent, "plugins"); //$NON-NLS-1$
- if (!Long.toString(plugins.lastModified()).equals(timestamps.getProperty(plugins.getAbsolutePath())))
- return false;
+ result.add(plugins);
File features = new File(parent, "features"); //$NON-NLS-1$
- if (!Long.toString(features.lastModified()).equals(timestamps.getProperty(features.getAbsolutePath())))
- return false;
+ result.add(features);
}
}
- // if we are in shared mode then check the timestamps of the parent configuration
+ // if we are in shared mode then record the same files for the parent configuration
File parentConfiguration = getParentConfigurationLocation();
if (parentConfiguration != null) {
- File platformXML = new File(parentConfiguration, PLATFORM_CFG);
- if (!Long.toString(platformXML.lastModified()).equals(timestamps.getProperty(platformXML.getAbsolutePath())))
- return false;
- // the plugins and features directories are always siblings to the configuration directory
+ result.add(new File(parentConfiguration, PLATFORM_CFG));
File parent = parentConfiguration.getParentFile();
if (parent != null) {
File plugins = new File(parent, "plugins"); //$NON-NLS-1$
- if (!Long.toString(plugins.lastModified()).equals(timestamps.getProperty(plugins.getAbsolutePath())))
- return false;
+ result.add(plugins);
File features = new File(parent, "features"); //$NON-NLS-1$
- if (!Long.toString(features.lastModified()).equals(timestamps.getProperty(features.getAbsolutePath())))
- return false;
+ result.add(features);
}
}
- // check dropins folders
+ // dropins folders
File[] dropins = getDropinsDirectories();
- for (int i = 0; i < dropins.length; i++) {
- if (!Long.toString(dropins[i].lastModified()).equals(timestamps.getProperty(dropins[i].getAbsolutePath())))
- return false;
- }
- // check links folder
+ result.addAll(getDropinsToCheck(dropins));
+
+ // links folders
File[] links = getLinksDirectories();
- for (int i = 0; i < links.length; i++) {
- if (!Long.toString(links[i].lastModified()).equals(timestamps.getProperty(links[i].getAbsolutePath())))
- return false;
+ result.addAll(getDropinsToCheck(links));
+
+ filesToCheck = result;
+ return filesToCheck;
+ }
+
+ /*
+ * Iterate over the given collection of files (could be dropins or links folders) and
+ * return a collection of files that might be interesting to check the timestamps of.
+ */
+ private Collection getDropinsToCheck(File[] files) {
+ Collection result = new HashSet();
+ for (int outer = 0; outer < files.length; outer++) {
+ // add top-level file/folder
+ result.add(files[outer]);
+
+ File[] children = files[outer].listFiles();
+ for (int inner = 0; children != null && inner < children.length; inner++) {
+ File child = children[inner];
+ if (child.isFile() && child.getName().toLowerCase().endsWith(EXT_LINK)) {
+ // if we have a link file then add the link file and its target
+ File target = DropinsRepositoryListener.getLinkedFile(child);
+ if (target == null || !target.exists())
+ continue;
+ result.add(child);
+ result.add(target);
+ File eclipse = new File(target, DIR_ECLIPSE);
+ result.add(eclipse);
+ result.add(new File(eclipse, DIR_PLUGINS));
+ result.add(new File(eclipse, DIR_FEATURES));
+
+ } else if (child.getName().equalsIgnoreCase(DIR_ECLIPSE)) {
+ // if it is an "eclipse" dir then add it as well as "plugins" and "features"
+ result.add(child);
+ result.add(new File(child, DIR_PLUGINS));
+ result.add(new File(child, DIR_FEATURES));
+
+ } else if (child.isDirectory()) {
+ // look for "dropins/foo/plugins" (and "features") and
+ // "dropins/foo/eclipse/plugins" (and "features")
+ // Note: we could have a directory-based bundle here but we
+ // will still add it since it won't hurt anything (one extra timestamp check)
+ result.add(child);
+ File parent;
+ File eclipse = new File(child, DIR_ECLIPSE);
+ if (eclipse.exists()) {
+ result.add(eclipse);
+ parent = eclipse;
+ } else {
+ parent = child;
+ }
+ File plugins = new File(parent, DIR_PLUGINS);
+ if (plugins.exists())
+ result.add(plugins);
+ File features = new File(parent, DIR_FEATURES);
+ if (features.exists())
+ result.add(features);
+ }
+ }
}
- return true;
+ return result;
}
/*
@@ -295,46 +376,10 @@ public class Activator implements BundleActivator {
*/
private void writeTimestamps() {
Properties timestamps = new Properties();
- // cache the platform.xml file timestamp
- File configuration = getConfigurationLocation();
- if (configuration != null) {
- File platformXML = new File(configuration, PLATFORM_CFG);
- // always write out the timestamp even if it doesn't exist so we can detect addition/removal
- timestamps.put(platformXML.getAbsolutePath(), Long.toString(platformXML.lastModified()));
- File parent = configuration.getParentFile();
- if (parent != null) {
- File plugins = new File(parent, "plugins"); //$NON-NLS-1$
- timestamps.put(plugins.getAbsolutePath(), Long.toString(plugins.lastModified()));
- File features = new File(parent, "features"); //$NON-NLS-1$
- timestamps.put(features.getAbsolutePath(), Long.toString(features.lastModified()));
- }
- }
- // if we are in shared mode then write out the information for the parent configuration
- File parentConfiguration = getParentConfigurationLocation();
- if (parentConfiguration != null) {
- File platformXML = new File(parentConfiguration, PLATFORM_CFG);
- // always write out the timestamp even if it doesn't exist so we can detect addition/removal
- timestamps.put(platformXML.getAbsolutePath(), Long.toString(platformXML.lastModified()));
- File parent = parentConfiguration.getParentFile();
- if (parent != null) {
- File plugins = new File(parent, "plugins"); //$NON-NLS-1$
- timestamps.put(plugins.getAbsolutePath(), Long.toString(plugins.lastModified()));
- File features = new File(parent, "features"); //$NON-NLS-1$
- timestamps.put(features.getAbsolutePath(), Long.toString(features.lastModified()));
- }
- }
-
- // cache the dropins folders timestamp
- // always write out the timestamp even if it doesn't exist so we can detect addition/removal
- File[] dropins = getDropinsDirectories();
- for (int i = 0; i < dropins.length; i++) {
- timestamps.put(dropins[i].getAbsolutePath(), Long.toString(dropins[i].lastModified()));
- }
- // cache links folders timestamps
- // always write out the timestamp even if it doesn't exist so we can detect addition/removal
- File[] links = getLinksDirectories();
- for (int i = 0; i < links.length; i++) {
- timestamps.put(links[i].getAbsolutePath(), Long.toString(links[i].lastModified()));
+ Collection files = getFilesToCheck();
+ for (Iterator iter = files.iterator(); iter.hasNext();) {
+ File file = (File) iter.next();
+ timestamps.put(file.getAbsolutePath(), Long.toString(file.lastModified()));
}
// write out the file
diff --git a/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/DropinsRepositoryListener.java b/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/DropinsRepositoryListener.java
index 8771e00f3..42a863046 100644
--- a/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/DropinsRepositoryListener.java
+++ b/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/DropinsRepositoryListener.java
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2008 IBM Corporation and others.
+ * Copyright (c) 2008, 2010 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@@ -26,6 +26,7 @@ import org.eclipse.equinox.internal.provisional.p2.core.repository.IRepository;
import org.eclipse.equinox.internal.provisional.p2.directorywatcher.RepositoryListener;
import org.eclipse.equinox.internal.provisional.p2.metadata.repository.IMetadataRepository;
import org.eclipse.equinox.internal.provisional.p2.metadata.repository.IMetadataRepositoryManager;
+import org.eclipse.osgi.util.NLS;
import org.osgi.framework.BundleContext;
import org.osgi.framework.ServiceReference;
@@ -77,7 +78,7 @@ public class DropinsRepositoryListener extends RepositoryListener {
return true;
}
- private String getLinkPath(File file) {
+ static File getLinkedFile(File file) {
Properties links = new Properties();
try {
InputStream input = new BufferedInputStream(new FileInputStream(file));
@@ -87,11 +88,11 @@ public class DropinsRepositoryListener extends RepositoryListener {
input.close();
}
} catch (IOException e) {
- // ignore
+ LogHelper.log(new Status(IStatus.ERROR, Activator.ID, NLS.bind(Messages.error_reading_link, file.getAbsolutePath()), e));
+ return null;
}
String path = links.getProperty(LINKS_PATH);
if (path == null) {
- // log
return null;
}
@@ -103,7 +104,19 @@ public class DropinsRepositoryListener extends RepositoryListener {
} else {
path = path.trim();
}
- return path;
+ File linkedFile = new File(path);
+ if (!linkedFile.isAbsolute()) {
+ // link support is relative to the install root
+ File root = Activator.getEclipseHome();
+ if (root != null)
+ linkedFile = new File(root, path);
+ }
+ try {
+ return linkedFile.getCanonicalFile();
+ } catch (IOException e) {
+ LogHelper.log(new Status(IStatus.ERROR, Activator.ID, NLS.bind(Messages.error_resolving_link, linkedFile.getAbsolutePath(), file.getAbsolutePath()), e));
+ return null;
+ }
}
private URL createRepositoryURL(File file) {
@@ -142,21 +155,13 @@ public class DropinsRepositoryListener extends RepositoryListener {
}
private URL getLinkRepository(File file, boolean logMissingLink) throws IOException {
- String path = getLinkPath(file);
- if (path == null) {
+ File linkedFile = getLinkedFile(file);
+ if (linkedFile == null) {
if (logMissingLink)
LogHelper.log(new Status(IStatus.ERROR, Activator.ID, "Unable to determine link location from file: " + file.getAbsolutePath())); //$NON-NLS-1$
return null;
}
- File linkedFile = new File(path);
- if (!linkedFile.isAbsolute()) {
- // link support is relative to the install root
- File root = Activator.getEclipseHome();
- if (root != null)
- linkedFile = new File(root, path);
- }
- File canonicalFile = linkedFile.getCanonicalFile();
- return canonicalFile.toURL();
+ return linkedFile.toURL();
}
public void getMetadataRepository(URL repoURL) {
diff --git a/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Messages.java b/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Messages.java
index d20774237..816a6c799 100644
--- a/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Messages.java
+++ b/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/Messages.java
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2008 IBM Corporation and others.
+ * Copyright (c) 2008, 2010 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
@@ -21,6 +21,9 @@ public class Messages extends NLS {
public static String errorLoadingRepository;
public static String errorProcessingConfg;
public static String metadata_repo_manager_not_registered;
+ public static String error_reading_link;
+ public static String error_resolving_link;
+
static {
// initialize resource bundle
NLS.initializeMessages(BUNDLE_NAME, Messages.class);
diff --git a/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/messages.properties b/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/messages.properties
index d8066d062..b4276f25c 100644
--- a/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/messages.properties
+++ b/bundles/org.eclipse.equinox.p2.reconciler.dropins/src/org/eclipse/equinox/internal/p2/reconciler/dropins/messages.properties
@@ -1,5 +1,5 @@
###############################################################################
-# Copyright (c) 2007, 2008 IBM Corporation and others.
+# Copyright (c) 2007, 2010 IBM Corporation and others.
# All rights reserved. This program and the accompanying materials
# are made available under the terms of the Eclipse Public License v1.0
# which accompanies this distribution, and is available at
@@ -11,4 +11,6 @@
artifact_repo_manager_not_registered=ArtifactRepositoryManager not registered.
errorLoadingRepository=Error occurred while loading repository at {0}.
errorProcessingConfg=Exception while processing configuration.
-metadata_repo_manager_not_registered=MetadataRepositoryManager not registered. \ No newline at end of file
+metadata_repo_manager_not_registered=MetadataRepositoryManager not registered.
+error_reading_link = Error occurred while reading link file at {0}.
+error_resolving_link = Error occurred while resolving linked folder {0} from {1}.

Back to the top