| /******************************************************************************* |
| * Copyright (c) 2005, 2012 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.core.tests.resources; |
| |
| import java.io.ByteArrayInputStream; |
| import java.io.InputStream; |
| import junit.framework.Test; |
| import junit.framework.TestSuite; |
| import org.eclipse.core.internal.content.*; |
| import org.eclipse.core.internal.resources.ContentDescriptionManager; |
| import org.eclipse.core.internal.resources.Workspace; |
| import org.eclipse.core.resources.*; |
| import org.eclipse.core.runtime.*; |
| import org.eclipse.core.runtime.content.*; |
| import org.eclipse.core.runtime.jobs.Job; |
| import org.osgi.service.prefs.BackingStoreException; |
| import org.osgi.service.prefs.Preferences; |
| |
| public class ContentDescriptionManagerTest extends ResourceTest { |
| |
| private static final String CONTENT_TYPE_RELATED_NATURE1 = "org.eclipse.core.tests.resources.contentTypeRelated1"; |
| private static final String CONTENT_TYPE_RELATED_NATURE2 = "org.eclipse.core.tests.resources.contentTypeRelated2"; |
| |
| public static Test suite() { |
| return new TestSuite(ContentDescriptionManagerTest.class); |
| } |
| |
| /** |
| * Blocks the calling thread until the cache flush job completes. |
| */ |
| public static void waitForCacheFlush() { |
| try { |
| Job.getJobManager().join(ContentDescriptionManager.FAMILY_DESCRIPTION_CACHE_FLUSH, null); |
| } catch (OperationCanceledException e) { |
| //ignore |
| } catch (InterruptedException e) { |
| //ignore |
| } |
| } |
| |
| public ContentDescriptionManagerTest(String name) { |
| super(name); |
| } |
| |
| private IContentDescription getDescription(String tag, IFile file) { |
| IContentDescription description; |
| description = null; |
| try { |
| description = file.getContentDescription(); |
| } catch (CoreException e) { |
| fail(tag, e); |
| } |
| return description; |
| } |
| |
| protected InputStream projectDescriptionWithNatures(String project, String[] natures) { |
| StringBuffer contents = new StringBuffer("<?xml version=\"1.0\" encoding=\"UTF-8\"?><projectDescription><name>" + project + "</name><natures>"); |
| for (String nature : natures) { |
| contents.append("<nature>" + nature + "</nature>"); |
| } |
| contents.append("</natures></projectDescription>"); |
| return new ByteArrayInputStream(contents.toString().getBytes()); |
| } |
| |
| /** |
| * Ensure we react to changes to the content type registry in an appropriated way. |
| */ |
| public void testBug79151() { |
| IWorkspace workspace = getWorkspace(); |
| IProject project = workspace.getRoot().getProject("MyProject"); |
| IContentTypeManager contentTypeManager = Platform.getContentTypeManager(); |
| IContentType xml = contentTypeManager.getContentType("org.eclipse.core.runtime.xml"); |
| String newExtension = "xml_bug_79151"; |
| IFile file1 = project.getFile("file.xml"); |
| IFile file2 = project.getFile("file." + newExtension); |
| ensureExistsInWorkspace(file1, getContents(CharsetTest.SAMPLE_XML_ISO_8859_1_ENCODING)); |
| ensureExistsInWorkspace(file2, getContents(CharsetTest.SAMPLE_XML_US_ASCII_ENCODING)); |
| // ensure we start in a known state |
| ((Workspace) workspace).getContentDescriptionManager().invalidateCache(true, null); |
| // wait for cache flush to finish |
| waitForCacheFlush(); |
| // cache is new at this point |
| assertEquals("0.9", ContentDescriptionManager.EMPTY_CACHE, ((Workspace) workspace).getContentDescriptionManager().getCacheState()); |
| |
| IContentDescription description1a = null, description1b = null, description1c = null, description1d = null; |
| IContentDescription description2 = null; |
| description1a = getDescription("1.0a", file1); |
| description2 = getDescription("1.0b", file2); |
| assertNotNull("1.1", description1a); |
| assertEquals("1.2", xml, description1a.getContentType()); |
| assertNull("1.3", description2); |
| |
| description1b = getDescription("2.0", file1); |
| // ensure it comes from the cache (should be the very same object) |
| assertNotNull(" 2.1", description1b); |
| assertSame("2.2", description1a, description1b); |
| try { |
| // change the content type |
| xml.addFileSpec(newExtension, IContentType.FILE_EXTENSION_SPEC); |
| } catch (CoreException e) { |
| fail("3.0", e); |
| } |
| try { |
| description1c = getDescription("4.0a", file1); |
| description2 = getDescription("4.0b", file2); |
| // ensure it does *not* come from the cache (should be a different object) |
| assertNotNull("4.1", description1c); |
| assertNotSame("4.2", description1a, description1c); |
| assertEquals("4.3", xml, description1c.getContentType()); |
| assertNotNull("4.4", description2); |
| assertEquals("4.5", xml, description2.getContentType()); |
| } finally { |
| try { |
| // dissociate the xml2 extension from the XML content type |
| xml.removeFileSpec(newExtension, IContentType.FILE_EXTENSION_SPEC); |
| } catch (CoreException e) { |
| fail("4.99", e); |
| } |
| } |
| description1d = getDescription("5.0a", file1); |
| description2 = getDescription("5.0b", file2); |
| // ensure it does *not* come from the cache (should be a different object) |
| assertNotNull("5.1", description1d); |
| assertNotSame("5.2", description1c, description1d); |
| assertEquals("5.3", xml, description1d.getContentType()); |
| assertNull("5.4", description2); |
| } |
| |
| public void testBug94516() { |
| IContentTypeManager contentTypeManager = Platform.getContentTypeManager(); |
| IContentType text = contentTypeManager.getContentType("org.eclipse.core.runtime.text"); |
| assertNotNull("0.1", text); |
| IProject project = getWorkspace().getRoot().getProject("proj1"); |
| IFile unrelatedFile = project.getFile("file." + getName()); |
| ensureExistsInWorkspace(unrelatedFile, ""); |
| |
| IContentDescription description = null; |
| description = getDescription("0.7", unrelatedFile); |
| assertNull("0.8", description); |
| |
| try { |
| try { |
| text.addFileSpec(unrelatedFile.getName(), IContentType.FILE_NAME_SPEC); |
| } catch (CoreException e) { |
| fail("0.99", e); |
| } |
| |
| description = getDescription("1.0", unrelatedFile); |
| assertNotNull("1.1", description); |
| assertEquals("1.2", text, description.getContentType()); |
| |
| final ProjectScope projectScope = new ProjectScope(project); |
| Preferences contentTypePrefs = projectScope.getNode(ContentTypeManager.CONTENT_TYPE_PREF_NODE); |
| // enable project-specific settings for this project |
| contentTypePrefs.putBoolean("enabled", true); |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("1.99", e); |
| } |
| // global settings should not matter anymore |
| description = getDescription("2.0", unrelatedFile); |
| assertNull("2.1", description); |
| |
| IContentTypeSettings settings = null; |
| try { |
| settings = text.getSettings(projectScope); |
| } catch (CoreException e) { |
| fail("3.0", e); |
| } |
| assertNotNull("3.1", settings); |
| assertNotSame("3.2", text, settings); |
| assertTrue("3.3", settings instanceof ContentTypeSettings); |
| |
| try { |
| settings.addFileSpec(unrelatedFile.getFullPath().getFileExtension(), IContentType.FILE_EXTENSION_SPEC); |
| } catch (CoreException e) { |
| fail("4.0", e); |
| } |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("4.1", e); |
| } |
| description = getDescription("5.0", unrelatedFile); |
| assertNotNull("5.1", description); |
| assertEquals("5.2", text, description.getContentType()); |
| } finally { |
| try { |
| text.removeFileSpec(unrelatedFile.getName(), IContentType.FILE_NAME_SPEC); |
| } catch (CoreException e) { |
| fail("6.0", e); |
| } |
| } |
| } |
| |
| /** |
| * Ensures content type-nature associations work as expected. |
| */ |
| public void testNatureContentTypeAssociation() { |
| IContentTypeManager contentTypeManager = Platform.getContentTypeManager(); |
| IContentType baseType = contentTypeManager.getContentType("org.eclipse.core.tests.resources.nature_associated_1"); |
| IContentType derivedType = contentTypeManager.getContentType("org.eclipse.core.tests.resources.nature_associated_2"); |
| assertNotNull("0.1", baseType); |
| assertNotNull("0.2", derivedType); |
| IProject project = getWorkspace().getRoot().getProject("proj1"); |
| IFile file = project.getFile("file.nature-associated"); |
| IFile descFile = project.getFile(IProjectDescription.DESCRIPTION_FILE_NAME); |
| ensureExistsInWorkspace(file, "it really does not matter"); |
| IContentDescription description = null; |
| |
| // originally, project description has no natures |
| try { |
| descFile.setContents(projectDescriptionWithNatures(project.getName(), new String[0]), IResource.FORCE, getMonitor()); |
| } catch (CoreException e) { |
| fail("1.0", e); |
| } |
| waitForCacheFlush(); |
| description = getDescription("1.1", file); |
| assertNotNull("1.2", description); |
| assertSame("1.3", ((ContentTypeHandler) baseType).getTarget(), ((ContentTypeHandler) description.getContentType()).getTarget()); |
| |
| // change project description to include one of the natures |
| try { |
| descFile.setContents(projectDescriptionWithNatures(project.getName(), new String[] {CONTENT_TYPE_RELATED_NATURE1}), IResource.FORCE, getMonitor()); |
| } catch (CoreException e) { |
| fail("2.0", e); |
| } |
| waitForCacheFlush(); |
| description = getDescription("2.1", file); |
| assertNotNull("2.2", description); |
| assertSame("2.3", ((ContentTypeHandler) baseType).getTarget(), ((ContentTypeHandler) description.getContentType()).getTarget()); |
| |
| // change project description to include the other nature |
| try { |
| descFile.setContents(projectDescriptionWithNatures(project.getName(), new String[] {CONTENT_TYPE_RELATED_NATURE2}), IResource.FORCE, getMonitor()); |
| } catch (CoreException e) { |
| fail("3.0", e); |
| } |
| waitForCacheFlush(); |
| description = getDescription("3.1", file); |
| assertNotNull("3.2", description); |
| assertSame("3.3", ((ContentTypeHandler) derivedType).getTarget(), ((ContentTypeHandler) description.getContentType()).getTarget()); |
| |
| // change project description to include both of the natures |
| try { |
| descFile.setContents(projectDescriptionWithNatures(project.getName(), new String[] {CONTENT_TYPE_RELATED_NATURE1, CONTENT_TYPE_RELATED_NATURE2}), IResource.FORCE, getMonitor()); |
| } catch (CoreException e) { |
| fail("4.0", e); |
| } |
| waitForCacheFlush(); |
| |
| description = getDescription("4.1", file); |
| assertNotNull("4.2", description); |
| assertSame("4.3", ((ContentTypeHandler) baseType).getTarget(), ((ContentTypeHandler) description.getContentType()).getTarget()); |
| |
| // back to no natures |
| try { |
| descFile.setContents(projectDescriptionWithNatures(project.getName(), new String[0]), IResource.FORCE, getMonitor()); |
| } catch (CoreException e) { |
| fail("5.0", e); |
| } |
| waitForCacheFlush(); |
| description = getDescription("5.1", file); |
| assertNotNull("5.2", description); |
| assertSame("5.3", ((ContentTypeHandler) baseType).getTarget(), ((ContentTypeHandler) description.getContentType()).getTarget()); |
| } |
| |
| public void testProjectSpecificCharset() throws CoreException { |
| IContentTypeManager contentTypeManager = Platform.getContentTypeManager(); |
| IContentType text = contentTypeManager.getContentType("org.eclipse.core.runtime.text"); |
| IContentType xml = contentTypeManager.getContentType("org.eclipse.core.runtime.xml"); |
| assertNotNull("0.1", text); |
| assertNotNull("0.2", xml); |
| IProject project = getWorkspace().getRoot().getProject("proj1"); |
| |
| IFile txtFile = project.getFile(getName() + ".txt"); |
| IFile xmlFile = project.getFile(getName() + ".xml"); |
| |
| ensureExistsInWorkspace(txtFile, ""); |
| ensureExistsInWorkspace(xmlFile, ""); |
| |
| project.setDefaultCharset("FOO", getMonitor()); |
| assertEquals("1.0", "FOO", txtFile.getCharset()); |
| assertEquals("1.1", "UTF-8", xmlFile.getCharset()); |
| |
| final ProjectScope projectScope = new ProjectScope(project); |
| Preferences contentTypePrefs = projectScope.getNode(ContentTypeManager.CONTENT_TYPE_PREF_NODE); |
| // enable project-specific settings for this project |
| contentTypePrefs.putBoolean("enabled", true); |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("2.0", e); |
| } |
| IContentTypeSettings settings = null; |
| settings = text.getSettings(projectScope); |
| settings.setDefaultCharset("BAR"); |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("2.1", e); |
| } |
| assertEquals("3.0", "BAR", txtFile.getCharset()); |
| assertEquals("3.1", "UTF-8", xmlFile.getCharset()); |
| |
| settings = xml.getSettings(projectScope); |
| settings.setDefaultCharset(""); |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("4.0", e); |
| } |
| assertEquals("4.1", "BAR", txtFile.getCharset()); |
| assertEquals("4.2", "FOO", xmlFile.getCharset()); |
| } |
| |
| public void testProjectSpecificFileAssociations() { |
| IContentTypeManager contentTypeManager = Platform.getContentTypeManager(); |
| IContentType text = contentTypeManager.getContentType("org.eclipse.core.runtime.text"); |
| IContentType xml = contentTypeManager.getContentType("org.eclipse.core.runtime.xml"); |
| assertNotNull("0.1", text); |
| assertNotNull("0.2", xml); |
| IProject project = getWorkspace().getRoot().getProject("proj1"); |
| |
| IFile txtFile = project.getFile(getName() + ".txt"); |
| IFile xmlFile = project.getFile(getName() + ".xml"); |
| IFile unrelatedFile = project.getFile("file." + getName()); |
| |
| ensureExistsInWorkspace(txtFile, ""); |
| ensureExistsInWorkspace(xmlFile, ""); |
| ensureExistsInWorkspace(unrelatedFile, ""); |
| IContentDescription description = null; |
| |
| description = getDescription("0.7a", txtFile); |
| assertNotNull("0.7b", description); |
| assertEquals("0.7c", text, description.getContentType()); |
| |
| description = getDescription("0.8a", xmlFile); |
| assertNotNull("0.8b", description); |
| assertEquals("0.8c", xml, description.getContentType()); |
| |
| assertNull("0.9b", getDescription("0.9a", unrelatedFile)); |
| |
| final ProjectScope projectScope = new ProjectScope(project); |
| Preferences contentTypePrefs = projectScope.getNode(ContentTypeManager.CONTENT_TYPE_PREF_NODE); |
| // enable project-specific settings for this project |
| contentTypePrefs.putBoolean("enabled", true); |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("0.99", e); |
| } |
| // there are no local settings yet, everything should be the same |
| description = getDescription("1.0a", txtFile); |
| assertNotNull("1.0b", description); |
| assertEquals("1.0c", text, description.getContentType()); |
| |
| description = getDescription("1.1a", xmlFile); |
| assertNotNull("1.1b", description); |
| assertEquals("1.1c", xml, description.getContentType()); |
| |
| assertNull("1.2b", getDescription("1.2a", unrelatedFile)); |
| |
| IContentTypeSettings settings = null; |
| try { |
| settings = text.getSettings(projectScope); |
| } catch (CoreException e) { |
| fail("2.0", e); |
| } |
| assertNotNull("2.1", settings); |
| assertNotSame("2.2", text, settings); |
| assertTrue("2.3", settings instanceof ContentTypeSettings); |
| |
| try { |
| settings.addFileSpec(getName(), IContentTypeSettings.FILE_EXTENSION_SPEC); |
| } catch (CoreException e) { |
| fail("3.0", e); |
| } |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("3.1", e); |
| } |
| description = getDescription("3.2a", unrelatedFile); |
| assertNotNull("3.2b", description); |
| assertEquals("3.2c", text, description.getContentType()); |
| |
| // other content types should still be recognized |
| description = getDescription("3.3a", txtFile); |
| assertNotNull("3.3b", description); |
| assertEquals("3.3c", text, description.getContentType()); |
| |
| description = getDescription("3.4a", xmlFile); |
| assertNotNull("3.4b", description); |
| assertEquals("3.4c", xml, description.getContentType()); |
| |
| // disable project-specific settings for this project |
| contentTypePrefs.putBoolean("enabled", false); |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("3.99", e); |
| } |
| |
| // no project settings should be in effect |
| description = getDescription("4.0a", txtFile); |
| assertNotNull("4.0b", description); |
| assertEquals("4.0c", text, description.getContentType()); |
| |
| description = getDescription("4.1a", xmlFile); |
| assertNotNull("4.1b", description); |
| assertEquals("4.1c", xml, description.getContentType()); |
| |
| assertNull("4.2b", getDescription("4.2a", unrelatedFile)); |
| |
| // enable project-specific settings again |
| contentTypePrefs.putBoolean("enabled", true); |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("4.99", e); |
| } |
| |
| // now associate the full name of the xml file to the text content type |
| try { |
| settings.addFileSpec(xmlFile.getName(), IContentTypeSettings.FILE_NAME_SPEC); |
| } catch (CoreException e) { |
| fail("5.0", e); |
| } |
| try { |
| contentTypePrefs.flush(); |
| } catch (BackingStoreException e) { |
| fail("5.1", e); |
| } |
| |
| description = getDescription("5.2a", unrelatedFile); |
| assertNotNull("5.2b", description); |
| assertEquals("5.2c", text, description.getContentType()); |
| |
| description = getDescription("5.3a", txtFile); |
| assertNotNull("5.3b", description); |
| assertEquals("5.3c", text, description.getContentType()); |
| |
| description = getDescription("5.4a", xmlFile); |
| assertNotNull("5.4b", description); |
| assertEquals("5.4c", text, description.getContentType()); |
| |
| } |
| |
| } |