You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

树莓派BLE传感器数据发送端极简Python实现及命名设置疑问

极简树莓派BLE外设实现(定时推送传感器数据)

核心脚本说明

你之前用Peripheral.writeCharacteristic的思路是错的——Peripheral在bluepy里是中心设备(主动连接其他BLE设备)的类,而你需要做的是BLE外设(被客户端连接的GATT服务器),下面是极简实现脚本:

1. 先安装依赖

sudo pip3 install bluepy

2. 完整Python脚本

from bluepy.btle import Advertisement, Service, Characteristic, UUID, Peripheral, BTLEException
import time
import threading

# 自定义广播类,设置设备名称和服务UUID
class MyAdvertisement(Advertisement):
    def __init__(self):
        Advertisement.__init__(self, 0, 0)
        self.setName("RPi-Sensor")  # 设置BLE显示名称
        self.addServiceUUID(UUID("FFE0"))  # 绑定服务UUID,方便客户端识别

# 自定义GATT服务
class MyService(Service):
    SERVICE_UUID = UUID("FFE0")
    def __init__(self, periph):
        Service.__init__(self, periph, self.SERVICE_UUID)
        self.addCharacteristic(MyCharacteristic(self))

# 自定义特征(支持通知,客户端订阅后可主动推送数据)
class MyCharacteristic(Characteristic):
    CHAR_UUID = UUID("FFE1")
    def __init__(self, service):
        # 开启通知权限
        Characteristic.__init__(self, service, self.CHAR_UUID, Characteristic.PROP_NOTIFY)
        # 添加描述符,客户端需订阅此描述符才能接收通知
        self.client_config = self.addDescriptor(Characteristic.ClientCharacteristicConfiguration())
        self.addDescriptor(Characteristic.UserDescriptionDescriptor("Sensor Data"))

# 定时推送数据线程
def push_sensor_data(characteristic, interval=5):
    sensor_counter = 0
    while True:
        # 检查是否有客户端订阅了通知
        if characteristic.client_config.getValue() == b"\x01\x00":
            # 替换这里的代码获取真实传感器数据
            sensor_data = f"Temp:25.6,Hum:42,Count:{sensor_counter}".encode("utf-8")
            characteristic.notify(sensor_data)
            print(f"已推送数据: {sensor_data.decode()}")
            sensor_counter += 1
        time.sleep(interval)

if __name__ == "__main__":
    try:
        periph = Peripheral()
        periph.addService(MyService(periph))
        periph.addAdvertisement(MyAdvertisement())
        periph.startAdvertising()
        print("BLE外设启动完成,设备名:RPi-Sensor,等待客户端连接...")

        # 获取特征对象,启动推送线程
        target_char = periph.getServiceByUUID(MyService.SERVICE_UUID).getCharacteristics(MyCharacteristic.CHAR_UUID)[0]
        threading.Thread(target=push_sensor_data, args=(target_char, 5), daemon=True).start()

        # 保持程序运行
        while True:
            time.sleep(1)

    except BTLEException as e:
        print(f"BLE运行错误: {str(e)}")
    finally:
        periph.stopAdvertising()
        periph.disconnect()

3. 运行说明

  • 必须用root权限运行:sudo python3 ble_server.py
  • 脚本逻辑:
    1. 启动BLE广播,对外显示名称RPi-Sensor
    2. 等待Flutter客户端(BLE中心设备)连接并订阅特征
    3. 每隔5秒向已订阅的客户端推送传感器数据(可修改interval参数调整间隔)

解决BLE名称显示N/A的问题

临时设置(仅当前会话有效)

脚本里的self.setName("RPi-Sensor")已经能设置广播名称,若要单独测试,可通过bluetoothctl命令临时修改:

sudo bluetoothctl
# 进入交互模式后输入:
system-alias RPi-Sensor
exit

永久设置(重启后生效)

  1. 编辑蓝牙配置文件:
sudo nano /etc/bluetooth/main.conf
  1. 找到#Name = BlueZ一行,去掉注释并修改为:
Name = RPi-Sensor
  1. 重启蓝牙服务:
sudo systemctl restart bluetooth

注意事项

  • 确保树莓派蓝牙已开启:sudo bluetoothctl power on
  • 若扫描不到设备,尝试重置蓝牙:sudo bluetoothctl power off && sudo bluetoothctl power on
  • 若bluepy版本过旧,更新至最新版:sudo pip3 install --upgrade bluepy

内容的提问来源于stack exchange,提问作者Mike_NotGuilty

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.25 12:32:41