Basic bluetooth linking implementation#1
Conversation
It's challenging to anticipate how vast the full implementation will be, but this is a version which compiles `CBCentralManager` and `CBPeripheralManager` with minimal implementations.
|
Thank you for your pull request and welcome to our community. We could not parse the GitHub identity of the following contributors: Ben Burgess.
|
|
Thank you for your pull request and welcome to our community. We could not parse the GitHub identity of the following contributors: Ben Burgess.
|
aabewhite
left a comment
There was a problem hiding this comment.
Amazing! I left just a few comments
| scanner?.stopScan(scanDelegate) | ||
| } | ||
|
|
||
| #if !SKIP |
There was a problem hiding this comment.
You have a number of #if !SKIP blocks, but the whole thing is surrounded by #if SKIP, so they aren't functional. This pattern is repeated in other files. Is this your way of excluding things that aren't implemented? If so, why not use @available(*, unavailable) for these? Do the signatures use types that aren't implemented or similar?
Sometimes in those cases we change the unimplemented types to Any (i.e. func f(x: Any /* OriginalType /) and mark @available(, unavailable) to hopefully give a better error message on attempted use. But fine either way - just checking that I understand.
There was a problem hiding this comment.
These are remnants from my initial implementation. I've replaced these sites with @available(*, unavailable) references instead. Sorry for the confusion here.
Sources/SkipBluetooth/CBPeer.swift
Outdated
| @@ -0,0 +1,12 @@ | |||
| #if SKIP | |||
| import SkipFoundation | |||
There was a problem hiding this comment.
Changed all other references as well.
Sources/SkipBluetooth/Utility.swift
Outdated
| /// This process is handled automatically by CoreBluetooth for Swift when you instantiate either | ||
| /// `CBCentralManager` or `CBPeripheralManager`, but Android requires the request | ||
| /// to occur within an activity. | ||
| @Composable |
There was a problem hiding this comment.
Is this the only reason the package relies on SkipUI?
If so, I think it's worth moving this to documentation and dropping the dependency. What do you think?
Come to think of it, we should probably add a general permission check utility to SkipUI itself... but that's another topic.
There was a problem hiding this comment.
Ah that dependency was vestigial! It's removed.
There was a problem hiding this comment.
Actually, it does look like we need to depend on SkipUI, since that brings in the compose dependencies we need for androidx.activity.result.contract.ActivityResultContracts and other things that are being used. That seems to be the only thing stopping CI from passing (https://github.com/skiptools/skip-bluetooth/actions/runs/10640472849), so if you add back the SkipUI dependency, then we should get a clean CI run.
There was a problem hiding this comment.
I'd rather not include the permission prompt util and not depend on SkipUI. What do you think?
There was a problem hiding this comment.
Oh yeah, if askForBluetoothPermissions() is removed, then it looks like the androidx.activity.compose and other imports can be removed, and it can just depend on skip-foundation.
There was a problem hiding this comment.
Removing that one function works for me. It's changed.
There was a problem hiding this comment.
I think you just need to remove the import androidx.core… and import androidx.activity.compose… from CBCentralManager.swift, and it looks like the CI run should pass (see the failure at https://github.com/skiptools/skip-bluetooth/actions/runs/10641143687).
There was a problem hiding this comment.
Ah I see. I wasn't checking the CI output -- fixed. Not sure what's causing the cla-bot failures though... Thank you for the help thus far!
| @@ -0,0 +1,42 @@ | |||
| import Foundation | |||
There was a problem hiding this comment.
Can you add the LGPL license header to this and the other files so they all have the same header?
There was a problem hiding this comment.
Sure thing, completed.
|
This looks great! We've added a couple of comments, but overall it seems like a really solid PR. Also, the weird "cla-bot" errors are indicating that it wants you to add your username to https://github.com/skiptools/clabot-config Once those are in place, we'll be ready to merge and we can cut a new release. Thanks! |
|
Thank you for your pull request and welcome to our community. We could not parse the GitHub identity of the following contributors: Ben Burgess.
|
|
Thank you for your pull request and welcome to our community. We could not parse the GitHub identity of the following contributors: Ben Burgess.
|
|
Thank you for your pull request and welcome to our community. We could not parse the GitHub identity of the following contributors: Ben Burgess.
|
|
Thank you for your pull request and welcome to our community. We could not parse the GitHub identity of the following contributors: Ben Burgess.
|
|
Thank you for your pull request and welcome to our community. We could not parse the GitHub identity of the following contributors: Ben Burgess.
|
|
Thank you for your pull request and welcome to our community. We could not parse the GitHub identity of the following contributors: Ben Burgess.
|
|
CI passed, looks good! I'll go ahead and merge and create a tagged release. FTR, not entirely sure what the cla-bot error is about (since you added your name there) – it looks like it might be happening from a lack of e-mail address, either configured in GitHub (https://github.com/settings/emails) or from your local git config ( Thanks again for the contribution! |
Overview
This PR contains a limited but functional implementation Apple's
CoreBluetoothof Bluetooth Low Energy (BLE) for Android.Because
CoreBluetooth's implementation is limited in many ways, i.e. not allowing certain advertisement data, this implementation also disables those features to emulate an experience as similar as possible.Features
With these changes, it is possible to perform critical functions of BLE:
Peripheral
CBPeripheralManager.add())Central
Next Steps
Ancillary API Delegate Implementations
There are a number of API calls which aren't strictly necessary in BLE communication which aren't implemented. As of the time of this PR, these include:
CBPeripheralDelegate
CBPeripheralManagerDelegate
CBCentralManagerDelegate
There are a smattering of other fields and properties which are also unimplemented, but they are notated with
@available(*, unavailable)which will signal compile-time failures.Better advertisement cleanup logic
Apple's
CoreBluetoothimplementation ostensibly cleans up all GATT database values after both invokingCBPeripheralManager.stopAdvertising()and the instance is de-initialized, but since we cannot reliably hook into thefinalizelifecycle in Skip, there is no guarantee the equivalent teardown functionBluetoothGattServer.cleanup()function would be called if it was placed in there. There may be some clever solution here to guarantee thecleanup()function is called at a similar point in the lifecycle, but I am not aware of one.Testing
Testing these APIs is quite challenging because their functionality requires hardware, and I am unfamiliar with testing to this end. This is a rich area for development going forward.