jaroslav@273: /** jaroslav@273: * Back 2 Browser Bytecode Translator jaroslav@273: * Copyright (C) 2012 Jaroslav Tulach jaroslav@273: * jaroslav@273: * This program is free software: you can redistribute it and/or modify jaroslav@273: * it under the terms of the GNU General Public License as published by jaroslav@273: * the Free Software Foundation, version 2 of the License. jaroslav@273: * jaroslav@273: * This program is distributed in the hope that it will be useful, jaroslav@273: * but WITHOUT ANY WARRANTY; without even the implied warranty of jaroslav@273: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the jaroslav@273: * GNU General Public License for more details. jaroslav@273: * jaroslav@273: * You should have received a copy of the GNU General Public License jaroslav@273: * along with this program. Look for COPYING file in the top folder. jaroslav@273: * If not, see http://opensource.org/licenses/GPL-2.0. jaroslav@273: */ jaroslav@372: package org.apidesign.bck2brwsr.vmtest.impl; jaroslav@273: jaroslav@372: import org.apidesign.bck2brwsr.vmtest.*; jaroslav@273: import java.lang.reflect.Method; jaroslav@372: import java.util.ArrayList; jaroslav@372: import java.util.List; jaroslav@384: import org.apidesign.bck2brwsr.launcher.Launcher; jaroslav@273: import org.testng.Assert; jaroslav@273: import org.testng.ITest; jaroslav@273: import org.testng.annotations.Factory; jaroslav@273: import org.testng.annotations.Test; jaroslav@273: jaroslav@273: /** A TestNG {@link Factory} that seeks for {@link Compare} annotations jaroslav@273: * in provided class and builds set of tests that compare the computations jaroslav@273: * in real as well as JavaScript virtual machines. Use as:
jaroslav@273:  * {@code @}{@link Factory} public static create() {
jaroslav@346:  *   return @{link VMTest}.{@link #create(YourClass.class);
jaroslav@273:  * }
jaroslav@273: * jaroslav@273: * @author Jaroslav Tulach jaroslav@273: */ jaroslav@372: public final class CompareCase implements ITest { jaroslav@372: private final Bck2BrwsrCase first, second; jaroslav@273: private final Method m; jaroslav@273: jaroslav@372: private CompareCase(Method m, Bck2BrwsrCase first, Bck2BrwsrCase second) { jaroslav@273: this.first = first; jaroslav@273: this.second = second; jaroslav@273: this.m = m; jaroslav@273: } jaroslav@273: jaroslav@346: /** Inspects clazz and for each {@lik Compare} method creates jaroslav@347: * instances of tests. Each instance runs the test in different virtual jaroslav@346: * machine and at the end they compare the results. jaroslav@346: * jaroslav@346: * @param clazz the class to inspect jaroslav@346: * @return the set of created tests jaroslav@346: */ jaroslav@273: public static Object[] create(Class clazz) { jaroslav@273: Method[] arr = clazz.getMethods(); jaroslav@372: List ret = new ArrayList<>(); jaroslav@372: jaroslav@384: final LaunchSetup l = LaunchSetup.INSTANCE; jaroslav@372: ret.add(l); jaroslav@372: jaroslav@383: String[] brwsr; jaroslav@383: { jaroslav@383: String p = System.getProperty("vmtest.brwsrs"); jaroslav@383: if (p != null) { jaroslav@383: brwsr = p.split(","); jaroslav@383: } else { jaroslav@383: brwsr = new String[0]; jaroslav@383: } jaroslav@383: } jaroslav@383: jaroslav@273: for (Method m : arr) { jaroslav@518: registerCompareCases(m, l, ret, brwsr); jaroslav@518: registerBrwsrCases(m, l, ret, brwsr); jaroslav@273: } jaroslav@372: return ret.toArray(); jaroslav@273: } jaroslav@346: jaroslav@346: /** Test that compares the previous results. jaroslav@346: * @throws Throwable jaroslav@346: */ jaroslav@280: @Test(dependsOnGroups = "run") public void compareResults() throws Throwable { jaroslav@280: Object v1 = first.value; jaroslav@280: Object v2 = second.value; jaroslav@356: if (v1 != null) { jaroslav@356: v1 = v1.toString(); jaroslav@356: } else { jaroslav@356: v1 = "null"; jaroslav@280: } jaroslav@393: try { jaroslav@393: Assert.assertEquals(v2, v1, "Comparing results"); jaroslav@393: } catch (AssertionError e) { jaroslav@393: StringBuilder sb = new StringBuilder(); jaroslav@393: sb.append(e.getMessage()); jaroslav@393: Bck2BrwsrCase.dumpJS(sb, second); jaroslav@393: throw new AssertionError(sb.toString()); jaroslav@393: } jaroslav@280: } jaroslav@280: jaroslav@346: /** Test name. jaroslav@346: * @return name of the tested method followed by a suffix jaroslav@346: */ jaroslav@280: @Override jaroslav@280: public String getTestName() { jaroslav@349: return m.getName() + "[Compare " + second.typeName() + "]"; jaroslav@280: } jaroslav@518: jaroslav@518: private static void registerCompareCases(Method m, final LaunchSetup l, List ret, String[] brwsr) { jaroslav@518: Compare c = m.getAnnotation(Compare.class); jaroslav@518: if (c == null) { jaroslav@518: return; jaroslav@518: } jaroslav@623: final Bck2BrwsrCase real = new Bck2BrwsrCase(m, "Java", null, false, null, null); jaroslav@518: ret.add(real); jaroslav@537: if (c.scripting()) { jaroslav@623: final Bck2BrwsrCase js = new Bck2BrwsrCase(m, "JavaScript", l.javaScript(), false, null, null); jaroslav@537: ret.add(js); jaroslav@537: ret.add(new CompareCase(m, real, js)); jaroslav@537: } jaroslav@518: for (String b : brwsr) { jaroslav@518: final Launcher s = l.brwsr(b); jaroslav@518: ret.add(s); jaroslav@623: final Bck2BrwsrCase cse = new Bck2BrwsrCase(m, b, s, false, null, null); jaroslav@518: ret.add(cse); jaroslav@518: ret.add(new CompareCase(m, real, cse)); jaroslav@518: } jaroslav@518: } jaroslav@518: private static void registerBrwsrCases(Method m, final LaunchSetup l, List ret, String[] brwsr) { jaroslav@518: BrwsrTest c = m.getAnnotation(BrwsrTest.class); jaroslav@518: if (c == null) { jaroslav@518: return; jaroslav@518: } jaroslav@526: HtmlFragment f = m.getAnnotation(HtmlFragment.class); jaroslav@526: if (f == null) { jaroslav@526: f = m.getDeclaringClass().getAnnotation(HtmlFragment.class); jaroslav@526: } jaroslav@667: Http.Resource[] r = {}; jaroslav@667: Http h = m.getAnnotation(Http.class); jaroslav@667: if (h == null) { jaroslav@667: h = m.getDeclaringClass().getAnnotation(Http.class); jaroslav@667: if (h != null) { jaroslav@667: r = h.value(); jaroslav@667: } jaroslav@667: } else { jaroslav@667: r = h.value(); jaroslav@623: } jaroslav@518: if (brwsr.length == 0) { jaroslav@518: final Launcher s = l.brwsr(null); jaroslav@518: ret.add(s); jaroslav@623: ret.add(new Bck2BrwsrCase(m, "Brwsr", s, true, f, r)); jaroslav@518: } else { jaroslav@518: for (String b : brwsr) { jaroslav@518: final Launcher s = l.brwsr(b); jaroslav@518: ret.add(s); jaroslav@623: ret.add(new Bck2BrwsrCase(m, b, s, true, f, r)); jaroslav@518: } jaroslav@518: } jaroslav@518: } jaroslav@273: }