Skip to content

Unified Bonding API supports Pairing on Windows. #906

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

axa88
Copy link

@axa88 axa88 commented Dec 15, 2024

Proposed support for Pairing on Windows, while adapting a common signature to the current Android implementation.

Surely the signature for this API should have had an associated return value and have the possibility for cancellation, even if both are left unused:

public Task<BondResult> BondAsync(IDevice device, BondingOptions bondingOptions = null, CancellationToken cts = CancellationToken.None);

Adding an optional parameter BondingOptions which can include any properties that the method may require, in this case Pairing parameters.
And return value BondResult as a unified object that represents the result of a Bond across any platforms rather than an arbitrarily, or no result from platform to platform.

(Arguably all API calls should have parameters and return values that inherent from a BaseOption and BaseResult to make adding functionality less brittle. BaseOptions having cancellation property, Baseresults having success property.)

The other key addition is adding a mechanism to support the Pairing Response , which allows interaction during the pairing process:

public class PairRespondedEventArgs(PairModes selectedMode, Action<IPairResponse> approvePairingResponse, string pin = null) : System.EventArgs

As the initial signature wasn't well thought out, and support on each platform varies, implementation includes 2 interfaces, IBondable and IPairProcess intended to be implemented on any platform which supports the feature.

IBondable indicates that a platform supports the programmatic request for Bonding and storing of keys. While IPairProcess indicates the the platform supports a programmatic implementation of the pairing process.
An interface arguably also provides a more agnostic way to implement non consistent features across multiple platforms, rather than relying on programmatic platform checking with loosely coupled and incomplete documentation.

On Windows:

namespace Plugin.BLE.Windows;

public class Adapter(BluetoothAdapter adapter) : AdapterBase, IBondable, IPairProcess

Where Android the pairing process is handled by the OS

namespace Plugin.BLE.Android;

public class Adapter(BluetoothAdapter adapter) : AdapterBase, IBondable

As implementation by application:

var cts = new CancellationTokenSource(TimeSpan.FromSeconds(30));
if (_adapter is IBondable bondable) // this platform supports bond requests
{
	var pairProcess = _adapter as IPairProcess; // this platform supports programmatic pairing
	if (pairProcess != null)
		pairProcess.PairResponded += OnPairResponded;

	try { var bondResult = await bondable.BondAsync(_selectedDevice, new(pairModes, ProtectionLevel.None), cts.Token); }
	catch (Exception ex) { Write(ex.Message); }
	finally 
	{
		if (pairProcess != null)
			pairProcess.PairResponded -= OnPairResponded;
	}

	void OnPairResponded(object? _, IPairProcess.PairRespondedEventArgs pairRespondedEventArgs)
	{
		switch (pairRespondedEventArgs.SelectedMode)
		{
			...
		}
	}
}

Example included in the Console Demo.

Regarding the Android implementation a few issues were addressed.
Firstly, throwing exceptions on non exceptional scenarios seems unhelpful. User cancels the Bond process? throw... Clicks outside a dialog? throw... Times out without input? throw... Bonding already in process? throw... These hardly seem like exceptional events, but ironically if bonding does actually fail or become unresponsive, it either swallows any indication of why it failed, or doesn't throw at all. And not only was there no current mechanism to cancel, but an unresponsive call to bond would hold a reference to the last request, no matter how long ago it was made, and then would throws on the next subsequent bond request, no matter when in the future it would again be made.
This all seems odd to me, but since the Bonding process in the Android OS appears solid, these bonding failures rarely manifest.

Feedback is requested as there are no project design or coding guide lines to follow. Not to mention i knew nothing about Bluetooth bonding before a few weeks ago

@axa88
Copy link
Author

axa88 commented Dec 17, 2024

@janusw

ci/github-actions / winBuild (pull_request) Failing after 6m

does this mean windows projects now need to be built targeting .net 9 or something?
Not sure i want to get into that right now

@janusw
Copy link
Member

janusw commented Dec 17, 2024

ci/github-actions / winBuild (pull_request) Failing after 6m

does this mean windows projects now need to be built targeting .net 9 or something?

No, this is due to .NET 7 going out of support. We need to remove the net7.0 targets to fix it (I'll take care of that).

Note that this is not related to your changes (also happens on master).

@janusw
Copy link
Member

janusw commented Dec 18, 2024

ci/github-actions / winBuild (pull_request) Failing after 6m

does this mean windows projects now need to be built targeting .net 9 or something?

No, this is due to .NET 7 going out of support. We need to remove the net7.0 targets to fix it (I'll take care of that).

I fixed the problem via #908 and rebased this branch/PR on top of the updated master branch (which should heal the CI failures).

@janusw
Copy link
Member

janusw commented Dec 19, 2024

Feedback is requested as there are no project design or coding guide lines to follow. Not to mention i knew nothing about Bluetooth bonding before a few weeks ago

To be honest, I have a hard time reviewing this PR, mostly because it is huge and contains lots of formatting and coding-style changes that do not relate to the proposed API changes at all.

First of all, you're changing whitespace and indentation in almost every file you touch. Luckily that's easy to ignore in GitHub and other diff viewers, but even then the diff has around 3000 lines. It includes lots of changes of variable names and other coding-style related changes, which are not really "necessary". That is not to say that all of these small changes are necessarily useless: Some may improve code quality, some may make things worse, and for some it may just be a matter of taste.

And I'm not really inclined to spend my limited time going through thousands of lines, just to wonder: What the hell has been changed here? And why the hell?

So I'd tend to simply reject the PR in this form (even if it may include useful extensions of functionality, which is hard to tell, because they are drowning in tons of small unrelated changes). I hope that reaction is understandable.

Maybe I can give a bit of advice on how to increase your chances of getting contributions accepted in this repository (or anywhere else on GitHub, for that matter):

  • Make smaller commits.
  • Separate functional and API changes from formatting changes and refactoring.
  • Give each commit a meaningful commit message.
  • Don't just change things for the sake of changing things. If in doubt, stick with what is there.

@axa88
Copy link
Author

axa88 commented Dec 20, 2024

LoL, i was trying hard not to change more. Well I don't blame you, my OCD, autism, or both, compelled me to clean up, but frankly every change was an improvement in both form and function.
So let's just leave it be, I suppose I'm just going to be working out of my own fork from here on out anyway.

@axa88
Copy link
Author

axa88 commented Dec 31, 2024

Verified to work with Bluetooth v4.2+ with Secure Connections.
Windows Pairing is fully supported.
Modifying PR from from Draft to Ready, take it or leave it.

@axa88 axa88 marked this pull request as ready for review December 31, 2024 23:35
@axa88 axa88 changed the title Unified Bonding API supports Pairing on Windows. Verified with Bluetooth v4.1 Unified Bonding API supports Pairing on Windows. Jan 1, 2025
Unified Bonding API supports Pairing on Windows
@axa88
Copy link
Author

axa88 commented Feb 2, 2025

It has come to my attention, that anyone looking to try this PR should be warned an explicit call to the 'new' BondAsync overload needs to be made in order to get full pairing support in windows:

This was initiated as a PR Draft with the intention of allowing access to both the old and new and get user feedback before removing the old and submitting. Though as i no longer believe I'll be doing any further work with this PR, it was submitted as is.

User note, you really need to know what kind of security your peripheral supports in order to pair with your peripheral correctly.
If your peripheral supports LE Secure Connection, and hope to use the automated pairing process in WinUI3, you need to explicitly call the overloaded method with BondingOptions = null. If it does not then you can explore the manual pairing process by providing a valid "BondingOptions" object.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy