Tuya Mesh

Last Updated on : 2023-05-22 06:38:25download

This topic describes the implementation of communication over Bluetooth based on Tuya’s proprietary mesh networking technology, also known as Tuya mesh. Each Tuya mesh device serves as a child node, and multiple mesh devices form a mesh network, in which the child nodes communicate with each other by advertising. This topic provides the development guidance on pairing, control, and management of devices that use Tuya mesh. For more information about Bluetooth mesh concepts, see Bluetooth Mesh.

Class name Description
TYBLEMeshManager Encapsulates all API methods of Tuya mesh.

Preparation

Enables Tuya mesh.

// Enables Tuya mesh during initialization.
[[TuyaSmartSDK sharedInstance] setValue:@(YES) forKey:@"bleMeshEnable"];

Management

Tuya mesh operation classes are included in the file TuyaSmartBleMesh.h.

Create a mesh network

A home can belong to multiple mesh networks, but one mesh network is recommended for each home. Before the request, check whether a mesh network is created. If not, you can call this API method to create one.

All mesh operations are implemented based on the initialized home data. For more information, see Home Management.

API description

+ (void)createBleMeshWithMeshName:(NSString *)meshName
                           homeId:(long long)homeId
                          success:(void(^)(TuyaSmartBleMeshModel *meshModel))success
                          failure:(TYFailureError)failure;

Parameters

Parameter Description
meshName The name of the Tuya mesh network. It can be customized.
homeId The home ID.
success The success callback.
failure The failure callback.

Example

TuyaSmartHome *home = #<The initialized home instance>;
long long homeId = home.homeModel.homeId;
[TuyaSmartBleMesh createBleMeshWithMeshName:@"yourMeshName" homeId:homeId success:^(TuyaSmartBleMeshModel *meshModel) {
    // success do...
} failure:^(NSError *error) {
    NSLog(@"create mesh error: %@", error);
}];

The meshName of this method is a custom parameter. We recommend that you uniquely set it in the format of mesh+<timestamp>.

Delete a mesh network

API description

Deletes a mesh network. If sub-devices are included in the mesh group, they are also removed. In this case, the Wi-Fi connector is also removed.

- (void)removeMeshWithSuccess:(TYSuccessHandler)success failure:(TYFailureError)failure;

Parameters

Parameter Description
success The success callback.
failure The failure callback.

Example

self.mesh = #<TuyaSmartBleMesh instance>;
[self.mesh removeMeshWithSuccess:^{
    // success do...
} failure:^(NSError *error) {
    XCTFail(@"test remove mesh failure: %@", error);
}];

Query a list of mesh networks in a home

API description

Returns a list of mesh networks for an initialized home instance.

- (void)getMeshListWithSuccess:(void(^)(NSArray <TuyaSmartBleMeshModel *> *list))success
                       failure:(TYFailureError)failure;

Parameters

Parameter Description
success The success callback.
failure The failure callback.

Example

TuyaSmartHome *home = #<home instance>
[home getMeshListWithSuccess:^(NSArray<TuyaSmartBleMeshModel *> *list) {
    // success do
} failure:^(NSError *error) {
    NSLog(@"get mesh list error: %@", error);
}];

Query a mesh instance

API description

+ (instancetype)bleMeshWithMeshId:(NSString *)meshId homeId:(long long)homeId;

Parameters

Parameter Description
meshId The mesh ID.
homeId The current home ID.

Example

You can create a mesh instance by using meshModel for the home instance of the TuyaSmartHome class. Pass the mesh instance to TuyaSmartUser. The SDK and the upper-layer encapsulation are based on whether TuyaSmartUser has the value.

// The mesh network is not queried.
if ([TuyaSmartUser sharedInstance].meshModel == nil) {
    TuyaSmartHome *home = #<home instance>
    [home getMeshListWithSuccess:^(NSArray<TuyaSmartBleMeshModel *> *list) {
            if (list.count > 0) {
                // Assigns values.
                [TuyaSmartUser sharedInstance].meshModel = home.meshModel;
                [TuyaSmartUser sharedInstance].mesh = [TuyaSmartBleMesh bleMeshWithMeshId:home.meshModel.meshId homeId:home.meshModel.homeId];

                // Subsequence operations.
            } else {
                // The created mesh instance is used if no mesh information is found in the cloud.
                NSTimeInterval interval = [[NSDate date] timeIntervalSince1970];
                NSString *meshName = [NSString stringWithFormat:@"tymesh%.0f", interval];

                [TuyaSmartBleMesh createBleMeshWithMeshName:meshName homeId:home.homeModel.homeId success:^(TuyaSmartBleMeshModel *meshModel) {
                    // Assigns values.
                    [TuyaSmartUser sharedInstance].meshModel = meshModel;
                    [TuyaSmartUser sharedInstance].mesh = [TuyaSmartBleMesh bleMeshWithMeshId:meshModel.meshId homeId:home.homeModel.homeId];

                    // Subsequence operations.
                } failure:^(NSError *error) {
                    // Processes errors.
                }];
            }
        } failure:^(NSError *error) {
            // Processes errors.
        }];
} else {
    // Subsequence operations.
}

Connect to a mesh sub-device

Connect a paired device to a Tuya mesh network. During this process, Bluetooth must be enabled.

API description

  • To run only a pairing task, enter the default mesh name and password. Then, only
    - (void)bleMeshManager:(TYBLEMeshManager *)manager didScanedDevice:(TYBleMeshDeviceModel *)device; of TYBLEMeshManagerDelegate returns the scanning result.

  • To connect a paired device to a mesh network, enter the name and password of the created mesh network. The data is returned by cloud-based API methods. Then, the paired device is automatically connected to the mesh network. The system also automatically queries the online status of each device once on the mesh network.

    - (void)startScanWithName:(NSString *)name
    					pwd:(NSString *)pwd
    				active:(BOOL)active
    			wifiAddress:(uint32_t)wifiAddress
    			otaAddress:(uint32_t)otaAddress;
    

Parameters

Parameter Description
name The name of the mesh network.
pwd The password of the mesh network.
active Specifies whether to pair and activate a device.
wifiAddress The Wi-Fi address. This parameter is required for pairing a gateway and set to 0 for other types of devices.
otaAddress The IP address of the OTA update device. This parameter is required for OTA update and set to 0 for other types of devices.

Callback

Queries the online status of all devices on a mesh network after a paired device is connected to the mesh network. In the callback, the delegate method TuyaSmartHomeDelegate is called.

// Device information such as a device name is changed.
- (void)home:(TuyaSmartHome *)home deviceInfoUpdate:(TuyaSmartDeviceModel *)device;

Example

// The parameters of `active`, `wifiAddress`, and `otaAddress`.
[[TYBLEMeshManager sharedInstance] startScanWithName:[TuyaSmartUser sharedInstance].meshModel.code pwd:[TuyaSmartUser sharedInstance].meshModel.password active:NO wifiAddress:0 otaAddress:0];

// Device information such as a device name is changed.
- (void)home:(TuyaSmartHome *)home deviceInfoUpdate:(TuyaSmartDeviceModel *)device {
    // The callback.
}

Pairing

A Bluetooth device in the reset and disconnected state can be paired to join a mesh network. Mesh devices to be paired are classified into:

  • A Tuya mesh sub-device, such as lights, sockets, and low-power devices. This type of device runs without a gateway.
  • A mesh gateway.

Tuya mesh operation classes are included in the file TYBLEMeshManager. It is a singleton class.

Reset devices

The default name of a device in the reset state is out_of_mesh and the default password is 123456. The following list describes common device resetting methods.

Product category Reset method State pending pairing
Lighting Turn on and off the light consecutively three times in a row The indicator is flickering quickly.
Socket Tap and hold the switch for three seconds The indicator is flickering quickly.
Gateway Tap and hold the switch for three seconds The red and blue indicators are flickering quickly.
Low-power device Tap and hold the switch for three seconds Press the switch once again to see that the indicator is steady on. The pairing process must be completed when the indicator is on.
Alarm Tap and hold the switch for three seconds The indicator is flickering quickly.

Scan for sub-devices pending pairing

To simplify scanning and subsequent pairing operations, Tuya encapsulates all operations in the same API.

  • To run only a pairing task, enter the default mesh name and password. Then, only
    - (void)bleMeshManager:(TYBLEMeshManager *)manager didScanedDevice:(TYBleMeshDeviceModel *)device; of TYBLEMeshManagerDelegate returns the scanning result.

  • To connect a paired device to a mesh network, enter the name and password of the created mesh network. The data is returned by cloud-based API methods. Then, the paired device is automatically connected to the mesh network. The system also automatically queries the online status of each device once on the mesh network.

API description

- (void)startScanWithName:(NSString *)name
                      pwd:(NSString *)pwd
                   active:(BOOL)active
              wifiAddress:(uint32_t)wifiAddress
               otaAddress:(uint32_t)otaAddress;

Parameters

Parameter Description
name The name of the mesh network.
pwd The password of the mesh network.
wifiAddress The Wi-Fi address. This parameter is required for pairing a gateway and set to 0 for other types of devices.
otaAddress The IP address of the OTA update device. This parameter is required for OTA update and set to 0 for other types of devices.

Callback

  • If name is the default value out_of_mesh in an activation task, the system will scan for surrounding devices to be paired. In the callback, TYBLEMeshManagerDelegate returns the scanning result.

  • To connect a paired device to a mesh network, subsequent operations will automatically proceed without a callback. The API calls are similar to those for connecting to and disconnecting from a mesh network.

    - (void)bleMeshManager:(TYBLEMeshManager *)manager didScanedDevice:(TYBleMeshDeviceModel *)device;
    

Parameters

Parameter Description
manager The mesh manager.
device The information about the device pending pairing.

Example

// Starts scanning for a device pending pairing.
[[TYBLEMeshManager sharedInstance] startScanWithName:@"out_of_mesh" pwd:@"123456" active:YES wifiAddress:0 otaAddress:0];

// The callback of `TYBLEMeshManagerDelegate`.
- (void)bleMeshManager:(TYBLEMeshManager *)manager didScanedDevice:(TYBleMeshDeviceModel *)device {

    // This callback method applies to scanning for both gateways and sub-devices.
    // `device.type` and `device.vendorInfo` determines whether the target device is a mesh gateway.
    if (device.type == [TPUtils getIntValueByHex:@"0x0108"] || ([TPUtils getIntValueByHex:[device.vendorInfo substringWithRange:NSMakeRange(0, 2)]] & 0x08) == 0x08) {
          // The mesh gateway.
        return;
    } else {
        // Mesh sub-devices.
    }
}

// Implements `getIntValueByHex`.
+ (uint32_t)getIntValueByHex:(NSString *)getStr
{
    NSScanner *tempScaner=[[NSScanner alloc] initWithString:getStr];
    uint32_t tempValue;
    [tempScaner scanHexInt:&tempValue];
    return tempValue;
}

Activate sub-devices

API description

- (void)activeMeshDeviceIncludeGateway:(BOOL)includeGateway;

Parameters

Parameter Description
includeGateway Indicates whether to activate a gateway. A value of yes indicates that a discovered gateway, rather than the sub-devices, will be activated. Otherwise, all discovered devices rather than the gateway will be activated.

Callback

- (void)activeDeviceSuccessWithName:(NSString *)name deviceId:(NSString *)deviceId error:(NSError *)error;

Parameters

Parameter Description
name The name of the device.
deviceId The device ID.
error The error message that might be returned during activation. If it is returned, name and deviceId are empty.

Activate a specific sub-device

API description

- (void)activeMeshDevice:(TYBleMeshDeviceModel *)deviceModel;

Parameters

Parameter Description
deviceModel The device model.

The pairing result will be returned by TYBLEMeshManagerDelegate.

Callback

- (void)activeWifiDeviceWithName:(NSString *)name address:(NSInteger)address mac:(NSInteger)mac error:(NSError *)error;

Parameters

Parameter Description
name The name of the device.
address The IP address of the device.
mac The MAC address of the gateway.
error The failure callback.

Query the pairing token for a mesh gateway

If the target device is a gateway device, after the callback of activeWifiDeviceWithName, the pairing with the Wi-Fi module must be implemented. The method TuyaSmartActivator is called.

API description

This token is valid for 10 minutes.

- (void)getTokenWithMeshId:(NSString *)meshId
                    nodeId:(NSString *)nodeId
                 productId:(NSString *)productId
                      uuid:(NSString *)uuid
                   authKey:(NSString *)authKey
                   version:(NSString *)version
                   success:(TYSuccessString)success
                   failure:(TYFailureError)failure;

Parameters

Parameter Description
meshId The mesh ID.
nodeId The node ID.
productId The product ID (PID).
uuid The UUID of the device.
authKey The AuthKey of the device.
success The success callback. A pairing token is returned.
failure The failure callback.

Pair a mesh gateway

Pairs a mesh gateway by using the pairing token and the hotspot name and password of the router. This method can be called only the callback of activeWifiDeviceWithName of TYBLEMeshManagerDelegate is executed.

API description

- (void)startBleMeshConfigWiFiWithSsid:(NSString *)ssid
                              password:(NSString *)password
                                 token:(NSString *)token
                               timeout:(NSTimeInterval)timeout;

Parameters

Parameter Description
ssid The hotspot name of the router.
password The hotspot password of the router.
token The pairing token.
timeout The timeout value of a pairing task. Default value: 100. Unit: seconds.

Example

// Pairs a mesh device without a mesh gateway.
// 1. Activates a sub-device.
[[TYBLEMeshManager sharedInstance] activeMeshDeviceIncludeGateway:NO];

// 2. Executes the callback of `TYBLEMeshManagerDelegate`.
- (void)activeDeviceSuccessWithName:(NSString *)name deviceId:(NSString *)deviceId error:(NSError *)error {

    if (error) {
        NSLog(@"error : %@", error);
        return;
    }

    // 3. A sub-device is activated.
}
// Activates the mesh gateway.
// 1. Activates a sub-device.
[[TYBLEMeshManager sharedInstance] activeMeshDeviceIncludeGateway:NO];

// 2. Executes the callback of `TYBLEMeshManagerDelegate`.
- (void)activeWifiDeviceWithName:(NSString *)name address:(NSInteger)address mac:(NSInteger)mac error:(NSError *)error {
    if (error) {
       NSLog(@"error : %@", error);
       return;
    }

    // The gateway is activated. Only the Bluetooth module is activated, and you need to continue to activate the Wi-Fi module.
    // 3. The user enters the password for reconnection. After the device is reconnected, the SSID, password, and token are sent.
    // This operation is required. Otherwise, a Wi-Fi data writing error will occur and cause the pairing task to be failed.
    [TYBLEMeshManager sharedInstance].wifiMac = (int)mac;

    // 4. Returns the pairing token.
    NSString *nodeId = [NSString stringWithFormat:@"%02x", (int)address];
    [[TuyaSmartActivator sharedInstance] getTokenWithMeshId:[TuyaSmartUser sharedInstance].meshModel.meshId
                                                 nodeId:nodeId
                                              productId:[TYBLEMeshManager sharedInstance].productId
                                                   uuid:[TYBLEMeshManager sharedInstance].uuid
                                                authKey:[TYBLEMeshManager sharedInstance].authKey
                                                version:[TYBLEMeshManager sharedInstance].version
                                                success:^(NSString *token) {
                                                    // 5. Sets a pairing delegate to receive the activation result.
                                                    [TuyaSmartActivator sharedInstance].delegate = self;
                                                    // 6. Starts Wi-Fi pairing.
                                                    [[TuyaSmartActivator sharedInstance] startBleMeshConfigWiFiWithSsid:@"Wi-Fi name" password:@"Wi-Fi password" token:token timeout:100];
                                                } failure:^(NSError *error) {
                                                    NSLog(@"error: %@", error);
                                                }];
}

- (void)meshActivator:(TuyaSmartActivator *)activator didReceiveDeviceId:(NSString *)deviceId meshId:(NSString *)meshId error:(NSError *)error {
      // 7. Returns the activation result.

  }

Identify mesh connections

Checks whether Bluetooth devices are connected to a mesh network. This result determines the way to send control and operation commands.

// The mesh connection tag. If a Bluetooth device is connected to the mesh network, this value is `yes`.
BOOL isLogin = [TYBLEMeshManager sharedInstance].isLogin;

Pairing error codes

Error code Description
3088 Failed to activate the device.
3090 The specified mesh name and password are incorrect.
3091 Failed to log in.
3092 Failed to log in and decrypt.
3093 Failed to query the AuthKey.
3094 The length of the address has exceeded the upper limit.
3095 Failed to change the address.
3096 Failed to write the mesh information.
3097 The mesh information is empty.
3098 The mesh device has not been connected to the network.
3099 Failed to write data.
4000 An error has occurred while processing the Wi-Fi information.
4001 The Wi-Fi pairing token is incorrect.
4010 A timeout error has occurred while logging in.
4011 A timeout error has occurred while querying AuthKey.
4012 A timeout error has occurred while modifying the address.
4013 A timeout error has occurred while writing the mesh information.
4014 A timeout error has occurred while setting the Wi-Fi information.

Devices

The device class is TuyaSmartDevice. In this class, the deviceType field of TuyaSmartDeviceModel indicates a device type. The value of deviceType for mesh devices is TuyaSmartDeviceModelTypeSIGMeshSubDev.

Rename a sub-device

API description

- (void)renameMeshSubDeviceWithDeviceId:(NSString *)deviceId name:(NSString *)name success:(TYSuccessHandler)success failure:(TYFailureError)failure;

Parameters

Parameter Description
deviceId The device ID.
name The new name.
success The success callback.
failure The failure callback.

Example

[[TuyaSmartUser sharedInstance].mesh renameMeshSubDeviceWithDeviceId:self.device.devId name:name success:^{
            // success do
        } failure:^(NSError *error) {
            // failure do
        }];

Add a paired device to a mesh network (v2.0)

The SDK automatically processes this method during pairing. You can ignore this method.

- (void)addSubDeviceWithUuid:(NSString *)uuid
                      homeId:(long long)homeId
                     authKey:(NSString *)authKey
                      nodeId:(NSString *)nodeId
                  productKey:(NSString *)productKey
                         ver:(NSString *)ver
                     success:(void (^)(NSString *devId, NSString *name))success
                     failure:(TYFailureError)failure;

Parameters

Parameter Description
uuid The short address of a Bluetooth sub-device.
authKey The authorization key.
nodeId The mesh node ID (short address).
productKey The product ID.
ver The version number.
success The success callback.
failure The failure callback.

Example

[[TuyaSmartUser sharedInstance].mesh addSubDeviceWithUuid:_uuid homeId:[TuyaSmartUser sharedInstance].meshModel.homeId authKey:_authKey nodeId:nodeHex productKey:_selectedPeripheral.productId ver:_selectedPeripheral.version success:^(NSString *devId, NSString *name) {
                    // success do
                    } failure:^(NSError *error) {
                    // failure do
                    }];

Locally connect to sub-devices

Mesh sub-devices can be connected locally or in another online status. Connects to a mesh device over Bluetooth from a mobile phone on which Bluetooth is enabled. Commands are sent to the device over Bluetooth. You can use deviceModel.isOnline && deviceModel.isMeshBleOnline to check the device connection status.

Connect to sub-devices through a gateway

Mesh sub-devices can also be connected through a gateway. Connect to a mesh device through a mesh gateway from a mobile phone on which Bluetooth is disabled or that is far away from the device. Commands are sent to the device over Wi-Fi. You can use deviceModel.isOnline && !deviceModel.isMeshBleOnline to check the device connection status.

Remove a sub-device

Removes a sub-device from both the cloud and the local app.

Locally remove a sub-device

// Removes the device over Bluetooth.
- (void)kickoutLightWithAddress:(uint32_t)address type:(NSString *)type;

// Removes the device through a gateway.
- (NSString *)rawDataKickoutLightWithAddress:(uint32_t)address type:(NSString *)type;

   /**
    Sends commands of Raw type to the device.

    @param raw The value of Raw type.
    @param success The success callback.
    @param failure The failure callback.
    */
- (void)publishRawDataWithRaw:(NSString *)raw
                          pcc:(NSString *)pcc
                      success:(TYSuccessHandler)success
                      failure:(TYFailureError)failure;

Remove a sub-device from the cloud

- (void)removeMeshSubDeviceWithDeviceId:(NSString *)deviceId success:(TYSuccessHandler)success failure:(TYFailureError)failure;

Parameters

Parameter Description
deviceId The device ID.
success The success callback.
failure The failure callback.

Example

 int address = [smartDevice.deviceModel.nodeId intValue] << 8;

        // 1. Removes the device from the cloud.
        [[TuyaSmartUser sharedInstance].mesh removeMeshSubDeviceWithDeviceId:[smartDevice.deviceModel.devId success:^{

        } failure:^(NSError *error) {

        }];

        // 2. Locally removes the device.
        // Checks whether the device is connected through a gateway or over Bluetooth.
        if ([TYBLEMeshManager sharedInstance].isLogin) {

            [[TYBLEMeshManager sharedInstance] kickoutLightWithAddress:address type:[smartDevice.deviceModel.pcc];

        } else {

            [[TuyaSmartUser sharedInstance].mesh publishRawDataWithRaw:[[TYBLEMeshManager sharedInstance] rawDataKickoutLightWithAddress:address type:[smartDevice.deviceModel.pcc] pcc:[smartDevice.deviceModel.pcc success:^{

            } failure:^(NSError *error) {

            }];
        }

Query sub-device status

API description

- (void)getDeviceStatusAllWithAddress:(uint32_t)address
                                 type:(NSString *)type;

Parameters

Parameter Description
address The IP address of the device.
type The category and type of the device.

Groups

Certain devices on a mesh network can be grouped, so they can be controlled with group control commands. For example, all lights are added to a group. Users can control the switch status and colors of the group and thus control all lights in the group with the same properties.

The following methods of TuyaSmartBleMeshGroup are available.

Create a mesh group

  • The value of localId for a mesh group starts from 0x8001 and is sequentially incremented.

  • A mesh group and its sub-devices follow the same rules of categories and types.

  • Currently, each mesh network supports up to 255 groups and each device can be added to up to 8 groups at the same time.

    We recommend that devices of different categories do not belong to the same group. Otherwise, group device control might fail due to different device features.

API description

+ (void)createMeshGroupWithGroupName:(NSString *)groupName
                              meshId:(NSString *)meshId
                             localId:(NSString *)localId
                                 pcc:(NSString *)pcc
                             success:(TYSuccessInt)success
                             failure:(TYFailureError)failure;

Parameters

Parameter Description
groupName The name of the mesh group.
meshId The mesh ID.
localId The local short address of the group.
pcc The category and type of the group device.
success The success callback.
failure The failure callback.

Example

NSInteger localId = 0x8001;
[TuyaSmartBleMeshGroup createMeshGroupWithGroupName:@<Group name> meshId:[TuyaSmartUser sharedInstance].meshModel.meshId localId:[NSString stringWithFormat:@"%lx", localId] pcc:#<The category and type of the group> success:^(int result) {
     // success do
    // Queries the group instance.
     self.meshGroup = [TuyaSmartBleMeshGroup meshGroupWithGroupId:result];

    } failure:^(NSError *error) {
       // failure do
    }];

Add sub-devices to a mesh group

Before a sub-device can be added to a mesh group, it must be verified both locally and in the cloud. Multiple sub-devices must be added one by one to the mesh group. They cannot be removed concurrently in the same task.

Process

Tuya Mesh

API description

// Locally-connected sub-device.
// The result is returned by `TYBLEMeshManagerDelegate`.
- (void)addDeviceAddress:(uint32_t)deviceAddress type:(NSString *)type groupAddress:(uint32_t)groupAddress;

// TYBLEMeshManagerDelegate
- (void)deviceAddGroupAddress:(uint32_t)address error:(NSError *)error;

// Sub-device connected through a gateway.
  // Queries the command of Raw type to add a sub-device to a mesh group.
- (NSString *)rawDataAddDeviceAddress:(uint32_t)deviceAddress groupAddress:(uint32_t)groupAddress type:(NSString *)type;

API description

Sends pass-through commands to the device.

- (void)publishRawDataWithRaw:(NSString *)raw
                            pcc:(NSString *)pcc
                        success:(TYSuccessHandler)success
                        failure:(TYFailureError)failure;

  // The result is returned by ``TuyaSmartBleMeshDelegate` - (void)bleMeshReceiveRawData:(NSString *)raw`.
  // TuyaSmartBleMeshDelegate
- (void)bleMeshReceiveRawData:(NSString *)raw;

Parameters

Parameter Description
raw The value of Raw type.
success The success callback.
failure The failure callback.

API description

Records the operation in the cloud after the verification and continues to add the next sub-device.

- (void)addDeviceWithDeviceId:(NSString *)deviceId success:(TYSuccessHandler)success failure:(TYFailureError)failure;

Parameters

Parameter Description
success The success callback.
failure The failure callback.

Example

- (void)addDeviceToGroup:(TuyaSmartDeviceModel *)model {
        int nodeId = [model.nodeId intValue] << 8;
        // Records the IP address of the current device for future use.
        _address = nodeId >> 8;

        if ([TYBLEMeshManager sharedInstance].isLogin) {
            // Bluetooth LE
            [[TYBLEMeshManager sharedInstance] addDeviceAddress:nodeId type:self.meshGroup.meshGroupModel.pcc groupAddress:[self.meshGroup.meshGroupModel.localId intValue]];
        } else {
            // Wi-Fi
            [[TuyaSmartUser sharedInstance].mesh publishRawDataWithRaw:[[TYBLEMeshManager sharedInstance] rawDataAddDeviceAddress:nodeId groupAddress:[self.meshGroup.meshGroupModel.localId intValue] type:self.meshGroup.meshGroupModel.pcc] pcc:self.meshGroup.meshGroupModel.pcc success:^{
            } failure:^(NSError *error) {
            }];
        }

        // The current operation is flagged as adding a device.
        _isAdd = YES;

    // Customizes a timeout value. After this timeout period, the failure callback is executed and the system continues to add the next device. Recommended value: `5`. Unit: seconds.
}

#pragma mark - TYBLEMeshManagerDelegate
- (void)deviceAddGroupAddress:(uint32_t)address; {
    NSLog(@" --- deviceAddGroupAddress %d ", address);

    if (_address == address) {

            [self.meshGroup addDeviceWithDeviceId:_devId success:^{
                // Proceeds to add the next device after the success callback.
            } failure:^(NSError *error) {

            }];
    }
}

#pragma mark - TuyaSmartBleMeshDelegate

// Adds sub-devices that are connected through a gateway to a mesh group.
- (void)bleMeshReceiveRawData:(NSString *)raw {
    if ([[raw substringWithRange:NSMakeRange(4, 2)] isEqualToString:@"d4"] && _address == [TPUtils getIntValueByHex:[raw substringWithRange:NSMakeRange(0, 2)]]) {

        if (raw.length < 14) {
            NSLog(@"Length error of raw data.");
            return;
        }

        BOOL isNewProtocol = [TPUtils getIntValueByHex:[raw substringWithRange:NSMakeRange(10, 2)]] == 255;

        if (isNewProtocol) {
            int state = [TPUtils getIntValueByHex:[raw substringWithRange:NSMakeRange(12, 2)]];

            if (state == 1 || state == 255) {
                NSLog(@"The device is added to the group.");
            } else {
                   // Proceeds to add the next device after the failure callback.
                return;
            }

        }

            [self.meshGroup addDeviceWithDeviceId:_devId success:^{
                // Proceeds to add the next device after the success callback.
            } failure:^(NSError *error) {
            }];
    }
}

Remove sub-devices from a group

Similar to the addition process, before a sub-device can be removed from a mesh group, it must be verified both locally and in the cloud. Multiple sub-devices must be removed one by one from the mesh group. They cannot be removed concurrently in the same task.

Process

Tuya Mesh

API description

// Locally-connected sub-device.
// The result is returned by `TYBLEMeshManagerDelegate`.
- (void)deleteDeviceAddress:(uint32_t)deviceAddress type:(NSString *)type groupAddress:(uint32_t)groupAddress;

// TYBLEMeshManagerDelegate
- (void)deviceAddGroupAddress:(uint32_t)address error:(NSError *)error;

// Sub-device connected through a gateway.
// Queries the command of Raw type to remove a sub-device from a mesh group.
- (NSString *)rawDataDeleteDeviceAddress:(uint32_t)deviceAddress groupAddress:(uint32_t)groupAddress type:(NSString *)type;

API description

- (void)publishRawDataWithRaw:(NSString *)raw
                          pcc:(NSString *)pcc
                      success:(TYSuccessHandler)success
                      failure:(TYFailureError)failure;

// The result is returned by ``TuyaSmartBleMeshDelegate` - (void)bleMeshReceiveRawData:(NSString *)raw`.
// TuyaSmartBleMeshDelegate
- (void)bleMeshReceiveRawData:(NSString *)raw;

Parameters

Parameter Description
raw The value of Raw type.
success The success callback.
failure The failure callback.

API description

Records the operation in the cloud after the verification and continues to add the next sub-device.

- (void)removeDeviceWithDeviceId:(NSString *)deviceId success:(TYSuccessHandler)success failure:(TYFailureError)failure;

Parameters

Parameter Description
deviceId The device ID.
success The success callback.
failure The failure callback.

Example

- (void)deleteDeviceFromGroup:(TuyaSmartDeviceModel *)model {

        int nodeId = [model.nodeId intValue] << 8;

        // Records the IP address of the current device for future use.
        _address = nodeId >> 8;
        if ([TYBLEMeshManager sharedInstance].isLogin) {
            // Bluetooth LE
            [[TYBLEMeshManager sharedInstance] deleteDeviceAddress:nodeId type:self.meshGroup.meshGroupModel.pcc groupAddress:[self.meshGroup.meshGroupModel.localId intValue]];
        } else {
            // Wi-Fi
            [[TuyaSmartUser sharedInstance].mesh publishRawDataWithRaw:[[TYBLEMeshManager sharedInstance] rawDataDeleteDeviceAddress:nodeId groupAddress:[self.meshGroup.meshGroupModel.localId intValue] type:self.meshGroup.meshGroupModel.pcc] pcc:self.meshGroup.meshGroupModel.pcc success:^{
            } failure:^(NSError *error) {
            }];
        }

        // The current operation is flagged as removing a device.
        _isAdd = NO;

    // Customizes a timeout value. After this timeout period, the failure callback is executed and the system continues to add the next device. Recommended value: `5`. Unit: seconds.
}

#pragma mark - TYBLEMeshManagerDelegate
- (void)deviceAddGroupAddress:(uint32_t)address; {
    NSLog(@" --- deviceAddGroupAddress %d ", address);

    if (_address == address) {

            [self.meshGroup removeDeviceWithDeviceId:_devId success:^{
                // Proceeds to add the next device after the success callback.
            } failure:^(NSError *error) {
            }];
    }
}

#pragma mark - TuyaSmartBleMeshDelegate

// Adds sub-devices that are connected through a gateway to a mesh group.
- (void)bleMeshReceiveRawData:(NSString *)raw {
    if ([[raw substringWithRange:NSMakeRange(4, 2)] isEqualToString:@"d4"] && _address == [TPUtils getIntValueByHex:[raw substringWithRange:NSMakeRange(0, 2)]]) {

        if (raw.length < 14) {
            NSLog(@"Length error of raw data.");
            return;
        }

        BOOL isNewProtocol = [TPUtils getIntValueByHex:[raw substringWithRange:NSMakeRange(10, 2)]] == 255;

        if (isNewProtocol) {
            int state = [TPUtils getIntValueByHex:[raw substringWithRange:NSMakeRange(12, 2)]];

            if (state == 1 || state == 255) {
                NSLog(@"The device is added to the group.");
            } else {
                   // Proceeds to add the next device after the failure callback.
                return;
            }

        }

            [self.meshGroup removeDeviceWithDeviceId:_devId success:^{
                // Proceeds to remove the next device after the success callback.
            } failure:^(NSError *error) {
            }];
    }
}

Query a mesh group instance

API description

+ (instancetype)meshGroupWithGroupId:(NSInteger)groupId;

Parameters

Parameter Description
groupId The group ID.

groupId is different from localId. It is the group ID returned from the cloud after the group is created. All group operations require the address indicated by localId, rather than the group ID.

Rename a mesh group

API description

- (void)updateMeshGroupName:(NSString *)meshGroupName success:(TYSuccessHandler)success failure:(TYFailureError)failure;

Parameters

Parameter Description
meshGroupName The name of the mesh group.
success The success callback.
failure The failure callback.

Delete a mesh group

Deletes a mesh group locally or from the cloud, in a similar way like removing a device.

API description

// Locally remove the device.
- (void)deleteGroupAddress:(uint32_t)groupAddress type:(NSString *)type;

// Sub-device connected through a gateway.
- (NSString *)rawDataDeleteGroupAddress:(uint32_t)groupAddress type:(NSString *)type

API description

// Sends commands of Raw type to the device.
- (void)publishRawDataWithRaw:(NSString *)raw
                          pcc:(NSString *)pcc
                      success:(TYSuccessHandler)success
                      failure:(TYFailureError)failure;

Parameters

Parameter Description
raw The value of Raw type.
success The success callback.
failure The failure callback.

API description

// Removes the device from the cloud.
- (void)removeMeshGroupWithSuccess:(TYSuccessHandler)success failure:(TYFailureError)failure;

Parameters

Parameter Description
success The success callback.
failure The failure callback.

Example

[self.meshGroup removeMeshGroupWithSuccess:^{
		// The success callback.
} failure:^(NSError *error) {
	// The failure callback.
}];

// Locally-connected sub-device.
if ([TYBLEMeshManager sharedInstance].isLogin) {

	// Removes a group over Bluetooth.
	[[TYBLEMeshManager sharedInstance] deleteGroupAddress:[self.meshGroup.meshGroupModel.localId intValue] type:self.meshGroup.meshGroupModel.pcc];
} else {
	// Wi-Fi
	// Removes a group through a gateway.
	[[TuyaSmartUser sharedInstance].mesh publishRawDataWithRaw:[[TYBLEMeshManager sharedInstance] rawDataDeleteGroupAddress:[self.meshGroup.meshGroupModel.localId intValue] type:self.meshGroup.meshGroupModel.pcc] pcc:self.meshGroup.meshGroupModel.pcc success:^{
	} failure:^(NSError *error) {
	}];
}

Query a mesh group device

API description

- (void)getDeviveListInfoWithSuccess:(void (^)(NSArray <TuyaSmartDeviceModel *> *deviceList))success failure:(TYFailureError)failure;

Example

[self.meshGroup getDeviveListInfoWithSuccess:^(NSArray<TuyaSmartDeviceModel *> *deviceList) {
        // The success callback.
} failure:^(NSError *error) {
            // The failure callback.
        }];

Control

Smart devices are managed with DPs. Tuya mesh devices are also controlled by device DPs.

Mesh commands carry DP data when they are sent to target devices.

Command format

DPs are sent to control devices in the following format: {"(dpId)" : "(dpValue)"}. Example: @{@"101" : @"44"}. For more information about DPs, see Device Control.

Send DPs to control a device

API description

- (void)publishNodeId:(NSString *)nodeId
                  pcc:(NSString *)pcc
                  dps:(NSDictionary *)dps
              success:(TYSuccessHandler)success
              failure:(TYFailureError)failure;

Parameters

Parameter Description
nodeId The short address of a Bluetooth sub-device.
pcc The product category and type.
dps The DPs in the dictionary format.
success The success callback.
failure The failure callback.

Example

int address = [[self.smartDevice deviceModel].nodeId intValue] << 8;

[self.mesh publishNodeId:[NSString stringWithFormat:@"%d", address] pcc:self.smartDevice.deviceModel.pcc dps:@{@"1":@(1)} success:^{
    // success do
    } failure:^(NSError *error) {
    // error do
}];

Send DPs to control a group

API description

- (void)multiPublishWithLocalId:(NSString *)localId
                            pcc:(NSString *)pcc
                            dps:(NSDictionary *)dps
                        success:(TYSuccessHandler)success
                        failure:(TYFailureError)failure;

Parameters

Parameter Description
localId localId
pcc The product category and type.
dps The DPs in the dictionary format.
success The success callback.
failure The failure callback.

Example

int address = [[self.meshGroup meshGroupModel].localId intValue];

[self.mesh multiPublishWithLocalId:[NSString stringWithFormat:@"%d", address] pcc:self.meshGroup.meshGroupModel.pcc dps:@{@"1":@(1)} success:^{
    // success do
    } failure:^(NSError *error) {
    // error do
}];

Send data of Raw type

TYBLEMeshManager provides commands to send data of Raw type.

Sends commands of Raw type to devices

API description

- (void)publishRawDataWithRaw:(NSString *)raw
                          pcc:(NSString *)pcc
                      success:(TYSuccessHandler)success
                      failure:(TYFailureError)failure;

Parameters

Parameter Description
raw The value of Raw type.
success The success callback.
failure The failure callback.

Update device data

Updates device data. The device response is returned by the delegate TuyaSmartHomeDelegate.

API description

// Updates DP data.
- (void)home:(TuyaSmartHome *)home device:(TuyaSmartDeviceModel *)device dpsUpdate:(NSDictionary *)dps;

Update

Get firmware update information

API description

- (void)getFirmwareUpgradeInfo:(void (^)(NSArray <TuyaSmartFirmwareUpgradeModel *> *upgradeModelList))success failure:(TYFailureError)failure;

/**
The update information is returned in the response. You can check the `type` field to determine whether an update is required. Valid values:
     `0`: updating
     `1`: no update available
     `2`: forced update or update notification
     `3`: check for updates

If an update is required, the firmware address is included in the response. The firmware can be downloaded and converted into firmware data for subsequent operations.
*/

Update sub-devices

Before the update, make sure that the target device has been connected over Bluetooth.

  • To run only a pairing task, enter the default mesh name and password. Then, only
    - (void)bleMeshManager:(TYBLEMeshManager *)manager didScanedDevice:(TYBleMeshDeviceModel *)device; of TYBLEMeshManagerDelegate returns the scanning result.

  • To connect a paired device to a mesh network, enter the name and password of the created mesh network. The data is returned by cloud-based API methods. Then, the paired device is automatically connected to the mesh network. The system also automatically queries the online status of each device once on the mesh network.

API description

- (void)startScanWithName:(NSString *)name
                      pwd:(NSString *)pwd
                   active:(BOOL)active
              wifiAddress:(uint32_t)wifiAddress
               otaAddress:(uint32_t)otaAddress;

Parameters

Parameter Description
name The name of the mesh network.
pwd The password of the mesh network.
active Specifies whether to pair and activate a device.
wifiAddress The Wi-Fi address. This parameter is required for pairing a gateway and set to 0 for other types of devices.
otaAddress The IP address of the OTA update device. This parameter is required for OTA update and set to 0 for other types of devices.

The pairing result will be returned by TYBLEMeshManagerDelegate.

API description

Connects to the mesh network to enable the update.

- (void)notifyLoginSuccessWithAddress:(uint32_t)address;

Parameters

Parameter Description
address The IP address of the device.

Send update package after callback

- (void)sendOTAPackWithAddress:(NSInteger)address version:(NSString *)version otaData:(NSData *)otaData success:(TYSuccessHandler)success failure:(TYFailureHandler)failure;

Parameters

Parameter Description
address The IP address of the device.
version The version number.
otaData The update data.
success The success callback.
failure The failure callback.

Update version number in the cloud

- (void)updateDeviceVersion:(NSString *)version type:(NSInteger)type success:(TYSuccessHandler)success failure:(TYFailureError)failure;

Parameters

Parameter Description
version The version number.
type The type of firmware.
success The success callback.
failure The failure callback.

Example

1. Prepare for the update.
int otaAddress = [self.device.deviceModel.nodeId intValue] << 8;
// Connected without a gateway.
    [[TYBLEMeshManager sharedInstance] startScanWithName:[TuyaSmartUser sharedInstance].meshModel.code pwd:[TuyaSmartUser sharedInstance].meshModel.password active:NO wifiAddress:0 otaAddress:otaAddress];
    [TYBLEMeshManager sharedInstance].delegate = self;

2. Receive the callback and send the update package.
- (void)notifyLoginSuccessWithAddress:(uint32_t)address {
    [[TYBLEMeshManager sharedInstance] sendOTAPackWithAddress:address version:@"Target version number" otaData:_otaData success:^{
        [self updateVersion];
    } failure:^{
        NSLog(@"ota failure!");
    }];
}

3. Update the version number in the cloud.
- (void)updateVersion {
    WEAKSELF_AT
    [self.smartDevice updateDeviceVersion:_upgradeModel.version type:_upgradeModel.type success:^{
       // success do..
    } failure:^(NSError *error) {
       // error do..
    }];
}

Update light format in smart scenes

Before the update, make sure that the firmware supports smart scenes.

Scenes 1 to 4 are the static color mode. Update Scene 1:

{set_scene1="0ff808000000000E0"}

`0`: the static color mode
`ff`: R
`80`: G
`80`: B
`00`: W, warm
`00`: C, cold
`00`: L, brightness
`00`: S, step (set to `0`)
`E0`: V, the validity of `RGBWCLS`. `RGB` validity is `E0` and `WCL` validity is `1C`.

Scenes 5 to 8 are the dazzling mode. Update Scene 5:

{set_scene5="180ff560055AA0055AA"}

`1`: the dazzling mode
`80`: L, brightness of `HLS`
`ff`: S, saturation of `HLS`
`56`: the binary value `01010110`. Higher 5 bits indicate the gradient time=10 (unit: 200 ms). It represents the real time 10 × 200 ms = 2s. Lower 3 bits indicate the number of gradient groups=6 groups.
`00`, `55`, `AA`, `00`, `55`, and `AA`: H, hue of `HLS`, 6 groups
Based on the values of `L` and `S`, as well as `H` for each group, the RGB values of six groups are calculated.

0 c7 ed cc c8 37 64 00 e0

Start a scene and send `null` to query the values for the scene.

{set_scene1=null}

Switch to white: 109 = "white"
Switch to color: send the `rgb` command or `109 = "colour"`.

Switch to Scene 1: 109 = "scene_1"
Switch to Scene 2: 109 = "scene_2"
Switch to Scene 3: 109 = "scene_3"
...
Switch to Scene 8: 109 = "scene_8"

Set Scenes 1 to 8: sequentially send DPs 111 to 118.
For example, to set Scene 5: 115 = "0f19ec27f806400e0"
The format follows the previously mentioned DP format.