noble-winrt icon indicating copy to clipboard operation
noble-winrt copied to clipboard

Fails to discover characteristics for service

Open acstacey opened this issue 6 years ago • 4 comments

No matter what I put in for the array of characteristic UUIDs it fails to discover characteristics and never calls the callback. The same code discovers all characteristics in noble-uwp. (The service is successfully discovered)

GetCharacteristicsForUuidAsync: no characteristic with given id BLEManager::Notify::<lambda_a1184b3e8bf00761754d30ee7a9f05b8>::operator (): GetCharacteristic error

server.discoverServices(serviceFilter, function (err, services) {
    logger.info("Discovering services");
    if (err) {
        logger.error('Service discovery error: ' + err);
        bt.properties.bluetoothDevice.disconnect();
        return;
    }
    console.log(services[0]);
    services[0].discoverCharacteristics([], function (err, characteristics) {
        if (err) {
            logger.error('Characteristic discovery error: ' + err);
            bt.properties.bluetoothDevice.disconnect();
            return;
        }
        console.log(characteristics);
    });
});

acstacey avatar Nov 26 '18 12:11 acstacey

@acstacey The error looks like you're trying to subscribe to a characteristic before discovering it (BLEManager::Notify). Can you post or link the whole code that fails?

geovie avatar Nov 26 '18 12:11 geovie

@geovie Not sure how that could be happening - code below

let filters = {
  services: ["0001"]
};
let peripheral = await connectToDevice(filters);
let discoveredCharacs = await getCharacteristicsForService(peripheral, "0001");
function connectToDevice(filters) {
    return new Promise((res, rej) => {
        if (!filters) {
            rej('No device filters provided');
            return;
        }
        if (!filters.services) {
            filters.services = [];
        }
        if (adaptorState !== 'poweredOn') {
            rej("Bluetooth state: " + adaptorState);
            return;
        }
        logger.info('Starting BLE scan ...');

        noble.once('scanStop', scanStopCallback = function () {
            if (!bt.properties.bluetoothDevice) {
                res(false);
            }
            scanStopCallback = null;
        });
        if (discoverCallback) {
            noble.removeListener('discover', discoverCallback);
            discoverCallback = null;
        }
        noble.on('discover', discoverCallback = function (peripheral) {
            logger.info('peripheral discovered (' + peripheral.id +
                ' with address <' + peripheral.address + ', ' + peripheral.addressType + '>,' +
                ' connectable ' + peripheral.connectable + ',' +
                ' RSSI ' + peripheral.rssi + ', Name: ' + peripheral.advertisement.localName + 
                ', Services: ' + peripheral.advertisement.serviceUuids);
            
            if (scanStopCallback) {
                noble.removeListener('scanStop', scanStopCallback);
                scanStopCallback = null;
            }
            
            noble.stopScanning();
            logger.info("Attempting to connect...");
            peripheral.connect(function (err) {
                if (err) {
                    logger.error('Connection error: ' + err);
                    rej(err);
                    return;
                }
                peripheral.once('disconnect', onDisconnected);
                res(peripheral);
            });
        });
        noble.startScanning(filters.services, false);
    });
}

function getCharacteristicsForService(peripheral, serviceUUID) {
  return new Promise((res, rej) => {
    let serviceFilter;
    if (serviceUUID == null) {
      serviceFilter = [];
    } else {
      serviceFilter = [serviceUUID];
    }
    // For windows, server is the same as bluetoothDevice
    peripheral.discoverServices(serviceFilter, function (err, services) {
      logger.info("Discovering services");
      if (err) {
        logger.error('Service discovery error: ' + err);
        peripheral.disconnect();
        rej(err);
        return;
      }
      console.log("Services: " + services)
      services[0].discoverCharacteristics([], function (err, characteristics) {
        if (err) {
          logger.error('Characteristic discovery error: ' + err);
          peripheral.disconnect();
          rej(err);
          return;
        }
        res(characteristics);
        return;
      })

      if (services.length == 0) {
        console.log("No services found")
        res([])
      }
    });
  });
}

acstacey avatar Nov 28 '18 12:11 acstacey

It also sometimes fails with: GetGattServicesForUuidAsync: no service with given id BLEManager::DiscoverCharacteristics::<lambda_a73116e2e0cccea7020b7d62e7fe8c95>::operator (): GetService error

acstacey avatar Nov 28 '18 12:11 acstacey

I get this error reading a service from time to time too. Haven't dug into it yet. Works most of the time, figured it was a windows hiccup.

tony-gutierrez avatar Oct 25 '20 19:10 tony-gutierrez