blob: 9e8b329a03b4c8cbddbe83ad02d71cbee050964d [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2000, 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
*
* Contributors:
* IBM Corporation - initial API and implementation
*******************************************************************************/
package org.eclipse.jdt.internal.core;
import org.eclipse.core.resources.ResourcesPlugin;
import org.eclipse.core.runtime.jobs.ISchedulingRule;
import org.eclipse.jdt.core.IJavaElement;
import org.eclipse.jdt.core.JavaModelException;
/*
* Abstract class for operations that change the classpath
*/
public abstract class ChangeClasspathOperation extends JavaModelOperation {
protected boolean canChangeResources;
public ChangeClasspathOperation(IJavaElement[] elements, boolean canChangeResources) {
super(elements);
this.canChangeResources = canChangeResources;
}
protected boolean canModifyRoots() {
// changing the classpath can modify roots
return true;
}
/*
* The resolved classpath of the given project may have changed:
* - generate a delta
* - trigger indexing
* - update project references
* - create resolved classpath markers
*/
protected void classpathChanged(ClasspathChange change, boolean refreshExternalFolder) throws JavaModelException {
// reset the project's caches early since some clients rely on the project's caches being up-to-date when run inside an IWorkspaceRunnable
// (see https://bugs.eclipse.org/bugs/show_bug.cgi?id=212769#c5 )
JavaProject project = change.project;
project.resetCaches();
if (this.canChangeResources) {
// workaround for https://bugs.eclipse.org/bugs/show_bug.cgi?id=177922
if (isTopLevelOperation() && !ResourcesPlugin.getWorkspace().isTreeLocked()) {
new ClasspathValidation(project).validate();
}
// delta, indexing and classpath markers are going to be created by the delta processor
// while handling the resource change (either .classpath change, or project touched)
// however ensure project references are updated
// since some clients rely on the project references when run inside an IWorkspaceRunnable
new ProjectReferenceChange(project, change.oldResolvedClasspath).updateProjectReferencesIfNecessary();
// and ensure that external folders are updated as well
new ExternalFolderChange(project, change.oldResolvedClasspath).updateExternalFoldersIfNecessary(refreshExternalFolder, null);
} else {
DeltaProcessingState state = JavaModelManager.getDeltaState();
JavaElementDelta delta = new JavaElementDelta(getJavaModel());
int result = change.generateDelta(delta, true/*add classpath change*/);
if ((result & ClasspathChange.HAS_DELTA) != 0) {
// create delta
addDelta(delta);
// need to recompute root infos
state.rootsAreStale = true;
// ensure indexes are updated
change.requestIndexing();
// ensure classpath is validated on next build
state.addClasspathValidation(project);
}
if ((result & ClasspathChange.HAS_PROJECT_CHANGE) != 0) {
// ensure project references are updated on next build
state.addProjectReferenceChange(project, change.oldResolvedClasspath);
}
if ((result & ClasspathChange.HAS_LIBRARY_CHANGE) != 0) {
// ensure external folders are updated on next build
state.addExternalFolderChange(project, change.oldResolvedClasspath);
}
}
}
protected ISchedulingRule getSchedulingRule() {
return null; // no lock taken while changing classpath
}
public boolean isReadOnly() {
return !this.canChangeResources;
}
}