Skip to content

Commit ff05feb

Browse files
committed
Update to use new bleio API
1 parent 89e8cdb commit ff05feb

File tree

5 files changed

+103
-102
lines changed

5 files changed

+103
-102
lines changed

adafruit_ble/beacon.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ def __init__(self, advertising_packet):
4141
4242
:param AdvertisingPacket advertising_packet
4343
"""
44-
self._broadcaster = bleio.Peripheral(name=None)
44+
self._broadcaster = bleio.Peripheral()
4545
self._advertising_packet = advertising_packet
4646

4747
def start(self, interval=1.0):

adafruit_ble/current_time_client.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,7 @@ class CurrentTimeClient:
6666
LOCAL_TIME_INFORMATION_UUID = UUID(0x2A0F)
6767

6868
def __init__(self, name=None, tx_power=0):
69-
self._periph = Peripheral(name=name)
69+
self._periph = Peripheral(name)
7070
self._advertisement = SolicitationAdvertisement(self._periph.name,
7171
(self.CTS_UUID,), tx_power=tx_power)
7272
self._current_time_char = self._local_time_char = None

adafruit_ble/device_information_service.py

Lines changed: 54 additions & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -28,65 +28,69 @@
2828
* Author(s): Dan Halbert for Adafruit Industries
2929
3030
"""
31-
from bleio import Attribute, Characteristic, Service, UUID
31+
from bleio import Attribute, Characteristic, UUID
3232

33-
# pylint: disable=invalid-name
34-
def DeviceInformationService(*, model_number=None, serial_number=None, firmware_revision=None,
35-
hardware_revision='', software_revision='', manufacturer=''):
36-
"""
37-
Set up a Service with fixed Device Information Service charcteristics.
38-
All values are optional.
33+
class DeviceInformationService:
34+
"""This is a factory class only, and has no instances."""
3935

40-
Note that this is a pseudo class: It returns a Service, but is not a subclass of Service,
41-
because Service is a native class and doesn't handle subclassing.
36+
@staticmethod
37+
def add_to_peripheral(peripheral, *, model_number=None, serial_number=None,
38+
firmware_revision=None, hardware_revision='',
39+
software_revision='', manufacturer=''):
40+
"""
41+
Add a Service with fixed Device Information Service characteristics to the given Peripheral.
42+
All values are optional.
4243
43-
:param str model_number: Device model number. If None use `sys.platform`.
44-
:param str serial_number: Device serial number. If None use a hex representation of
45-
``microcontroller.cpu.id``.
46-
:param str firmware_revision: Device firmware revision. If None use ``os.uname().version``.
47-
:param str hardware_revision: Device hardware revision.
48-
:param str software_revision: Device software revision.
49-
:param str manufacturer: Device manufacturer name
44+
:param str model_number: Device model number. If None use `sys.platform`.
45+
:param str serial_number: Device serial number. If None use a hex representation of
46+
``microcontroller.cpu.id``.
47+
:param str firmware_revision: Device firmware revision.
48+
If None use ``os.uname().version``.
49+
:param str hardware_revision: Device hardware revision.
50+
:param str software_revision: Device software revision.
51+
:param str manufacturer: Device manufacturer name
52+
:return: the created Service
5053
51-
Example::
54+
Example::
5255
53-
dis = DeviceInformationService(software_revision="1.2.4", manufacturer="Acme Corp")
54-
"""
56+
peripheral = Peripheral()
57+
dis = DeviceInformationService.add_to_peripheral(
58+
peripheral, software_revision="1.2.4", manufacturer="Acme Corp")
59+
"""
5560

56-
# Avoid creating constants with names if not necessary. Just takes up space.
57-
# Device Information Service UUID = 0x180A
58-
# Module Number UUID = 0x2A24
59-
# Serial Number UUID = 0x2A25
60-
# Firmware Revision UUID = 0x2A26
61-
# Hardware Revision UUID = 0x2A27
62-
# Software Revision UUID = 0x2A28
63-
# Manufacturer Name UUID = 0x2A29
61+
# Avoid creating constants with names if not necessary. Just takes up space.
62+
# Device Information Service UUID = 0x180A
63+
# Module Number UUID = 0x2A24
64+
# Serial Number UUID = 0x2A25
65+
# Firmware Revision UUID = 0x2A26
66+
# Hardware Revision UUID = 0x2A27
67+
# Software Revision UUID = 0x2A28
68+
# Manufacturer Name UUID = 0x2A29
6469

65-
characteristics = []
66-
# Values must correspond to UUID numbers.
70+
service = peripheral.add_service(UUID(0x180A))
6771

68-
if model_number is None:
69-
import sys
70-
model_number = sys.platform
71-
if serial_number is None:
72-
import microcontroller
73-
import binascii
74-
serial_number = binascii.hexlify(microcontroller.cpu.uid).decode('utf-8') # pylint: disable=no-member
72+
if model_number is None:
73+
import sys
74+
model_number = sys.platform
75+
if serial_number is None:
76+
import microcontroller
77+
import binascii
78+
serial_number = binascii.hexlify(microcontroller.cpu.uid).decode('utf-8') # pylint: disable=no-member
7579

76-
if firmware_revision is None:
77-
import os
78-
firmware_revision = os.uname().version
80+
if firmware_revision is None:
81+
import os
82+
firmware_revision = os.uname().version
7983

80-
for uuid_num, string in zip(
81-
range(0x2A24, 0x2A29+1),
82-
(model_number, serial_number,
83-
firmware_revision, hardware_revision, software_revision,
84-
manufacturer)):
84+
# Values must correspond to UUID numbers.
85+
for uuid_num, value in zip(
86+
range(0x2A24, 0x2A29+1),
87+
(model_number, serial_number,
88+
firmware_revision, hardware_revision, software_revision,
89+
manufacturer)):
8590

86-
char = Characteristic(UUID(uuid_num), properties=Characteristic.READ,
87-
read_perm=Attribute.OPEN, write_perm=Attribute.NO_ACCESS,
88-
fixed_length=True, max_length=len(string))
89-
char.value = string
90-
characteristics.append(char)
91+
service.add_characteristic(UUID(uuid_num), properties=Characteristic.READ,
92+
read_perm=Attribute.OPEN, write_perm=Attribute.NO_ACCESS,
93+
fixed_length=True, max_length=len(value),
94+
initial_value=value)
9195

92-
return Service(UUID(0x180A), characteristics)
96+
return service

adafruit_ble/hid_server.py

Lines changed: 39 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@
3535
# for __version__
3636
import adafruit_ble
3737

38-
from bleio import Attribute, Characteristic, Descriptor, Peripheral, Service, UUID
38+
from bleio import Attribute, Characteristic, Peripheral, UUID
3939
from .advertising import ServerAdvertisement
4040
from .device_information_service import DeviceInformationService
4141

@@ -208,89 +208,83 @@ class HIDServer:
208208
}
209209

210210
def __init__(self, name=None, tx_power=0):
211+
self._periph = Peripheral(name)
212+
213+
# iOS requires Device Information Service. Android does not.
214+
DeviceInformationService.add_to_peripheral(
215+
self._periph, software_revision=adafruit_ble.__version__,
216+
manufacturer="Adafruit Industries")
217+
218+
service = self._periph.add_service(UUID(_HID_SERVICE_UUID_NUM))
219+
211220
self._input_chars = {}
212221
for report_id in sorted(self._INPUT_REPORT_SIZES.keys()):
213-
desc = Descriptor(self._REPORT_REF_DESCR_UUID,
214-
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.NO_ACCESS)
215-
desc.value = struct.pack('<BB', report_id, _REPORT_TYPE_INPUT)
216-
report_size = self._INPUT_REPORT_SIZES[report_id]
217-
self._input_chars[report_id] = Characteristic(
222+
input_char = service.add_characteristic(
218223
self._REPORT_UUID, properties=Characteristic.READ | Characteristic.NOTIFY,
219224
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.NO_ACCESS,
220-
max_length=report_size, fixed_length=True,
221-
descriptors=(desc,))
222-
self._input_chars[report_id].value = bytes(report_size)
225+
max_length=self._INPUT_REPORT_SIZES[report_id], fixed_length=True)
226+
input_char.add_descriptor(
227+
self._REPORT_REF_DESCR_UUID,
228+
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.NO_ACCESS,
229+
initial_value=struct.pack('<BB', report_id, _REPORT_TYPE_INPUT))
230+
self._input_chars[report_id] = input_char
223231

224232
self._output_chars = {}
225233
for report_id in sorted(self._OUTPUT_REPORT_SIZES.keys()):
226-
desc = Descriptor(self._REPORT_REF_DESCR_UUID,
227-
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.NO_ACCESS)
228-
desc.value = struct.pack('<BB', report_id, _REPORT_TYPE_OUTPUT)
229-
report_size = self._OUTPUT_REPORT_SIZES[report_id]
230-
self._output_chars[report_id] = Characteristic(
234+
output_char = service.add_characteristic(
231235
self._REPORT_UUID,
232236
properties=(Characteristic.READ | Characteristic.WRITE |
233237
Characteristic.WRITE_NO_RESPONSE),
234238
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.ENCRYPT_NO_MITM,
235-
max_length=report_size, fixed_length=True,
236-
descriptors=(desc,))
237-
self._output_chars[report_id].value = bytes(report_size)
239+
max_length=self._OUTPUT_REPORT_SIZES[report_id], fixed_length=True)
240+
output_char.add_descriptor(
241+
self._REPORT_REF_DESCR_UUID,
242+
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.NO_ACCESS,
243+
initial_value=struct.pack('<BB', report_id, _REPORT_TYPE_OUTPUT))
244+
self._output_chars[report_id] = output_char
238245

239246
# Protocol mode: boot or report. Make it read-only for now because
240247
# it can't be changed
241248

242-
protocol_mode_char = Characteristic(
243-
UUID(_PROTOCOL_MODE_UUID_NUM), properties=Characteristic.READ | Characteristic.WRITE_NO_RESPONSE,
249+
service.add_characteristic(
250+
UUID(_PROTOCOL_MODE_UUID_NUM),
251+
properties=Characteristic.READ | Characteristic.WRITE_NO_RESPONSE,
244252
read_perm=Attribute.OPEN, write_perm=Attribute.OPEN,
245-
max_length=1, fixed_length=True)
246-
protocol_mode_char.value = _PROTOCOL_MODE_REPORT
253+
max_length=1, fixed_length=True,
254+
initial_value=_PROTOCOL_MODE_REPORT)
247255

248-
boot_keyboard_input_report = Characteristic(
256+
service.add_characteristic(
249257
UUID(_BOOT_KEYBOARD_INPUT_REPORT_UUID_NUM),
250258
properties=Characteristic.READ | Characteristic.NOTIFY,
251259
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.NO_ACCESS,
252260
max_length=self._INPUT_REPORT_SIZES[self.REPORT_ID_KEYBOARD], fixed_length=True)
253261

254-
boot_keyboard_output_report = Characteristic(
262+
service.add_characteristic(
255263
UUID(_BOOT_KEYBOARD_OUTPUT_REPORT_UUID_NUM),
256264
properties=(Characteristic.READ | Characteristic.WRITE |
257265
Characteristic.WRITE_NO_RESPONSE),
258266
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.ENCRYPT_NO_MITM,
259267
max_length=self._OUTPUT_REPORT_SIZES[self.REPORT_ID_KEYBOARD], fixed_length=True)
260268

261269
# This is the USB HID descriptor (not to be confused with a BLE Descriptor).
262-
report_map_char = Characteristic(
270+
service.add_characteristic(
263271
UUID(_REPORT_MAP_UUID_NUM), properties=Characteristic.READ,
264272
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.NO_ACCESS,
265-
max_length=len(self.HID_DESCRIPTOR), fixed_length=True)
266-
report_map_char.value = self.HID_DESCRIPTOR
273+
max_length=len(self.HID_DESCRIPTOR), fixed_length=True,
274+
initial_value=self.HID_DESCRIPTOR)
267275

268276
# bcdHID (version), bCountryCode (0 not localized), Flags: RemoteWake, NormallyConnectable
269-
hid_information_char = Characteristic(
270-
UUID(_HID_INFORMATION_UUID_NUM), properties=Characteristic.READ,
271-
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.NO_ACCESS)
272277
# bcd1.1, country = 0, flag = normal connect
273-
hid_information_char.value = b'\x01\x01\x00\x02'
278+
service.add_characteristic(
279+
UUID(_HID_INFORMATION_UUID_NUM), properties=Characteristic.READ,
280+
read_perm=Attribute.ENCRYPT_NO_MITM, write_perm=Attribute.NO_ACCESS,
281+
initial_value=b'\x01\x01\x00\x02')
274282

275283
# 0 = suspend; 1 = exit suspend
276-
self._hid_control_point_char = Characteristic(
284+
service.add_characteristic(
277285
UUID(_HID_CONTROL_POINT_UUID_NUM), properties=Characteristic.WRITE_NO_RESPONSE,
278286
read_perm=Attribute.NO_ACCESS, write_perm=Attribute.ENCRYPT_NO_MITM)
279287

280-
# iOS requires Device Information Service. Android does not.
281-
dis = DeviceInformationService(software_revision=adafruit_ble.__version__,
282-
manufacturer="Adafruit Industries")
283-
hid_service = Service(UUID(_HID_SERVICE_UUID_NUM),
284-
tuple(self._input_chars.values()) +
285-
tuple(self._output_chars.values()) +
286-
(boot_keyboard_input_report,
287-
boot_keyboard_output_report,
288-
protocol_mode_char,
289-
report_map_char,
290-
hid_information_char,
291-
self._hid_control_point_char,
292-
))
293-
self._periph = Peripheral((dis, hid_service), name=name)
294288
self._advertisement = ServerAdvertisement(self._periph, tx_power=tx_power,
295289
appearance=_APPEARANCE_HID_KEYBOARD)
296290

adafruit_ble/uart_server.py

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@
2828
* Author(s): Dan Halbert for Adafruit Industries
2929
3030
"""
31-
from bleio import Attribute, Characteristic, CharacteristicBuffer, Peripheral, Service
31+
from bleio import Attribute, Characteristic, CharacteristicBuffer, Peripheral
3232
from .advertising import ServerAdvertisement
3333
from .uart import NUS_SERVICE_UUID, NUS_RX_CHAR_UUID, NUS_TX_CHAR_UUID
3434

@@ -56,20 +56,23 @@ class UARTServer:
5656
"""
5757

5858
def __init__(self, *, timeout=1.0, buffer_size=64, name=None):
59-
self._read_char = Characteristic(
59+
self._periph = Peripheral(name)
60+
service = self._periph.add_service(NUS_SERVICE_UUID)
61+
62+
self._read_char = service.add_characteristic(
6063
NUS_RX_CHAR_UUID,
6164
properties=Characteristic.WRITE | Characteristic.WRITE_NO_RESPONSE,
6265
read_perm=Attribute.NO_ACCESS, write_perm=Attribute.OPEN)
63-
self._write_char = Characteristic(
66+
67+
self._write_char = service.add_characteristic(
6468
NUS_TX_CHAR_UUID,
6569
properties=Characteristic.NOTIFY,
6670
read_perm=Attribute.OPEN, write_perm=Attribute.NO_ACCESS)
71+
6772
self._read_buffer = CharacteristicBuffer(self._read_char,
6873
timeout=timeout, buffer_size=buffer_size)
6974

70-
nus_uart_service = Service(NUS_SERVICE_UUID, (self._read_char, self._write_char))
7175

72-
self._periph = Peripheral((nus_uart_service,), name=name)
7376
self._advertisement = ServerAdvertisement(self._periph)
7477

7578
def start_advertising(self):

0 commit comments

Comments
 (0)