Skip to content

Commit

Permalink
Switch to using zcl_struct_items_by_struct_and_cluster_name in templa…
Browse files Browse the repository at this point in the history
…tes. (#26226)

Our existing uses of zcl_struct_items_by_struct_name were broken if two
different clusters used structs with the same name: we would end up enumerating
all the struct fields from both structs in a bunch of places.

The fix is to use zcl_struct_items_by_struct_and_cluster_name, which takes as
input the struct name _and_ the cluster name.

No visible codegen changes for now, because we have no such name collisions so
far, due to it leading to incorrect codegen.  Instead we have been working
around it by having our naming not match the spec.

This required a few changes other than just the change of helper:

1. The valueEquals in chip-tool did not use to take a cluster name.  That needed
   to be added, and threaded through the call-chain from the place where a
   cluster name is available, as well as through the recursive invocations of
   valueEquals.
2. In the java codegen, the cluster name being passed in to encode_value and
   decode_value was the already-upper-camel-cased version, which does not work
   as input to zcl_struct_items_by_struct_and_cluster_name.  Callsites were
   changed to pass in the raw cluster name, and actual uses of the name were
   changed to asUpperCamelCase as needed.
3. While testing, using actual name collisions, a bug was found in the Python
   codegen: the id of the command being processed was being used when the id of
   the cluster was intended.
  • Loading branch information
bzbarsky-apple authored and pull[bot] committed Jul 21, 2023
1 parent ff4cacb commit f13d740
Show file tree
Hide file tree
Showing 20 changed files with 51 additions and 51 deletions.
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
{{~#if hasExpectedValue}}
{{~>valueEquals actual=(asPropertyValue dontUnwrapValue=true) label=(asLowerCamelCase name) expected=expectedValue depth=0~}}
{{~>valueEquals actual=(asPropertyValue dontUnwrapValue=true) label=(asLowerCamelCase name) expected=expectedValue cluster=cluster depth=0~}}
{{~/if~}}
Original file line number Diff line number Diff line change
Expand Up @@ -29,11 +29,11 @@
{{else}}
{{#if_is_struct type}}

{{#zcl_struct_items_by_struct_name type}}
{{#zcl_struct_items_by_struct_and_cluster_name type ns}}
{{#if_include_struct_item_value ../definedValue name}}
{{>commandValue ns=parent.ns container=(concat parent.container "." (asLowerCamelCase label)) definedValue=(lookup ../definedValue name) depth=(incrementDepth ../depth)}}
{{/if_include_struct_item_value}}
{{/zcl_struct_items_by_struct_name}}
{{/zcl_struct_items_by_struct_and_cluster_name}}

{{else}}
{{container}} =
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ switch(mTestSubStepIndex)
{{asDecodableType}} value;
VerifyOrReturn(CheckDecodeValue(chip::app::DataModel::Decode(*data, value)));
{{#chip_tests_item_response_parameters}}
{{>maybeCheckExpectedValue}}
{{>maybeCheckExpectedValue cluster=../cluster}}
{{>maybeCheckExpectedConstraints}}
{{>maybeSaveAs}}
{{/chip_tests_item_response_parameters}}
Expand Down
18 changes: 9 additions & 9 deletions examples/chip-tool/templates/tests/partials/value_equals.zapt
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{{#if isOptional}}
VerifyOrReturn(CheckValuePresent("{{label}}", {{actual}}));
{{>valueEquals label=(concat label ".Value()") actual=(concat actual ".Value()") expected=expected isOptional=false depth=(incrementDepth depth)}}
{{>valueEquals label=(concat label ".Value()") actual=(concat actual ".Value()") expected=expected isOptional=false cluster=cluster depth=(incrementDepth depth)}}
{{else if isNullable}}
{{#if (isLiteralNull expected)}}
VerifyOrReturn(CheckValueNull("{{label}}", {{actual}}));
Expand All @@ -14,15 +14,15 @@
else
{
VerifyOrReturn(CheckValueNonNull("{{label}}", {{actual}}));
{{>valueEquals label=(concat label ".Value()") actual=(concat actual ".Value()") expected=(concat expected ".Value()") isNullable=false keepAsExpected=true depth=(incrementDepth depth)}}
{{>valueEquals label=(concat label ".Value()") actual=(concat actual ".Value()") expected=(concat expected ".Value()") isNullable=false keepAsExpected=true cluster=cluster depth=(incrementDepth depth)}}
}
{{else}}
VerifyOrReturn(CheckValueNonNull("{{label}}", {{actual}}));
{{>valueEquals label=(concat label ".Value()") actual=(concat actual ".Value()") expected=expected isNullable=false keepAsExpected=true depth=(incrementDepth depth)}}
{{>valueEquals label=(concat label ".Value()") actual=(concat actual ".Value()") expected=expected isNullable=false keepAsExpected=true cluster=cluster depth=(incrementDepth depth)}}
{{/if}}
{{else}}
VerifyOrReturn(CheckValueNonNull("{{label}}", {{actual}}));
{{>valueEquals label=(concat label ".Value()") actual=(concat actual ".Value()") expected=expected isNullable=false depth=(incrementDepth depth)}}
{{>valueEquals label=(concat label ".Value()") actual=(concat actual ".Value()") expected=expected isNullable=false cluster=cluster depth=(incrementDepth depth)}}
{{/if}}
{{/if}}
{{else if isArray}}
Expand All @@ -31,26 +31,26 @@
auto iter_{{depth}} = {{actual}}.begin();
{{#each expected}}
VerifyOrReturn(CheckNextListItemDecodes<decltype({{../actual}})>("{{../label}}", iter_{{../depth}}, {{@index}}));
{{>valueEquals label=(concat ../label "[" @index "]") actual=(concat "iter_" ../depth ".GetValue()") expected=this isArray=false type=../type chipType=../chipType depth=(incrementDepth ../depth) parent=../parent}}
{{>valueEquals label=(concat ../label "[" @index "]") actual=(concat "iter_" ../depth ".GetValue()") expected=this isArray=false type=../type chipType=../chipType cluster=../cluster depth=(incrementDepth ../depth) parent=../parent}}
{{/each}}
VerifyOrReturn(CheckNoMoreListItems<decltype({{actual}})>("{{label}}", iter_{{depth}}, {{expected.length}}));
}
{{else if isEvent}}
{{#zcl_events_fields_by_event_name type}}
{{#if (hasProperty ../expected label)}}
{{>valueEquals label=(concat ../label "." (asLowerCamelCase label)) actual=(concat ../actual "." (asLowerCamelCase label)) expected=(lookup ../expected label) depth=(incrementDepth ../depth)}}
{{>valueEquals label=(concat ../label "." (asLowerCamelCase label)) actual=(concat ../actual "." (asLowerCamelCase label)) expected=(lookup ../expected label) cluster=../cluster depth=(incrementDepth ../depth)}}
{{/if}}
{{/zcl_events_fields_by_event_name}}
{{else}}
{{#if_is_struct type}}
{{! Iterate over the actual types in the struct, so we pick up the right
type/optionality/nullability information for them for our recursive
call. }}
{{#zcl_struct_items_by_struct_name type}}
{{#zcl_struct_items_by_struct_and_cluster_name type cluster}}
{{#if (hasProperty ../expected label)}}
{{>valueEquals label=(concat ../label "." (asLowerCamelCase label)) actual=(concat ../actual "." (asLowerCamelCase label)) expected=(lookup ../expected label) depth=(incrementDepth ../depth)}}
{{>valueEquals label=(concat ../label "." (asLowerCamelCase label)) actual=(concat ../actual "." (asLowerCamelCase label)) expected=(lookup ../expected label) cluster=../cluster depth=(incrementDepth ../depth)}}
{{/if}}
{{/zcl_struct_items_by_struct_name}}
{{/zcl_struct_items_by_struct_and_cluster_name}}
{{! Maybe we should add a check for properties in the expected object (other
than "global") that are not present in the struct ? }}
{{else}}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,9 @@
{{else}}
{{#if_is_struct type}}
{{target}} = [{{asObjectiveCClass type cluster forceNotList=true}} new];
{{#zcl_struct_items_by_struct_name type}}
{{#zcl_struct_items_by_struct_and_cluster_name type cluster}}
{{>decodable_value target=(concat ../target "." (asStructPropertyName label)) source=(concat ../source "." (asLowerCamelCase label)) cluster=../cluster depth=(incrementDepth ../depth) }}
{{/zcl_struct_items_by_struct_name}}
{{/zcl_struct_items_by_struct_and_cluster_name}}
{{else}}
{{#if_is_strongly_typed_chip_enum type}}
{{target}} = [NSNumber numberWith{{asObjectiveCNumberType "" type false}}:chip::to_underlying({{source}})];
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,11 @@
{{! Iterate over the actual types in the struct, so we pick up the right
type/optionality/nullability information for them for our recursive
call. }}
{{#zcl_struct_items_by_struct_name type}}
{{#zcl_struct_items_by_struct_and_cluster_name type cluster}}
{{#if (hasProperty ../expected label)}}
{{>check_test_value actual=(concat "((MTR" (asUpperCamelCase ../cluster) "Cluster" (asUpperCamelCase ../type) " *)" ../actual ")." (asStructPropertyName label)) expected=(lookup ../expected label) cluster=../cluster}}
{{/if}}
{{/zcl_struct_items_by_struct_name}}
{{/zcl_struct_items_by_struct_and_cluster_name}}
{{! Maybe we should add a check for properties in the expected object (other
than "global") that are not present in the struct ? }}
{{else}}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,14 +19,14 @@
{{else}}
{{#if_is_struct type}}
{{target}} = [[MTR{{asUpperCamelCase cluster}}Cluster{{asUpperCamelCase type}} alloc] init];
{{#zcl_struct_items_by_struct_name type}}
{{#zcl_struct_items_by_struct_and_cluster_name type cluster}}
{{#if_include_struct_item_value ../definedValue name}}
{{! target may be some place where we lost type information (e.g. an
id), so add explicit cast when trying to assign to our
properties. }}
{{>test_value target=(concat "((MTR" (asUpperCamelCase ../cluster) "Cluster" (asUpperCamelCase ../type) " *)" ../target ")." (asStructPropertyName label)) definedValue=(lookup ../definedValue name) cluster=../cluster depth=(incrementDepth ../depth)}}
{{/if_include_struct_item_value}}
{{/zcl_struct_items_by_struct_name}}
{{/zcl_struct_items_by_struct_and_cluster_name}}

{{else}}
{{target}} =
Expand Down
2 changes: 1 addition & 1 deletion integrations/docker/images/chip-cert-bins/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ ARG COMMITHASH=7b99e6399c6069037c613782d78132c69b9dcabb
# ZAP Development install, so that it runs on both x64 and arm64
# Generally this should match with the ZAP version that is used for codegen within the
# specified SHA
ARG ZAP_VERSION=v2023.04.18-nightly
ARG ZAP_VERSION=v2023.04.21-nightly

# Ensure TARGETPLATFORM is set
RUN case ${TARGETPLATFORM} in \
Expand Down
2 changes: 1 addition & 1 deletion scripts/setup/zap.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
"mac-arm64",
"windows-amd64"
],
"tags": ["version:2@v2023.04.18-nightly.1"]
"tags": ["version:2@v2023.04.21-nightly.1"]
}
]
}
2 changes: 1 addition & 1 deletion scripts/tools/zap/zap_execution.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@
# Use scripts/tools/zap/version_update.py to manage ZAP versioning as many
# files may need updating for versions
#
MIN_ZAP_VERSION = '2023.4.18'
MIN_ZAP_VERSION = '2023.4.21'


class ZapTool:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ jobject DecodeAttributeValue(const app::ConcreteAttributePath & aPath, TLV::TLVR
{
return nullptr;
}
{{>decode_value target="value" source="cppValue" cluster=(asUpperCamelCase parent.name) depth=0 earlyReturn="nullptr"}}
{{>decode_value target="value" source="cppValue" cluster=parent.name depth=0 earlyReturn="nullptr"}}
return value;
}
{{/zcl_attributes_server}}
Expand Down
2 changes: 1 addition & 1 deletion src/controller/java/templates/CHIPClustersWrite-JNI.zapt
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ JNI_METHOD(void, {{asUpperCamelCase ../name}}Cluster, write{{asUpperCamelCase na
std::vector<Platform::UniquePtr<JniByteArray>> cleanupByteArrays;
std::vector<Platform::UniquePtr<JniUtfString>> cleanupStrings;

{{>encode_value target="cppValue" source="value" cluster=(asUpperCamelCase parent.name) depth=0}}
{{>encode_value target="cppValue" source="value" cluster=parent.name depth=0}}

std::unique_ptr<CHIPDefaultSuccessCallback, void (*)(CHIPDefaultSuccessCallback *)> onSuccess(Platform::New<CHIPDefaultSuccessCallback>(callback), Platform::Delete<CHIPDefaultSuccessCallback>);
VerifyOrReturn(onSuccess.get() != nullptr, chip::AndroidClusterExceptions::GetInstance().ReturnIllegalStateException(env, callback, "Error creating native success callback", CHIP_ERROR_NO_MEMORY));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ jobject DecodeEventValue(const app::ConcreteEventPath & aPath, TLV::TLVReader &
return nullptr;
}
{{#zcl_event_fields}}
{{>decode_value target=(concat "value_" (asLowerCamelCase name)) source=(concat "cppValue." (asLowerCamelCase name)) cluster=(asUpperCamelCase parent.parent.name) depth=0 earlyReturn="nullptr"}}
{{>decode_value target=(concat "value_" (asLowerCamelCase name)) source=(concat "cppValue." (asLowerCamelCase name)) cluster=parent.parent.name depth=0 earlyReturn="nullptr"}}

{{/zcl_event_fields}}
jclass {{asLowerCamelCase name}}StructClass;
Expand Down
2 changes: 1 addition & 1 deletion src/controller/java/templates/CHIPInvokeCallbacks-src.zapt
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ void CHIP{{asUpperCamelCase parent.name}}Cluster{{asUpperCamelCase name}}Callbac
VerifyOrReturn(err == CHIP_NO_ERROR, ChipLogError(Zcl, "Error invoking Java callback: %s", ErrorStr(err)));

{{#zcl_command_arguments}}
{{>decode_value source=(concat "dataResponse." (asLowerCamelCase name)) target=(asSymbol label) cluster=(asUpperCamelCase parent.parent.name) depth=0}}
{{>decode_value source=(concat "dataResponse." (asLowerCamelCase name)) target=(asSymbol label) cluster=parent.parent.name depth=0}}
{{/zcl_command_arguments}}

env->CallVoidMethod(javaCallbackRef, javaMethod{{#zcl_command_arguments}}, {{asSymbol label}}{{/zcl_command_arguments}});
Expand Down
4 changes: 2 additions & 2 deletions src/controller/java/templates/CHIPReadCallbacks-src.zapt
Original file line number Diff line number Diff line change
Expand Up @@ -139,7 +139,7 @@ void CHIP{{asUpperCamelCase parent.name}}{{asUpperCamelCase name}}AttributeCallb
err = chip::JniReferences::GetInstance().FindMethod(env, javaCallbackRef, "onSuccess", "(Ljava/util/List;)V", &javaMethod);
VerifyOrReturn(err == CHIP_NO_ERROR, ChipLogError(Zcl, "Could not find onSuccess() method"));

{{>decode_value source="list" target="arrayListObj" cluster=(asUpperCamelCase parent.name) depth=0}}
{{>decode_value source="list" target="arrayListObj" cluster=parent.name depth=0}}

env->ExceptionClear();
env->CallVoidMethod(javaCallbackRef, javaMethod, arrayListObj);
Expand All @@ -165,7 +165,7 @@ void CHIP{{asUpperCamelCase parent.name}}{{asUpperCamelCase name}}AttributeCallb
err = chip::JniReferences::GetInstance().FindMethod(env, javaCallbackRef, "onSuccess", "({{#if isArray}}{{else if isStruct}}{{else if isOptional}}Ljava/util/Optional;{{else if (isOctetString type)}}[B{{else if (isCharString type)}}Ljava/lang/String;{{else}}{{asJniSignatureBasic type true}}{{/if}})V", &javaMethod);
VerifyOrReturn(err == CHIP_NO_ERROR, ChipLogError(Zcl, "Could not find onSuccess() method"));

{{>decode_value source="value" target="javaValue" cluster=(asUpperCamelCase parent.name) depth=0}}
{{>decode_value source="value" target="javaValue" cluster=parent.name depth=0}}

env->CallVoidMethod(javaCallbackRef, javaMethod, javaValue);
}
Expand Down
24 changes: 12 additions & 12 deletions src/controller/java/templates/partials/decode_value.zapt
Original file line number Diff line number Diff line change
Expand Up @@ -27,32 +27,32 @@ if ({{source}}.IsNull()) {
}
{{else}}
{{#if_is_struct type}}
{{#zcl_struct_items_by_struct_name type}}
{{#zcl_struct_items_by_struct_and_cluster_name type cluster}}
{{>decode_value target=(concat ../target "_" (asLowerCamelCase label)) source=(concat ../source "." (asLowerCamelCase label)) cluster=../cluster depth=(incrementDepth ../depth) omitDeclaration=false earlyReturn=../earlyReturn}}
{{/zcl_struct_items_by_struct_name}}
{{/zcl_struct_items_by_struct_and_cluster_name}}

jclass {{asLowerCamelCase type}}StructClass_{{depth}};
err = chip::JniReferences::GetInstance().GetClassRef(env, "chip/devicecontroller/ChipStructs${{cluster}}Cluster{{asUpperCamelCase type}}", {{asLowerCamelCase type}}StructClass_{{depth}});
err = chip::JniReferences::GetInstance().GetClassRef(env, "chip/devicecontroller/ChipStructs${{asUpperCamelCase cluster}}Cluster{{asUpperCamelCase type}}", {{asLowerCamelCase type}}StructClass_{{depth}});
if (err != CHIP_NO_ERROR) {
ChipLogError(Zcl, "Could not find class ChipStructs${{cluster}}Cluster{{asUpperCamelCase type}}");
ChipLogError(Zcl, "Could not find class ChipStructs${{asUpperCamelCase cluster}}Cluster{{asUpperCamelCase type}}");
return {{earlyReturn}};
}
jmethodID {{asLowerCamelCase type}}StructCtor_{{depth}} = env->GetMethodID({{asLowerCamelCase type}}StructClass_{{depth}}, "<init>"
, "({{#zcl_struct_items_by_struct_name type}}{{asJniSignature type null ../cluster true}}{{/zcl_struct_items_by_struct_name}})V");
, "({{#zcl_struct_items_by_struct_and_cluster_name type cluster}}{{asJniSignature type null (asUpperCamelCase ../cluster) true}}{{/zcl_struct_items_by_struct_and_cluster_name}})V");
if ({{asLowerCamelCase type}}StructCtor_{{depth}} == nullptr) {
ChipLogError(Zcl, "Could not find ChipStructs${{cluster}}Cluster{{asUpperCamelCase type}} constructor");
ChipLogError(Zcl, "Could not find ChipStructs${{asUpperCamelCase cluster}}Cluster{{asUpperCamelCase type}} constructor");
return {{earlyReturn}};
}

{{target}} = env->NewObject({{asLowerCamelCase type}}StructClass_{{depth}}, {{asLowerCamelCase type}}StructCtor_{{depth}}
{{#zcl_struct_items_by_struct_name type}}
{{#zcl_struct_items_by_struct_and_cluster_name type cluster}}
, {{../target}}_{{asLowerCamelCase label}}
{{/zcl_struct_items_by_struct_name}}
{{/zcl_struct_items_by_struct_and_cluster_name}}
);
{{else}}
{{#if_is_strongly_typed_chip_enum type}}
std::string {{target}}ClassName = "{{asJniClassName type null cluster}}";
std::string {{target}}CtorSignature = "({{asJniSignature type null cluster false}})V";
std::string {{target}}ClassName = "{{asJniClassName type null (asUpperCamelCase cluster)}}";
std::string {{target}}CtorSignature = "({{asJniSignature type null (asUpperCamelCase cluster) false}})V";
chip::JniReferences::GetInstance().CreateBoxedObject<{{asUnderlyingBasicType type}}>({{target}}ClassName.c_str(), {{target}}CtorSignature.c_str(), static_cast<{{asUnderlyingBasicType type}}>({{source}}), {{target}});
{{else}}
{{#if (isOctetString type)}}
Expand All @@ -62,8 +62,8 @@ if ({{source}}.IsNull()) {
{{else if (isCharString type)}}
LogErrorOnFailure(chip::JniReferences::GetInstance().CharToStringUTF({{source}}, {{target}}));
{{else}}
std::string {{target}}ClassName = "{{asJniClassName type null cluster}}";
std::string {{target}}CtorSignature = "({{asJniSignature type null cluster false}})V";
std::string {{target}}ClassName = "{{asJniClassName type null (asUpperCamelCase cluster)}}";
std::string {{target}}CtorSignature = "({{asJniSignature type null (asUpperCamelCase cluster) false}})V";
{{#if_is_strongly_typed_bitmap type}}
chip::JniReferences::GetInstance().CreateBoxedObject<{{asUnderlyingBasicType type}}>({{target}}ClassName.c_str(), {{target}}CtorSignature.c_str(), {{source}}.Raw(), {{target}});
{{else}}
Expand Down
6 changes: 3 additions & 3 deletions src/controller/java/templates/partials/encode_value.zapt
Original file line number Diff line number Diff line change
Expand Up @@ -42,11 +42,11 @@
{{target}} = cleanupStrings.back()->charSpan();
{{else}}
{{#if_is_struct type}}
{{#zcl_struct_items_by_struct_name type}}
{{#zcl_struct_items_by_struct_and_cluster_name type cluster}}
jobject {{../source}}_{{asLowerCamelCase label}}Item_{{../depth}};
chip::JniReferences::GetInstance().GetObjectField({{../source}}, "{{asLowerCamelCase label}}", "{{asJniSignature type null ../cluster true}}", {{../source}}_{{asLowerCamelCase label}}Item_{{../depth}});
chip::JniReferences::GetInstance().GetObjectField({{../source}}, "{{asLowerCamelCase label}}", "{{asJniSignature type null (asUpperCamelCase ../cluster) true}}", {{../source}}_{{asLowerCamelCase label}}Item_{{../depth}});
{{>encode_value target=(concat ../target "." (asLowerCamelCase label)) source=(concat ../source "_" (asLowerCamelCase label) "Item_" ../depth) cluster=../cluster depth=(incrementDepth ../depth)}}
{{/zcl_struct_items_by_struct_name}}
{{/zcl_struct_items_by_struct_and_cluster_name}}
{{else}}
{{#if_chip_enum type}}
{{target}} = static_cast<std::remove_reference_t<decltype({{target}})>>(chip::JniReferences::GetInstance().{{asJavaType type null parent.parent.name forceNotList=true}}ToPrimitive({{source}}));
Expand Down
8 changes: 4 additions & 4 deletions src/controller/python/templates/python-CHIPClusters-py.zapt
Original file line number Diff line number Diff line change
Expand Up @@ -27,11 +27,11 @@ class ChipClusters:
"args": {
{{#zcl_command_arguments}}
{{#if_is_struct type}}
{{#zcl_struct_items_by_struct_name type}}
"{{asLowerCamelCase label}}": "{{#if (isCharString type)}}str{{else}}{{as_underlying_python_zcl_type type ../../id}}{{/if}}",
{{/zcl_struct_items_by_struct_name}}
{{#zcl_struct_items_by_struct_and_cluster_name type ../../name}}
"{{asLowerCamelCase label}}": "{{#if (isCharString type)}}str{{else}}{{as_underlying_python_zcl_type type ../../../id}}{{/if}}",
{{/zcl_struct_items_by_struct_and_cluster_name}}
{{else}}
"{{asLowerCamelCase label}}": "{{#if (isCharString type)}}str{{else}}{{as_underlying_python_zcl_type type ../id}}{{/if}}",
"{{asLowerCamelCase label}}": "{{#if (isCharString type)}}str{{else}}{{as_underlying_python_zcl_type type ../../id}}{{/if}}",
{{/if_is_struct}}
{{/zcl_command_arguments}}
},
Expand Down
Loading

0 comments on commit f13d740

Please sign in to comment.