php - 通过 tcp 套接字将 mysql 选择查询的结果从 php 发送到 python
问题描述
我正在尝试使用 PHP 通过 TCP 套接字将我的 MYSQL 选择查询的结果发送到我的 Rpi 服务器。
这是PHP代码:
<!DOCTYPE html>
<html>
<body>
<?php
$servername = "localhost";
$username = "";
$password = "";
$dbname = "fyp_lora";
$host = "localhost";
$port = 12345;
$f = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
socket_set_option($f, SOL_SOCKET, SO_SNDTIMEO, array('sec' => 1, 'usec'
=> 500000));
$s = socket_connect($f, $host, $port);
// Create connection
$conn = new mysqli($servername, $username, $password, $dbname);
// Check connection
if ($conn->connect_error) {
die("Connection failed: " . $conn->connect_error);
}
$sql = "SELECT * FROM led_control";
$result = $conn->query($sql);
$data = array();
if ($result->num_rows > 0) {
// output data of each row
while($row = mysqli_fetch_array($result, MYSQLI_ASSOC)) {
$data[] = $row;
echo $row["ID"]. ",". $row["LED"]. "," . $row["Status"] . "<br>";
}
} else {
echo "0 results";
}
$conn->close();
foreach($data as $value)
{
$msg= $value["ID"]. ",". $value["LED"]. "," . $value["Status"] . "<br>";
$len = strlen($msg);
while (true) {
print($msg);
$sent = socket_write($f, $msg, $len);
if ($sent === false) {
break;
}
// Check if the entire message has been sent
if ($sent < $len) {
// If not send the entire message.
// Get the part of the message that has not yet been sent as message
$msg = substr($msg, $sent);
// Get the length of the not sent part
$len -= $sent;
} else {
socket_close($f);
break;
}
}
}
?>
</body>
</html>
这是引用的python代码: Sending a message from PHP to Python through a socket
import socket
s = socket.socket()
host = "localhost"
port = 12345
s.bind((host, port))
s.listen(5) #allows for 5 connections to be established
while True:
c, addr = s.accept()
data = c.recv(1024)
if data: print (str(data.decode().split(",")))
c.close() #closes the socket
在 Rpi 服务器上,它只会接收第一行消息,例如:['1', 'LED 1', 'OFF']但它不会接收其余的消息。
完整信息如下:
1,LED 1,OFF
2,LED 2,OFF
3,LED 3,OFF
4,LED 4,ON
我将不胜感激任何帮助:)
解决方案
仅收到第一行的原因是因为您socket_close()
在循环中发送每一行之后调用以将数据写入套接字。这意味着套接字不再可socket_write()
用于其余行的后续循环。
鉴于您只是在 Raspberry Pi 上运行它,您可以执行以下操作作为快速而肮脏的修复:
foreach ($data as $value) {
$msg= $value["ID"]. ",". $value["LED"]. "," . $value["Status"] . "\n";
$len = strlen($msg);
$connected = socket_connect($f, $host, $port);
if ($connected) {
while (true) {
$sent = socket_write($f, $msg, $len);
if ($sent === false) {
break;
}
if ($sent < $len) {
$msg = substr($msg, $sent);
$len -= $sent;
} else {
break;
}
}
socket_close($f);
}
}
推荐阅读
- list - 列表元组的函数
- ansible - 使用 Ansible 的文件模块时如何防止 ToCToU 问题?
- django - Django QuerySet 用于通过多对多相关的对象
- python - Python Pyside2 暂停脚本,直到用户从滑块或 qlineedit 返回值
- android - Getting "Conflicting overloads" for every function in one Kotlin file whenever I change it
- apache - How to combine a http->https redirect with a 404 redirect to /
- java - How to replace the properties of the fragment
- java - Gradle build finished with 662 warnings(s) in 37s 879ms
- android - Can you extract the www folder from a cordova app downloaded from the app store
- .net - Entity Framework Core 2.0 选择多对多问题的查询