{% include 'menu.html' %}

{{ title }}


{% macro kb_link(doc) -%} {% if doc %} {% if doc is string %} 📚 KB {% elif doc is iterable %} {% for url in doc %} 📚 KB {% endfor %} {% endif %} {% endif %} {%- endmacro %} {% set non_cert_text = "NOT READY FOR CERTIFICATION" %} {% set unsterile_run_warning = "Unsterile run mode is set - a certifying run must be sterile." %}
1
Flavor
2
Schema
3
Modules
4
Tests
5
Review
{% with messages = get_flashed_messages(with_categories=true) %} {% if messages %} {% for category, message in messages %} {% endfor %} {% endif %} {% endwith %} {% if error %} {% endif %} {% if warning %} {% endif %}
{% if step_num == 1 %}

Step 1: Select Certification Flavor

Choose the type of certification you want to run.

Mandatory Module: Cloud Connectivity
Tests gateway's BLE scans & MQTT data uploads capabilities.

Mandatory Module: Edge Management
Requires at least one additional module beyond the mandatory Edge Management module.

Mandatory Modules: Cloud Connectivity + Edge Management
Requires at least one additional bridge module beyond the mandatory Edge Management module.
Tests both gateway and bridge capabilities.

{% elif step_num == 2 %}

Step 2: Upload Validation Schema

Upload the JSON validation schema file for your device. 📚 KB

Select a JSON validation schema file that matches your selected flavor.
{% if flavor == 'bridge_only' or flavor == 'combo' %}
{% set api_version_field_name = cert_schema.title ~ '_api_version' %} {% set api_version_field = cert_schema.fields | selectattr('name', 'equalto', 'api_version') | first %} {% set api_version_value = form_data.get(api_version_field_name, api_version_field.default if api_version_field and api_version_field.default is not none else '') %}
Bridge API version (required for bridge and combo flavors).
{% endif %} {% if schema_path %}
Schema uploaded: {{ schema_path.split('/')[-1] }}
{% endif %} {% elif step_num == 3 %}

Step 3: Select Modules

Select the modules you want to test. Mandatory modules are pre-selected.

{% if flavor == 'bridge_only' %}
Note: Bridge only requires at least one additional module beyond the mandatory Edge Management module.
{% elif flavor == 'combo' %}
Note: Combo requires at least one additional bridge module beyond the mandatory Edge Management module.
{% endif %} {% for mod in filtered_modules %} {% set is_mandatory = mod.is_mandatory | default(False) %} {% set is_selected = mod.name in selected_modules %} {% set has_selections = selected_modules|length > 0 %} {% set mod_doc = None %} {% if mod.tests and mod.tests|length > 0 %} {% for test in mod.tests %} {% if test.meta.documentation and not mod_doc %} {% set mod_doc = test.meta.documentation %} {% endif %} {% endfor %} {% endif %}

{{ mod.tests|length }} test(s) available

{% endfor %} {% elif step_num == 4 %}

Step 4: Select Tests

Select the specific tests to run. Mandatory tests are pre-selected and cannot be deselected.

{% for mod in filtered_modules %} {% if mod.name in selected_modules %} {% set mod_id = 'mod_' ~ mod.name|replace('/', '_') %}
{{ mod.name }} ({{ mod.tests|length }} tests)
{% for t in mod.tests %} {% set test_id = 'test_' ~ t.id|replace('/','_') %} {% set is_mandatory = t.meta.mandatory | default(0) == 1 %} {% set is_selected = t.id in selected_tests %} {% set has_selections = selected_tests|length > 0 %} {% set tip_id = 'tip_' ~ t.id|replace('/','_') %} {% set test_doc = t.meta.documentation %}
{% if t.tooltip %}
{{ t.tooltip }}
{% endif %}
{# Test parameters #} {% set params_list = t.meta.allSupportedValues | default([]) %} {% if params_list %} {% set has_dynamic = "dynamic_parameters" in params_list %} {% if has_dynamic %} {# Use params_list[1] as default if it exists, otherwise "1" #} {% if params_list|length > 1 %} {% set default_value = params_list[1] %} {% else %} {% set default_value = "1" %} {% endif %} {# Check if value exists in form_data (for restoring saved values) #} {% set dynamic_param_name = "params_" ~ t.id|replace('/','_') ~ "_dynamic" %} {% set saved_value = form_data.get(dynamic_param_name, default_value) %} {% endif %}
{% if has_dynamic %}
Dynamic Parameter
{# Dynamic parameter: integer input #}
{% else %}
Parameters
{# Regular parameters: checkboxes #}
{% for p in params_list %} {% set pid = test_id ~ '_p_' ~ loop.index %}
{% endfor %}
{% endif %}
{% endif %}
{% endfor %}
{% endif %} {% endfor %} {% set cert_schema = cert_schema %}

Run Parameters

{% set common_parameters = ['dut', 'gw_api_version', 'custom_broker', 'max_output_power', 'dual_polarization_antenna'] %} {% if flavor in ['gw_only', 'combo'] %} {% set primary_parameters = ['dut', 'gw_api_version', 'max_output_power', 'dual_polarization_antenna'] %} {% else %} {% set primary_parameters = ['dut', 'max_output_power', 'dual_polarization_antenna'] %} {% endif %} {% for param_name in primary_parameters %} {% for f in cert_schema.fields %} {% if f.name != 'validation_schema' and f.name != 'tl' and f.name != 'custom_broker' and f.name == param_name %} {% set is_signal_indicator_field = f.name == 'max_output_power' or f.name == 'dual_polarization_antenna' %} {% set arg_label = (f.option_strings|join(', ') if f.option_strings else f.name) %} {% set tip_id = 'help_' ~ f.name %} {% set field_name = cert_schema.title ~ '_' ~ f.name %} {% if f.is_flag %} {# For flags, check if explicitly set in form_data #} {# Empty string means unchecked, "on" means checked, None means use default #} {% set field_value = form_data.get(field_name) %} {% if field_value is none %} {# Not in form_data, use default #} {% set field_value = f.default if f.default is not none else True %} {% else %} {# In form_data: "on" or truthy = checked, empty string = unchecked #} {% set field_value = field_value if field_value else False %} {% endif %} {% else %} {% set field_value = form_data.get(field_name, f.default if f.default is not none else '') %} {% endif %} {% endif %} {% endfor %} {% endfor %} {% set cert_schema = cert_schema %} {% set broker_field_prefix = cert_schema.title ~ '_custom_broker_' %}
Custom MQTT Broker Configuration *
{% for field_key, field_default in custom_broker_defaults.items() %} {% set field_name = broker_field_prefix ~ field_key %} {% set field_value = form_data.get(field_name, field_default) %} {% set input_type = 'number' if field_key == 'port' else 'password' if field_key == 'password' else 'text' %} {% set is_required = field_key not in ['username', 'password'] %}
{% if field_key in custom_broker_help.keys() %}
{{ custom_broker_help[field_key] }}
{% endif %}
{% endfor %}
Advanced Parameters
{% for f in cert_schema.fields %} {% if f.name != 'validation_schema' and f.name != 'tl' and f.name != 'api_version' and f.name not in common_parameters %} {% set arg_label = (f.option_strings|join(', ') if f.option_strings else f.name) %} {% set tip_id = 'help_' ~ f.name %} {% set field_name = cert_schema.title ~ '_' ~ f.name %} {% set field_value = form_data.get(field_name, f.default if f.default is not none else '') %}
{% if f.widget == "select" %}
{% elif f.is_flag %}
{% elif f.name == "port" %}
{% else %}
{% endif %} {% if f.help or f.help_link %}
{{ f.help }} {% if f.help_link %} Knowledge Base {% endif %}
{% endif %}
{% endif %} {% endfor %}
{% elif step_num == 5 %}

Step 5: Review and Run

Configuration Summary

Flavor: {% if flavor == 'gw_only' %}Gateway Only {% elif flavor == 'bridge_only' %}Bridge Only {% elif flavor == 'combo' %}Combo (Gateway + Bridge) {% endif %}

Validation Schema: {{ schema_path.split('/')[-1] if schema_path else 'Not uploaded' }}

Selected Modules: {{ selected_modules|join(', ') }}

Selected Tests: {{ total_test_count }} test(s)

Certification Status: {% if is_certified %} READY FOR CERTIFICATION All mandatory modules and tests are selected {% else %} {{ non_cert_text }} {% if not unsterile_run %} Some mandatory modules or tests are missing {% endif %} {% endif %}

{% if unsterile_run %}
⚠️ Warning: {{ unsterile_run_warning }}
{% endif %} {% if not is_certified %} {% if missing_modules %}
Missing Mandatory Modules:
    {% for mod in missing_modules %}
  • {{ mod }}
  • {% endfor %}
{% endif %} {% if missing_additional_module %}
Missing Additional Module:
    {% if flavor == 'bridge_only' %}
  • Bridge Only requires at least one additional module beyond the mandatory module (edge_mgmt)
  • {% elif flavor == 'combo' %}
  • Combo requires at least one additional bridge module beyond the mandatory modules (cloud_connectivity and edge_mgmt)
  • {% endif %}
{% endif %} {% if missing_tests_details %}
Missing Mandatory Tests from Selected Modules:
    {% for test in missing_tests_details %}
  • {{ test.label }} ({{ test.module }})
  • {% endfor %}
When a module is selected, its mandatory tests must also be selected.
{% endif %} {% endif %}
Schema Verification
{% if schema_errors or schema_warnings or missing_modules_by_schema %}

Schema Status: SCHEMA DOES NOT MATCH RUN SETTINGS

{% if schema_errors %}
Errors:
    {% for err in schema_errors %}
  • {{ err }}
  • {% endfor %}
{% endif %} {% if schema_warnings %}
Warnings:
    {% for warn in schema_warnings %}
  • {{ warn }}
  • {% endfor %}
{% endif %} {% if missing_modules_by_schema %}
Missing Modules Mandatory by Schema:
    {% for mod in missing_modules_by_schema %}
  • {{ mod }}
  • {% endfor %}
These modules are declared in your validation schema but are not selected. They should be included for proper certification.
{% endif %} {% else %}

Schema Status: SCHEMA MATCHES RUN SETTINGS The uploaded schema matches the selected flavor, modules, and tests

{% endif %}

Need to make changes?

Edit Flavor Edit Schema {% if flavor != 'gw_only' %} Edit Modules {% endif %} Edit Tests
{% endif %}
{% if step_num > 1 %} {% else %}
{% endif %} {% if step_num < 5 %} {% else %}
{% endif %}
{% if step_num == 1 %}

OR Use Previous Run Settings...

Load Previous Run Settings
Select a previously exported certificate run settings file.
{% endif %}