@HttpResource allows a test to connect back to the server and read static resource emul
authorJaroslav Tulach <jaroslav.tulach@apidesign.org>
Thu, 31 Jan 2013 17:39:47 +0100
branchemul
changeset 6234af0d3dedb9d
parent 622 a07253cf2ca4
child 624 e79ab81a7656
@HttpResource allows a test to connect back to the server and read static resource
launcher/src/main/java/org/apidesign/bck2brwsr/launcher/Bck2BrwsrLauncher.java
launcher/src/main/java/org/apidesign/bck2brwsr/launcher/InvocationContext.java
vmtest/src/main/java/org/apidesign/bck2brwsr/vmtest/HttpResource.java
vmtest/src/main/java/org/apidesign/bck2brwsr/vmtest/impl/Bck2BrwsrCase.java
vmtest/src/main/java/org/apidesign/bck2brwsr/vmtest/impl/CompareCase.java
vmtest/src/test/java/org/apidesign/bck2brwsr/tck/HttpResourceTest.java
     1.1 --- a/launcher/src/main/java/org/apidesign/bck2brwsr/launcher/Bck2BrwsrLauncher.java	Thu Jan 31 16:58:27 2013 +0100
     1.2 +++ b/launcher/src/main/java/org/apidesign/bck2brwsr/launcher/Bck2BrwsrLauncher.java	Thu Jan 31 17:39:47 2013 +0100
     1.3 @@ -147,13 +147,40 @@
     1.4      private void executeInBrowser() throws InterruptedException, URISyntaxException, IOException {
     1.5          wait = new CountDownLatch(1);
     1.6          server = initServer(".", true);
     1.7 -        ServerConfiguration conf = server.getServerConfiguration();
     1.8 +        final ServerConfiguration conf = server.getServerConfiguration();
     1.9 +        
    1.10 +        class DynamicResourceHandler extends HttpHandler {
    1.11 +            private final InvocationContext ic;
    1.12 +            public DynamicResourceHandler(InvocationContext ic) {
    1.13 +                if (ic == null || ic.httpPath == null) {
    1.14 +                    throw new NullPointerException();
    1.15 +                }
    1.16 +                this.ic = ic;
    1.17 +                conf.addHttpHandler(this, ic.httpPath);
    1.18 +            }
    1.19 +
    1.20 +            public void close() {
    1.21 +                conf.removeHttpHandler(this);
    1.22 +            }
    1.23 +            
    1.24 +            @Override
    1.25 +            public void service(Request request, Response response) throws Exception {
    1.26 +                if (ic.httpPath.equals(request.getRequestURI())) {
    1.27 +                    LOG.log(Level.INFO, "Serving HttpResource for {0}", request.getRequestURI());
    1.28 +                    response.setContentType(ic.httpType);
    1.29 +                    response.getWriter().write(ic.httpContent);
    1.30 +                }
    1.31 +            }
    1.32 +        }
    1.33 +        
    1.34          conf.addHttpHandler(new Page(resources, 
    1.35              "org/apidesign/bck2brwsr/launcher/harness.xhtml"
    1.36          ), "/execute");
    1.37 +        
    1.38          conf.addHttpHandler(new HttpHandler() {
    1.39              int cnt;
    1.40              List<InvocationContext> cases = new ArrayList<>();
    1.41 +            DynamicResourceHandler prev;
    1.42              @Override
    1.43              public void service(Request request, Response response) throws Exception {
    1.44                  String id = request.getParameter("request");
    1.45 @@ -165,6 +192,11 @@
    1.46                      cases.get(Integer.parseInt(id)).result(value, null);
    1.47                  }
    1.48                  
    1.49 +                if (prev != null) {
    1.50 +                    prev.close();
    1.51 +                    prev = null;
    1.52 +                }
    1.53 +                
    1.54                  InvocationContext mi = methods.take();
    1.55                  if (mi == END) {
    1.56                      response.getWriter().write("");
    1.57 @@ -174,6 +206,10 @@
    1.58                      return;
    1.59                  }
    1.60                  
    1.61 +                if (mi.httpPath != null) {
    1.62 +                    prev = new DynamicResourceHandler(mi);
    1.63 +                }
    1.64 +                
    1.65                  cases.add(mi);
    1.66                  final String cn = mi.clazz.getName();
    1.67                  final String mn = mi.methodName;
     2.1 --- a/launcher/src/main/java/org/apidesign/bck2brwsr/launcher/InvocationContext.java	Thu Jan 31 16:58:27 2013 +0100
     2.2 +++ b/launcher/src/main/java/org/apidesign/bck2brwsr/launcher/InvocationContext.java	Thu Jan 31 17:39:47 2013 +0100
     2.3 @@ -55,6 +55,9 @@
     2.4       * perform an HTTP query and obtain a resource relative to the page.
     2.5       */
     2.6      public void setHttpResource(String relativePath, String mimeType, String content) {
     2.7 +        if (relativePath == null || mimeType == null || content == null) {
     2.8 +            throw new NullPointerException();
     2.9 +        }
    2.10          this.httpPath = relativePath;
    2.11          this.httpType = mimeType;
    2.12          this.httpContent = content;
     3.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     3.2 +++ b/vmtest/src/main/java/org/apidesign/bck2brwsr/vmtest/HttpResource.java	Thu Jan 31 17:39:47 2013 +0100
     3.3 @@ -0,0 +1,39 @@
     3.4 +/**
     3.5 + * Back 2 Browser Bytecode Translator
     3.6 + * Copyright (C) 2012 Jaroslav Tulach <jaroslav.tulach@apidesign.org>
     3.7 + *
     3.8 + * This program is free software: you can redistribute it and/or modify
     3.9 + * it under the terms of the GNU General Public License as published by
    3.10 + * the Free Software Foundation, version 2 of the License.
    3.11 + *
    3.12 + * This program is distributed in the hope that it will be useful,
    3.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
    3.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    3.15 + * GNU General Public License for more details.
    3.16 + *
    3.17 + * You should have received a copy of the GNU General Public License
    3.18 + * along with this program. Look for COPYING file in the top folder.
    3.19 + * If not, see http://opensource.org/licenses/GPL-2.0.
    3.20 + */
    3.21 +package org.apidesign.bck2brwsr.vmtest;
    3.22 +
    3.23 +import java.lang.annotation.ElementType;
    3.24 +import java.lang.annotation.Retention;
    3.25 +import java.lang.annotation.RetentionPolicy;
    3.26 +import java.lang.annotation.Target;
    3.27 +
    3.28 +/** Exposes an HTTP page to the running {@link BrwsrTest}, so it can access
    3.29 + * under the relative path.
    3.30 + *
    3.31 + * @author Jaroslav Tulach <jtulach@netbeans.org>
    3.32 + */
    3.33 +@Retention(RetentionPolicy.RUNTIME)
    3.34 +@Target({ ElementType.METHOD, ElementType.TYPE})
    3.35 +public @interface HttpResource {
    3.36 +    /** path on the server that the test can use to access the exposed resource */
    3.37 +    String path();
    3.38 +    /** the content of the HttpResource */
    3.39 +    String content();
    3.40 +    /** mime type of the resource */
    3.41 +    String mimeType();
    3.42 +}
     4.1 --- a/vmtest/src/main/java/org/apidesign/bck2brwsr/vmtest/impl/Bck2BrwsrCase.java	Thu Jan 31 16:58:27 2013 +0100
     4.2 +++ b/vmtest/src/main/java/org/apidesign/bck2brwsr/vmtest/impl/Bck2BrwsrCase.java	Thu Jan 31 17:39:47 2013 +0100
     4.3 @@ -25,6 +25,8 @@
     4.4  import java.lang.reflect.Method;
     4.5  import org.apidesign.bck2brwsr.launcher.Launcher;
     4.6  import org.apidesign.bck2brwsr.launcher.InvocationContext;
     4.7 +import org.apidesign.bck2brwsr.vmtest.HtmlFragment;
     4.8 +import org.apidesign.bck2brwsr.vmtest.HttpResource;
     4.9  import org.testng.ITest;
    4.10  import org.testng.annotations.Test;
    4.11  
    4.12 @@ -37,15 +39,17 @@
    4.13      private final Launcher l;
    4.14      private final String type;
    4.15      private final boolean fail;
    4.16 +    private final HtmlFragment html;
    4.17 +    private final HttpResource http;
    4.18      Object value;
    4.19 -    private final String html;
    4.20  
    4.21 -    Bck2BrwsrCase(Method m, String type, Launcher l, boolean fail, String html) {
    4.22 +    Bck2BrwsrCase(Method m, String type, Launcher l, boolean fail, HtmlFragment html, HttpResource http) {
    4.23          this.l = l;
    4.24          this.m = m;
    4.25          this.type = type;
    4.26          this.fail = fail;
    4.27          this.html = html;
    4.28 +        this.http = http;
    4.29      }
    4.30  
    4.31      @Test(groups = "run")
    4.32 @@ -53,7 +57,10 @@
    4.33          if (l != null) {
    4.34              InvocationContext c = l.createInvocation(m.getDeclaringClass(), m.getName());
    4.35              if (html != null) {
    4.36 -                c.setHtmlFragment(html);
    4.37 +                c.setHtmlFragment(html.value());
    4.38 +            }
    4.39 +            if (http != null) {
    4.40 +                c.setHttpResource(http.path(), http.mimeType(), http.content());
    4.41              }
    4.42              String res = c.invoke();
    4.43              value = res;
     5.1 --- a/vmtest/src/main/java/org/apidesign/bck2brwsr/vmtest/impl/CompareCase.java	Thu Jan 31 16:58:27 2013 +0100
     5.2 +++ b/vmtest/src/main/java/org/apidesign/bck2brwsr/vmtest/impl/CompareCase.java	Thu Jan 31 17:39:47 2013 +0100
     5.3 @@ -111,17 +111,17 @@
     5.4          if (c == null) {
     5.5              return;
     5.6          }
     5.7 -        final Bck2BrwsrCase real = new Bck2BrwsrCase(m, "Java", null, false, null);
     5.8 +        final Bck2BrwsrCase real = new Bck2BrwsrCase(m, "Java", null, false, null, null);
     5.9          ret.add(real);
    5.10          if (c.scripting()) {
    5.11 -            final Bck2BrwsrCase js = new Bck2BrwsrCase(m, "JavaScript", l.javaScript(), false, null);
    5.12 +            final Bck2BrwsrCase js = new Bck2BrwsrCase(m, "JavaScript", l.javaScript(), false, null, null);
    5.13              ret.add(js);
    5.14              ret.add(new CompareCase(m, real, js));
    5.15          }
    5.16          for (String b : brwsr) {
    5.17              final Launcher s = l.brwsr(b);
    5.18              ret.add(s);
    5.19 -            final Bck2BrwsrCase cse = new Bck2BrwsrCase(m, b, s, false, null);
    5.20 +            final Bck2BrwsrCase cse = new Bck2BrwsrCase(m, b, s, false, null, null);
    5.21              ret.add(cse);
    5.22              ret.add(new CompareCase(m, real, cse));
    5.23          }
    5.24 @@ -135,16 +135,19 @@
    5.25          if (f == null) {
    5.26              f = m.getDeclaringClass().getAnnotation(HtmlFragment.class);
    5.27          }
    5.28 -        String html = f == null ? null : f.value();
    5.29 +        HttpResource r = m.getAnnotation(HttpResource.class);
    5.30 +        if (r == null) {
    5.31 +            r = m.getDeclaringClass().getAnnotation(HttpResource.class);
    5.32 +        }
    5.33          if (brwsr.length == 0) {
    5.34              final Launcher s = l.brwsr(null);
    5.35              ret.add(s);
    5.36 -            ret.add(new Bck2BrwsrCase(m, "Brwsr", s, true, html));
    5.37 +            ret.add(new Bck2BrwsrCase(m, "Brwsr", s, true, f, r));
    5.38          } else {
    5.39              for (String b : brwsr) {
    5.40                  final Launcher s = l.brwsr(b);
    5.41                  ret.add(s);
    5.42 -                ret.add(new Bck2BrwsrCase(m, b, s, true, html));
    5.43 +                ret.add(new Bck2BrwsrCase(m, b, s, true, f, r));
    5.44              }
    5.45          }
    5.46      }
     6.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     6.2 +++ b/vmtest/src/test/java/org/apidesign/bck2brwsr/tck/HttpResourceTest.java	Thu Jan 31 17:39:47 2013 +0100
     6.3 @@ -0,0 +1,53 @@
     6.4 +/**
     6.5 + * Back 2 Browser Bytecode Translator
     6.6 + * Copyright (C) 2012 Jaroslav Tulach <jaroslav.tulach@apidesign.org>
     6.7 + *
     6.8 + * This program is free software: you can redistribute it and/or modify
     6.9 + * it under the terms of the GNU General Public License as published by
    6.10 + * the Free Software Foundation, version 2 of the License.
    6.11 + *
    6.12 + * This program is distributed in the hope that it will be useful,
    6.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
    6.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    6.15 + * GNU General Public License for more details.
    6.16 + *
    6.17 + * You should have received a copy of the GNU General Public License
    6.18 + * along with this program. Look for COPYING file in the top folder.
    6.19 + * If not, see http://opensource.org/licenses/GPL-2.0.
    6.20 + */
    6.21 +package org.apidesign.bck2brwsr.tck;
    6.22 +
    6.23 +import org.apidesign.bck2brwsr.core.JavaScriptBody;
    6.24 +import org.apidesign.bck2brwsr.vmtest.BrwsrTest;
    6.25 +import org.apidesign.bck2brwsr.vmtest.HttpResource;
    6.26 +import org.apidesign.bck2brwsr.vmtest.VMTest;
    6.27 +import org.testng.annotations.Factory;
    6.28 +
    6.29 +/**
    6.30 + *
    6.31 + * @author Jaroslav Tulach <jtulach@netbeans.org>
    6.32 + */
    6.33 +public class HttpResourceTest {
    6.34 +    
    6.35 +    @HttpResource(path = "/xhr", content = "Hello Brwsr!", mimeType = "text/plain")
    6.36 +    @BrwsrTest
    6.37 +    public String testReadContentViaXHR() throws Exception {
    6.38 +        String msg = read("/xhr");
    6.39 +        assert "Hello Brwsr!".equals(msg) : "The message was " + msg;
    6.40 +        return msg;
    6.41 +    }
    6.42 +    
    6.43 +    @JavaScriptBody(args = { "url" }, body = 
    6.44 +          "var req = new XMLHttpRequest();\n"
    6.45 +        + "req.open('GET', url, false);\n"
    6.46 +        + "req.send();\n"
    6.47 +        + "return req.responseText;"
    6.48 +    )
    6.49 +    private static native String read(String url);
    6.50 +    
    6.51 +    
    6.52 +    @Factory
    6.53 +    public static Object[] create() {
    6.54 +        return VMTest.create(HttpResourceTest.class);
    6.55 +    }
    6.56 +}