Not able to writeValue to a Bluetooth Peripheral when announced properties state writing+reading is available

I am trying to send a simple JSON to a connected Bluetooth peripheral but getting some problems in the process.


The properties read from the peripheral in the didDiscoverCharacteristicsFor method are the following:


po characteristic.properties
▿ CBCharacteristicProperties
  - rawValue : 10

Which as this is a mask and if I am not mistaken this states that I can read (2) and write (8) from/to the device.


I am writing the data as soon as I discover a new characteristic that matches the requirements in the following way


func peripheral(_ peripheral: CBPeripheral, didDiscoverCharacteristicsFor service: CBService,error: Error?) {

        for characteristic in service.characteristics! {
            let characteristic = characteristic as CBCharacteristic
            print(characteristic.uuid)
            if characteristic.uuid.isEqual(RX_UUID) {

                // Received only support for writing with response, writing without response is not allowed
                if characteristic.properties.contains(CBCharacteristicProperties.write) {
                    self.writeJsonStringToPeripheral(peripheral: peripheral, characteristic: characteristic, writeType: .withResponse)
                } else if characteristic.properties.contains(CBCharacteristicProperties.writeWithoutResponse) {
                    self.writeJsonStringToPeripheral(peripheral: peripheral, characteristic: characteristic, writeType: .withoutResponse)
                }
            }
        }
    }

    func writeJsonStringToPeripheral(peripheral: CBPeripheral, characteristic: CBCharacteristic, writeType: CBCharacteristicWriteType) {

        do {

            let msgDictionary = ["SSID": self.wiFiCredentials.SSID, "Password": self.wiFiCredentials.Password]
            let jsonData = try JSONSerialization.data(withJSONObject: msgDictionary, options: [])
            //let data = "".data(using: .utf8)

            peripheral.writeValue(jsonData, for: characteristic, type: writeType)

        } catch let error as NSError {
            debugPrint("Error in auth message JSON: \(error.description)")
    

This snippet calls the function at line 10 indicating the possibility of writing with a response and after callign it the didWriteValueFor delegate method is called.


func peripheral(_ peripheral: CBPeripheral, didWriteValueFor characteristic: CBCharacteristic, error: Error?) {

        if let error = error {
            print(error)
        } else {
            print("Value writen sucessfully.")
        }
    }

Printing the following error.


Error Domain=CBATTErrorDomain Code=3 "Writing is not permitted." UserInfo={NSLocalizedDescription=Writing is not permitted.}

I've made myself sure that the device is connected and I can also see it in the Settings.app. I am a bit lost and I don't know what could be going on here.


On the other side if I force the writing to be withoutResponse I get another console log


2020-03-25 22:23:50.286662+0100 Cloudy[2595:1232291] [CoreBluetooth] WARNING: Characteristic  does not specify the "Write Without Response" property - ignoring response-less write


After sending the specified JSON to the device it should start a sequence to connect to the specified WiFi SSID. I am sure the hardware works because I can set those values using the console on the device itself and the process works so there must be something I am missing here that causes this to fail.


This test has been done using an iPhone 6S running ios 13.3.1.

Replies

Hi 👋
Did you manage to resolve this issue? currently I'm facing the same issue, 2 days and not finding where I'm going wrong? Thanks.

Hi, did you have a solution for this issue? I am facing the same problem. Thank you for any info.