bidi-bluetooth-helper.js (4275B)
1 'use strict'; 2 3 const DEVICE_NAME = 'LE Device'; 4 const DEVICE_ADDRESS = '09:09:09:09:09:09'; 5 const HEART_RATE_SERVICE_UUID = '0000180d-0000-1000-8000-00805f9b34fb' 6 const DATE_TIME_CHARACTERISTIC_UUID = '00002a08-0000-1000-8000-00805f9b34fb' 7 const CHARACTERISTIC_USER_DESCRIPTION_DESCRIPTOR_UUID = '00002901-0000-1000-8000-00805f9b34fb' 8 9 /** 10 * Waits until the document has finished loading. 11 * @returns {Promise<void>} Resolves if the document is already completely 12 * loaded or when the 'onload' event is fired. 13 */ 14 function waitForDocumentReady() { 15 return new Promise(resolve => { 16 if (document.readyState === 'complete') { 17 resolve(); 18 } 19 20 window.addEventListener('load', () => { 21 resolve(); 22 }, {once: true}); 23 }); 24 } 25 26 /** 27 * Simulates a user activation prior to running |callback|. 28 * @param {Function} callback The function to run after the user activation. 29 * @returns {Promise<*>} Resolves when the user activation has been simulated 30 * with the result of |callback|. 31 */ 32 async function callWithTrustedClick(callback) { 33 await waitForDocumentReady(); 34 return new Promise(resolve => { 35 let button = document.createElement('button'); 36 button.textContent = 'click to continue test'; 37 button.style.display = 'block'; 38 button.style.fontSize = '20px'; 39 button.style.padding = '10px'; 40 button.onclick = () => { 41 document.body.removeChild(button); 42 resolve(callback()); 43 }; 44 document.body.appendChild(button); 45 test_driver.click(button); 46 }); 47 } 48 49 /** 50 * Register a one-time handler that selects the first device in the device 51 * prompt upon a device prompt updated event. 52 * @returns {Promise} fulfilled after the bluetooth device prompt 53 * is handled, or rejected if the operation fails. 54 */ 55 function selectFirstDeviceOnDevicePromptUpdated() { 56 return test_driver.bidi.bluetooth.request_device_prompt_updated.once().then( 57 (promptEvent) => { 58 assert_greater_than(promptEvent.devices.length, 0); 59 return test_driver.bidi.bluetooth.handle_request_device_prompt({ 60 prompt: promptEvent.prompt, 61 accept: true, 62 device: promptEvent.devices[0].id 63 }); 64 }); 65 } 66 67 /** 68 * Create a GATT connection to the `device` by registering a one-time handler 69 * that simulate a successful GATT connection response upon a GATT connection 70 * attempted event and making a GATT connection to it. 71 * @returns {Promise} fulfilled after the GATT connection is created, or 72 * rejected if the operation fails. 73 */ 74 async function createGattConnection(device) { 75 const simulationProcessedPromise = 76 test_driver.bidi.bluetooth.gatt_connection_attempted.once().then( 77 (event) => { 78 return test_driver.bidi.bluetooth.simulate_gatt_connection_response({ 79 address: event.address, 80 code: 0x0, 81 }); 82 }); 83 const connectPromise = device.gatt.connect(); 84 await Promise.all([connectPromise, simulationProcessedPromise]); 85 } 86 87 /** 88 * Calls requestDevice() in a context that's 'allowed to show a popup'. 89 * @returns {Promise<BluetoothDevice>} Resolves with a Bluetooth device if 90 * successful or rejects with an error. 91 */ 92 function requestDeviceWithTrustedClick(...args) { 93 return callWithTrustedClick( 94 () => navigator.bluetooth.requestDevice(...args)); 95 } 96 97 /** 98 * This is a test helper to run promise_test with Bluetooth emulation setup 99 * before the test and teardown after the test. 100 * @param {function{*}: Promise<*>} test_function The test to run. 101 * @param {string} name The name or description of the test. 102 * @returns {Promise<void>} Resolves if the test ran successfully, or rejects if 103 * the test failed. 104 */ 105 function bluetooth_test(test_function, name) { 106 return promise_test(async (t) => { 107 assert_implements(navigator.bluetooth, 'missing navigator.bluetooth'); 108 await test_driver.bidi.bluetooth.simulate_adapter({ 109 state: "powered-on" 110 }); 111 await test_driver.bidi.bluetooth.simulate_preconnected_peripheral({ 112 address: DEVICE_ADDRESS, 113 name: DEVICE_NAME, 114 manufacturerData: [], 115 knownServiceUuids: [] 116 }); 117 try { 118 await test_function(t); 119 } finally { 120 await test_driver.bidi.bluetooth.disable_simulation(); 121 } 122 }, name); 123 }