I'm writing a react-native application that uses a bluetooth module. My goal is to make the scan/connect/discover function async, so that I can wait on it and manage the return value accordingly.
This is the code I have right now:
async writeData(data) {
this.store.dispatch({type: "START_LOADER"})
await this.manager.isDeviceConnected(this.deviceId).then(res => {
if (res) {
const device = this.store.getState().store.device
device.writeCharacteristicWithoutResponseForService(
data.serviceId,
data.charId,
data.dataToWrite
).then(res => {
this.store.dispatch({type: "SET_STATUS", payload: `${data.message}!\n`})
this.store.dispatch({type: "STOP_LOADER"})
}).catch(error => {
this.store.dispatch({type: "SET_ERROR", payload: error.message})
this.store.dispatch({type: "STOP_LOADER"})
})
return true
} else {
const timeout = setTimeout(() => {
this.store.dispatch({type: "STOP_LOADER"})
this.store.dispatch({type: "SET_ERROR", payload: 'Function timeout: device not found'})
return
}, 10000)
this.manager.startDeviceScan(null, null, (error, device) => {
if (error) {
this.store.dispatch({type: "SET_ERROR", payload: error.message})
return
}
if (device.id === this.deviceId) {
clearTimeout(timeout)
this.store.dispatch({type: "SET_STATUS", payload: "North Sense found, stopping device scan...\n"})
this.store.dispatch({type: "SET_DEVICE", payload: device})
this.manager.stopDeviceScan();
device.connect().then((device) => {
this.store.dispatch({type: "SET_STATUS", payload: "device is connected!\n"})
return device.discoverAllServicesAndCharacteristics()
}).then((device) => {
device.writeCharacteristicWithoutResponseForService(
data.serviceId,
data.charId,
data.dataToWrite
).then(res => {
this.store.dispatch({type: "SET_STATUS", payload: `${data.message}!\n`})
this.store.dispatch({type: "STOP_LOADER"})
}).catch(error => {
this.store.dispatch({type: "SET_ERROR", payload: error.message})
this.store.dispatch({type: "STOP_LOADER"})
})
}).catch((error) => {
this.store.dispatch({type: "SET_ERROR", payload: error.message})
this.store.dispatch({type: "STOP_LOADER"})
});
}
});
}
}).catch(error => {
this.store.dispatch({type: "SET_ERROR", payload: error.message})
return error
})
}
This code is inserted in the context of a class, so the way I use this function is the following:
const blApi = new blApi(deviceId)
console.log('1')
blApi.writeData({
serviceId: Config.SERVICE_ID,
charId: Config.ADD_PROGRAM_CHAR_ID,
dataToWrite: btoa(`4;${this.state.bearing};${Config.SENSING_LOCATION_INDEX}`),
message: "Person has been successfully added.",
})
console.log('2')
The logs don't wait for the function to return, especially when the case of the timeout is triggered (in case the bluetooth device is not around) and the timeout expires after 10 seconds I would expect the function to wait those 10 seconds before continuing to the next line.
How can I fix this?