Arquillian TomEE 嵌入式测试与网络套接字

Arquillian TomEE embedded test with web sockets

我正在尝试在 arquillian 测试中使用 websockets 编写服务器端点测试。我收到一条错误消息

Caused by: org.glassfish.tyrus.core.HandshakeException: Response code was not 101: 404.

部署时,我在 tomee 的日志中收到警告:

WARNING: Can't set TomEE ServerEndpointConfig$Configurator
java.lang.NoSuchFieldException: defaultImpl
    at java.lang.Class.getDeclaredField(Class.java:2070)
    at org.apache.tomee.catalina.TomcatWebAppBuilder.forceEEServerEndpointConfigurator(TomcatWebAppBuilder.java:338)
    at org.apache.tomee.catalina.TomcatWebAppBuilder.<init>(TomcatWebAppBuilder.java:284)
    at org.apache.tomee.catalina.TomcatLoader.initialize(TomcatLoader.java:222)
    at org.apache.tomee.embedded.Container.start(Container.java:293)
    ....

端点定义如下:

@ServerEndpoint("/games")
public class GameEndPoint {

    @Inject
    GameManager gameManager;
    @Inject
    private GameSessionHandler sessionHandler;

    @OnOpen
    public void open(Session session) {
    }

    @OnClose
    public void close(Session session) {
    }

    @OnError
    public void onError(Throwable error) {
    }

    @OnMessage
    public void handleMessage(String payload, Session session) {
    }
}

@ClientEndpoint
public class SocketClient {

    @OnOpen
    public void onOpen(Session session) {
    }

    @OnMessage
    public void onMessage(String message, Session session) {
    }

    @OnClose
    public void onClose(Session session, CloseReason closeReason) {
        LOGGER.info(String.format("Session %s close because of %s",     session.getId(), closeReason));
    }

    public void openConnection(URL url) {//URL injected arquillian resource, where url is for http connection..
        WebSocketContainer container = ContainerProvider.getWebSocketContainer();
        try {
            URI uri = URI.create(url.toString().replace("http", "ws") + "games");
            container.connectToServer(this, uri);
        } catch (DeploymentException | IOException ex) {
            LOGGER.log(Level.SEVERE, null, ex);
            throw new RuntimeException(ex);
        }
    }
}

我的测试是用 spock 写的,安装失败

@RunWith(ArquillianSputnik)
class GameServiceSocketIT extends Specification {

    @Deployment
    public static Archive archive() {
        return createDeployment();//shrinkwrap stuff
    }
    @ArquillianResource
    URL url;
    @Inject
    SocketClient client;

    def Game currentGame = null

    def setup() { // run before every feature method
        client.openConnection(url);
    }

    def 'init new game' () {
        given: 'blabla'
            blabla
        when: 'blalba'
            blabla
        then: 'blabla'
            blablabla...
    }
}

我的 pom 依赖项:

    <dependency>
        <groupId>javax.websocket</groupId>
        <artifactId>javax.websocket-api</artifactId>
        <version>1.0</version>
        <scope>provided</scope>
    </dependency>
    <dependency>
        <groupId>junit</groupId>
        <artifactId>junit</artifactId>
        <version>4.12</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.jboss.arquillian.spock</groupId>
        <artifactId>arquillian-spock-container</artifactId>
        <version>1.0.0.Beta3</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.spockframework</groupId>
        <artifactId>spock-core</artifactId>
        <version>0.7-groovy-2.0</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.codehaus.groovy</groupId>
        <artifactId>groovy-all</artifactId>
        <version>2.1.8</version>
        <scope>test</scope>
    </dependency>
    <!-- For Arquillian Integration tests in TOMEE -->
    <dependency>
        <groupId>org.apache.openejb</groupId>
        <artifactId>arquillian-tomee-embedded</artifactId>
        <version>1.7.2</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.apache.openejb</groupId>
        <artifactId>tomee-embedded</artifactId>
        <version>1.7.2</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.glassfish.tyrus</groupId>
        <artifactId>tyrus-container-jdk-client</artifactId>
        <version>1.8.3</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>javax</groupId>
        <artifactId>javaee-web-api</artifactId>
        <version>6.0</version>
        <scope>provided</scope>
    </dependency>

编辑:

我的 createDeployment 方法:

return ShrinkWrap.create(WebArchive.class, "test.war")
            .addAsWebInfResource(EmptyAsset.INSTANCE, ArchivePaths.create("beans.xml"))
            .addPackages(true, Filters.exclude(".*IT.class"), "engine")
            .addPackages(true, Filters.exclude(".*IT.class"), "socket")
            .addPackages(true, Filters.exclude(".*IT.class"), "persistence");

替换依赖项:

<dependency>
    <groupId>javax.websocket</groupId>
    <artifactId>javax.websocket-api</artifactId>
    <version>1.0</version>
    <scope>provided</scope>
</dependency>

具有依赖性:

<dependency>
    <groupId>org.apache.tomcat</groupId>
    <artifactId>tomcat7-websocket</artifactId>
    <version>7.0.59</version>
    <scope>provided</scope>
</dependency>

解决了问题,我现在让客户端连接到我的服务器,但是现在我的 ServerEndPoint 中出现了 CDI 注入问题。这似乎是另一个问题..