使用 python 将数据添加到 sqlite3,然后 php5 使用 python、php5、sqlite3 在 apache2 服务器上动态检索数据
Using python to add data to sqlite3, then php5 to retrieve data on apache2 server dynamically using python, php5, sqlite3
*更新
我正在尝试为我的儿子制作一个游戏,它有 2 个振动传感器代表 Balls 和 Strikes(用于棒球)。当传感器被击中时,我有一个循环,可以为击球或球添加一个滴答声。当传感器被击中时,我希望它也进入我的 sqlite 数据库。然后我有一个 php 文件,它读取 sqlite 数据库并实时显示球和击球。我正在使用 php5、sqlite3 和 apache2 服务器。我有服务器设置,python 脚本正确检测传感器并更新 2 个变量,balls 和 strikes。我似乎无法 link 将文件复制到 php 文件,所以当我导航到 basesloaded.php 时,它会执行 sensor.py。如果我 运行 py 脚本首先处于空闲状态,然后导航到 php 页面,它会正确更新 运行 来自 php 文件的 py 脚本。
#sensor.py file
#!/usr/bin/env python
import RPi.GPIO as GPIO
import time
import sqlite3
KnockPin = 12
ShockPin = 13
BtnPin = 15
inning = 1
runs = 0
strikes = 0
balls = 0
print ("Welcome to Bases Loaded!")
def setstr():
global strikes
strikes = 0
global balls
balls = 0
def setup():
GPIO.setmode(GPIO.BOARD)
GPIO.setup(KnockPin, GPIO.IN, pull_up_down=GPIO.PUD_UP)
GPIO.setup(ShockPin, GPIO.IN, pull_up_down=GPIO.PUD_UP)
GPIO.setup(BtnPin, GPIO.IN, pull_up_down=GPIO.PUD_UP)
def knock(ev=None):
with sqlite3.connect('basesLoaded.db') as conn;
global strikes
strikes += 1
if strikes ==0:
pass
elif strikes == 1:
conn.execute("UPDATE bl set STRIKE = 1 WHERE ID =1");
print ("Strike 1 :", conn.total_changes);
elif strikes == 2:
conn.execute("UPDATE bl set STRIKE = 2 WHERE ID=1");
print ("Strike 2 :", conn.total_changes);
elif strikes == 3:
conn.execute("UPDATE bl set STRIKE = 0 WHERE ID=1");
print ("Strike 3 Your Out :", conn.total_changes);
global inning
inning +=1
conn.execute("UPDATE bl set INNING = inning WHERE ID=1");
setstr()
print ("Inning Number :", inning);
def shock(ev=None):
with sqlite3.connect('basesLoaded.db') as conn;
print ("Opened database successfully");
global balls
balls += 1
if balls ==0:
pass
elif balls == 1:
conn.execute("UPDATE bl set BALL = 1 WHERE ID=1");
print ("Ball 1 :", conn.total_changes);
elif balls == 2:
conn.execute("UPDATE bl set BALL = 2 WHERE ID=1");
print ("Ball 2 :", conn.total_changes);
elif balls == 3:
conn.execute("UPDATE bl set BALL = 3 WHERE ID=1");
print ("Ball 3 :", conn.total_changes);
elif balls == 4:
global runs
runs += 1
conn.execute("UPDATE bl set BALL = 0 WHERE ID=1");
conn.execute("UPDATE bl set RUN = 'runs' WHERE ID=1");
print ("Run Scored! score is :", runs);
setstr()
def loop():
GPIO.add_event_detect(ShockPin, GPIO.FALLING, callback=shock, bouncetime=2500)
GPIO.add_event_detect(KnockPin, GPIO.FALLING, callback=knock, bouncetime=2500)
if __name__ == '__main__': # Program start from here
setup()
try:
loop()
except KeyboardInterrupt:
destroy()
这是我的 php 检索 sqlite 数据的脚本 -
#basesLoaded.php file
<?php
$try = exec('python sensor.py');
print_r ($try);
$db = new SQLite3('basesLoaded.db');
echo '<br>';
echo '<br>';
$strikes = ($db->querySingle('SELECT STRIKE FROM bl WHERE ID = 1'));
$balls = ($db->querySingle('SELECT BALL FROM bl WHERE ID = 1'));
$outs = ($db->querySingle('SELECT OUT FROM bl WHERE ID = 1'));
$runs = ($db->querySingle('SELECT RUN FROM bl WHERE ID = 1'));
$inning = ($db->querySingle('SELECT INNING FROM bl WHERE ID = 1'));
echo 'Strikes: ' . $strikes . '<br>';
echo 'Balls: ' . $balls . '<br>';
echo 'Outs: ' . $outs . '<br>';
echo 'Runs: ' . $runs . '<br>';
echo 'Inning: ' . $inning . '<br>';
?>
正如@Parfait 在评论中提到的,您需要提交更新以使其持久化。您的 PHP 代码没有看到更新,因为它们没有提交。
您可以在代码中调用 conn.commit()
,但是,保证更新已提交(或在出现错误时回滚)的简单方法是使用 [=18= 打开数据库],即使用 with
语句,例如:
def knock(ev=None):
with sqlite3.connect('basesLoaded.db') as conn:
conn.execute("UPDATE bl set STRIKE = 1 WHERE ID =1")
现在您的更新将在 with
语句终止时自动提交,在本例中为函数 knock()
returns 时,或者如果发生异常则回滚。
更新
如评论中所述,事件处理似乎存在问题。我怀疑您的代码需要显式保留 运行ning 否则,一旦主线程终止,整个程序将终止。你可以这样做:
WAIT_PIN = 14
def register_callbacks():
GPIO.add_event_detect(ShockPin, GPIO.FALLING, callback=shock, bouncetime=2500)
GPIO.add_event_detect(KnockPin, GPIO.FALLING, callback=knock, bouncetime=2500)
def wait():
GPIO.wait_for_edge(WAIT_PIN, GPIO.BOTH) # wait for level change
# # Or wait in a while loop
# while True:
# time.sleep(0.1)
# # Or wait for keyboard input
# input('Press <ENTER> to quit: ')
if __name__ == '__main__':
try:
setup()
register_callbacks()
wait() # block the main thread
except KeyboardInterrupt:
destroy()
您需要一直使用此 Python 脚本 运行ning。它独立于 PHP 脚本,后者 运行 仅用于响应通过您的网络服务器的 HTTP 请求。您可以 运行 Python 脚本作为后台进程:
$ python sensor.py &
此外,从您的 PHP 脚本中删除 exec()
调用。
*更新 我正在尝试为我的儿子制作一个游戏,它有 2 个振动传感器代表 Balls 和 Strikes(用于棒球)。当传感器被击中时,我有一个循环,可以为击球或球添加一个滴答声。当传感器被击中时,我希望它也进入我的 sqlite 数据库。然后我有一个 php 文件,它读取 sqlite 数据库并实时显示球和击球。我正在使用 php5、sqlite3 和 apache2 服务器。我有服务器设置,python 脚本正确检测传感器并更新 2 个变量,balls 和 strikes。我似乎无法 link 将文件复制到 php 文件,所以当我导航到 basesloaded.php 时,它会执行 sensor.py。如果我 运行 py 脚本首先处于空闲状态,然后导航到 php 页面,它会正确更新 运行 来自 php 文件的 py 脚本。
#sensor.py file
#!/usr/bin/env python
import RPi.GPIO as GPIO
import time
import sqlite3
KnockPin = 12
ShockPin = 13
BtnPin = 15
inning = 1
runs = 0
strikes = 0
balls = 0
print ("Welcome to Bases Loaded!")
def setstr():
global strikes
strikes = 0
global balls
balls = 0
def setup():
GPIO.setmode(GPIO.BOARD)
GPIO.setup(KnockPin, GPIO.IN, pull_up_down=GPIO.PUD_UP)
GPIO.setup(ShockPin, GPIO.IN, pull_up_down=GPIO.PUD_UP)
GPIO.setup(BtnPin, GPIO.IN, pull_up_down=GPIO.PUD_UP)
def knock(ev=None):
with sqlite3.connect('basesLoaded.db') as conn;
global strikes
strikes += 1
if strikes ==0:
pass
elif strikes == 1:
conn.execute("UPDATE bl set STRIKE = 1 WHERE ID =1");
print ("Strike 1 :", conn.total_changes);
elif strikes == 2:
conn.execute("UPDATE bl set STRIKE = 2 WHERE ID=1");
print ("Strike 2 :", conn.total_changes);
elif strikes == 3:
conn.execute("UPDATE bl set STRIKE = 0 WHERE ID=1");
print ("Strike 3 Your Out :", conn.total_changes);
global inning
inning +=1
conn.execute("UPDATE bl set INNING = inning WHERE ID=1");
setstr()
print ("Inning Number :", inning);
def shock(ev=None):
with sqlite3.connect('basesLoaded.db') as conn;
print ("Opened database successfully");
global balls
balls += 1
if balls ==0:
pass
elif balls == 1:
conn.execute("UPDATE bl set BALL = 1 WHERE ID=1");
print ("Ball 1 :", conn.total_changes);
elif balls == 2:
conn.execute("UPDATE bl set BALL = 2 WHERE ID=1");
print ("Ball 2 :", conn.total_changes);
elif balls == 3:
conn.execute("UPDATE bl set BALL = 3 WHERE ID=1");
print ("Ball 3 :", conn.total_changes);
elif balls == 4:
global runs
runs += 1
conn.execute("UPDATE bl set BALL = 0 WHERE ID=1");
conn.execute("UPDATE bl set RUN = 'runs' WHERE ID=1");
print ("Run Scored! score is :", runs);
setstr()
def loop():
GPIO.add_event_detect(ShockPin, GPIO.FALLING, callback=shock, bouncetime=2500)
GPIO.add_event_detect(KnockPin, GPIO.FALLING, callback=knock, bouncetime=2500)
if __name__ == '__main__': # Program start from here
setup()
try:
loop()
except KeyboardInterrupt:
destroy()
这是我的 php 检索 sqlite 数据的脚本 -
#basesLoaded.php file
<?php
$try = exec('python sensor.py');
print_r ($try);
$db = new SQLite3('basesLoaded.db');
echo '<br>';
echo '<br>';
$strikes = ($db->querySingle('SELECT STRIKE FROM bl WHERE ID = 1'));
$balls = ($db->querySingle('SELECT BALL FROM bl WHERE ID = 1'));
$outs = ($db->querySingle('SELECT OUT FROM bl WHERE ID = 1'));
$runs = ($db->querySingle('SELECT RUN FROM bl WHERE ID = 1'));
$inning = ($db->querySingle('SELECT INNING FROM bl WHERE ID = 1'));
echo 'Strikes: ' . $strikes . '<br>';
echo 'Balls: ' . $balls . '<br>';
echo 'Outs: ' . $outs . '<br>';
echo 'Runs: ' . $runs . '<br>';
echo 'Inning: ' . $inning . '<br>';
?>
正如@Parfait 在评论中提到的,您需要提交更新以使其持久化。您的 PHP 代码没有看到更新,因为它们没有提交。
您可以在代码中调用 conn.commit()
,但是,保证更新已提交(或在出现错误时回滚)的简单方法是使用 [=18= 打开数据库],即使用 with
语句,例如:
def knock(ev=None):
with sqlite3.connect('basesLoaded.db') as conn:
conn.execute("UPDATE bl set STRIKE = 1 WHERE ID =1")
现在您的更新将在 with
语句终止时自动提交,在本例中为函数 knock()
returns 时,或者如果发生异常则回滚。
更新
如评论中所述,事件处理似乎存在问题。我怀疑您的代码需要显式保留 运行ning 否则,一旦主线程终止,整个程序将终止。你可以这样做:
WAIT_PIN = 14
def register_callbacks():
GPIO.add_event_detect(ShockPin, GPIO.FALLING, callback=shock, bouncetime=2500)
GPIO.add_event_detect(KnockPin, GPIO.FALLING, callback=knock, bouncetime=2500)
def wait():
GPIO.wait_for_edge(WAIT_PIN, GPIO.BOTH) # wait for level change
# # Or wait in a while loop
# while True:
# time.sleep(0.1)
# # Or wait for keyboard input
# input('Press <ENTER> to quit: ')
if __name__ == '__main__':
try:
setup()
register_callbacks()
wait() # block the main thread
except KeyboardInterrupt:
destroy()
您需要一直使用此 Python 脚本 运行ning。它独立于 PHP 脚本,后者 运行 仅用于响应通过您的网络服务器的 HTTP 请求。您可以 运行 Python 脚本作为后台进程:
$ python sensor.py &
此外,从您的 PHP 脚本中删除 exec()
调用。