1 19 20 package org.netbeans.test.jsf.el; 21 import java.awt.Color ; 22 import java.awt.Component ; 23 import java.awt.Font ; 24 import java.awt.Graphics ; 25 import java.beans.PropertyChangeEvent ; 26 import java.beans.PropertyChangeListener ; 27 import java.io.File ; 28 import java.lang.reflect.Method ; 29 import java.util.Arrays ; 30 import java.util.Iterator ; 31 import java.util.List ; 32 import javax.swing.JEditorPane ; 33 import javax.swing.JLabel ; 34 import javax.swing.JList ; 35 import javax.swing.SwingUtilities ; 36 import javax.swing.text.Caret ; 37 import junit.framework.Test; 38 import org.netbeans.editor.Utilities; 39 import org.netbeans.editor.ext.CompletionQuery.ResultItem; 40 import org.netbeans.jellytools.JellyTestCase; 41 import org.netbeans.jellytools.modules.editor.CompletionJListOperator; 42 import org.netbeans.jemmy.JemmyException; 43 import org.netbeans.jemmy.util.PNGEncoder; 44 import org.netbeans.junit.AssertionFailedErrorException; 45 import org.netbeans.junit.NbTestCase; 46 import org.netbeans.editor.BaseDocument; 47 import org.netbeans.spi.editor.completion.CompletionItem; 48 import org.netbeans.editor.TokenID; 49 import org.netbeans.editor.TokenItem; 50 import org.netbeans.editor.ext.ExtSyntaxSupport; 51 import org.openide.actions.UndoAction; 52 import org.openide.cookies.EditorCookie; 53 import org.openide.cookies.EditorCookie.Observable; 54 import org.openide.filesystems.FileObject; 55 import org.openide.loaders.DataObject; 56 import org.openide.util.actions.SystemAction; 57 58 59 60 90 public class CompletionTest extends JellyTestCase { 91 private FileObject testFileObj; 92 protected boolean debug = false; 93 protected final static List xmlExts = Arrays.asList(new String [] 94 {"xml","xsd","html","tld","jspx"}); 95 protected final static List jspExts = Arrays.asList(new String [] {"jsp","tag"}); 96 97 98 public CompletionTest(String name, FileObject testFileObj) { 99 super(name); 100 this.testFileObj = testFileObj; 101 } 102 103 public void setUp() { 104 System.out.println("######## "+getName()+" #######"); 105 } 106 107 public static Test suite() { 108 File dataDir = new CompletionTest(null, null).getDataDir(); 110 File projectsDir = new File (dataDir, "tests"); 111 FileObjectFilter filter = new FileObjectFilter() { 112 public boolean accept(FileObject fo) { 113 String ext = fo.getExt(); 114 String name = fo.getName(); 115 return (name.startsWith("test") || name.startsWith("Test")) 116 && (xmlExts.contains(ext) || jspExts.contains(ext) || jspExts.equals("java")); 117 } 118 }; 119 return RecurrentSuiteFactory.createSuite(CompletionTest.class, 120 projectsDir, filter); 121 } 122 123 public void runTest() throws Exception { 124 String ext = testFileObj.getExt(); 125 if (jspExts.contains(ext)) { 126 test(testFileObj, "<%--CC", "--%>"); 127 } else if (xmlExts.contains(ext)) { 128 test(testFileObj, "<!--CC", "-->"); 129 } else if (ext.equals("java")) { 130 test(testFileObj, "/**CC", "*/"); 131 } else { 132 throw new JemmyException("File extension of: "+testFileObj.getNameExt() 133 +" is unsupported."); 134 } 135 } 136 137 private void test(FileObject fileObj, String stepStart, String stepEnd) throws Exception { 138 boolean inStepData = false; 139 String [] stepData = new String [3]; 140 int dataLineIdx = 0; 141 142 try { 143 DataObject dataObj = DataObject.find(fileObj); 145 EditorCookie.Observable ed = (Observable) dataObj.getCookie(Observable.class); 146 147 final Waiter waiter = new Waiter(); 149 final PropertyChangeListener pcl = new PropertyChangeListener () { 150 public void propertyChange(PropertyChangeEvent evt) { 151 if (evt.getPropertyName().equals(Observable.PROP_OPENED_PANES)) { 152 waiter.notifyFinished(); 153 } 154 } 155 }; 156 ed.addPropertyChangeListener(pcl); 157 BaseDocument doc = (BaseDocument) ed.openDocument(); 159 ed.open(); 160 assertTrue("The editor pane was not opened in 10 secs.", waiter.waitFinished(10000)); 162 ed.removePropertyChangeListener(pcl); 163 Thread.sleep(3000); 165 JEditorPane editor = ed.getOpenedPanes()[0]; 166 ExtSyntaxSupport ess = (ExtSyntaxSupport) doc.getSyntaxSupport(); 167 TokenItem token = ess.getTokenChain(0, doc.getLength()); 168 List steps = new java.util.ArrayList (); 169 while (token != null) { 171 TokenID tokenID = token.getTokenID(); 172 if (debug) { 173 String tImage = token.getImage(); 174 int tEnd = token.getOffset() + tImage.length(); 175 System.err.println("# [" + token.getOffset() + "," + tEnd + "] " 176 + tokenID.getName() + " :: " + token.getImage()); 177 } 178 if (tokenID.getName().indexOf("comment") == -1) { 179 token = token.getNext(); 180 continue; 181 } 182 if (inStepData){ 183 if (token.getImage().indexOf(stepEnd) > -1) { 185 inStepData = false; 186 if (dataLineIdx == 3) { 188 int offset = token.getOffset() + token.getImage() 189 .length(); 190 TestStep step = new TestStep(stepData, offset); 191 steps.add(step); 192 } else { 193 ref("EE: expected data lines number: 3 but was: " 194 + dataLineIdx); 195 } 196 } else { 197 if (dataLineIdx > 2) { 199 String msg = "EE: to much lines in CC Test Data"; 200 ref(msg); 201 ref(dumpToken(token)); 202 fail(msg); 203 } 204 String str = token.getImage(); 205 if (str.endsWith("\n")) { 207 str = str.substring(0, str.length()-1); 208 } 209 stepData[dataLineIdx++] = str; 210 } 211 } else { 212 String text = token.getImage(); 213 if(text.startsWith(stepStart)) { 214 if (text.endsWith(stepEnd)) { 215 String [] lines = text.split("\n\r?|\r\n?"); 217 if (lines.length == 5) { 218 int offset = token.getOffset() + token.getImage().length(); 219 for (int i = 0; i < 3; i++) { 220 stepData[i] = lines[i+1]; 221 } 222 TestStep step = new TestStep(stepData, offset); 223 steps.add(step); 224 } else { 225 String msg = "EE: expected 5 lines lenght token but got: " 226 + lines.length; 227 ref(msg); 228 ref(text); 229 for (int i = 0; i < lines.length; i++) { 230 ref(i+"::"+lines[i]); 231 } 232 } 233 } else { 234 inStepData = true; 236 dataLineIdx = 0; 237 } 238 } 239 } 240 token = token.getNext(); 241 } Iterator it = steps.iterator(); 243 while (it.hasNext()) { 244 exec(editor, (TestStep) it.next()); 245 } 246 } catch (Exception ex) { 247 throw new AssertionFailedErrorException(ex); 248 } 249 compareReferenceFiles(); 250 } 251 252 private void exec(JEditorPane editor, TestStep step) throws Exception { 253 boolean ccError = false; 254 try { 255 ref(step.toString()); 256 System.out.println("step: "+step.toString()); 257 BaseDocument doc = (BaseDocument) editor.getDocument(); 258 doc.insertString(step.getOffset(), "\n" + step.getPrefix(), null); 260 Caret caret = editor.getCaret(); 261 caret.setDot(step.getCursorPos()); 262 Thread.sleep(500); 264 CompletionJListOperator comp = null; 267 try { 268 comp = CompletionJListOperator.showCompletion(); 269 } catch (JemmyException e) { 270 ccError = true; 271 ref("EE: The CC window did not appear"); 272 e.printStackTrace(); 273 } 274 Thread.sleep(1500); 276 if (comp != null) { 277 Iterator items = comp.getCompletionItems().iterator(); 279 CompletionItem selectedItem = null; 280 while (items.hasNext()) { 281 TextGraphics2D g = new TextGraphics2D(comp.getSource()); 282 Object next = items.next(); 283 String dispText = null; 284 if (next instanceof ResultItem) { 285 ResultItem resItem = (ResultItem) next; 286 Component component = resItem.getPaintComponent((JList )comp.getSource(), 287 false, true); 288 Method drawM = findMethod(component.getClass(), "draw", new Class [] {Graphics .class}); 290 if(drawM != null) { 291 drawM.setAccessible(true); 292 drawM.invoke(component, new Object [] {g}); 293 } else if (component instanceof JLabel ) { 294 System.out.println("graph1: "+((JLabel ) component).getText().trim()); 296 g.drawString(((JLabel ) component).getText().trim(), 0, 0); 297 } else { 298 System.out.println("graph2: "+((JLabel ) component).getText().trim()); 299 g.drawString(component.toString(), 0, 0); 300 } 301 } else if (next instanceof CompletionItem) { 302 CompletionItem cItem = (CompletionItem) next; 303 cItem.render(g, Font.decode("Dialog-Plain-12"), Color.BLACK, Color.WHITE, 400, 30, false); 304 } else { 305 System.out.println("next:"+ next.toString()); 306 g.drawString(next.toString(),0 ,0); 307 } 308 dispText = g.getTextUni(); 309 System.out.println("DispText: "+dispText); 310 if (dispText.equals(step.getChoice())) { 312 assertInstanceOf(CompletionItem.class, next); 313 selectedItem = (CompletionItem) next; 314 } 315 System.out.println("getTextUni: "+g.getTextUni()); 316 ref(g.getTextUni()); 317 } 318 class DefaultActionRunner implements Runnable { 319 CompletionItem item; 320 JEditorPane editor; 321 public DefaultActionRunner(CompletionItem item, 322 JEditorPane editor) { 323 this.item=item; 324 this.editor=editor; 325 } 326 327 public void run() { 328 item.defaultAction(editor); 329 } 330 331 } 332 if (selectedItem != null) { 334 Runnable run = new DefaultActionRunner(selectedItem, editor); 336 Thread.currentThread().sleep(500); 338 runInAWT(run); 339 } else { 340 ref("EE: cannot find completion item: " + step.getChoice()); 341 } 342 } else if (!ccError) { 343 ref("Instant substitution performed"); 345 } 346 if (comp != null) { 348 int i = 0; 349 while (comp.isShowing()) { 350 Thread.currentThread().sleep(500); 351 if (i++ >= 12) { 352 long time = System.currentTimeMillis(); 354 String screenFile = time + "-screen.png"; 355 log("["+time+"]The CompletionJList was not hidden in 5 secs"); 356 log("step: "+step); 357 log("captureScreen:" + screenFile); 358 try { 359 PNGEncoder.captureScreen(getWorkDir().getAbsolutePath() 360 +File.separator+screenFile); 361 } catch (Exception e1) {} 362 break; 363 } 364 } 365 } 366 Thread.currentThread().sleep(500); int rowStart = Utilities.getRowStart(doc, step.getOffset() + 1); 368 int rowEnd = Utilities.getRowEnd(doc, step.getOffset() + 1); 369 String result = doc.getText(new int[] {rowStart, rowEnd}); 370 if (!result.equals(step.getResult())) { 371 ref("EE: unexpected CC result:\n< " + result + "\n> " 372 + step.getResult()); 373 } 374 ref("End cursor position = " + caret.getDot()); 375 } finally { 376 Thread.currentThread().sleep(500); final UndoAction ua = (UndoAction)SystemAction.get(UndoAction.class); 379 assertNotNull("Cannot obtain UndoAction", ua); 380 while (ua.isEnabled()) { 381 runInAWT(new Runnable () { 382 public void run() { 383 ua.performAction(); 384 } 385 }); 386 Thread.currentThread().sleep(50); } 388 Thread.currentThread().sleep(500); 389 } 390 391 } 392 393 private static void runInAWT(Runnable r) { 394 if (SwingUtilities.isEventDispatchThread()) { 395 r.run(); 396 } else { 397 SwingUtilities.invokeLater(r); 398 } 399 } 400 401 private Method findMethod(Class clazz, String name, Class [] paramTypes) { 402 Method method = null; 403 for (Class cls=clazz; cls.getSuperclass() != null; cls=cls.getSuperclass()) { 404 try { 405 method = cls.getDeclaredMethod(name, paramTypes); 406 } catch (NoSuchMethodException e) { 407 } 409 if (method != null) { 410 return method; 411 } 412 } 413 return null; 414 } 415 416 protected void assertInstanceOf(Class expectedType, Object actual) { 417 if (!expectedType.isAssignableFrom(actual.getClass())) { 418 fail("Expected type: "+expectedType.getName()+"\nbut was: "+ 419 actual.getClass().getName()); 420 } 421 } 422 423 private static class TestStep { 424 private String prefix; 425 private String choice; 426 private String result; 427 private int offset; 428 private int cursorPos; 429 430 public TestStep(String data[], int offset) { 431 this.prefix = data[0]; 432 this.choice = data[1]; 433 this.result = data[2]; 434 this.offset = offset; 435 436 cursorPos = prefix.indexOf('|'); 437 if (cursorPos != -1) { 438 prefix = prefix.replaceFirst("\\|", ""); 439 } else { 440 cursorPos = prefix.length(); 441 } 442 cursorPos += offset + 1; 443 } 444 445 public String toString() { 446 StringBuffer sb = new StringBuffer (prefix); 447 sb.insert(cursorPos - offset - 1, '|'); 448 return "[" + sb + ", " + choice + ", "+ result + ", " + offset + "]"; 449 } 450 451 public String getPrefix() { 452 return prefix; 453 } 454 455 public String getChoice() { 456 return choice; 457 } 458 459 public String getResult() { 460 return result; 461 } 462 463 public int getOffset() { 464 return offset; 465 } 466 467 public int getCursorPos() { 468 return cursorPos; 469 } 470 471 }; 472 473 474 public static void main(java.lang.String [] args) { 475 junit.textui.TestRunner.run(suite()); 477 } 478 479 private String dumpToken(TokenItem tokenItem) { 480 StringBuffer sb = new StringBuffer (); 481 sb.append("<token \name='"); 482 sb.append(tokenItem.getTokenID().getName()); 483 sb.append("'>\n"); 484 sb.append(tokenItem.getTokenContextPath()); 485 sb.append("</token>"); 486 return sb.toString(); 487 } 488 } 489 | Popular Tags |