为什么JavaFX中WebView无法连接到WebSocket?

问题描述 投票:0回答:1

我正在尝试从 JavaFX 中的

WebSocket
连接到
WebView
(因为我想使用仅在 Javascript 中可用的第三方组件)。在
WebView
的 HTML 文件中,我使用 Javascript 创建了
WebSocket
实例,在 JavaFX 部分中,我使用
Java-WebSocket
创建了
WebSocketServer
。但是现在,在
WebSocketServer
启动并且 Javascript
WebSocket
客户端初始化后,
WebSocketServer
似乎没有打开与
WebView
的连接。此外,如果我在运行应用程序时在浏览器中打开 HTML 文件(使用 IntelliJ IDEA 的“在浏览器中打开”功能),
WebSocket
似乎会打开一个连接。

我在 Stack Overflow 上搜索了一些答案,但它们似乎都已经过时了。


这是代码。

HelloApplication.java

package com.remmymilkyway.websocketdemo;

import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Scene;
import javafx.scene.web.WebView;
import javafx.stage.Stage;
import org.java_websocket.WebSocket;
import org.java_websocket.handshake.ClientHandshake;
import org.java_websocket.server.WebSocketServer;

import java.io.IOException;
import java.net.InetSocketAddress;
import java.util.Objects;

public class HelloApplication extends Application {
    private WebSocketServer server;

    @Override
    public void start(Stage stage) {
        WebView webView = new WebView();
        webView.getEngine().load(Objects.requireNonNull(this.getClass().getResource("web-view.html")).toExternalForm());

        server = new WebSocketServer(new InetSocketAddress("localhost", 8080)) {
            @Override
            public void onOpen(WebSocket conn, ClientHandshake handshake) {
                System.out.println("New connection: " + conn.getRemoteSocketAddress().getAddress().getHostAddress());
            }

            @Override
            public void onClose(WebSocket conn, int code, String reason, boolean remote) {
                System.out.println("Connection closed: " + conn.getRemoteSocketAddress().getAddress().getHostAddress());
            }

            @Override
            public void onMessage(WebSocket conn, String message) {
                System.out.println("Received message: " + message);
            }

            @Override
            public void onError(WebSocket conn, Exception ex) {
                System.out.println("An error occurred: " + ex);
            }

            @Override
            public void onStart() {
                System.out.println("Server started");
            }
        };
        server.start();
        server.broadcast("Server started.");

        Scene scene = new Scene(webView);
        stage.setTitle("Hello!");
        stage.setScene(scene);
        stage.show();
    }

    @Override
    public void stop() throws Exception {
        super.stop();
        server.stop();
        System.out.println("Server stopped");
    }

    public static void main(String[] args) {
        launch();
    }
}

web-view.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
</head>
<body>
<p id="text"></p>
<script>
    var webSocket = new WebSocket("ws://localhost:8080");
    document.getElementById("text").innerHTML = "WebSocket instance created: " + webSocket.url; // show the URL of the WebSocket instance
</script>
</body>
</html>

pom.xml

<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.remmymilkyway</groupId>
    <artifactId>WebSocketDemo</artifactId>
    <version>1.0-SNAPSHOT</version>
    <name>WebSocketDemo</name>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <junit.version>5.10.2</junit.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.openjfx</groupId>
            <artifactId>javafx-controls</artifactId>
            <version>22.0.1</version>
        </dependency>
        <dependency>
            <groupId>org.openjfx</groupId>
            <artifactId>javafx-fxml</artifactId>
            <version>22.0.1</version>
        </dependency>

        <dependency>
            <groupId>org.junit.jupiter</groupId>
            <artifactId>junit-jupiter-api</artifactId>
            <version>${junit.version}</version>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>org.junit.jupiter</groupId>
            <artifactId>junit-jupiter-engine</artifactId>
            <version>${junit.version}</version>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>org.openjfx</groupId>
            <artifactId>javafx-web</artifactId>
            <version>22.0.1</version>
        </dependency>
        <dependency>
            <groupId>org.java-websocket</groupId>
            <artifactId>Java-WebSocket</artifactId>
            <version>1.5.7</version>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>3.13.0</version>
                <configuration>
                    <source>22</source>
                    <target>22</target>
                </configuration>
            </plugin>
            <plugin>
                <groupId>org.openjfx</groupId>
                <artifactId>javafx-maven-plugin</artifactId>
                <version>0.0.8</version>
                <executions>
                    <execution>
                        <!-- Default configuration for running with: mvn clean javafx:run -->
                        <id>default-cli</id>
                        <configuration>
                            <mainClass>
                                com.remmymilkyway.websocketdemo/com.remmymilkyway.websocketdemo.HelloApplication
                            </mainClass>
                            <launcher>app</launcher>
                            <jlinkZipName>app</jlinkZipName>
                            <jlinkImageName>app</jlinkImageName>
                            <noManPages>true</noManPages>
                            <stripDebug>true</stripDebug>
                            <noHeaderFiles>true</noHeaderFiles>
                        </configuration>
                    </execution>
                </executions>
            </plugin>
        </plugins>
    </build>
</project>

模块信息.java

module com.remmymilkyway.websocketdemo {
    requires javafx.controls;
    requires javafx.fxml;
    requires javafx.web;
    requires org.java_websocket;


    opens com.remmymilkyway.websocketdemo to javafx.fxml;
    exports com.remmymilkyway.websocketdemo;
}

这是我运行应用程序时得到的输出和异常。

SLF4J: No SLF4J providers were found.
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See https://www.slf4j.org/codes.html#noProviders for further details.
Server started
xxxx-xx-xx xx:xx:xx.xxx java[76456:7816534] +[IMKClient subclass]: chose IMKClient_Modern
xxxx-xx-xx xx:xx:xx.xxx java[76456:7816534] +[IMKInputSession subclass]: chose IMKInputSession_Modern
Server stopped

如果我在浏览器选项卡中打开

web-view.html
,这是我得到的附加输出。

New connection: 127.0.0.1
Connection closed: 127.0.0.1
java javafx websocket webview
1个回答
0
投票

总结我们的对话,这个问答研究了一个相关问题。尽管已经过时,该版本仍然支持modulo后端口延迟。在这种情况下,影响多个版本的JDK-8331765是相关的。由于您使用的是受到影响的 v22.0.1,因此您可以尝试更高版本。我发现 v21.0.5 [LTS] 足够了,@jewelsea 发现 v23.0.1 有效。

最新问题
© www.soinside.com 2019 - 2025. All rights reserved.