001: /*
002: * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
003: *
004: * Copyright 1997-2007 Sun Microsystems, Inc. All rights reserved.
005: *
006: * The contents of this file are subject to the terms of either the GNU
007: * General Public License Version 2 only ("GPL") or the Common
008: * Development and Distribution License("CDDL") (collectively, the
009: * "License"). You may not use this file except in compliance with the
010: * License. You can obtain a copy of the License at
011: * http://www.netbeans.org/cddl-gplv2.html
012: * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
013: * specific language governing permissions and limitations under the
014: * License. When distributing the software, include this License Header
015: * Notice in each file and include the License file at
016: * nbbuild/licenses/CDDL-GPL-2-CP. Sun designates this
017: * particular file as subject to the "Classpath" exception as provided
018: * by Sun in the GPL Version 2 section of the License file that
019: * accompanied this code. If applicable, add the following below the
020: * License Header, with the fields enclosed by brackets [] replaced by
021: * your own identifying information:
022: * "Portions Copyrighted [year] [name of copyright owner]"
023: *
024: * Contributor(s):
025: *
026: * Copyright 2006 Sun Microsystems, Inc. All rights reserved.
027: */
028:
029: package org.netbeans.lib.uihandlerserver;
030:
031: import java.io.ByteArrayInputStream;
032: import java.io.ByteArrayOutputStream;
033: import java.io.DataInputStream;
034: import java.io.DataOutputStream;
035: import java.io.File;
036: import java.io.FileInputStream;
037: import java.io.FileOutputStream;
038: import java.io.InputStream;
039: import java.io.OutputStream;
040: import java.io.UnsupportedEncodingException;
041: import java.lang.reflect.Method;
042: import java.util.ArrayList;
043: import java.util.List;
044: import java.util.Random;
045: import java.util.ResourceBundle;
046: import java.util.logging.Handler;
047: import java.util.logging.Level;
048: import java.util.logging.LogRecord;
049: import java.util.logging.Logger;
050: import java.util.zip.GZIPOutputStream;
051: import javax.xml.parsers.DocumentBuilder;
052: import javax.xml.parsers.DocumentBuilderFactory;
053: import junit.framework.Test;
054: import org.netbeans.junit.Log;
055: import org.netbeans.junit.NbTestCase;
056: import org.netbeans.junit.NbTestSuite;
057: import org.netbeans.lib.uihandler.LogRecords;
058: import org.netbeans.lib.uihandler.TestHandler;
059: import org.w3c.dom.Document;
060: import org.xml.sax.SAXException;
061:
062: /**
063: *
064: * @author Jaroslav Tulach
065: */
066: public class LogRecordsTest extends NbTestCase {
067: private Logger LOG;
068:
069: public LogRecordsTest(String testName) {
070: super (testName);
071: }
072:
073: public static Test suite() {
074: return new NbTestSuite(LogRecordsTest.class);
075: // return new LogRecordsTest("testCanReadEmpty");
076: }
077:
078: protected Level logLevel() {
079: return Level.FINEST;
080: }
081:
082: protected void setUp() throws Exception {
083: LOG = Logger.getLogger("TEST-" + getName());
084: }
085:
086: protected void tearDown() throws Exception {
087: }
088:
089: public void testParamsGetCleared() throws Exception {
090: String r = "<record>" + "<date>2006-11-17T10:16:14</date>"
091: + "<millis>1163729774285</millis>"
092: + "<sequence>20</sequence>" + "<level>INFO</level>"
093: + "<thread>12</thread>" + "<message>MSG</message>"
094: + "<key>MSG</key>"
095: + "<catalog>a.bundle.somewhere</catalog>"
096: + "<param>1</param>" + "</record>" +
097:
098: "<record>" + "<date>2006-11-17T10:16:14</date>"
099: + "<millis>1163729774285</millis>"
100: + "<sequence>20</sequence>" + "<level>INFO</level>"
101: + "<thread>12</thread>" + "<message>MSG</message>"
102: + "<key>MSG</key>"
103: + "<catalog>a.bundle.somewhere</catalog>"
104: + "<param>2</param>" + "</record>";
105:
106: class H extends Handler {
107: int cnt;
108:
109: public void publish(LogRecord arg0) {
110: cnt++;
111: assertNotNull("We have params " + cnt, arg0
112: .getParameters());
113: assertEquals("One argument for " + cnt + "th record",
114: 1, arg0.getParameters().length);
115: }
116:
117: public void flush() {
118: }
119:
120: public void close() throws SecurityException {
121: }
122: }
123: H h = new H();
124:
125: LogRecords.scan(new ByteArrayInputStream(r.getBytes()), h);
126:
127: assertEquals("Two records", 2, h.cnt);
128: }
129:
130: public void testWriteAndRead() throws Exception {
131: doWriteAndReadTest(System.currentTimeMillis(), false);
132: }
133:
134: public void testNewFailureOn1165572711706() throws Exception {
135: doWriteAndReadTest(1165572711706L, false);
136: }
137:
138: public void testFailureOn1159804485342() throws Exception {
139: doWriteAndReadTest(1159804485342L, false);
140: }
141:
142: public void testWriteGZIPAndRead() throws Exception {
143: doWriteAndReadTest(System.currentTimeMillis(), true);
144: }
145:
146: public void testMakeSureItIsReadable() throws Exception {
147: InputStream is = getClass().getResourceAsStream(
148: "NB1216449736.xml");
149: TestHandler records = new TestHandler(is);
150: int cnt = 0;
151: for (;;) {
152: LOG.log(Level.INFO, "Reading {0}th record", cnt);
153: LogRecord r = records.read();
154: if (r == null) {
155: break;
156: }
157: LOG.log(Level.INFO, "Read {0}th record", cnt);
158: cnt++;
159: }
160: is.close();
161: }
162:
163: public void testReadException() throws Exception {
164: String what = "NB1216449736.xml";
165:
166: InputStream is = getClass().getResourceAsStream(what);
167: int cnt = 0;
168:
169: class H extends Handler {
170: int cnt;
171: LogRecord first;
172:
173: public void publish(LogRecord record) {
174: if (cnt == 0) {
175: first = record;
176: }
177: cnt++;
178: }
179:
180: public void flush() {
181: }
182:
183: public void close() throws SecurityException {
184: }
185: }
186:
187: LogRecord first = null;
188: TestHandler records = new TestHandler(is);
189: for (;;) {
190: LOG.log(Level.INFO, "Reading {0}th record", cnt);
191: LogRecord r = records.read();
192: if (r == null) {
193: break;
194: }
195: if (first == null) {
196: first = r;
197: }
198: LOG.log(Level.INFO, "Read {0}th record", cnt);
199: cnt++;
200: }
201: is.close();
202:
203: H h = new H();
204: is = getClass().getResourceAsStream(what);
205: LogRecords.scan(is, h);
206: is.close();
207:
208: assertNotNull(first);
209: assertNotNull(h.first);
210: assertEquals("Same message", first.getMessage(), h.first
211: .getMessage());
212: assertNotNull("exception from read", first.getThrown());
213: assertNotNull("exception from scan", h.first.getThrown());
214: assertEquals("Same exception message", first.getThrown()
215: .getMessage(), h.first.getThrown().getMessage());
216:
217: StackTraceElement[] arr1 = first.getThrown().getStackTrace();
218: StackTraceElement[] arr2 = h.first.getThrown().getStackTrace();
219:
220: assertEquals("Same length", arr1.length, arr2.length);
221:
222: for (int i = 0; i < arr1.length; i++) {
223: if (!arr1[i].equals(arr2[i])) {
224: fail(i + " th stack differ: " + arr1[i] + " != "
225: + arr2[i] + "\nline: "
226: + arr1[i].getLineNumber() + " and "
227: + arr2[i].getLineNumber());
228: }
229: }
230:
231: assertEquals("The same amount of records", cnt, h.cnt);
232:
233: }
234:
235: public void testCanReadEmpty() throws Exception {
236: InputStream is = getClass().getResourceAsStream("Empty.xml");
237: int cnt = 0;
238: TestHandler records = new TestHandler(is);
239: for (;;) {
240: LOG.log(Level.INFO, "Reading {0}th record", cnt);
241: LogRecord r = records.read();
242: if (r == null) {
243: break;
244: }
245: LOG.log(Level.INFO, "Read {0}th record", cnt);
246: cnt++;
247: }
248: is.close();
249:
250: assertEquals("No records", 0, cnt);
251: }
252:
253: public void testMakeSureItIsScannable() throws Exception {
254: InputStream is = getClass().getResourceAsStream(
255: "NB1216449736.xml");
256: int cnt = 0;
257:
258: class H extends Handler {
259: int cnt;
260:
261: public void publish(LogRecord record) {
262: cnt++;
263: }
264:
265: public void flush() {
266: }
267:
268: public void close() throws SecurityException {
269: }
270: }
271:
272: TestHandler records = new TestHandler(is);
273: for (;;) {
274: LOG.log(Level.INFO, "Reading {0}th record", cnt);
275: LogRecord r = records.read();
276: if (r == null) {
277: break;
278: }
279: LOG.log(Level.INFO, "Read {0}th record", cnt);
280: cnt++;
281: }
282: is.close();
283:
284: H h = new H();
285: is = getClass().getResourceAsStream("NB1216449736.xml");
286: LogRecords.scan(is, h);
287: is.close();
288:
289: assertEquals("The same amount of records", cnt, h.cnt);
290: }
291:
292: public void testBadUserIsBad() throws Exception {
293: String what = "baduser.xml";
294: InputStream is = getClass().getResourceAsStream(what);
295: int cnt = 0;
296:
297: class H extends Handler {
298: int cnt;
299:
300: public void publish(LogRecord record) {
301: cnt++;
302: }
303:
304: public void flush() {
305: }
306:
307: public void close() throws SecurityException {
308: }
309: }
310:
311: TestHandler records = new TestHandler(is);
312: for (;;) {
313: LOG.log(Level.INFO, "Reading {0}th record", cnt);
314: LogRecord r = records.read();
315: if (r == null) {
316: break;
317: }
318: LOG.log(Level.INFO, "Read {0}th record", cnt);
319: cnt++;
320: }
321: is.close();
322:
323: H h = new H();
324: is = getClass().getResourceAsStream(what);
325: LogRecords.scan(is, h);
326: is.close();
327:
328: assertEquals("The same amount of records", cnt, h.cnt);
329: }
330:
331: public void testDoesNotAskForWrongBunles() throws Exception {
332: LogRecord rec = new LogRecord(Level.FINER,
333: "UI_ACTION_BUTTON_PRESS"); // NOI18N
334: rec.setParameters(new Object[] { "0", "1" });
335: rec.setResourceBundle(ResourceBundle
336: .getBundle(LogRecordsTest.class.getPackage().getName()
337: + ".Props"));
338:
339: ByteArrayOutputStream os = new ByteArrayOutputStream();
340: LogRecords.write(os, rec);
341: os.close();
342:
343: class H extends Handler {
344: int cnt;
345:
346: public void publish(LogRecord arg0) {
347: cnt++;
348: assertNotNull("We have params " + cnt, arg0
349: .getParameters());
350: assertEquals("Two argument for " + cnt + "th record",
351: 2, arg0.getParameters().length);
352: }
353:
354: public void flush() {
355: }
356:
357: public void close() throws SecurityException {
358: }
359: }
360: H h = new H();
361:
362: CharSequence log = Log.enable("", Level.INFO);
363: LogRecords.scan(new ByteArrayInputStream(os.toByteArray()), h);
364:
365: assertEquals("One record", 1, h.cnt);
366:
367: if (log.toString().indexOf("Cannot find resource") < 0) {
368: fail(log.toString());
369: }
370: }
371:
372: public void testAlwaysSetParamters() throws Exception {
373: String what = "actionDelegates.xml";
374: InputStream is = getClass().getResourceAsStream(what);
375: class H extends Handler {
376: int cnt;
377:
378: public void publish(LogRecord record) {
379: cnt++;
380: if (record.getParameters() == null) {
381: fail("Each record shall have paramters, #" + cnt
382: + " did not: " + record.getMessage());
383: }
384: }
385:
386: public void flush() {
387: }
388:
389: public void close() throws SecurityException {
390: }
391: }
392:
393: H h = new H();
394: is = getClass().getResourceAsStream(what);
395: LogRecords.scan(is, h);
396: is.close();
397:
398: assertEquals("The four amount of records", 5, h.cnt);
399: }
400:
401: public void testSurviveNumberFormatExc() throws Exception {
402: String what = "NB1101666645.1";
403: InputStream is = getClass().getResourceAsStream(what);
404: class H extends Handler {
405: int cnt;
406:
407: public void publish(LogRecord record) {
408: cnt++;
409: }
410:
411: public void flush() {
412: }
413:
414: public void close() throws SecurityException {
415: }
416: }
417:
418: H h = new H();
419: is = getClass().getResourceAsStream(what);
420: LogRecords.scan(is, h);
421: is.close();
422: }
423:
424: public void testScanEmpty91974() throws Exception {
425: String what = "uigestures-iz91974.xml";
426: InputStream is = getClass().getResourceAsStream(what);
427: int cnt = 0;
428:
429: class H extends Handler {
430: int cnt;
431:
432: public void publish(LogRecord record) {
433: cnt++;
434: }
435:
436: public void flush() {
437: }
438:
439: public void close() throws SecurityException {
440: }
441: }
442:
443: TestHandler records = new TestHandler(is);
444: for (;;) {
445: LOG.log(Level.INFO, "Reading {0}th record", cnt);
446: LogRecord r = records.read();
447: if (r == null) {
448: break;
449: }
450: LOG.log(Level.INFO, "Read {0}th record", cnt);
451: cnt++;
452: }
453: is.close();
454:
455: H h = new H();
456: is = getClass().getResourceAsStream(what);
457: LogRecords.scan(is, h);
458: is.close();
459:
460: assertEquals("The same amount of records", cnt, h.cnt);
461: }
462:
463: public void testNotFinishedFiles() throws Exception {
464: String what = "eof.xml";
465: InputStream is = getClass().getResourceAsStream(what);
466: int expectRecords = 1;
467:
468: class H extends Handler {
469: int cnt;
470:
471: public void publish(LogRecord record) {
472: cnt++;
473: }
474:
475: public void flush() {
476: }
477:
478: public void close() throws SecurityException {
479: }
480: }
481:
482: H h = new H();
483: is = getClass().getResourceAsStream(what);
484: LogRecords.scan(is, h);
485: is.close();
486:
487: assertEquals("The same amount of records", expectRecords, h.cnt);
488: }
489:
490: public void testScanFileThatClaimsTohaveWrongUTF8Char()
491: throws Exception {
492: InputStream is = getClass().getResourceAsStream(
493: "wrongutfchar.xml");
494:
495: final List<LogRecord> recs = new ArrayList<LogRecord>();
496: class H extends Handler {
497: int cnt;
498:
499: public void publish(LogRecord record) {
500: cnt++;
501: recs.add(record);
502: }
503:
504: public void flush() {
505: }
506:
507: public void close() throws SecurityException {
508: }
509: }
510:
511: H h = new H();
512: is = getClass().getResourceAsStream("wrongutfchar.xml");
513: LogRecords.scan(is, h);
514: is.close();
515:
516: assertEquals("The same amount of records", 232, h.cnt);
517:
518: try {
519: DocumentBuilder db1 = DocumentBuilderFactory.newInstance()
520: .newDocumentBuilder();
521: Document d1 = db1.parse(getClass().getResourceAsStream(
522: "wrongutfchar.xml"));
523: fail("Parsing must fail here");
524: } catch (SAXException ex) {
525: // ok, the original document is not well formed
526: }
527:
528: // but if we save it
529: File f = new File(getWorkDir(), "tst.xml");
530: FileOutputStream os = new FileOutputStream(f);
531: os.write("<uigestures>\n".getBytes());
532: for (LogRecord r : recs) {
533: LogRecords.write(os, r);
534: }
535: os.write("</uigestures>\n".getBytes());
536: os.close();
537:
538: // it will be parseable
539: DocumentBuilder db = DocumentBuilderFactory.newInstance()
540: .newDocumentBuilder();
541: Document d = db.parse(f);
542: assertNotNull("Parsed", d);
543: }
544:
545: private void doWriteAndReadTest(long seed, boolean gzip)
546: throws Exception {
547: Logger.getAnonymousLogger().info("seed is: " + seed);
548:
549: File file = new File(getWorkDir(), "feed.txt");
550: Random r = new Random(seed);
551: OutputStream os = new FileOutputStream(file);
552: if (gzip) {
553: os = new GZIPOutputStream(os);
554: }
555: DataOutputStream out = new DataOutputStream(os);
556:
557: int cnt = r.nextInt(500);
558: final LogRecord[] arr = new LogRecord[cnt];
559: for (int i = 0; i < cnt; i++) {
560: LogRecord rec = generateLogRecord(r);
561: arr[i] = rec;
562: LogRecords.write(out, rec);
563: }
564: out.close();
565:
566: {
567: DataInputStream in = new DataInputStream(
568: new FileInputStream(file));
569: TestHandler records = new TestHandler(in);
570: for (int i = 0; i < cnt; i++) {
571: LogRecord rec = records.read();
572: assertLog(i + "-th record is the same", rec, arr[i]);
573: }
574: in.close();
575: }
576:
577: class H extends Handler {
578: int cnt;
579:
580: public void publish(LogRecord rec) {
581: try {
582: assertLog(cnt + "-th record is the same", rec,
583: arr[cnt]);
584: } catch (Exception ex) {
585: throw (RuntimeException) new RuntimeException()
586: .initCause(ex);
587: }
588: cnt++;
589: }
590:
591: public void flush() {
592: assertEquals("All read", cnt, arr.length);
593: cnt = -1;
594: }
595:
596: public void close() throws SecurityException {
597: }
598: }
599:
600: H h = new H();
601: {
602: LOG.info("Scanning " + file);
603: DataInputStream in = new DataInputStream(
604: new FileInputStream(file));
605: LogRecords.scan(in, h);
606: in.close();
607: }
608: assertEquals("Cleared", -1, h.cnt);
609: }
610:
611: private LogRecord generateLogRecord(Random r)
612: throws UnsupportedEncodingException {
613: LogRecord rec = new LogRecord(randomLevel(r), randomString(r));
614: return rec;
615: }
616:
617: private void assertLog(String string, LogRecord r1, LogRecord r2)
618: throws Exception {
619: if (r1 == null && r2 != null) {
620: fail("r1: null r2 not: " + r(r2));
621: }
622: if (r1 != null && r2 == null) {
623: fail("r2: null r1 not: " + r(r2));
624: }
625:
626: for (Method m : LogRecord.class.getMethods()) {
627: if (m.getName().startsWith("get")
628: && m.getParameterTypes().length == 0) {
629: Object o1 = m.invoke(r1);
630: Object o2 = m.invoke(r2);
631:
632: if (o1 == null && o2 == null) {
633: continue;
634: }
635: if (o1 == null || o2 == null || !o1.equals(o2)) {
636: assertEquals("Logs differ in result of "
637: + m.getName() + "\nrec1: " + r(r1)
638: + "\nrec2: " + r(r2), o1, o2);
639: }
640: }
641: }
642: }
643:
644: private static String r(LogRecord r) {
645: return r.getMessage();
646: }
647:
648: private static Level randomLevel(Random r) {
649: int lev = r.nextInt(1100);
650: if (lev >= Level.SEVERE.intValue())
651: return Level.SEVERE;
652: if (lev >= Level.WARNING.intValue())
653: return Level.WARNING;
654: if (lev >= Level.INFO.intValue())
655: return Level.INFO;
656: if (lev >= Level.CONFIG.intValue())
657: return Level.CONFIG;
658: if (lev >= Level.FINE.intValue())
659: return Level.FINE;
660: if (lev >= Level.FINER.intValue())
661: return Level.FINER;
662: if (lev >= Level.FINEST.intValue())
663: return Level.FINEST;
664: return Level.OFF;
665: }
666:
667: private static String randomString(Random r)
668: throws UnsupportedEncodingException {
669: int len = r.nextInt(50);
670: byte[] arr = new byte[len];
671: for (int i = 0; i < arr.length; i++) {
672: int ch = r.nextInt(256);
673: if (ch < 32) {
674: ch = 32;
675: }
676: if (ch > 'z') {
677: ch = 'z';
678: }
679: arr[i] = (byte) ch;
680: }
681: return new String(new String(arr, "utf-8").getBytes(), "utf-8");
682: }
683: }
|