Skip to content
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

New features: included, secondary services + finer handles control #88

Closed
wants to merge 2 commits into from

Conversation

wino45
Copy link

@wino45 wino45 commented Dec 17, 2014

  • added include service …
  • added secondary service
  • added relative and absolute handles (use it with care)
  • added example of this features

- added secondary service
- added relative and absolute handles (use it with care)
- added example of this features
@wino45
Copy link
Author

wino45 commented Dec 17, 2014

Included example is working but should be cleaned and GATT service example implemented. The GATT service structure from Core specification isin main.js. But this is just array with structure snd should be implemented.

@sandeepmistry
Copy link
Collaborator

@wino45 thanks for the pull request!

A few things:

  • I'm not to keen on exposing the relative and absolute handles (as I don't think CoreBluetooth/blued on OS X will support it). Can included services be implemented without them?
  • It would be great to have included services as an array field like the characteristics field of services. What do you think?
  • Before this is merged, OS X support will have to be added, see lib/mac/bindings.js

It's great that you provided examples. Is it common for a secondary service to include another secondary service? (almost all of the BLE devices I've played with don't use secondary/included services)

@wino45
Copy link
Author

wino45 commented Dec 26, 2014

  • Included service can be implemented without absolute/relative handles.
  • I am not sure what you mean. Included service B is added to service A using array:
    BatteryService.super_.call(this, {
        uuid: '180F',
        included: ['secondaryID'],
        characteristics: [
            new BatteryLevelCharacteristic()
        ],
        relativeHandle: '10'
    });

But this is just reference to service B. The service B can be primary or secondary. Service B can be referenced (included) in service A, C or D.
In the code of service A you just put array of identifiers of included services (in example just one service with ID secondaryID.

  • I will try to merge Linux file with OSX file but I cannot check it since I do not have Mac.
  • Two level (or more) includes are valid (allowed by core specification). I have not seen this feature on any device. Since it is possible why not implement it ? :-)

@wino45
Copy link
Author

wino45 commented Dec 26, 2014

The relative and absolute handles are needed since devices with non-continuous handles are existing. If one wants to write device discovery software one must handle them. Bleno is IMO the best way to test such cases. Please do not remove it.

@sandeepmistry
Copy link
Collaborator

@wino45 here's the message id format for OS X peripheral, for the following code: https://github.com/sandeepmistry/osx-ble-peripheral/blob/master/BLEPeripheral/BPAppDelegate.m#L105

2015-01-04 11:14:29.920 BLEPeripheral[18451:2380730] sendMsg: 1, {
    kCBMsgArgName = "ca.sandeepmistry.BLEPeripheral";
    kCBMsgArgOptions =     {
        kCBInitOptionShowPowerAlert = 1;
    };
    kCBMsgArgType = 1;
}
2015-01-04 11:14:29.922 BLEPeripheral[18451:2380756] handleMsg: 6, {
    kCBMsgArgState = 5;
}
2015-01-04 11:14:29.922 BLEPeripheral[18451:2380730] peripheralManagerDidUpdateState: 5
2015-01-04 11:14:29.924 BLEPeripheral[18451:2380730] sendMsg: 10, {
    kCBMsgArgAttributeID = 1;
    kCBMsgArgAttributeIDs =     (
    );
    kCBMsgArgCharacteristics =     (
                {
            kCBMsgArgAttributeID = 2;
            kCBMsgArgAttributePermissions = 1;
            kCBMsgArgCharacteristicProperties = 2;
            kCBMsgArgData = <67686f73 74>;
            kCBMsgArgDescriptors =             (
            );
            kCBMsgArgUUID = "Unknown (<a6282ac7 7fca4852 a2e61d69 121fd44a>)";
        }
    );
    kCBMsgArgType = 0;
    kCBMsgArgUUID = "Unknown (<a5b288c3 fc55491f af3827d2 f7d7bf25>)";
}
2015-01-04 11:14:29.925 BLEPeripheral[18451:2380730] sendMsg: 10, {
    kCBMsgArgAttributeID = 3;
    kCBMsgArgAttributeIDs =     (
        1
    );
    kCBMsgArgCharacteristics =     (
                {
            kCBMsgArgAttributeID = 4;
            kCBMsgArgAttributePermissions = 1;
            kCBMsgArgCharacteristicProperties = 2;
            kCBMsgArgData = <7a6f6d62 6965>;
            kCBMsgArgDescriptors =             (
            );
            kCBMsgArgUUID = "Unknown (<ddca9b49 a6f5462f a89ac214 4083ca7f>)";
        }
    );
    kCBMsgArgType = 1;
    kCBMsgArgUUID = "Unknown (<bd0f6577 4a384d71 af1b4e8f 57708080>)";
}
2015-01-04 11:14:29.925 BLEPeripheral[18451:2380756] handleMsg: 18, {
    kCBMsgArgAttributeID = 1;
    kCBMsgArgResult = 0;
}

I think it has a similar setup to your Linux patch, where secondary services are referred by id in a primary service.

We will not be able to support relative and absolute handles on OS X.

Another question, how practical is it to have a secondary service included in more than one primary service? I was thinking of a API like:

new PrimaryService({
  uuid: '180F',
  included: [
    new SecondaryService({
      uuid: '180E',
      characteristics: [
         // ....
      ]
    })
  ],
  characteristics: [
    new BatteryLevelCharacteristic()
  ]
});

That way we don't have to reference included services by id.

@wino45
Copy link
Author

wino45 commented Jan 13, 2015

Hi
My intentions in modifying Bleno was to add as much flexibility as possible - everything that is allowed by specification should be do able. This will make Bleno a perfect project to test any central device against all possible cases (that is why I miss indication support in Bleno even it is Linux-only).
There is no problem for me with "included: [new SecondaryService({..})]" if both types are supported. I do not like string identifiers either but I have no found way to be fully flexible. IMO the idea of included services are that they are shared between other services - no matter which ones are primary or secondary.

Sorry for delayed answer, I will try to answer quickly next time.

@sandeepmistry
Copy link
Collaborator

@wino45 I understand your desired to make bleno as flexible as possible, but one of the projects goals is to have an unified API for both Linux and OS X.

How about passing the included service in by reference:

var secondaryService1 = new SecondaryService({
  // ...
});

var secondaryService2 = new SecondaryService({
  // ...
});

var primaryService1 = new PrimaryService({
  // ...
  includeServices: [
    secondaryService1,
    secondaryService2
  ],
  // ...
});

bleno.on('advertisingStart', function(error) {
  console.log('on -> advertisingStart: ' + (error ? 'error ' + error : 'success'));
  if (!error) {
    bleno.setServices([
      primaryService1,
      secondaryService1,
      secondaryService2
    ]);
  }
});

This is very similar to the OS X CoreBluetooth API, as well a mix of your proposal and my previous. It eliminates the need for secondary service id's.

@wino45
Copy link
Author

wino45 commented Jan 19, 2015

@sandeepmistry this IMO looks good.

As of unified API for Linux and OS X. It looks like that Linux is much more flexible then OSX. Maybe you can add some kind of properties with flags what is supported and what is not on particular platform ?
This will allow to write JS code that will be aware of available APIs.

@sandeepmistry
Copy link
Collaborator

@wino45 I'll add working on OS X side to my todo list, then compare it to your Linux PR, hopefully it gets done in the next few weeks.

I'm thinking about not supporting the relative and absolute handles for initial secondary service API, then we can discuss again later on.

You can distinguish OS via:

var os = require('os');

var platform = os.platform();

@sandeepmistry
Copy link
Collaborator

@wino45 see new branch, I've started with OS X, but seems a little unstable with more than one included service:

https://github.com/sandeepmistry/bleno/tree/included-services

@sandeepmistry
Copy link
Collaborator

This enhancement will cause issues on OS X, closing for now ...

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