1 package com
.intellij
.testFramework
;
3 import com
.intellij
.ide
.util
.treeView
.AbstractTreeNode
;
4 import com
.intellij
.ide
.util
.treeView
.AbstractTreeStructure
;
5 import com
.intellij
.openapi
.application
.ApplicationManager
;
6 import com
.intellij
.openapi
.fileEditor
.FileDocumentManager
;
7 import com
.intellij
.openapi
.util
.io
.FileUtil
;
8 import com
.intellij
.openapi
.util
.text
.StringUtil
;
9 import com
.intellij
.openapi
.vfs
.LocalFileSystem
;
10 import com
.intellij
.openapi
.vfs
.VfsUtil
;
11 import com
.intellij
.openapi
.vfs
.VirtualFile
;
12 import com
.intellij
.openapi
.vfs
.VirtualFileFilter
;
13 import com
.intellij
.util
.containers
.HashMap
;
14 import com
.intellij
.util
.io
.ZipUtil
;
15 import junit
.framework
.Assert
;
16 import junit
.framework
.AssertionFailedError
;
17 import org
.jetbrains
.annotations
.NotNull
;
21 import java
.io
.FilenameFilter
;
22 import java
.io
.IOException
;
24 import java
.util
.jar
.JarFile
;
26 public class IdeaTestUtil
extends PlatformTestUtil
{
29 * Measured on dual core p4 3HZ 1gig ram
31 private static final long ETALON_TIMING
= 438;
34 public static final Comparator
<AbstractTreeNode
> DEFAULT_COMPARATOR
= new Comparator
<AbstractTreeNode
>() {
35 public int compare(AbstractTreeNode o1
, AbstractTreeNode o2
) {
36 String displayText1
= o1
.getTestPresentation();
37 String displayText2
= o2
.getTestPresentation();
38 return displayText1
.compareTo(displayText2
);
42 public static final boolean COVERAGE_ENABLED_BUILD
= "true".equals(System
.getProperty("idea.coverage.enabled.build"));
43 public static final MyVirtualFileFilter CVS_FILE_FILTER
= new MyVirtualFileFilter();
45 private static HashMap
<String
, VirtualFile
> buildNameToFileMap(VirtualFile
[] files
, VirtualFileFilter filter
) {
46 HashMap
<String
, VirtualFile
> map
= new HashMap
<String
, VirtualFile
>();
47 for (VirtualFile file
: files
) {
48 if (filter
!= null && !filter
.accept(file
)) continue;
49 map
.put(file
.getName(), file
);
54 public static void assertDirectoriesEqual(VirtualFile dirAfter
, VirtualFile dirBefore
, VirtualFileFilter fileFilter
) throws IOException
{
55 FileDocumentManager
.getInstance().saveAllDocuments();
56 VirtualFile
[] childrenAfter
= dirAfter
.getChildren();
57 File
[] ioAfter
= new File(dirAfter
.getPath()).listFiles();
58 shallowCompare(childrenAfter
, ioAfter
);
59 VirtualFile
[] childrenBefore
= dirBefore
.getChildren();
60 File
[] ioBefore
= new File(dirBefore
.getPath()).listFiles();
61 shallowCompare(childrenBefore
, ioBefore
);
63 HashMap
<String
, VirtualFile
> mapAfter
= buildNameToFileMap(childrenAfter
, fileFilter
);
64 HashMap
<String
, VirtualFile
> mapBefore
= buildNameToFileMap(childrenBefore
, fileFilter
);
66 Set
<String
> keySetAfter
= mapAfter
.keySet();
67 Set
<String
> keySetBefore
= mapBefore
.keySet();
68 Assert
.assertEquals(keySetAfter
, keySetBefore
);
70 for (String name
: keySetAfter
) {
71 VirtualFile fileAfter
= mapAfter
.get(name
);
72 VirtualFile fileBefore
= mapBefore
.get(name
);
73 if (fileAfter
.isDirectory()) {
74 assertDirectoriesEqual(fileAfter
, fileBefore
, fileFilter
);
77 assertFilesEqual(fileAfter
, fileBefore
);
82 private static void shallowCompare(final VirtualFile
[] vfs
, final File
[] io
) {
83 List
<String
> vfsPaths
= new ArrayList
<String
>();
84 for (VirtualFile file
: vfs
) {
85 vfsPaths
.add(file
.getPath());
88 List
<String
> ioPaths
= new ArrayList
<String
>();
89 for (File file
: io
) {
90 ioPaths
.add(file
.getPath().replace(File
.separatorChar
, '/'));
93 Assert
.assertEquals(sortAndJoin(vfsPaths
), sortAndJoin(ioPaths
));
96 private static String
sortAndJoin(List
<String
> strings
) {
97 Collections
.sort(strings
);
98 StringBuilder buf
= new StringBuilder();
99 for (String string
: strings
) {
103 return buf
.toString();
106 public static void assertFilesEqual(VirtualFile fileAfter
, VirtualFile fileBefore
) throws IOException
{
107 assertJarFilesEqual(VfsUtil
.virtualToIoFile(fileAfter
), VfsUtil
.virtualToIoFile(fileBefore
));
110 public static void assertJarFilesEqual(File file1
, File file2
) throws IOException
{
111 final JarFile jarFile1
;
112 final JarFile jarFile2
;
114 jarFile1
= new JarFile(file1
);
115 jarFile2
= new JarFile(file2
);
117 catch (IOException e
) {
118 String textAfter
= String
.valueOf(FileUtil
.loadFileText(file1
));
119 String textBefore
= String
.valueOf(FileUtil
.loadFileText(file2
));
120 textAfter
= StringUtil
.convertLineSeparators(textAfter
);
121 textBefore
= StringUtil
.convertLineSeparators(textBefore
);
122 Assert
.assertEquals(file1
.getPath(), textAfter
, textBefore
);
126 final File tempDirectory1
= IdeaTestCase
.createTempDir("tmp1");
127 final File tempDirectory2
= IdeaTestCase
.createTempDir("tmp2");
128 ZipUtil
.extract(jarFile1
, tempDirectory1
, CVS_FILE_FILTER
);
129 ZipUtil
.extract(jarFile2
, tempDirectory2
, CVS_FILE_FILTER
);
132 final VirtualFile dirAfter
= LocalFileSystem
.getInstance().refreshAndFindFileByIoFile(tempDirectory1
);
133 final VirtualFile dirBefore
= LocalFileSystem
.getInstance().refreshAndFindFileByIoFile(tempDirectory2
);
134 ApplicationManager
.getApplication().runWriteAction(new Runnable() {
136 dirAfter
.refresh(false, true);
137 dirBefore
.refresh(false, true);
140 assertDirectoriesEqual(dirAfter
, dirBefore
, CVS_FILE_FILTER
);
143 public static StringBuffer
print(AbstractTreeStructure structure
,
146 Comparator comparator
,
149 StringBuffer buffer
= new StringBuffer();
150 doPrint(buffer
, currentLevel
, node
, structure
, comparator
, maxRowCount
, 0, paddingChar
);
154 private static int doPrint(StringBuffer buffer
,
157 AbstractTreeStructure structure
,
158 Comparator comparator
,
162 if (currentLine
>= maxRowCount
&& maxRowCount
!= -1) return currentLine
;
164 StringUtil
.repeatSymbol(buffer
, paddingChar
, currentLevel
);
165 buffer
.append(toString(node
)).append("\n");
167 Object
[] children
= structure
.getChildElements(node
);
169 if (comparator
!= null) {
170 ArrayList
<?
> list
= new ArrayList
<Object
>(Arrays
.asList(children
));
171 Collections
.sort(list
, comparator
);
172 children
= list
.toArray(new Object
[list
.size()]);
174 for (Object child
: children
) {
175 currentLine
= doPrint(buffer
, currentLevel
+ 1, child
, structure
, comparator
, maxRowCount
, currentLine
, paddingChar
);
181 public static String
print(Collection c
) {
182 StringBuilder result
= new StringBuilder();
183 for (Iterator iterator
= c
.iterator(); iterator
.hasNext();) {
184 Object each
= iterator
.next();
185 result
.append(toString(each
));
186 if (iterator
.hasNext()) {
191 return result
.toString();
194 public static String
print(ListModel model
) {
195 StringBuilder result
= new StringBuilder();
196 for (int i
= 0; i
< model
.getSize(); i
++) {
197 result
.append(toString(model
.getElementAt(i
)));
200 return result
.toString();
203 public static String
print(JTree tree
) {
204 return print(tree
, false);
207 public static void assertTreeStructureEquals(final AbstractTreeStructure treeStructure
, final String expected
) {
208 Assert
.assertEquals(expected
, print(treeStructure
, treeStructure
.getRootElement(), 0, null, -1, ' ').toString());
211 public static void assertTiming(String message
, long expected
, long actual
) {
212 if (COVERAGE_ENABLED_BUILD
) return;
213 long expectedOnMyMachine
= expected
* Timings
.MACHINE_TIMING
/ ETALON_TIMING
;
214 final double acceptableChangeFactor
= 1.1;
216 // Allow 10% more in case of test machine is busy.
217 // For faster machines (expectedOnMyMachine < expected) allow nonlinear performance rating:
218 // just perform better than acceptable expected
219 if (actual
> expectedOnMyMachine
* acceptableChangeFactor
&&
220 (expectedOnMyMachine
> expected
|| actual
> expected
* acceptableChangeFactor
)) {
221 int percentage
= (int)(((float)100 * (actual
- expectedOnMyMachine
)) / expectedOnMyMachine
);
222 Assert
.fail(message
+ ". Operation took " + percentage
+ "% longer than expected. Expected on my machine: " + expectedOnMyMachine
+
223 ". Actual: " + actual
+ ". Expected on Etalon machine: " + expected
+ "; Actual on Etalon: " +
224 (actual
* ETALON_TIMING
/ Timings
.MACHINE_TIMING
));
227 int percentage
= (int)(((float)100 * (actual
- expectedOnMyMachine
)) / expectedOnMyMachine
);
228 System
.out
.println(message
+ ". Operation took " + percentage
+ "% longer than expected. Expected on my machine: " +
229 expectedOnMyMachine
+ ". Actual: " + actual
+ ". Expected on Etalon machine: " + expected
+
230 "; Actual on Etalon: " + (actual
* ETALON_TIMING
/ Timings
.MACHINE_TIMING
));
234 public static void assertTiming(String message
, long expected
, @NotNull Runnable actionToMeasure
) {
235 assertTiming(message
, expected
, 4, actionToMeasure
);
238 public static void assertTiming(String message
, long expected
, int attempts
, @NotNull Runnable actionToMeasure
) {
241 long start
= System
.currentTimeMillis();
242 actionToMeasure
.run();
243 long finish
= System
.currentTimeMillis();
245 assertTiming(message
, expected
, finish
- start
);
248 catch (AssertionFailedError e
) {
249 if (attempts
== 0) throw e
;
257 public static void main(String
[] args
) {
258 printDetectedPerformanceTimings();
261 public static void printDetectedPerformanceTimings() {
262 System
.out
.println("Etalon timing: " + ETALON_TIMING
);
263 System
.out
.println("This machine timing: " + Timings
.MACHINE_TIMING
);
266 public static class MyVirtualFileFilter
implements VirtualFileFilter
, FilenameFilter
{
267 public boolean accept(VirtualFile file
) {
268 return !file
.isDirectory() || !"CVS".equals(file
.getName());
271 public boolean accept(File dir
, String name
) {
272 return name
.indexOf("CVS") == -1;