### Eclipse Workspace Patch 1.0 #P org.eclipse.jdt.core Index: model/org/eclipse/jdt/core/IJavaModelStatusConstants.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/core/IJavaModelStatusConstants.java,v retrieving revision 1.37 diff -u -r1.37 IJavaModelStatusConstants.java --- model/org/eclipse/jdt/core/IJavaModelStatusConstants.java 10 May 2006 18:03:42 -0000 1.37 +++ model/org/eclipse/jdt/core/IJavaModelStatusConstants.java 16 Jan 2007 17:52:20 -0000 @@ -320,4 +320,16 @@ * @since 3.2 */ public static final int UNKNOWN_JAVADOC_FORMAT = 1009; + /** + *

Status constant indicating that the variable is deprecated.

+ * + * @since 3.3 + */ + public static final int DEPRECATED_VARIABLE = 1010; + /** + *

Status constant indicating that the variable is read-only.

+ * + * @since 3.3 + */ + public static final int READ_ONLY_VARIABLE = 1011; } Index: model/org/eclipse/jdt/core/IClasspathEntry.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/core/IClasspathEntry.java,v retrieving revision 1.59 diff -u -r1.59 IClasspathEntry.java --- model/org/eclipse/jdt/core/IClasspathEntry.java 29 Sep 2006 17:13:57 -0000 1.59 +++ model/org/eclipse/jdt/core/IClasspathEntry.java 16 Jan 2007 17:52:20 -0000 @@ -15,7 +15,7 @@ /** * An entry on a Java project classpath identifying one or more package fragment * roots. A classpath entry has a content kind (either source, - * K_SOURCE, or binary, K_BINARY), which is inherited + * {@link IPackageFragmentRoot#K_SOURCE}, or binary, {@link IPackageFragmentRoot#K_BINARY}), which is inherited * by each package fragment root and package fragment associated with the entry. *

* A classpath entry can refer to any of the following:

*

- * The result of IJavaProject#getResolvedClasspath will have all entries of type - * CPE_VARIABLE and CPE_CONTAINER resolved to a set of - * CPE_SOURCE, CPE_LIBRARY or CPE_PROJECT + * The result of {@link IJavaProject#getResolvedClasspath} will have all entries of type + * {@link #CPE_VARIABLE} and {@link #CPE_CONTAINER} resolved to a set of + * {@link #CPE_SOURCE}, {@link #CPE_LIBRARY} or {@link #CPE_PROJECT} * classpath entries. *

- * Any classpath entry other than a source folder (kind CPE_SOURCE) can + * Any classpath entry other than a source folder (kind {@link #CPE_SOURCE}) can * be marked as being exported. Exported entries are automatically contributed to * dependent projects, along with the project's default output folder, which is * implicitly exported, and any auxiliary output folders specified on source @@ -102,7 +102,7 @@ * followed by the any exported entries. *

* This interface is not intended to be implemented by clients. - * Classpath entries can be created via methods on JavaCore. + * Classpath entries can be created via methods on {@link JavaCore}. *

* * @see JavaCore#newLibraryEntry(org.eclipse.core.runtime.IPath, org.eclipse.core.runtime.IPath, org.eclipse.core.runtime.IPath) @@ -170,11 +170,11 @@ * Returns the kind of files found in the package fragments identified by this * classpath entry. * - * @return IPackageFragmentRoot.K_SOURCE for files containing - * source code, and IPackageFragmentRoot.K_BINARY for binary + * @return {@link IPackageFragmentRoot#K_SOURCE} for files containing + * source code, and {@link IPackageFragmentRoot#K_BINARY} for binary * class files. - * There is no specified value for an entry denoting a variable (CPE_VARIABLE) - * or a classpath container (CPE_CONTAINER). + * There is no specified value for an entry denoting a variable ({@link #CPE_VARIABLE}) + * or a classpath container ({@link #CPE_CONTAINER}). */ int getContentKind(); @@ -183,16 +183,16 @@ * * @return one of: * */ @@ -344,11 +344,11 @@ /** * Returns the full path to the specific location where the builder writes * .class files generated for this source entry - * (entry kind CPE_SOURCE). + * (entry kind {@link #CPE_SOURCE}). *

* Source entries can optionally be associated with a specific output location. * If none is provided, the source entry will be implicitly associated with its project - * default output location (see IJavaProject#getOutputLocation). + * default output location (see {@link IJavaProject#getOutputLocation}). *

* NOTE: A specific output location cannot coincidate with another source/library entry. *

@@ -364,24 +364,24 @@ * Returns the path of this classpath entry. * * The meaning of the path of a classpath entry depends on its entry kind: * @@ -410,7 +410,7 @@ * Returns the path within the source archive or folder where package fragments * are located. An empty path indicates that packages are located at * the root of the source archive or folder. Returns a non-null value - * if and only if getSourceAttachmentPath returns + * if and only if {@link #getSourceAttachmentPath} returns * a non-null value. * * @return the path within the source archive or folder, or null if @@ -421,7 +421,7 @@ /** * Returns whether this entry is exported to dependent projects. * Always returns false for source entries (kind - * CPE_SOURCE), which cannot be exported. + * {@link #CPE_SOURCE}), which cannot be exported. * * @return true if exported, and false otherwise * @since 2.0 Index: model/org/eclipse/jdt/core/ClasspathVariableInitializer.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/core/ClasspathVariableInitializer.java,v retrieving revision 1.12 diff -u -r1.12 ClasspathVariableInitializer.java --- model/org/eclipse/jdt/core/ClasspathVariableInitializer.java 10 May 2006 18:03:42 -0000 1.12 +++ model/org/eclipse/jdt/core/ClasspathVariableInitializer.java 16 Jan 2007 17:52:20 -0000 @@ -25,6 +25,13 @@ */ public abstract class ClasspathVariableInitializer { + /** + * Initialized variable flags. + */ + int flags = 0; // default is no flag + final static int DEPRECATED = 0x01; + final static int READ_ONLY = 0x02; + /** * Creates a new classpath variable initializer. */ @@ -49,4 +56,26 @@ * @see JavaCore#setClasspathVariables(String[], org.eclipse.core.runtime.IPath[], org.eclipse.core.runtime.IProgressMonitor) */ public abstract void initialize(String variable); + + /** + * Return whether the initialized variable is deprecated or not. + * + * @return true if the initialized variable is deprecated, + * false otherwise. + * @since 3.3 + */ + public final boolean isDeprecated() { + return (this.flags & DEPRECATED) != 0; + } + + /** + * Return whether the initialized variable is read-only or not. + * + * @return true if the initialized variable is read-only, + * false otherwise. + * @since 3.3 + */ + public final boolean isReadOnly() { + return (this.flags & READ_ONLY) != 0; + } } Index: model/org/eclipse/jdt/core/JavaCore.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/core/JavaCore.java,v retrieving revision 1.559 diff -u -r1.559 JavaCore.java --- model/org/eclipse/jdt/core/JavaCore.java 12 Jan 2007 17:58:48 -0000 1.559 +++ model/org/eclipse/jdt/core/JavaCore.java 16 Jan 2007 17:52:21 -0000 @@ -1617,55 +1617,7 @@ return variablePath; } - // even if persisted value exists, initializer is given priority, only if no initializer is found the persisted value is reused - final ClasspathVariableInitializer initializer = JavaCore.getClasspathVariableInitializer(variableName); - if (initializer != null){ - if (JavaModelManager.CP_RESOLVE_VERBOSE){ - Util.verbose( - "CPVariable INIT - triggering initialization\n" + //$NON-NLS-1$ - " variable: " + variableName + '\n' + //$NON-NLS-1$ - " initializer: " + initializer + '\n' + //$NON-NLS-1$ - " invocation stack trace:"); //$NON-NLS-1$ - new Exception("").printStackTrace(System.out); //$NON-NLS-1$ - } - manager.variablePut(variableName, JavaModelManager.VARIABLE_INITIALIZATION_IN_PROGRESS); // avoid initialization cycles - boolean ok = false; - try { - // let OperationCanceledException go through - // (see https://bugs.eclipse.org/bugs/show_bug.cgi?id=59363) - initializer.initialize(variableName); - - variablePath = manager.variableGet(variableName); // initializer should have performed side-effect - if (variablePath == JavaModelManager.VARIABLE_INITIALIZATION_IN_PROGRESS) return null; // break cycle (initializer did not init or reentering call) - if (JavaModelManager.CP_RESOLVE_VERBOSE){ - Util.verbose( - "CPVariable INIT - after initialization\n" + //$NON-NLS-1$ - " variable: " + variableName +'\n' + //$NON-NLS-1$ - " variable path: " + variablePath); //$NON-NLS-1$ - } - manager.variablesWithInitializer.add(variableName); - ok = true; - } catch (RuntimeException e) { - if (JavaModelManager.CP_RESOLVE_VERBOSE) { - e.printStackTrace(); - } - throw e; - } catch (Error e) { - if (JavaModelManager.CP_RESOLVE_VERBOSE) { - e.printStackTrace(); - } - throw e; - } finally { - if (!ok) JavaModelManager.getJavaModelManager().variablePut(variableName, null); // flush cache - } - } else { - if (JavaModelManager.CP_RESOLVE_VERBOSE){ - Util.verbose( - "CPVariable INIT - no initializer found\n" + //$NON-NLS-1$ - " variable: " + variableName); //$NON-NLS-1$ - } - } - return variablePath; + return initializeClasspathVariable(variableName, variablePath); } /** @@ -1690,7 +1642,8 @@ IConfigurationElement [] configElements = extensions[i].getConfigurationElements(); for(int j = 0; j < configElements.length; j++){ try { - String varAttribute = configElements[j].getAttribute("variable"); //$NON-NLS-1$ + IConfigurationElement configElement = configElements[j]; + String varAttribute = configElement.getAttribute("variable"); //$NON-NLS-1$ if (variable.equals(varAttribute)) { if (JavaModelManager.CP_RESOLVE_VERBOSE) { Util.verbose( @@ -1700,7 +1653,16 @@ } Object execExt = configElements[j].createExecutableExtension("class"); //$NON-NLS-1$ if (execExt instanceof ClasspathVariableInitializer){ - return (ClasspathVariableInitializer)execExt; + ClasspathVariableInitializer initializer = (ClasspathVariableInitializer)execExt; + String deprecatedAttribute = configElement.getAttribute("deprecated"); //$NON-NLS-1$ + if (deprecatedAttribute != null) { + initializer.flags |= ClasspathVariableInitializer.DEPRECATED; + } + String readOnlyAttribute = configElement.getAttribute("readOnly"); //$NON-NLS-1$ + if (JavaModelManager.TRUE.equals(readOnlyAttribute)) { + initializer.flags |= ClasspathVariableInitializer.READ_ONLY; + } + return initializer; } } } catch(CoreException e){ @@ -3012,7 +2974,117 @@ if (monitor != null) monitor.done(); } } - + + /* + * Initialize classpath variable + */ + private static IPath initializeClasspathVariable(final String variableName, IPath variablePath) { + // even if persisted value exists, initializer is given priority, only if no initializer is found the persisted value is reused + final ClasspathVariableInitializer initializer = JavaCore.getClasspathVariableInitializer(variableName); + if (initializer != null){ + if (JavaModelManager.CP_RESOLVE_VERBOSE){ + Util.verbose( + "CPVariable INIT - triggering initialization\n" + //$NON-NLS-1$ + " variable: " + variableName + '\n' + //$NON-NLS-1$ + " initializer: " + initializer + '\n' + //$NON-NLS-1$ + " invocation stack trace:"); //$NON-NLS-1$ + new Exception("").printStackTrace(System.out); //$NON-NLS-1$ + } + JavaModelManager manager = JavaModelManager.getJavaModelManager(); + manager.variablePut(variableName, JavaModelManager.VARIABLE_INITIALIZATION_IN_PROGRESS); // avoid initialization cycles + boolean ok = false; + try { + // let OperationCanceledException go through + // (see https://bugs.eclipse.org/bugs/show_bug.cgi?id=59363) + initializer.initialize(variableName); + + variablePath = manager.variableGet(variableName); // initializer should have performed side-effect + if (variablePath == JavaModelManager.VARIABLE_INITIALIZATION_IN_PROGRESS) return null; // break cycle (initializer did not init or reentering call) + if (JavaModelManager.CP_RESOLVE_VERBOSE){ + Util.verbose( + "CPVariable INIT - after initialization\n" + //$NON-NLS-1$ + " variable: " + variableName +'\n' + //$NON-NLS-1$ + " variable path: " + variablePath); //$NON-NLS-1$ + } + manager.variablesWithInitializer.put(variableName, initializer.flags); + ok = true; + } catch (RuntimeException e) { + if (JavaModelManager.CP_RESOLVE_VERBOSE) { + e.printStackTrace(); + } + throw e; + } catch (Error e) { + if (JavaModelManager.CP_RESOLVE_VERBOSE) { + e.printStackTrace(); + } + throw e; + } finally { + if (!ok) JavaModelManager.getJavaModelManager().variablePut(variableName, null); // flush cache + } + } else { + if (JavaModelManager.CP_RESOLVE_VERBOSE){ + Util.verbose( + "CPVariable INIT - no initializer found\n" + //$NON-NLS-1$ + " variable: " + variableName); //$NON-NLS-1$ + } + } + return variablePath; + } + + /** + * Returns whether a given classpath variable is deprecated or not. + * + * @param variableName + * @return true if the classpath variable is deprecated, + * false otherwise of if the variable is not initialized yet. + * @since 3.3 + */ + public static boolean isClasspathVariableDeprecated(final String variableName) { + JavaModelManager manager = JavaModelManager.getJavaModelManager(); + IPath variablePath = manager.variableGet(variableName); + if (variablePath == JavaModelManager.VARIABLE_INITIALIZATION_IN_PROGRESS){ + return false; // currently do not store previous session result + } + + if (variablePath != null) { + if (variablePath == JavaModelManager.CP_ENTRY_IGNORE_PATH) { + return false; + } + } else { + initializeClasspathVariable(variableName, variablePath); + } + + int flags = manager.variableFlagsGet(variableName); + return flags > 0 && (flags & 0x01) != 0; + } + + /** + * Returns whether a given classpath variable is deprecated or not. + * + * @param variableName + * @return true if the classpath variable is deprecated, + * false otherwise of if the variable is not initialized yet. + * @since 3.3 + */ + public static boolean isClasspathVariableReadOnly(final String variableName) { + JavaModelManager manager = JavaModelManager.getJavaModelManager(); + IPath variablePath = manager.variableGet(variableName); + if (variablePath == JavaModelManager.VARIABLE_INITIALIZATION_IN_PROGRESS){ + return false; // currently do not store previous session result + } + + if (variablePath != null) { + if (variablePath == JavaModelManager.CP_ENTRY_IGNORE_PATH) { + return false; + } + } else { + initializeClasspathVariable(variableName, variablePath); + } + + int flags = manager.variableFlagsGet(variableName); + return flags > 0 && (flags & 0x02) != 0; + } + /** * Returns whether the given file name's extension is a Java-like extension. * @@ -3023,7 +3095,7 @@ public static boolean isJavaLikeFileName(String fileName) { return Util.isJavaLikeFileName(fileName); } - + /** * Returns whether the given marker references the given Java element. * Used for markers, which denote a Java element rather than a resource. Index: model/org/eclipse/jdt/internal/core/JavaModelOperation.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/JavaModelOperation.java,v retrieving revision 1.64 diff -u -r1.64 JavaModelOperation.java --- model/org/eclipse/jdt/internal/core/JavaModelOperation.java 23 Nov 2005 15:41:57 -0000 1.64 +++ model/org/eclipse/jdt/internal/core/JavaModelOperation.java 16 Jan 2007 17:52:25 -0000 @@ -61,7 +61,7 @@ protected HashMap attributes; public static final String HAS_MODIFIED_RESOURCE_ATTR = "hasModifiedResource"; //$NON-NLS-1$ - public static final String TRUE = "true"; //$NON-NLS-1$ + public static final String TRUE = JavaModelManager.TRUE; //public static final String FALSE = "false"; /** Index: model/org/eclipse/jdt/internal/core/JavaModelStatus.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/JavaModelStatus.java,v retrieving revision 1.42 diff -u -r1.42 JavaModelStatus.java --- model/org/eclipse/jdt/internal/core/JavaModelStatus.java 29 Mar 2006 03:08:48 -0000 1.42 +++ model/org/eclipse/jdt/internal/core/JavaModelStatus.java 16 Jan 2007 17:52:25 -0000 @@ -126,7 +126,7 @@ this(code, new IJavaElement[]{element}); this.string = string; } - + /** * Constructs an Java model status with the given corresponding * element and path @@ -134,7 +134,18 @@ public JavaModelStatus(int code, IJavaElement element, IPath path) { this(code, new IJavaElement[]{element}); this.path = path; - } + } + + /** + * Constructs an Java model status with the given corresponding + * element and path + */ + public JavaModelStatus(int severity, int code, IJavaElement element, IPath path) { + super(severity, JavaCore.PLUGIN_ID, code, "JavaModelStatus", null); //$NON-NLS-1$ + this.elements= new IJavaElement[]{element}; + this.path = path; + } + /** * Constructs an Java model status with the given corresponding * element, path and string @@ -172,6 +183,9 @@ * Returns the message that is relevant to the code of this status. */ public String getMessage() { + if (isMultiStatus()) { + return Messages.status_multiple; + } Throwable exception = getException(); if (exception == null) { switch (getCode()) { @@ -326,53 +340,63 @@ if (description == null) description = path.makeRelative().toString(); return Messages.bind(Messages.classpath_invalidContainer, new String[] {description, javaProject.getElementName()}); - case CP_VARIABLE_PATH_UNBOUND: - javaProject = (IJavaProject)elements[0]; - return Messages.bind(Messages.classpath_unboundVariablePath, new String[] {path.makeRelative().toString(), javaProject.getElementName()}); - - case CLASSPATH_CYCLE: - javaProject = (IJavaProject)elements[0]; - return Messages.bind(Messages.classpath_cycle, javaProject.getElementName()); - - case DISABLED_CP_EXCLUSION_PATTERNS: - javaProject = (IJavaProject)elements[0]; - String projectName = javaProject.getElementName(); - IPath newPath = path; - if (path.segment(0).toString().equals(projectName)) { - newPath = path.removeFirstSegments(1); - } - return Messages.bind(Messages.classpath_disabledInclusionExclusionPatterns, new String[] {newPath.makeRelative().toString(), projectName}); - - case DISABLED_CP_MULTIPLE_OUTPUT_LOCATIONS: - javaProject = (IJavaProject)elements[0]; - projectName = javaProject.getElementName(); - newPath = path; - if (path.segment(0).toString().equals(projectName)) { - newPath = path.removeFirstSegments(1); - } - return Messages.bind(Messages.classpath_disabledMultipleOutputLocations, new String[] {newPath.makeRelative().toString(), projectName}); + case CP_VARIABLE_PATH_UNBOUND: + javaProject = (IJavaProject)elements[0]; + return Messages.bind(Messages.classpath_unboundVariablePath, new String[] {path.makeRelative().toString(), javaProject.getElementName()}); + + case CLASSPATH_CYCLE: + javaProject = (IJavaProject)elements[0]; + return Messages.bind(Messages.classpath_cycle, javaProject.getElementName()); - case INCOMPATIBLE_JDK_LEVEL: + case DISABLED_CP_EXCLUSION_PATTERNS: javaProject = (IJavaProject)elements[0]; - return Messages.bind(Messages.classpath_incompatibleLibraryJDKLevel, new String[]{ - javaProject.getElementName(), - javaProject.getOption(JavaCore.COMPILER_CODEGEN_TARGET_PLATFORM, true), - path.makeRelative().toString(), - string, - }); - case CANNOT_RETRIEVE_ATTACHED_JAVADOC : - if (elements != null && elements.length == 1) { + String projectName = javaProject.getElementName(); + IPath newPath = path; + if (path.segment(0).toString().equals(projectName)) { + newPath = path.removeFirstSegments(1); + } + return Messages.bind(Messages.classpath_disabledInclusionExclusionPatterns, new String[] {newPath.makeRelative().toString(), projectName}); + + case DISABLED_CP_MULTIPLE_OUTPUT_LOCATIONS: + javaProject = (IJavaProject)elements[0]; + projectName = javaProject.getElementName(); + newPath = path; + if (path.segment(0).toString().equals(projectName)) { + newPath = path.removeFirstSegments(1); + } + return Messages.bind(Messages.classpath_disabledMultipleOutputLocations, new String[] {newPath.makeRelative().toString(), projectName}); + + case INCOMPATIBLE_JDK_LEVEL: + javaProject = (IJavaProject)elements[0]; + return Messages.bind(Messages.classpath_incompatibleLibraryJDKLevel, new String[]{ + javaProject.getElementName(), + javaProject.getOption(JavaCore.COMPILER_CODEGEN_TARGET_PLATFORM, true), + path.makeRelative().toString(), + string, + }); + + case CANNOT_RETRIEVE_ATTACHED_JAVADOC : + if (elements != null && elements.length == 1) { + if (this.string != null) { + return Messages.bind(Messages.status_cannot_retrieve_attached_javadoc, ((JavaElement)elements[0]).toStringWithAncestors(), this.string); + } + return Messages.bind(Messages.status_cannot_retrieve_attached_javadoc, ((JavaElement)elements[0]).toStringWithAncestors(), ""); //$NON-NLS-1$ + } if (this.string != null) { - return Messages.bind(Messages.status_cannot_retrieve_attached_javadoc, ((JavaElement)elements[0]).toStringWithAncestors(), this.string); + return Messages.bind(Messages.status_cannot_retrieve_attached_javadoc, this.string, "");//$NON-NLS-1$ } - return Messages.bind(Messages.status_cannot_retrieve_attached_javadoc, ((JavaElement)elements[0]).toStringWithAncestors(), ""); //$NON-NLS-1$ - } - if (this.string != null) { - return Messages.bind(Messages.status_cannot_retrieve_attached_javadoc, this.string, "");//$NON-NLS-1$ - } - break; - case UNKNOWN_JAVADOC_FORMAT : - return Messages.bind(Messages.status_unknown_javadoc_format, ((JavaElement)elements[0]).toStringWithAncestors()); + break; + + case UNKNOWN_JAVADOC_FORMAT : + return Messages.bind(Messages.status_unknown_javadoc_format, ((JavaElement)elements[0]).toStringWithAncestors()); + + case DEPRECATED_VARIABLE : + javaProject = (IJavaProject)elements[0]; + return Messages.bind(Messages.classpath_deprecated_variable, new String[] {path.segment(0).toString(), javaProject.getElementName()}); + + case READ_ONLY_VARIABLE : + javaProject = (IJavaProject)elements[0]; + return Messages.bind(Messages.classpath_read_only_variable, new String[] {path.segment(0).toString(), javaProject.getElementName()}); } if (string != null) { return string; @@ -466,6 +490,9 @@ public static IJavaModelStatus newMultiStatus(IJavaModelStatus[] children) { JavaModelStatus jms = new JavaModelStatus(); jms.children = children; + if (children != null && children.length > 0) { + jms.setCode(children[0].getCode()); + } return jms; } /** Index: model/org/eclipse/jdt/internal/core/ClasspathEntry.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/ClasspathEntry.java,v retrieving revision 1.94 diff -u -r1.94 ClasspathEntry.java --- model/org/eclipse/jdt/internal/core/ClasspathEntry.java 3 Oct 2006 09:43:27 -0000 1.94 +++ model/org/eclipse/jdt/internal/core/ClasspathEntry.java 16 Jan 2007 17:52:24 -0000 @@ -26,6 +26,7 @@ import org.eclipse.core.runtime.AssertionFailedException; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IPath; +import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.Path; import org.eclipse.jdt.core.IAccessRule; import org.eclipse.jdt.core.IClasspathAttribute; @@ -1616,21 +1617,50 @@ // variable entry check case IClasspathEntry.CPE_VARIABLE : - if (path != null && path.segmentCount() >= 1){ - try { - entry = JavaCore.getResolvedClasspathEntry(entry); - } catch (AssertionFailedException e) { - // Catch the assertion failure and throw java model exception instead - // see bug https://bugs.eclipse.org/bugs/show_bug.cgi?id=55992 - return new JavaModelStatus(IJavaModelStatusConstants.INVALID_PATH, e.getMessage()); - } - if (entry == null){ - return new JavaModelStatus(IJavaModelStatusConstants.CP_VARIABLE_PATH_UNBOUND, project, path); - } - return validateClasspathEntry(project, entry, checkSourceAttachment, recurseInContainers); - } else { + // Verify path + if (path == null || path.segmentCount() < 1) { return new JavaModelStatus(IJavaModelStatusConstants.INVALID_CLASSPATH, Messages.bind(Messages.classpath_illegalVariablePath, new String[] {entryPathMsg, projectName})); } + + // Resolve the entry + try { + entry = JavaCore.getResolvedClasspathEntry(entry); + } catch (AssertionFailedException e) { + // Catch the assertion failure and throw java model exception instead + // see bug https://bugs.eclipse.org/bugs/show_bug.cgi?id=55992 + return new JavaModelStatus(IJavaModelStatusConstants.INVALID_PATH, e.getMessage()); + } + if (entry == null){ + return new JavaModelStatus(IJavaModelStatusConstants.CP_VARIABLE_PATH_UNBOUND, project, path); + } + + // Get validation status + IJavaModelStatus status = validateClasspathEntry(project, entry, checkSourceAttachment, recurseInContainers); + if (!status.isOK()) { + return status; + } + + // Verify deprecation and read-only + String variableName = path.segment(0); + if (JavaCore.isClasspathVariableDeprecated(variableName)) { + if (JavaCore.isClasspathVariableReadOnly(variableName)) { + // put the two warnings in a multi-status + return JavaModelStatus.newMultiStatus( + new IJavaModelStatus[] { + new JavaModelStatus(IStatus.WARNING, IJavaModelStatusConstants.DEPRECATED_VARIABLE, project, path), + new JavaModelStatus(IStatus.WARNING, IJavaModelStatusConstants.READ_ONLY_VARIABLE, project, path) + } + ); + } + // only deprecated warning + return new JavaModelStatus(IStatus.WARNING, IJavaModelStatusConstants.DEPRECATED_VARIABLE, project, path); + } else if (JavaCore.isClasspathVariableReadOnly(variableName)) { + // only read-on warning + return new JavaModelStatus(IStatus.WARNING, IJavaModelStatusConstants.READ_ONLY_VARIABLE, project, path); + } + + // Status is OK + return status; // library entry check case IClasspathEntry.CPE_LIBRARY : Index: model/org/eclipse/jdt/internal/core/JavaModelManager.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/JavaModelManager.java,v retrieving revision 1.350 diff -u -r1.350 JavaModelManager.java --- model/org/eclipse/jdt/internal/core/JavaModelManager.java 12 Jan 2007 17:58:49 -0000 1.350 +++ model/org/eclipse/jdt/internal/core/JavaModelManager.java 16 Jan 2007 17:52:24 -0000 @@ -86,9 +86,16 @@ * Classpath variables pool */ public HashMap variables = new HashMap(5); - public HashSet variablesWithInitializer = new HashSet(5); public HashMap previousSessionVariables = new HashMap(5); private ThreadLocal variableInitializationInProgress = new ThreadLocal(); + + /** + * Map of classpath variables which have an initializer. + * Keys are variable names and values are flags corresponding to initializer + * additional attributes (currently bit0 for deprecation and bit1 for read-only) + * @see ClasspathVariableInitializer + */ + public HashtableOfObjectToInt variablesWithInitializer = new HashtableOfObjectToInt(5); /** * Classpath containers pool @@ -120,6 +127,7 @@ public final static String CP_CONTAINER_PREFERENCES_PREFIX = JavaCore.PLUGIN_ID+".classpathContainer."; //$NON-NLS-1$ public final static String CP_ENTRY_IGNORE = "####"; //$NON-NLS-1$ public final static IPath CP_ENTRY_IGNORE_PATH = new Path(CP_ENTRY_IGNORE); + public final static String TRUE = "true"; //$NON-NLS-1$ private final static int VARIABLES_AND_CONTAINERS_FILE_VERSION = 2; @@ -278,9 +286,9 @@ continue; } // add config element in the group it belongs to - if ("true".equals(configElement.getAttribute("modifiesEnvironment"))) //$NON-NLS-1$ //$NON-NLS-2$ + if (TRUE.equals(configElement.getAttribute("modifiesEnvironment"))) //$NON-NLS-1$ modifyingEnv.add(configElement); - else if ("true".equals(configElement.getAttribute("createsProblems"))) //$NON-NLS-1$ //$NON-NLS-2$ + else if (TRUE.equals(configElement.getAttribute("createsProblems"))) //$NON-NLS-1$ creatingProblems.add(configElement); else others.add(configElement); @@ -1124,12 +1132,12 @@ if (propertyName.startsWith(CP_VARIABLE_PREFERENCES_PREFIX)) { String varName = propertyName.substring(CP_VARIABLE_PREFERENCES_PREFIX.length()); JavaModelManager manager = getJavaModelManager(); - if (manager.variablesWithInitializer.contains(varName)) { + if (manager.variablesWithInitializer.containsKey(varName)) { // revert preference value as we will not apply it to JavaCore classpath variable String oldValue = (String) event.getOldValue(); if (oldValue == null) { // unexpected old value => remove variable from set - manager.variablesWithInitializer.remove(varName); + manager.variablesWithInitializer.removeKey(varName); } else { manager.getInstancePreferences().put(varName, oldValue); } @@ -1200,58 +1208,58 @@ public void configurePluginDebugOptions(){ if(JavaCore.getPlugin().isDebugging()){ String option = Platform.getDebugOption(BUFFER_MANAGER_DEBUG); - if(option != null) BufferManager.VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) BufferManager.VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(BUILDER_DEBUG); - if(option != null) JavaBuilder.DEBUG = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) JavaBuilder.DEBUG = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(COMPILER_DEBUG); - if(option != null) Compiler.DEBUG = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) Compiler.DEBUG = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(COMPLETION_DEBUG); - if(option != null) CompletionEngine.DEBUG = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) CompletionEngine.DEBUG = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(CP_RESOLVE_DEBUG); - if(option != null) JavaModelManager.CP_RESOLVE_VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) JavaModelManager.CP_RESOLVE_VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(DELTA_DEBUG); - if(option != null) DeltaProcessor.DEBUG = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) DeltaProcessor.DEBUG = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(DELTA_DEBUG_VERBOSE); - if(option != null) DeltaProcessor.VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) DeltaProcessor.VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(HIERARCHY_DEBUG); - if(option != null) TypeHierarchy.DEBUG = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) TypeHierarchy.DEBUG = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(INDEX_MANAGER_DEBUG); - if(option != null) JobManager.VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) JobManager.VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(JAVAMODEL_DEBUG); - if(option != null) JavaModelManager.VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) JavaModelManager.VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(JAVAMODELCACHE_DEBUG); - if(option != null) JavaModelCache.VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) JavaModelCache.VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(POST_ACTION_DEBUG); - if(option != null) JavaModelOperation.POST_ACTION_VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) JavaModelOperation.POST_ACTION_VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(RESOLUTION_DEBUG); - if(option != null) NameLookup.VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) NameLookup.VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(SEARCH_DEBUG); - if(option != null) BasicSearchEngine.VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) BasicSearchEngine.VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(SELECTION_DEBUG); - if(option != null) SelectionEngine.DEBUG = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) SelectionEngine.DEBUG = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(ZIP_ACCESS_DEBUG); - if(option != null) JavaModelManager.ZIP_ACCESS_VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) JavaModelManager.ZIP_ACCESS_VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(SOURCE_MAPPER_DEBUG_VERBOSE); - if(option != null) SourceMapper.VERBOSE = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) SourceMapper.VERBOSE = option.equalsIgnoreCase(TRUE) ; option = Platform.getDebugOption(ENABLE_NEW_FORMATTER); - if(option != null) DefaultCodeFormatter.USE_NEW_FORMATTER = option.equalsIgnoreCase("true") ; //$NON-NLS-1$ + if(option != null) DefaultCodeFormatter.USE_NEW_FORMATTER = option.equalsIgnoreCase(TRUE) ; } // configure performance options @@ -3950,7 +3958,7 @@ // Note: no need to close the Java model as this just removes Java element infos from the Java model cache } - + public synchronized IPath variableGet(String variableName){ // check initialization in progress first HashSet initializations = variableInitializationInProgress(); @@ -3960,6 +3968,10 @@ return (IPath)this.variables.get(variableName); } + public synchronized int variableFlagsGet(String variableName){ + return this.variablesWithInitializer.get(variableName); + } + /* * Returns the set of variable names that are being initialized in the current thread. */ @@ -4011,7 +4023,7 @@ public void variablePreferencesPut(String variableName, IPath variablePath) { String variableKey = CP_VARIABLE_PREFERENCES_PREFIX+variableName; if (variablePath == null) { - this.variablesWithInitializer.remove(variableName); + this.variablesWithInitializer.removeKey(variableName); getInstancePreferences().remove(variableKey); } else { getInstancePreferences().put(variableKey, variablePath.toString()); Index: schema/classpathVariableInitializer.exsd =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/schema/classpathVariableInitializer.exsd,v retrieving revision 1.6 diff -u -r1.6 classpathVariableInitializer.exsd --- schema/classpathVariableInitializer.exsd 24 May 2005 14:25:21 -0000 1.6 +++ schema/classpathVariableInitializer.exsd 16 Jan 2007 17:52:27 -0000 @@ -63,6 +63,23 @@ + + + + String explaining the reason why the associated variable is deprecated + + + + + + + + + + Indicates that the associated variable cannot be modified + + + Index: buildnotes_jdt-core.html =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/buildnotes_jdt-core.html,v retrieving revision 1.5635 diff -u -r1.5635 buildnotes_jdt-core.html --- buildnotes_jdt-core.html 16 Jan 2007 11:20:11 -0000 1.5635 +++ buildnotes_jdt-core.html 16 Jan 2007 17:52:20 -0000 @@ -43,6 +43,118 @@ + +


+Eclipse Platform Build Notes
+Java Development Tooling Core

+Eclipse SDK 3.3M5 - 16th January 2007 +
Project org.eclipse.jdt.core v_732 +(cvs). +

What's new in this drop

+
    +
  • Classpath variable may now be flagged as deprecated or read-only (see bug 138599 +and bug 156226).
    +Two new attributes have been added on ClasspathVariableInitializer schema: +
    +   <element name="classpathVariableInitializer">
    +      <complexType>
    +         ...
    +         <attribute name="deprecated" type="string">
    +            <annotation>
    +               <documentation>
    +                  String explaining the reason why the associated variable is deprecated
    +               </documentation>
    +               <appInfo>
    +                  <meta.attribute translatable="true"/>
    +               </appInfo>
    +            </annotation>
    +         </attribute>
    +         <attribute name="readOnly" type="boolean">
    +            <annotation>
    +               <documentation>
    +                  Indicates that the associated variable cannot be modified
    +               </documentation>
    +            </annotation>
    +         </attribute>
    +      </complexType>
    +   </element>
    +
    +When these attributes are set on classpathVariableInitializer extension point, classpath entry validation +will return a mutli-status IJavaModelStatus with corresponding severity level and messages. +
    +For example, following extension point set the TEST classpath variable as deprecated +and read-only: +
    +   <extension
    +         point="org.eclipse.jdt.core.classpathVariableInitializer">
    +      <classpathVariableInitializer
    +            class="org.eclipse.jdt.tests.model.TestInitializer"
    +            deprecated="The reason why this variable is deprecated"
    +            readOnly="true"
    +            variable="TEST">
    +      </classpathVariableInitializer>
    +   </extension>
    +
    +The calling JavaConventions.validateClasspathEntry(IJavaProject, IClasspathEntry, boolean) +method on corresponding variable entry will return a status with IStatus.WARNING severity +and following message: +
    +Classpath variable 'TEST' in project P is deprecated; Classpath variable 'TEST' in project P is read only
    +
    +User can also get deprecated and read-only information using following API methods: +
      +
    • ClasspathVariableInitializer: +
      +/**
      + * Return whether the initialized variable is deprecated or not.
      + * 
      + * @return true if the initialized variable is deprecated,
      + * 	false otherwise.
      + * @since 3.3
      + */
      +public final boolean isDeprecated()
      +/**
      + * Return whether the initialized variable is read-only or not.
      + * 
      + * @return true if the initialized variable is read-only,
      + * 	false otherwise.
      + * @since 3.3
      + */
      +public final boolean isReadOnly()
      +
      +
    • +
    • JavaCore: +
      +/**
      + * Returns whether a given classpath variable is deprecated or not.
      + *
      + * @param variableName
      + * @return true if the classpath variable is deprecated,
      + * 	false otherwise of if the variable is not initialized yet.
      + * @since 3.3
      + */
      +public static boolean isClasspathVariableDeprecated(final String variableName)
      +/**
      + * Returns whether a given classpath variable is deprecated or not.
      + *
      + * @param variableName
      + * @return true if the classpath variable is deprecated,
      + * 	false otherwise of if the variable is not initialized yet.
      + * @since 3.3
      + */
      +public static boolean isClasspathVariableReadOnly(final String variableName)
      +
      +
    • +
    +
  • +
+ +

Problem Reports Fixed

+156226 +[model][classpath] Allow classpath variable to be marked as non modifiable +
138599 +[model][classpath] Need a way to mark a classpath variable as deprecated +


Eclipse Platform Build Notes
Index: model/org/eclipse/jdt/internal/core/util/messages.properties =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/util/messages.properties,v retrieving revision 1.62 diff -u -r1.62 messages.properties --- model/org/eclipse/jdt/internal/core/util/messages.properties 28 Jun 2006 08:52:07 -0000 1.62 +++ model/org/eclipse/jdt/internal/core/util/messages.properties 16 Jan 2007 17:52:27 -0000 @@ -117,6 +117,7 @@ status_invalidResource = Invalid resource: {0} status_invalidResourceType = Invalid resource type for {0} status_invalidSibling = Invalid sibling: {0} +status_multiple = Several warnings/errors occured status_nameCollision = {0} already exists in target status_noLocalContents = Cannot find local contents for resource: {0} status_OK = OK @@ -167,6 +168,8 @@ classpath_disabledMultipleOutputLocations = Multiple output locations are disabled in project {1}, cannot associate entry: ''{0}'' with a specific output classpath_incompatibleLibraryJDKLevel = Incompatible .class files version in required binaries. Project ''{0}'' is targeting a {1} runtime, but is compiled against ''{2}'' which requires a {3} runtime classpath_duplicateEntryExtraAttribute = Duplicate extra attribute: ''{0}'' in classpath entry ''{1}'' for project {2} +classpath_deprecated_variable = Classpath variable ''{0}'' in project {1} is deprecated +classpath_read_only_variable = Classpath variable ''{0}'' in project {1} is read only ### miscellaneous file_notFound = File not found: ''{0}'' Index: model/org/eclipse/jdt/internal/core/util/Messages.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/model/org/eclipse/jdt/internal/core/util/Messages.java,v retrieving revision 1.14 diff -u -r1.14 Messages.java --- model/org/eclipse/jdt/internal/core/util/Messages.java 28 Jun 2006 08:52:07 -0000 1.14 +++ model/org/eclipse/jdt/internal/core/util/Messages.java 16 Jan 2007 17:52:27 -0000 @@ -114,6 +114,7 @@ public static String status_invalidResource; public static String status_invalidResourceType; public static String status_invalidSibling; + public static String status_multiple; public static String status_nameCollision; public static String status_noLocalContents; public static String status_OK; @@ -161,6 +162,8 @@ public static String classpath_disabledMultipleOutputLocations; public static String classpath_incompatibleLibraryJDKLevel; public static String classpath_duplicateEntryExtraAttribute; + public static String classpath_deprecated_variable; + public static String classpath_read_only_variable; public static String file_notFound; public static String file_badFormat; public static String path_nullPath; #P org.eclipse.jdt.core.tests.model Index: src/org/eclipse/jdt/core/tests/model/ClasspathInitializerTests.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/model/ClasspathInitializerTests.java,v retrieving revision 1.42 diff -u -r1.42 ClasspathInitializerTests.java --- src/org/eclipse/jdt/core/tests/model/ClasspathInitializerTests.java 10 Jan 2007 18:13:53 -0000 1.42 +++ src/org/eclipse/jdt/core/tests/model/ClasspathInitializerTests.java 16 Jan 2007 17:52:34 -0000 @@ -11,7 +11,9 @@ package org.eclipse.jdt.core.tests.model; import java.util.HashMap; +import java.util.HashSet; import java.util.Map; +import java.util.Set; import org.eclipse.core.resources.*; import org.eclipse.core.runtime.*; @@ -19,6 +21,7 @@ import org.eclipse.jdt.core.*; import org.eclipse.jdt.core.compiler.CharOperation; import org.eclipse.jdt.internal.core.JavaModelManager; +import org.eclipse.jdt.internal.core.JavaModelStatus; import org.eclipse.jdt.internal.core.UserLibraryClasspathContainer; import org.eclipse.jdt.internal.core.UserLibraryManager; @@ -28,7 +31,7 @@ public static class DefaultVariableInitializer implements VariablesInitializer.ITestInitializer { Map variableValues; - + Set deprecatedVariables, readOnlyVariables; /* * values is [, ]* */ @@ -46,6 +49,26 @@ (IPath)variableValues.get(variable), null); } + + public boolean isDeprecated(String variable) { + if (deprecatedVariables == null) return false; + return deprecatedVariables.contains(variable); + } + + public void setDeprecated(String variable) { + if (deprecatedVariables == null) deprecatedVariables = new HashSet(); + deprecatedVariables.add(variable); + } + + public void setReadOnly(String variable) { + if (readOnlyVariables == null) readOnlyVariables = new HashSet(); + readOnlyVariables.add(variable); + } + + public boolean isReadOnly(String variable) { + if (readOnlyVariables == null) return false; + return readOnlyVariables.contains(variable); + } } public static class DefaultContainerInitializer implements ContainerInitializer.ITestInitializer { @@ -887,6 +910,8 @@ buffer.append("Setting variable " + variable + " to " + path + "\n"); JavaCore.setClasspathVariable(variable, path, null); } + public void setDeprecated(String variable) {} + public void setReadOnly(String variable) {} }); createJavaProject("P", new String[] {}, new String[] {"TEST_LIB,TEST_SRC,TEST_ROOT"}, ""); assertEquals( @@ -909,6 +934,8 @@ buffer.append("Setting variable " + variable + " to " + path + "\n"); JavaCore.setClasspathVariable(variable, path, null); } + public void setDeprecated(String variable) {} + public void setReadOnly(String variable) {} }); createJavaProject("P", new String[] {}, new String[] {"TEST_LIB,TEST_SRC,TEST_ROOT"}, ""); assertEquals( @@ -934,6 +961,8 @@ // do nothing buffer.append("Ignoring request to initialize"); } + public void setDeprecated(String variable) {} + public void setReadOnly(String variable) {} }); IPath path = JavaCore.getClasspathVariable("TEST_SRC"); assertEquals( @@ -1084,6 +1113,132 @@ assertEquals("JavaCore preferences value should be unchanged", preferences.get(varName, "X"), initialValue); } finally { VariablesInitializer.reset(); + deleteProject("P1"); + } +} + +/** + * @bug 138599: [model][classpath] Need a way to mark a classpath variable as deprecated + * @see "https://bugs.eclipse.org/bugs/show_bug.cgi?id=138599" + */ +public void testVariableInitializerDeprecated() throws CoreException { + try { + // Create initializer + String varName = "TEST_DEPRECATED"; + String filePath = "/P1/lib.jar"; + DefaultVariableInitializer testInitializer = new DefaultVariableInitializer(new String[] {varName, filePath}); + VariablesInitializer.setInitializer(testInitializer); + assertEquals("JavaCore classpath value should have been initialized", JavaCore.getClasspathVariable(varName).toString(), filePath); + + // Verify that Classpath Variable is deprecated + assertTrue("JavaCore classpath variable should be deprecated", JavaCore.isClasspathVariableDeprecated(varName)); + assertTrue("Classpath Variable initializer should be deprecated", testInitializer.isDeprecated(varName)); + + // Create project + IJavaProject project = createJavaProject("P1"); + createFile("/P1/lib.jar", ""); + IClasspathEntry variable = JavaCore.newVariableEntry(new Path("TEST_DEPRECATED"), null, null); + IJavaModelStatus status = JavaConventions.validateClasspathEntry(project, variable, false); + assertStatus("Classpath variable \'TEST_DEPRECATED\' in project P1 is deprecated", status); + assertFalse("Status should not be OK", status.isOK()); + assertEquals("Status should have WARNING severity", IStatus.WARNING, status.getSeverity()); + assertEquals("Status should have deprecated code", IJavaModelStatusConstants.DEPRECATED_VARIABLE, status.getCode()); + } finally { + VariablesInitializer.reset(); + deleteProject("P1"); + } +} +public void testVariableInitializerUnboundAndDeprecated() throws CoreException { + try { + // Create initializer + String varName = "TEST_DEPRECATED"; + String filePath = "/P1/lib.jar"; + DefaultVariableInitializer testInitializer = new DefaultVariableInitializer(new String[] {varName, filePath}); + VariablesInitializer.setInitializer(testInitializer); + assertEquals("JavaCore classpath value should have been initialized", JavaCore.getClasspathVariable(varName).toString(), filePath); + + // Verify that Classpath Variable is deprecated + assertTrue("JavaCore classpath variable should be deprecated", JavaCore.isClasspathVariableDeprecated(varName)); + assertTrue("Classpath Variable initializer should be deprecated", testInitializer.isDeprecated(varName)); + + // Create project + IJavaProject project = createJavaProject("P1"); + IClasspathEntry variable = JavaCore.newVariableEntry(new Path("TEST_DEPRECATED"), null, null); + IJavaModelStatus status = JavaConventions.validateClasspathEntry(project, variable, false); + assertStatus("Project P1 is missing required library: \'lib.jar\'", status); + assertFalse("Status should not be OK", status.isOK()); + assertEquals("Status should have WARNING severity", IStatus.ERROR, status.getSeverity()); + assertEquals("Status should have deprecated code", IJavaModelStatusConstants.INVALID_CLASSPATH, status.getCode()); + } finally { + VariablesInitializer.reset(); + deleteProject("P1"); + } +} + +/** + * @bug 156226: [model][classpath] Allow classpath variable to be marked as non modifiable + * @see "https://bugs.eclipse.org/bugs/show_bug.cgi?id=156226" + */ +public void testVariableInitializerReadOnly() throws CoreException { + try { + // Create initializer + String varName = "TEST_READ_ONLY"; + String path = "/P1/lib.jar"; + VariablesInitializer.setInitializer(new DefaultVariableInitializer(new String[] { varName, path })); + assertEquals("JavaCore classpath value should have been initialized", JavaCore.getClasspathVariable(varName).toString(), path); + + // verify that Classpath Variable is read-only + assertTrue("JavaCore classpath variable should be read-only", JavaCore.isClasspathVariableReadOnly(varName)); + ClasspathVariableInitializer initializer = JavaCore.getClasspathVariableInitializer(varName); + assertTrue("Classpath Variable initializer should be read-only", initializer.isReadOnly()); + + // Create project + IJavaProject project = createJavaProject("P1"); + createFile("/P1/lib.jar", ""); + IClasspathEntry variable = JavaCore.newVariableEntry(new Path("TEST_READ_ONLY"), null, null); + IJavaModelStatus status = JavaConventions.validateClasspathEntry(project, variable, false); + assertStatus("Classpath variable \'TEST_READ_ONLY\' in project P1 is read only", status); + assertFalse("Status should not be OK", status.isOK()); + assertEquals("Status should have WARNING severity", IStatus.WARNING, status.getSeverity()); + assertEquals("Status should have deprecated code", IJavaModelStatusConstants.READ_ONLY_VARIABLE, status.getCode()); + } finally { + VariablesInitializer.reset(); + deleteProject("P1"); + } +} +public void testVariableInitializerDeprecatedAndReadOnly() throws CoreException { + try { + // Create initializer + String varName = "TEST_DEPRECATED_READ_ONLY"; + String path = "/P1/lib.jar"; + VariablesInitializer.setInitializer(new DefaultVariableInitializer(new String[] { varName, path })); + assertEquals("JavaCore classpath value should have been initialized", JavaCore.getClasspathVariable(varName).toString(), path); + + // verify that Classpath Variable is read-only + assertTrue("JavaCore classpath variable should be read-only", JavaCore.isClasspathVariableDeprecated(varName)); + assertTrue("JavaCore classpath variable should be read-only", JavaCore.isClasspathVariableReadOnly(varName)); + ClasspathVariableInitializer initializer = JavaCore.getClasspathVariableInitializer(varName); + assertTrue("Classpath Variable initializer should be deprecated", initializer.isDeprecated()); + assertTrue("Classpath Variable initializer should be read-only", initializer.isReadOnly()); + + // Create project + IJavaProject project = createJavaProject("P1"); + createFile("/P1/lib.jar", ""); + IClasspathEntry variable = JavaCore.newVariableEntry(new Path("TEST_DEPRECATED_READ_ONLY"), null, null); + IJavaModelStatus status = JavaConventions.validateClasspathEntry(project, variable, false); + assertStatus("Several warnings/errors occured", status); + assertTrue("Wrong kind of status", status instanceof JavaModelStatus); + JavaModelStatus jms = (JavaModelStatus) status; + IStatus[] children = jms.getChildren(); + assertEquals("Wrong number of children for multi-status", 2, children.length); + assertStatus("Classpath variable \'TEST_DEPRECATED_READ_ONLY\' in project P1 is deprecated", children[0]); + assertStatus("Classpath variable \'TEST_DEPRECATED_READ_ONLY\' in project P1 is read only", children[1]); + assertFalse("Status should not be OK", status.isOK()); + assertEquals("Status should have WARNING severity", IStatus.WARNING, status.getSeverity()); + assertEquals("Status should have deprecated code", IJavaModelStatusConstants.DEPRECATED_VARIABLE, status.getCode()); + } finally { + VariablesInitializer.reset(); + deleteProject("P1"); } } Index: src/org/eclipse/jdt/core/tests/model/VariablesInitializer.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/model/VariablesInitializer.java,v retrieving revision 1.6 diff -u -r1.6 VariablesInitializer.java --- src/org/eclipse/jdt/core/tests/model/VariablesInitializer.java 10 May 2006 18:54:10 -0000 1.6 +++ src/org/eclipse/jdt/core/tests/model/VariablesInitializer.java 16 Jan 2007 17:52:34 -0000 @@ -21,6 +21,8 @@ public static interface ITestInitializer { public void initialize(String variable) throws JavaModelException; + public void setDeprecated(String variable); + public void setReadOnly(String variable); } public static void reset() { @@ -36,11 +38,13 @@ public static void setInitializer(ITestInitializer initializer) { VariablesInitializer.initializer = initializer; } - + public void initialize(String variable) { if (initializer == null) return; try { initializer.initialize(variable); + if (isDeprecated()) initializer.setDeprecated(variable); + if (isReadOnly()) initializer.setReadOnly(variable); } catch (JavaModelException e) { e.printStackTrace(); } Index: src/org/eclipse/jdt/core/tests/model/ClasspathTests.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/model/ClasspathTests.java,v retrieving revision 1.156 diff -u -r1.156 ClasspathTests.java --- src/org/eclipse/jdt/core/tests/model/ClasspathTests.java 28 Nov 2006 12:03:46 -0000 1.156 +++ src/org/eclipse/jdt/core/tests/model/ClasspathTests.java 16 Jan 2007 17:52:34 -0000 @@ -35,7 +35,6 @@ import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.Path; import org.eclipse.jdt.core.IAccessRule; import org.eclipse.jdt.core.IClasspathAttribute; @@ -128,22 +127,6 @@ entry, decoded); } -protected void assertStatus(String expected, IStatus status) { - String actual = status.getMessage(); - if (!expected.equals(actual)) { - System.out.print(Util.displayString(actual, 2)); - System.out.println(","); - } - assertEquals(expected, actual); -} -protected void assertStatus(String message, String expected, IStatus status) { - String actual = status.getMessage(); - if (!expected.equals(actual)) { - System.out.print(Util.displayString(actual, 2)); - System.out.println(","); - } - assertEquals(message, expected, actual); -} protected File createFile(File parent, String name, String content) throws IOException { File file = new File(parent, name); FileOutputStream out = new FileOutputStream(file); @@ -1795,6 +1778,7 @@ this.deleteProject("P2"); } } + /** * Adding an entry to the classpath for a library that does not exist * should not break the model. The classpath should contain the Index: src/org/eclipse/jdt/core/tests/model/ModifyingResourceTests.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core.tests.model/src/org/eclipse/jdt/core/tests/model/ModifyingResourceTests.java,v retrieving revision 1.45 diff -u -r1.45 ModifyingResourceTests.java --- src/org/eclipse/jdt/core/tests/model/ModifyingResourceTests.java 20 Dec 2006 16:11:55 -0000 1.45 +++ src/org/eclipse/jdt/core/tests/model/ModifyingResourceTests.java 16 Jan 2007 17:52:34 -0000 @@ -20,9 +20,6 @@ import org.eclipse.jdt.internal.compiler.batch.Main; import org.eclipse.jdt.internal.core.JavaElement; -/* - * Tests that modify resources in the workspace. - */ public class ModifyingResourceTests extends AbstractJavaModelTests { public ModifyingResourceTests(String name) { @@ -38,6 +35,22 @@ expected, actual); } +protected void assertStatus(String expected, IStatus status) { + String actual = status.getMessage(); + if (!expected.equals(actual)) { + System.out.print(Util.displayString(actual, 2)); + System.out.println(","); + } + assertEquals(expected, actual); +} +protected void assertStatus(String message, String expected, IStatus status) { + String actual = status.getMessage(); + if (!expected.equals(actual)) { + System.out.print(Util.displayString(actual, 2)); + System.out.println(","); + } + assertEquals(message, expected, actual); +} /** * E.g. * org.eclipse.jdt.tests.core.ModifyingResourceTests.generateClassFile( Index: plugin.xml =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core.tests.model/plugin.xml,v retrieving revision 1.29 diff -u -r1.29 plugin.xml --- plugin.xml 19 Oct 2006 02:47:24 -0000 1.29 +++ plugin.xml 16 Jan 2007 17:52:33 -0000 @@ -12,6 +12,22 @@ + + + + + +