我是一名初学者,目前正在使用带有LAMP堆栈的raspberrypi3和带有一些用于记录遥测的传感器的arduino进行项目。
我现在卡住了,因为我的Python脚本将数据导入MySQL 可以在shell中触发时连接到 / dev / ttyACM0 ,并且运行正常。当在PHP中触发system(),popen()或exec()时,它无法连接到串口。
我知道脚本正在运行,因为在PHP输出中,它显示了无法连接的消息到 / dev / ttyAMC0
这是我第一次使用PHP,所以它可能是非常愚蠢的东西。
目前我已经针对当前的问题引用了这些网站:
Calling Python in PHP
Execute PHP function with onClick
PHP - Command Line
这是我的index.php中的代码:
@charset "utf-8";
body {
background-color: rgba(233,233,233,1.00);
font-family: Gotham, "Helvetica Neue", Helvetica, Arial, sans-serif;
font-size: x-large;
}
h1 {
color: rgba(233,233,233,1.00);
background-color: rgba(55,55,55,1.00);
padding-top: 5px;
padding-right: 5px;
padding-bottom: 5px;
padding-left: 5px;
}
.button {
display: inline-block;
padding-top: 30px;
padding-right: 30px;
padding-bottom: 30px;
padding-left: 30px;
background-color: rgba(55,55,55,1.00);
color: rgba(233,233,233,1.00);
text-align: center;
margin-top: 10px;
margin-right: 10px;
margin-bottom: 10px;
margin-left: 10px;
}
<!doctype html>
<?php
function start_recording(){
system("./getdata.py");
}
function stop_recording(){
popen("pkill python");
}
if (isset($_GET['start'])) {
start_recording();
}
if (isset($_GET['stop'])) {
stop_recording();
}
?>
<html>
<head>
<meta charset="utf-8">
<title>Telemetry Computer</title>
<link href="/assets/stylesheet.css" rel="stylesheet" type="text/css">
</head>
<body>
<h1>Telemetry Box OS v1.0.0</h1>
<h4>by Jake Johnson</h4>
<a href="?start=true">
<div class="button">Start Recording Data</div>
</a><br>
<a href="?stop=true">
<div class="button">Kill Recording</div>
</a><br>
<a href="/data">
<div class="button">View Data</div>
</a><br>
<a href="/manage">
<div class="button">Data Managment</div>
</a>
</body>
</html>
这是我的python:
#!/usr/bin/python
import serial
import MySQLdb
#establish connection to MySQL. You'll have to change this for your database.
dbConn = MySQLdb.connect(host="localhost", user="ayylmao", passwd="ayylmao", db="telemetry") or die ("could not connect to database")
#open a cursor to the database
device = '/dev/ttyACM0'
try:
print "Trying...",device
arduino = serial.Serial(device, 9600)
except:
print "Failed to connect on",device
while True:
cursor = dbConn.cursor()
try:
print("--------- Inserting Data ---------")
data = arduino.readline() #read the data from the arduino
pieces = data.split("\t") #split the data by the tab
#insert the data into the Database
try:
cursor.execute("INSERT INTO telemetryData (runTime,tempF,rpm,xforce,yforce,zforce) VALUES (%s,%s,%s,%s,%s,%s)", (pieces[0],pieces[1],pieces[2],pieces[3],pieces[4],pieces[5]))
dbConn.commit() #commit the insert
cursor.close() #close the cursor
except MySQLdb.IntegrityError:
print "failed to insert data"
finally:
cursor.close() #close just incase it failed
except:
print "Failed to get data from Arduino!"
答案 0 :(得分:0)
问题可能出在dev节点的访问权限上。 Web服务器在不同的用户ID下运行,权限非常有限,这是有充分理由的。此外,您不能只chmod 777 /dev/ttyACM0
,因为每次重新启动系统时都会重置(严重的是,不要这样做,因为设备节点上的exec位可能不安全)。相反,你需要写一个udev rule,这可能需要一些时间来弄清楚如何。
Linux有一个神奇的组件udev,可以将sysfs的设备节点(可以从内核访问)安装到devfs,用户空间文件系统可以/dev
访问}。即udev
将决定是否将设备挂载到devfs以及要分配的访问权限
为了做出这些决定,udev提供了一组规则(也称为udev规则),这些规则用/lib/udev/rules.d/
中的配置文件编写(可能因分发而异)。以下是影响Ubuntu上串行设备的规则列表:
/lib/udev/rules.d/50-udev-default.rules
/lib/udev/rules.d/60-persistent-serial.rules
/lib/udev/rules.d/77-mm-usb-serial-adapters-greylist.rules
规则按递增顺序处理,因此50
规则将具有优先权。您还可以在/etc/udev/rules.d/
下添加自定义规则,可能以90+以上的方式启动它将是一个好主意。
最后,答案是:创建一个名为(例如)/etc/udev/rules.d/90-my-serial-dev-accessfix
的文件。它应该包含这样的内容:
ACTION=="remove", GOTO="accessfix_end"
SUBSYSTEM=="tty", KERNEL=="ttyACM[0-9]*", GROUP="tty", MODE="0666"
LABEL="accessfix_end"
我现在无法对此进行测试,因此此配置中可能存在错误或两个错误。但是,绝对值得一读关于修复它的udev规则。