/*******************************************************************************
 * Copyright (c) 2000, 2009 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v2.0
 * which accompanies this distribution, and is available at
 * https://www.eclipse.org/legal/epl-2.0/
 *
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *******************************************************************************/
package org.eclipse.wst.jsdt.core.tests.model;

import org.eclipse.core.resources.IFile;
import org.eclipse.core.resources.IFolder;
import org.eclipse.core.resources.IWorkspaceRunnable;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.Path;
import org.eclipse.wst.jsdt.core.*;
import org.eclipse.wst.jsdt.core.search.IJavaScriptSearchConstants;
import org.eclipse.wst.jsdt.core.search.IJavaScriptSearchScope;
import org.eclipse.wst.jsdt.core.search.SearchEngine;

import junit.framework.Test;

public class ExclusionPatternsTests extends ModifyingResourceTests {
	IJavaScriptProject project;
public ExclusionPatternsTests(String name) {
	super(name);
}
protected void setClasspath(String[] sourceFoldersAndExclusionPatterns) throws JavaScriptModelException {
	this.project.setRawIncludepath(createClasspath(sourceFoldersAndExclusionPatterns, false/*no inclusion*/, true/*exclusion*/), null);
}
protected void setUp() throws Exception {
	super.setUp();
	this.project = createJavaProject("P", new String[] {"src"});
	startDeltas();
}

// Use this static initializer to specify subset for tests
// All specified tests which do not belong to the class are skipped...
static {
//		TESTS_NAMES = new String[] { "testCreateExcludedPackage2" };
//		TESTS_NUMBERS = new int[] { 2, 12 };
//		TESTS_RANGE = new int[] { 16, -1 };
}
public static Test suite() {
	return buildModelTestSuite(ExclusionPatternsTests.class);
}

protected void tearDown() throws Exception {
	stopDeltas();
	deleteProject("P");
	super.tearDown();
}
/*
 * Ensure that adding an exclusion on a compilation unit
 * makes it disappear from the children of its package and it is added to the non-java resources.
 */
public void testAddExclusionOnCompilationUnit() throws CoreException {
	createFolder("/P/src/p");
	createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);
	
	clearDeltas();
	setClasspath(new String[] {"/P/src", "**/A.js"});
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN | CONTENT | CLASSPATH CHANGED}\n" + 
		"	src[*]: {ADDED TO CLASSPATH | REMOVED FROM CLASSPATH}\n" + 
		"	ResourceDelta(/P/.classpath)[*]"
	);
	
	IPackageFragment pkg = getPackage("/P/src/p");
	assertSortedElementsEqual(
		"Unexpected children",
		"",
		pkg.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"A.js",
		pkg.getNonJavaScriptResources());
}
/*
 * Ensure that adding an exclusion on a folder directly under a project (and prj=src)
 * makes it appear as a non-java resources.
 * (regression test for bug 29374 Excluded folder on project not returned by Java Model)
 */
public void testAddExclusionOnFolderUnderProject() throws CoreException {
	try {
		IJavaScriptProject javaProject = createJavaProject("P1", new String[] {""});
		createFolder("/P1/doc");

		clearDeltas();
		javaProject.setRawIncludepath(createClasspath(new String[] {"/P1", "doc/"}, false/*no inclusion*/, true/*exclusion*/), null);
	
		assertDeltas(
			"Unexpected deltas",
			"P1[*]: {CHILDREN | CONTENT | CLASSPATH CHANGED}\n" + 
			"	<project root>[*]: {ADDED TO CLASSPATH | REMOVED FROM CLASSPATH}\n" + 
			"	ResourceDelta(/P1/.classpath)[*]"
		);
	
		IPackageFragmentRoot root = getPackageFragmentRoot("/P1");
		assertSortedElementsEqual(
			"Unexpected children",
			"<default> [in <project root> [in P1]]",
			root.getChildren());
		
		assertResourceNamesEqual(
			"Unexpected non-java resources of project",
			".classpath\n" +
			".project\n" +
			"doc",
			javaProject.getNonJavaScriptResources());
	} finally {
		deleteProject("P1");
	}
}
/*
 * Ensure that adding an exclusion on a package
 * makes it disappear from the children of its package fragment root 
 * and it is added to the non-java resources.
 */
public void testAddExclusionOnPackage() throws CoreException {
	createFolder("/P/src/p");
	
	clearDeltas();
	setClasspath(new String[] {"/P/src", "p/"});
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN | CONTENT | CLASSPATH CHANGED}\n" + 
		"	src[*]: {ADDED TO CLASSPATH | REMOVED FROM CLASSPATH}\n" + 
		"	ResourceDelta(/P/.classpath)[*]"
	);
	
	IPackageFragmentRoot root = getPackageFragmentRoot("/P/src");
	assertSortedElementsEqual(
		"Unexpected children",
		"<default> [in src [in P]]",
		root.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"p",
		root.getNonJavaScriptResources());
}
/*
 * Ensure that adding an exclusion on a primary working copy
 * makes it disappear from the children of its package and it is added to the non-java resources.
 */
public void testAddExclusionOnPrimaryWorkingCopy() throws CoreException {
	createFolder("/P/src/p");
	createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);
		
	IJavaScriptUnit workingCopy = null;
	try {
		workingCopy = getCompilationUnit("/P/src/p/A.js");
		workingCopy.becomeWorkingCopy(null);
		
		clearDeltas();
		setClasspath(new String[] {"/P/src", "**/A.js"});
		
		assertDeltas(
			"Unexpected deltas",
			"P[*]: {CHILDREN | CONTENT | CLASSPATH CHANGED}\n" + 
			"	src[*]: {ADDED TO CLASSPATH | REMOVED FROM CLASSPATH}\n" + 
			"	ResourceDelta(/P/.classpath)[*]"
		);
		
		IPackageFragment pkg = getPackage("/P/src/p");
		assertSortedElementsEqual(
			"Unexpected children",
			"",
			pkg.getChildren());
			
		assertResourceNamesEqual(
			"Unexpected non-java resources",
			"A.js",
			pkg.getNonJavaScriptResources());
	} finally {
		if (workingCopy != null) {
			workingCopy.discardWorkingCopy();
		}
	}
}
/*
 * Ensure that adding a file to a folder that is excluded reports the correct delta.
 * (regression test for bug 29621 Wrong Delta When Adding to Filtered Folder)
 */
public void testAddToExcludedFolder() throws CoreException {
	createFolder("/P/src/icons");
	
	// exclude folder and its contents
	setClasspath(new String[] {"/P/src", "icons/"});
	
	clearDeltas();
	createFile("/P/src/icons/my.txt", "");
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CONTENT}\n" + 
		"		ResourceDelta(/P/src/icons)[*]"
	);
	
	clearDeltas();
	deleteFile("/P/src/icons/my.txt");
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CONTENT}\n" + 
		"		ResourceDelta(/P/src/icons)[*]"
	);
}
/*
 * Ensure that creating an excluded compilation unit 
 * doesn't make it appear as a child of its package but it is a non-java resource.
 */
public void testCreateExcludedCompilationUnit() throws CoreException {
	setClasspath(new String[] {"/P/src", "**/A.js"});
	createFolder("/P/src/p");
	IPackageFragment pkg = getPackage("/P/src/p");

	clearDeltas();
	pkg.createCompilationUnit(
		"A.js",
		"package p;\n" +
		"public class A {\n" +
		"}",
		false,
		null);
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CHILDREN}\n" + 
		"		p[*]: {CONTENT}\n" + 
		"			ResourceDelta(/P/src/p/A.java)[+]"
	);
	
	assertSortedElementsEqual(
		"Unexpected children",
		"",
		pkg.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"A.js",
		pkg.getNonJavaScriptResources());
}
/*
 * Ensure that crearing an excluded package 
 * doesn't make it appear as a child of its package fragment root but it is a non-java resource.
 */
public void testCreateExcludedPackage() throws CoreException {
	setClasspath(new String[] {"/P/src", "p/"});
	IPackageFragmentRoot root = getPackageFragmentRoot("/P/src");
	
	clearDeltas();
	root.createPackageFragment("p", false, null);
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CONTENT}\n" + 
		"		ResourceDelta(/P/src/p)[+]"
	);
	
	assertSortedElementsEqual(
		"Unexpected children",
		"<default> [in src [in P]]",
		root.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"p",
		root.getNonJavaScriptResources());
}
/*
 * Ensure that crearing an excluded package doesn't make it appear as a child of its package fragment root but it is a non-java resource.
 * (regression test for bug 65637 [model] Excluded package still in Java model)
 */
public void testCreateExcludedPackage2() throws CoreException {
	setClasspath(new String[] {"/P/src", "org/*|org/eclipse/*"});
	
	clearDeltas();
	createFolder("/P/src/org/eclipse/mypack");
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CONTENT}\n" + 
		"		ResourceDelta(/P/src/org)[+]"
	);
	
	IPackageFragmentRoot root = getPackageFragmentRoot("/P/src");
	assertSortedElementsEqual(
		"Unexpected children",
		"<default> [in src [in P]]\n" + 
		"org.eclipse.mypack [in src [in P]]",
		root.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"org",
		root.getNonJavaScriptResources());
}
/*
 * Ensure that creating a folder that represents an excluded and included package
 * have the correct delta, Java elements and non-Java resources.
 * (regression test for 67789 Java element delta from refresh contains excluded package)
 */
public void testCreateExcludedAndIncludedPackages() throws CoreException {
	setClasspath(new String[] {"/P/src", "p1/p2/"});
	IPackageFragmentRoot root = getPackageFragmentRoot("/P/src");
	
	clearDeltas();
	createFolder("/P/src/p1/p2");
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CHILDREN}\n" + 
		"		p1[+]: {}"
	);
	
	assertSortedElementsEqual(
		"Unexpected children",
		"<default> [in src [in P]]\n" + 
		"p1 [in src [in P]]",
		root.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"p2",
		root.getPackageFragment("p1").getNonJavaScriptResources());
}
/*
 * Ensure that creating a file that corresponds to an excluded compilation unit 
 * doesn't make it appear as a child of its package but it is a non-java resource.
 */
public void testCreateResourceExcludedCompilationUnit() throws CoreException {
	setClasspath(new String[] {"/P/src", "**/A.js"});
	createFolder("/P/src/p");
	
	clearDeltas();
	createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CHILDREN}\n" + 
		"		p[*]: {CONTENT}\n" + 
		"			ResourceDelta(/P/src/p/A.java)[+]"
	);
	
	IPackageFragment pkg = getPackage("/P/src/p");
	assertSortedElementsEqual(
		"Unexpected children",
		"",
		pkg.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"A.js",
		pkg.getNonJavaScriptResources());
}
/*
 * Ensure that creating a folder that corresponds to an excluded package 
 * doesn't make it appear as a child of its package fragment root but it is a non-java resource.
 */
public void testCreateResourceExcludedPackage() throws CoreException {
	setClasspath(new String[] {"/P/src", "p/"});
	
	clearDeltas();
	createFolder("/P/src/p");
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CONTENT}\n" + 
		"		ResourceDelta(/P/src/p)[+]"
	);
	
	IPackageFragmentRoot root = getPackageFragmentRoot("/P/src");
	assertSortedElementsEqual(
		"Unexpected children",
		"<default> [in src [in P]]",
		root.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"p",
		root.getNonJavaScriptResources());
}
/*
 * Ensures that a cu that is not excluded is on the classpath of the project.
 */
public void testIsOnClasspath1() throws CoreException {
	setClasspath(new String[] {"/P/src", ""});
	createFolder("/P/src/p");
	IFile file = createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);
	assertTrue("Resource should be on classpath", project.isOnIncludepath(file));
	
	IJavaScriptUnit cu = getCompilationUnit("/P/src/p/A.js");
	assertTrue("CU should be on classpath", project.isOnIncludepath(cu));
}
/*
 * Ensures that a cu that is excluded is not on the classpath of the project.
 */
public void testIsOnClasspath2() throws CoreException {
	setClasspath(new String[] {"/P/src", "**/A.js"});
	createFolder("/P/src/p");
	IFile file = createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);
	assertTrue("Resource should not be on classpath", !project.isOnIncludepath(file));
	
	IJavaScriptUnit cu = getCompilationUnit("/P/src/p/A.js");
	assertTrue("CU should not be on classpath", !project.isOnIncludepath(cu));
}
/*
 * Ensures that a non-java resource that is not excluded is on the classpath of the project.
 */
public void testIsOnClasspath3() throws CoreException {
	setClasspath(new String[] {"/P/src", ""});
	createFolder("/P/src/p");
	IFile file = createFile("/P/src/p/readme.txt", "");
	assertTrue("Resource should be on classpath", project.isOnIncludepath(file));
}
/*
 * Ensures that a non-java resource that is excluded is not on the classpath of the project.
 */
public void testIsOnClasspath4() throws CoreException {
	setClasspath(new String[] {"/P/src", "p/**"});
	createFolder("/P/src/p");
	IFile file = createFile("/P/src/p/readme.txt", "");
	assertTrue("Resource should not be on classpath", !project.isOnIncludepath(file));
}
/*
 * Ensures that an excluded nested source folder doesn't appear as a non-java resource of the outer folder.
 * (regression test for bug 28115 Ubiquitous resource in the JavaModel)
 * 
 */
public void testNestedSourceFolder1() throws CoreException {
	setClasspath(new String[] {"/P/src1", "src2/**", "/P/src1/src2", ""});
	createFolder("/P/src1/src2");
	IPackageFragmentRoot root1 = getPackageFragmentRoot("/P/src1");
	assertResourceNamesEqual(
		"Unexpected non-java resources for /P/src1",
		"",
		root1.getNonJavaScriptResources());
}
/*
 * Ensures that adding a .java file in a nested source folder reports 
 * a delta on the nested source folder and not on the outer one.
 */
public void testNestedSourceFolder2() throws CoreException {
	setClasspath(new String[] {"/P/src1", "src2/**", "/P/src1/src2", ""});
	createFolder("/P/src1/src2");
	
	clearDeltas();
	createFile(
		"/P/src1/src2/A.js",
		"public class A {\n" +
		"}"
	);
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src1/src2[*]: {CHILDREN}\n" + 
		"		<default>[*]: {CHILDREN}\n" + 
		"			A.java[+]: {}"
	);
}
/*
 * Ensures that adding a .txt file in a nested source folder reports 
 * a resource delta on the nested source folder and not on the outer one.
 */
public void testNestedSourceFolder3() throws CoreException {
	setClasspath(new String[] {"/P/src1", "src2/**", "/P/src1/src2", ""});
	createFolder("/P/src1/src2");
	
	clearDeltas();
	createFile("/P/src1/src2/readme.txt", "");
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src1/src2[*]: {CONTENT}\n" + 
		"		ResourceDelta(/P/src1/src2/readme.txt)[+]"
	);
}
/*
 * Ensures that adding a folder in a nested source folder reports 
 * a delta on the nested source folder and not on the outer one.
 */
public void testNestedSourceFolder4() throws CoreException {
	setClasspath(new String[] {"/P/src1", "src2/**", "/P/src1/src2", ""});
	createFolder("/P/src1/src2");
	
	clearDeltas();
	createFolder("/P/src1/src2/p");
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src1/src2[*]: {CHILDREN}\n" + 
		"		p[+]: {}"
	);
}
/*
 * Ensures that adding a folder in a outer source folder reports 
 * a delta on the outer source folder and not on the nested one.
 */
public void testNestedSourceFolder5() throws CoreException {
	setClasspath(new String[] {"/P/src1", "src2/**", "/P/src1/src2", ""});
	createFolder("/P/src1/src2");
	
	clearDeltas();
	createFolder("/P/src1/p");
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src1[*]: {CHILDREN}\n" + 
		"		p[+]: {}"
	);
}
/*
 * Ensures that moving a package from an outer source folder to a nested
 * source folder reports a move delta.
 */
public void testNestedSourceFolder6() throws CoreException {
	setClasspath(new String[] {"/P/src1", "src2/**", "/P/src1/src2", ""});
	createFolder("/P/src1/src2");
	createFolder("/P/src1/p");
	
	clearDeltas();
	moveFolder("/P/src1/p", "/P/src1/src2/p");
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src1[*]: {CHILDREN}\n" + 
		"		p[-]: {MOVED_TO(p [in src1/src2 [in P]])}\n" + 
		"	src1/src2[*]: {CHILDREN}\n" + 
		"		p[+]: {MOVED_FROM(p [in src1 [in P]])}"
	);
}
/*
 * Ensure that renaming an excluded compilation unit so that it is not excluded any longer
 * makes it appears as a child of its package and it is removed from the non-java resources.
 */
public void testRenameExcludedCompilationUnit() throws CoreException {
	setClasspath(new String[] {"/P/src", "**/A.js"});
	createFolder("/P/src/p");
	IFile file = createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);

	clearDeltas();
	file.move(new Path("/P/src/p/B.js"), false, null);
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CHILDREN}\n" + 
		"		p[*]: {CHILDREN | CONTENT}\n" + 
		"			B.java[+]: {}\n" + 
		"			ResourceDelta(/P/src/p/A.java)[-]"
	);
	
	IPackageFragment pkg = getPackage("/P/src/p");
	assertSortedElementsEqual(
		"Unexpected children",
		"B.java [in p [in src [in P]]]",
		pkg.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"",
		pkg.getNonJavaScriptResources());
}
/*
 * Ensure that renaming an excluded package so that it is not excluded any longer
 * makes it appears as a child of its package fragment root 
 * and it is removed from the non-java resources.
 */
public void testRenameExcludedPackage() throws CoreException {
	setClasspath(new String[] {"/P/src", "p/"});
	IPackageFragmentRoot root = getPackageFragmentRoot("/P/src");
	IPackageFragment pkg = root.createPackageFragment("p", false, null);
	
	clearDeltas();
	pkg.getResource().move(new Path("/P/src/q"), false, null);
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CHILDREN | CONTENT}\n" + 
		"		q[+]: {}\n" + 
		"		ResourceDelta(/P/src/p)[-]"
	);
	
	assertSortedElementsEqual(
		"Unexpected children",
		"<default> [in src [in P]]\n" + 
		"q [in src [in P]]",
		root.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"",
		root.getNonJavaScriptResources());
}
/*
 * Ensure that renaming a file that corresponds to an excluded compilation unit so that it is not excluded any longer
 * makes it appears as a child of its package and it is removed from the non-java resources.
 */
public void testRenameResourceExcludedCompilationUnit() throws CoreException {
	setClasspath(new String[] {"/P/src", "**/A.js"});
	createFolder("/P/src/p");
	IFile file = createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);
	
	clearDeltas();
	file.move(new Path("/P/src/p/B.js"),  false, null);
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CHILDREN}\n" + 
		"		p[*]: {CHILDREN | CONTENT}\n" + 
		"			B.java[+]: {}\n" + 
		"			ResourceDelta(/P/src/p/A.java)[-]"
	);
	
	IPackageFragment pkg = getPackage("/P/src/p");
	assertSortedElementsEqual(
		"Unexpected children",
		"B.java [in p [in src [in P]]]",
		pkg.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"",
		pkg.getNonJavaScriptResources());
}
/*
 * Ensure search doesn't find matches in an excluded compilation unit.
 */
public void testSearchWithExcludedCompilationUnit1() throws CoreException {
	setClasspath(new String[] {"/P/src", "**/A.js"});
	createFolder("/P/src/p");
	createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);
	
	JavaSearchTests.JavaSearchResultCollector resultCollector = new JavaSearchTests.JavaSearchResultCollector();
	search(
		"A", 
		IJavaScriptSearchConstants.TYPE,
		IJavaScriptSearchConstants.DECLARATIONS,
		SearchEngine.createJavaSearchScope(new IJavaScriptProject[] {getJavaProject("P")}), 
		resultCollector);
	assertEquals(
		"Unexpected matches found",
		"",
		resultCollector.toString());
}
/*
 * Ensure search find matches in a compilation unit that was excluded but that is not any longer.
 */
public void testSearchWithExcludedCompilationUnit2() throws CoreException {
	setClasspath(new String[] {"/P/src", "A.js"});
	createFolder("/P/src/p");
	createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);
	
	setClasspath(new String[] {"/P/src", ""});
	JavaSearchTests.JavaSearchResultCollector resultCollector = new JavaSearchTests.JavaSearchResultCollector();
	search(
		"A", 
		IJavaScriptSearchConstants.TYPE,
		IJavaScriptSearchConstants.DECLARATIONS,
		SearchEngine.createJavaSearchScope(new IJavaScriptProject[] {getJavaProject("P")}), 
		resultCollector);
	assertEquals(
		"Unexpected matches found",
		"src/p/A.java p.A [A]",
		resultCollector.toString());
}
/*
 * Ensure that removing a folder that represents an excluded and included package
 * have the correct delta, Java elements and non-Java resources.
 * (regression test for 67789 Java element delta from refresh contains excluded package)
 */
public void testRemoveExcludedAndIncludedPackages() throws CoreException {
	setClasspath(new String[] {"/P/src", "p1/p2/"});
	IPackageFragmentRoot root = getPackageFragmentRoot("/P/src");
	createFolder("/P/src/p1/p2");
	
	clearDeltas();
	deleteFolder("/P/src/p1");
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CHILDREN}\n" + 
		"		p1[-]: {}"
	);
	
	assertSortedElementsEqual(
		"Unexpected children",
		"<default> [in src [in P]]",
		root.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"",
		root.getNonJavaScriptResources());
}

/*
 * Ensure that renaming a folder that corresponds to an excluded package 
 * so that it is not excluded any longer
 * makes it appears as a child of its package fragment root 
 * and it is removed from the non-java resources.
 */
public void testRenameResourceExcludedPackage() throws CoreException {
	setClasspath(new String[] {"/P/src", "p/"});
	IFolder folder = createFolder("/P/src/p");
	
	clearDeltas();
	folder.move(new Path("/P/src/q"), false, null);
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN}\n" + 
		"	src[*]: {CHILDREN | CONTENT}\n" + 
		"		q[+]: {}\n" + 
		"		ResourceDelta(/P/src/p)[-]"
	);
	
	IPackageFragmentRoot root = getPackageFragmentRoot("/P/src");
	assertSortedElementsEqual(
		"Unexpected children",
		"<default> [in src [in P]]\n" + 
		"q [in src [in P]]",
		root.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"",
		root.getNonJavaScriptResources());
}
/*
 * Ensure that a potential match in the output folder is not indexed.
 * (regression test for bug 32041 Multiple output folders fooling Java Model)
 */
public void testSearchPotentialMatchInOutput() throws CoreException {
	try {
		JavaScriptCore.run(new IWorkspaceRunnable() {
			public void run(IProgressMonitor monitor) throws CoreException {
				IJavaScriptProject javaProject = createJavaProject("P2", new String[] {});
				javaProject.setRawIncludepath(createClasspath(new String[] {"/P2", "src/", "/P2/src", ""}, false/*no inclusion*/, true/*exclusion*/), null);
				createFile(
					"/P2/bin/X.js",
					"public class X {\n" +
					"}"
				);
			}
		}, null);
		
		JavaSearchTests.JavaSearchResultCollector resultCollector = new JavaSearchTests.JavaSearchResultCollector();
		IJavaScriptSearchScope scope = SearchEngine.createJavaSearchScope(new IJavaScriptElement[] {getJavaProject("P")});
		search(
			"X", 
			IJavaScriptSearchConstants.TYPE,
			IJavaScriptSearchConstants.DECLARATIONS,
			scope, 
			resultCollector);
		assertEquals("", resultCollector.toString());
	} finally {
		deleteProject("P2");
	}
}
/*
 * Ensure that removing the exclusion on a compilation unit
 * makes it appears as a child of its package and it is removed from the non-java resources.
 */
public void testRemoveExclusionOnCompilationUnit() throws CoreException {
	setClasspath(new String[] {"/P/src", "A.js"});
	createFolder("/P/src/p");
	createFile(
		"/P/src/p/A.js",
		"package p;\n" +
		"public class A {\n" +
		"}"
	);
	
	clearDeltas();
	setClasspath(new String[] {"/P/src", ""});
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN | CONTENT | CLASSPATH CHANGED}\n" + 
		"	src[*]: {ADDED TO CLASSPATH | REMOVED FROM CLASSPATH}\n" + 
		"	ResourceDelta(/P/.classpath)[*]"
	);
	
	IPackageFragment pkg = getPackage("/P/src/p");
	assertSortedElementsEqual(
		"Unexpected children",
		"A.java [in p [in src [in P]]]",
		pkg.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"",
		pkg.getNonJavaScriptResources());
}
/*
 * Ensure that removing the exclusion on a package
 * makes it appears as a child of its package fragment root 
 * and it is removed from the non-java resources.
 */
public void testRemoveExclusionOnPackage() throws CoreException {
	setClasspath(new String[] {"/P/src", "p"});
	createFolder("/P/src/p");
	
	clearDeltas();
	setClasspath(new String[] {"/P/src", ""});
	
	assertDeltas(
		"Unexpected deltas",
		"P[*]: {CHILDREN | CONTENT | CLASSPATH CHANGED}\n" + 
		"	src[*]: {ADDED TO CLASSPATH | REMOVED FROM CLASSPATH}\n" + 
		"	ResourceDelta(/P/.classpath)[*]"
	);
	
	IPackageFragmentRoot root = getPackageFragmentRoot("/P/src");
	assertSortedElementsEqual(
		"Unexpected children",
		"<default> [in src [in P]]\n" + 
		"p [in src [in P]]",
		root.getChildren());
		
	assertResourceNamesEqual(
		"Unexpected non-java resources",
		"",
		root.getNonJavaScriptResources());
}
}
