Web socket disconnecting on OpenShift (with WildFl

2019-01-28 16:30发布

问题:

I am using OpenShift and WildFly 8.2.1 final to implement the new HTML5 websocket. I used this tutorial to set this project up.

Whenever I open my MyTest.html, this is what the JavaScript logs:

JS: Server Connected...
JS: Server Disconnected...

The server connects and then immediately disconnects. Why? What am I doing wrong? Is there something that I am missing?

Here is mode code -->

serverendpoint.java

package testing;

import javax.websocket.OnClose;
import javax.websocket.OnError;
import javax.websocket.OnMessage;
import javax.websocket.OnOpen;
import javax.websocket.server.ServerEndpoint;

@ServerEndpoint("/serverendpoint")
public class serverendpoint {
    @OnOpen
    public void handleOpen () {
        System.out.println("JAVA: Client is now connected...");
    }

    @OnMessage
    public String handleMessage (String message) {
        System.out.println("JAVA: Received from client: "+ message);
        String replyMessage = "echo "+ message; 
        System.out.println("JAVA: Send to client: "+ replyMessage);
        return replyMessage;
    }

    @OnClose
    public void handleClose() {
        System.out.println("JAVA: Client is now disconnected...");
    }

    @OnError
    public void handleError (Throwable t) {
        t.printStackTrace();
    }
}

MyTest.html:

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>My WS Website</title>
</head>
<body>
    <form>
        <input id="textMessage" type="text">
        <input onclick="sendMessage();" value="Send Message" type="button">
    </form>
    <br>
    <textarea id="messageTextArea" rows="10" cols="50"></textarea>
    <script type="text/javascript">
        var wsUri = "ws://" + document.location.hostname + ":8000" + document.location.pathname + "serverendpoint";
        var webSocket = new WebSocket(wsUri);
        var messageTextArea = document.getElementById("messageTextArea");
        webSocket.onopen = function(message) { processOpen(message);};
        webSocket.onmessage = function(message) { processMessage(message);};
        webSocket.onclose = function(message) { processClose(message);};
        webSocket.onerror = function(message) { processError(message);};
        function processOpen (message) {
            messageTextArea.value += "JS: Server Connected..."+"\n";
        }
        function processMessage(message) {
            messageTextArea.value += "JS: Receive from Server ==> "+message.data+"\n";
        }
        function sendMessage () {
            if (textMessage.value !="close") {
                webSocket.send(textMessage.value);
                messageTextArea.value += "JS: Send to Server ==> "+textMessage.value+"\n";
                textMessage.value="";
            } else webSocket.close();
        }
        function processClose(message) {
            webSocket.send("JS: Client disconnected...")
            messageTextArea.value += "JS: Server Disconnected..."+"\n";
        }
        function processError (message) {
            messageTextArea.value += "JS: error ..."+"\n";
        }
    </script>
</body>
</html>

And the pom.xml file:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>testing</groupId>
    <artifactId>testing</artifactId>
    <packaging>war</packaging>
    <version>1.0-SNAPSHOT</version>
    <name>testing</name>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <maven.compiler.source>1.8</maven.compiler.source>
        <maven.compiler.target>1.8</maven.compiler.target>
    </properties>

    <dependencies>
        <dependency>
            <groupId>javax</groupId>
            <artifactId>javaee-api</artifactId>
            <version>7.0</version>
            <scope>provided</scope>
        </dependency>
    </dependencies>

<profiles>
    <profile>
     <!-- When built in OpenShift the 'openshift' profile will be used when invoking mvn. -->
     <!-- Use this profile for any OpenShift specific customization your app will need. -->
     <!-- By default that is to put the resulting archive into the 'deployments' folder. -->
     <!-- http://maven.apache.org/guides/mini/guide-building-for-different-environments.html -->
     <id>openshift</id>
     <build>
        <finalName>testing</finalName>
        <plugins>
          <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-war-plugin</artifactId>
                <version>2.3</version>
                <configuration>
                    <failOnMissingWebXml>false</failOnMissingWebXml>
                    <outputDirectory>deployments</outputDirectory>
                      <warName>ROOT</warName>
                </configuration>
            </plugin>
        </plugins>
      </build>
    </profile>
  </profiles>
</project>

Thank you for your help!

回答1:

I think you are trying to connect to a non-existing endpoint, when opening the websocket.

This (note that you are missinng /../):

var wsUri = "ws://" + document.location.hostname + ":8000" + document.location.pathname + "/../serverendpoint";

...will work for your files deployed to WildFly as follows:

├── pom.xml
└── src
    └── main
        ├── java
        │   └── testing
        │       └── serverendpoint.java
        └── webapp
            ├── MyTest.html
            └── WEB-INF
                └── web.xml

I've checked this using your code (with the modified endpoint path) on WildFly 10 cartridge on OpenShift Online.



回答2:

Open shift had some odd rules on port numbering for sockets. You name it one thing, refer to it as something else....

I think you want port 8080 for server, let client find its own port.

Note: I've only used sockets at Open Shift via node.js I remember pulling my hair out on port #'s. ...here is my code:

self.ipaddress = process.env.OPENSHIFT_NODEJS_IP;
self.port      = process.env.OPENSHIFT_NODEJS_PORT || 8080;    

I don't know exactly whats at those two variable names..

You may want to check out this link.

Update: I've been working on reproducing the issue, all to no avail. First I'm trying to reproduce the tutorial on my localhost (win7 desktop) but I'm not making much progress. I am using Java JDK 1.8.0_65, and with that is wildfly-8.2.1.Final... I can get the server to display at http://localhost:8080/ (with wildfly splash screen) but I can not get the http://localhost:8080/chat/ to function at all (404 - Not Found). So, I'm not of much help... yet.

Bingo... I had to change the url in the browser client to http://localhost:8080/websocket-chat/ so now I am functional on desktop local host. I will push to OpenShift tomorrow.

So I've been attempting to duplicate your push to OpenShift. I'm now understanding your pom.xml issues. The real problem is you can't FTP files to OpenShift, you have to push them via git. That library javee7-libraries is huge, and the pom.xml files are very intertwined. No way you'd want to push the entire library to openshift, and there is no simple way to integrate the POM files to simplicity (I've tried!) I keep getting maven errors.

The tutorial is sort of a hack.. he generates the war files inside the javee7 library (and avoiding all the POM dependency difficulty), then copies them back to a virgin chat component directory. Then he deletes nearly everything in the chat component directory, including the source code, then pushes the war files thru git to openshift. Ugh. Note: I'm doing all of this via atom.io and command line.

What you are trying to do makes a lot more sense to me, but I'm unable to figure out the correct pom.xml for the standalone chat directory to avoid maven errors.

I've been working on this most of the day. Here's what I learned.

  • I was able to get the sample to work fine on my local host.
  • Your pom.xml (which came with the cartridge "WildFly Application Server 8.2.1.Final" is absolutely correct, less testing files.
  • You have to generate the .war file with the command '$ mvn -f pom.xml package -Popenshift`
  • In order to push the .war file up to the OpenShift server via git, you have to modify the .gitignore file so it recognizes .war files (duh.)
  • I played around a whole lot with different port #s, and ws:// codes
  • When all that is done, I'm still getting the same output as you. I get a connection, and when I try to send text, I get a JS error with an immediate disconnect.
  • rhc tools are a total pain on windows machine. In fact I could never get that to work at all.
  • When I look closely at the code, the socket stuff is simple JS implementation of sockets via html5. My suspicion is that version isn't all that robust. I'd much rather see a dedicated JS socket library like sock.js The other note is, with the html5 version we have no control to tell the server which port to host the sockets on. The only code we can control is the client side code, and that's not really what we want.
  • The only way to test that is use the library update the javascript code and move this along.