ฉันกำลังลองใช้ websockets โดยใช้ spring กับ java/เว็บแอปพลิเคชัน เพื่ออนุญาตให้แลกเปลี่ยนข้อความกับแอปพลิเคชันที่เขียนด้วย c++ โดยใช้ qt (และไลบรารี websockets จากนั้น)
ฉันมีการกำหนดค่านี้ในแอปพลิเคชัน java/spring:
WebScoketConfig.java
@Configuration
@EnableWebSocket
public class WebSocketConfig implements WebSocketConfigurer {
public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) {
registry.addHandler(new SocketHandler(), "/name");
}
}
SocketHandler.java
@Component
public class SocketHandler extends TextWebSocketHandler {
List<WebSocketSession> sessions = new CopyOnWriteArrayList<>();
@Override
public void handleTextMessage(WebSocketSession session, TextMessage message) throws InterruptedException, IOException {
Map<String, String> value = new Gson().fromJson(message.getPayload(), Map.class);
session.sendMessage(new TextMessage("Hello " + value.get("name") + " !"));
}
@Override
public void afterConnectionEstablished(WebSocketSession session) throws Exception {
sessions.add(session);
}
}
และฉันสร้างโปรเจ็กต์ qt-creator ที่เรียบง่ายมากด้วยฟังก์ชัน main
และหนึ่งคลาส MainWindow
โดยมีสองอ็อบเจ็กต์: lineEdit
โดยที่ผู้ใช้พิมพ์ข้อความเพื่อส่งไปยังเซิร์ฟเวอร์ และ pushButton
เพื่อดำเนินการส่งข้อมูลต่อไป
ในคลาส MainWindow
ของฉัน ฉันใช้สล็อตนี้เพื่อจัดการการแลกเปลี่ยนข้อมูล:
void MainWindow::on_pushButton_clicked()
{
QString message = this->ui->lineEdit->text();
QWebSocket m_webSocket;
m_webSocket.open(QUrl(QStringLiteral("ws://localhost:8080/name")));
m_webSocket.sendTextMessage("Hello " + message + " !");
m_webSocket.close();
}
แต่เมื่อฉันรันทั้งสองแอปพลิเคชั่น และลองส่งข้อความสำหรับจาวา/เว็บแอปพลิเคชั่น ก็ไม่มีอะไรเกิดขึ้น ฉันค่อนข้างแน่ใจว่าข้อผิดพลาดที่ฉันทำนั้นอยู่ที่ฝั่ง c++/qt เนื่องจากในด้าน java/spring ฉันมีรหัส html/javascript ซึ่งอนุญาตให้ฉันทดสอบการแลกเปลี่ยนข้อความและทำงานได้ดี
ใครสามารถบอกฉันว่าฉันทำอะไรผิดที่นี่?
อัปเดต: ตัวอย่างที่สามารถทำซ้ำได้น้อยที่สุด - java/spring
สามารถสร้างโปรเจ็กต์ได้ด้วย start.spring.io โดยมี spring-websocket เป็นการพึ่งพาเท่านั้น นอกจาก 2 ไฟล์ที่ฉันเพิ่มไว้ข้างต้นแล้ว โปรเจ็กต์นี้จะมี:
ทรัพยากร/static/index.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Hello WebSocket</title>
<link href="/th/main.css" rel="stylesheet">
</head>
<body>
<table>
<tr>
<td>
<button id="connect" type="button" onclick="connect();">Connect</button>
<button id="disconnect" type="button" disabled="disabled" onclick="disconnect();">Disconnect</button>
</td>
<td>
<label for="name">What is your name?</label>
<input type="text" id="name" placeholder="Your name here...">
<button id="send" type="button" onclick="send();">Send</button>
</td>
</tr>
</table>
<hr>
<table id="conversation" border="2">
<thead>
<tr>
<th>Greetings</th>
</tr>
</thead>
<tbody id="greetings">
</tbody>
</table>
<script src="/app.js"></script>
</body>
</html>
ทรัพยากร/app.js
ต่างกันอย่างไร;
function connect() {
ws = new WebSocket('ws://localhost:8080/name');
ws.onmessage = function(text) {
var tr = document.createElement("tr");
var td = document.createElement("td");
td.innerText = text.data;
tr.appendChild(td);
document.querySelector("#greetings").appendChild(tr);
}
document.querySelector("#connect").setAttribute("disabled", "disabled");
document.querySelector("#disconnect").removeAttribute("disabled");
document.querySelector("#conversation").style.display = 'block';
document.querySelector("#greetings").innerHTML = "";
}
function disconnect() {
if (ws != null)
ws.close();
document.querySelector("#connect").removeAttribute("disabled");
document.querySelector("#disconnect").setAttribute("disabled", "disabled");
document.querySelector("#conversation").style.display = 'none';
document.querySelector("#greetings").innerHTML = "";
}
function send() {
var name = document.querySelector("#name");
var data = JSON.stringify({'name': name.value});
ws.send(data);
}
หลังจากสร้างด้วย mvn package
ให้รันด้วย java -jar target/app.jar
อัปเดต: ตัวอย่างที่ทำซ้ำได้น้อยที่สุด - c++/qt
โปรเจ็กต์ถูกสร้างขึ้นด้วย qt-creator เป็นประเภท qt-widget มันจะสร้างโปรเจ็กต์ที่มี 5 ไฟล์: websocket.pro
, mainwindow.ui
, mainwindow.h
, mainwindow.cpp
และ main.cpp
เปิด mainwindow.ui
และเพิ่ม lineEdit
และ pushButton
จากแถบเครื่องมือ คลิกขวาที่ปุ่มกดแล้วเลือก Go to slot
และเลือก clicked()
เพิ่มรหัสด้านบน
อัปเดต 2
void MainWindow::on_pushButton_clicked()
{
QString message = ui->lineEdit->text();
connect(&m_webSocket, &QWebSocket::connected, [this, message](){
QJsonObject object
{
{"name", message}
};
QJsonDocument d(object);
m_webSocket.sendTextMessage(d.toJson().toStdString().c_str());
m_webSocket.close();
});
m_webSocket.open(QUrl(QStringLiteral("ws://localhost:8080/name")));
}
QWebSocket::sendTextMessage
จะไม่ส่งข้อความทันที แต่จะเลื่อนการส่งจนกว่าคุณจะกลับการควบคุมไปยังลูปเหตุการณ์ Qt ในกรณีนี้ข้อความอาจหายไปเมื่อQWebSocket
ของคุณอยู่นอกขอบเขต - person G.M.   schedule 09.04.2020QWebSocket
m_webSocket
เป็นสมาชิกข้อมูลของคลาสMainWindow
- person G.M.   schedule 10.04.2020m_websocket
เป็นสมาชิกข้อมูลของMainWindow
เท่านั้นไม่ได้ทำให้สิ่งนี้ทำงานได้ - person Kleber Mota   schedule 10.04.2020