mirror of
https://github.com/servo/servo.git
synced 2025-08-05 21:50:18 +01:00
refactor Connect/Disconnect calls
This commit is contained in:
parent
6efea399ed
commit
6e02cb2eb9
24 changed files with 649 additions and 33 deletions
|
@ -106,6 +106,10 @@ impl Bluetooth {
|
|||
self.global().as_window().bluetooth_thread()
|
||||
}
|
||||
|
||||
pub fn get_device_map(&self) -> &DOMRefCell<HashMap<String, MutJS<BluetoothDevice>>> {
|
||||
&self.device_instance_map
|
||||
}
|
||||
|
||||
// https://webbluetoothcg.github.io/web-bluetooth/#request-bluetooth-devices
|
||||
fn request_bluetooth_devices(&self,
|
||||
p: &Rc<Promise>,
|
||||
|
|
|
@ -10,6 +10,8 @@ use dom::bindings::codegen::Bindings::BluetoothDeviceBinding::BluetoothDeviceMet
|
|||
use dom::bindings::codegen::Bindings::BluetoothRemoteGATTServerBinding::BluetoothRemoteGATTServerMethods;
|
||||
use dom::bindings::codegen::Bindings::EventHandlerBinding::EventHandlerNonNull;
|
||||
use dom::bindings::error::Error;
|
||||
use dom::bindings::error::ErrorResult;
|
||||
use dom::bindings::inheritance::Castable;
|
||||
use dom::bindings::js::{MutJS, MutNullableJS, Root};
|
||||
use dom::bindings::reflector::{DomObject, reflect_dom_object};
|
||||
use dom::bindings::str::DOMString;
|
||||
|
@ -22,7 +24,7 @@ use dom::bluetoothremotegattservice::BluetoothRemoteGATTService;
|
|||
use dom::eventtarget::EventTarget;
|
||||
use dom::globalscope::GlobalScope;
|
||||
use dom::promise::Promise;
|
||||
use ipc_channel::ipc::IpcSender;
|
||||
use ipc_channel::ipc::{self, IpcSender};
|
||||
use js::jsapi::JSContext;
|
||||
use std::cell::Cell;
|
||||
use std::collections::HashMap;
|
||||
|
@ -72,6 +74,10 @@ impl BluetoothDevice {
|
|||
BluetoothDeviceBinding::Wrap)
|
||||
}
|
||||
|
||||
fn get_context(&self) -> Root<Bluetooth> {
|
||||
self.context.get()
|
||||
}
|
||||
|
||||
pub fn get_or_create_service(&self,
|
||||
service: &BluetoothServiceMsg,
|
||||
server: &BluetoothRemoteGATTServer)
|
||||
|
@ -119,6 +125,13 @@ impl BluetoothDevice {
|
|||
return bt_characteristic;
|
||||
}
|
||||
|
||||
pub fn is_represented_device_null(&self) -> bool {
|
||||
let (sender, receiver) = ipc::channel().unwrap();
|
||||
self.get_bluetooth_thread().send(
|
||||
BluetoothRequest::IsRepresentedDeviceNull(self.Id().to_string(), sender)).unwrap();
|
||||
receiver.recv().unwrap()
|
||||
}
|
||||
|
||||
pub fn get_or_create_descriptor(&self,
|
||||
descriptor: &BluetoothDescriptorMsg,
|
||||
characteristic: &BluetoothRemoteGATTCharacteristic)
|
||||
|
@ -139,6 +152,60 @@ impl BluetoothDevice {
|
|||
fn get_bluetooth_thread(&self) -> IpcSender<BluetoothRequest> {
|
||||
self.global().as_window().bluetooth_thread()
|
||||
}
|
||||
|
||||
// https://webbluetoothcg.github.io/web-bluetooth/#clean-up-the-disconnected-device
|
||||
#[allow(unrooted_must_root)]
|
||||
pub fn clean_up_disconnected_device(&self) {
|
||||
// Step 1.
|
||||
self.Gatt().set_connected(false);
|
||||
|
||||
// TODO: Step 2: Implement activeAlgorithms internal slot for BluetoothRemoteGATTServer.
|
||||
|
||||
// Step 3: We don't need `context`, we get the attributeInstanceMap from the device.
|
||||
// https://github.com/WebBluetoothCG/web-bluetooth/issues/330
|
||||
|
||||
// Step 4.
|
||||
let mut service_map = self.attribute_instance_map.0.borrow_mut();
|
||||
let service_ids = service_map.drain().map(|(id, _)| id).collect();
|
||||
|
||||
let mut characteristic_map = self.attribute_instance_map.1.borrow_mut();
|
||||
let characteristic_ids = characteristic_map.drain().map(|(id, _)| id).collect();
|
||||
|
||||
let mut descriptor_map = self.attribute_instance_map.2.borrow_mut();
|
||||
let descriptor_ids = descriptor_map.drain().map(|(id, _)| id).collect();
|
||||
|
||||
// Step 5, 6.4, 7.
|
||||
// TODO: Step 6: Implement `active notification context set` for BluetoothRemoteGATTCharacteristic.
|
||||
let _ = self.get_bluetooth_thread().send(
|
||||
BluetoothRequest::SetRepresentedToNull(service_ids, characteristic_ids, descriptor_ids));
|
||||
|
||||
// Step 8.
|
||||
self.upcast::<EventTarget>().fire_bubbling_event(atom!("gattserverdisconnected"));
|
||||
}
|
||||
|
||||
// https://webbluetoothcg.github.io/web-bluetooth/#garbage-collect-the-connection
|
||||
#[allow(unrooted_must_root)]
|
||||
pub fn garbage_collect_the_connection(&self) -> ErrorResult {
|
||||
// Step 1: TODO: Check if other systems using this device.
|
||||
|
||||
// Step 2.
|
||||
let context = self.get_context();
|
||||
for (id, device) in context.get_device_map().borrow().iter() {
|
||||
// Step 2.1 - 2.2.
|
||||
if id == &self.Id().to_string() {
|
||||
if device.get().Gatt().Connected() {
|
||||
return Ok(());
|
||||
}
|
||||
// TODO: Step 2.3: Implement activeAlgorithms internal slot for BluetoothRemoteGATTServer.
|
||||
}
|
||||
}
|
||||
|
||||
// Step 3.
|
||||
let (sender, receiver) = ipc::channel().unwrap();
|
||||
self.get_bluetooth_thread().send(
|
||||
BluetoothRequest::GATTServerDisconnect(String::from(self.Id()), sender)).unwrap();
|
||||
receiver.recv().unwrap().map_err(Error::from)
|
||||
}
|
||||
}
|
||||
|
||||
impl BluetoothDeviceMethods for BluetoothDevice {
|
||||
|
|
|
@ -15,7 +15,7 @@ use dom::bluetoothdevice::BluetoothDevice;
|
|||
use dom::bluetoothuuid::{BluetoothServiceUUID, BluetoothUUID};
|
||||
use dom::globalscope::GlobalScope;
|
||||
use dom::promise::Promise;
|
||||
use ipc_channel::ipc::{self, IpcSender};
|
||||
use ipc_channel::ipc::IpcSender;
|
||||
use js::jsapi::JSContext;
|
||||
use std::cell::Cell;
|
||||
use std::rc::Rc;
|
||||
|
@ -46,6 +46,10 @@ impl BluetoothRemoteGATTServer {
|
|||
fn get_bluetooth_thread(&self) -> IpcSender<BluetoothRequest> {
|
||||
self.global().as_window().bluetooth_thread()
|
||||
}
|
||||
|
||||
pub fn set_connected(&self, connected: bool) {
|
||||
self.connected.set(connected);
|
||||
}
|
||||
}
|
||||
|
||||
impl BluetoothRemoteGATTServerMethods for BluetoothRemoteGATTServer {
|
||||
|
@ -86,27 +90,14 @@ impl BluetoothRemoteGATTServerMethods for BluetoothRemoteGATTServer {
|
|||
|
||||
// Step 2.
|
||||
if !self.Connected() {
|
||||
return Ok(());
|
||||
return Ok(())
|
||||
}
|
||||
let (sender, receiver) = ipc::channel().unwrap();
|
||||
self.get_bluetooth_thread().send(
|
||||
BluetoothRequest::GATTServerDisconnect(String::from(self.Device().Id()), sender)).unwrap();
|
||||
let server = receiver.recv().unwrap();
|
||||
|
||||
// TODO: Step 3: Implement the `clean up the disconnected device` algorithm.
|
||||
// Step 3.
|
||||
self.Device().clean_up_disconnected_device();
|
||||
|
||||
// TODO: Step 4: Implement representedDevice internal slot for BluetoothDevice.
|
||||
|
||||
// TODO: Step 5: Implement the `garbage-collect the connection` algorithm.
|
||||
match server {
|
||||
Ok(connected) => {
|
||||
self.connected.set(connected);
|
||||
Ok(())
|
||||
},
|
||||
Err(error) => {
|
||||
Err(Error::from(error))
|
||||
},
|
||||
}
|
||||
// Step 4 - 5:
|
||||
self.Device().garbage_collect_the_connection()
|
||||
}
|
||||
|
||||
#[allow(unrooted_must_root)]
|
||||
|
@ -134,6 +125,14 @@ impl AsyncBluetoothListener for BluetoothRemoteGATTServer {
|
|||
match response {
|
||||
// https://webbluetoothcg.github.io/web-bluetooth/#dom-bluetoothremotegattserver-connect
|
||||
BluetoothResponse::GATTServerConnect(connected) => {
|
||||
// Step 5.2.3
|
||||
if self.Device().is_represented_device_null() {
|
||||
if let Err(e) = self.Device().garbage_collect_the_connection() {
|
||||
return promise.reject_error(promise_cx, Error::from(e));
|
||||
}
|
||||
return promise.reject_error(promise_cx, Error::Network);
|
||||
}
|
||||
|
||||
// Step 5.2.4.
|
||||
self.connected.set(connected);
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue