Custom Test Scenarios¶
Simulate real-world conditions and protocol edge cases
Test scenarios allow you to configure the emulator to simulate various real-world conditions like packet loss, network delays, malformed packets, and more. This is useful for testing how your application handles protocol errors and network unreliability.
Overview¶
Scenarios are organized in a hierarchical structure with automatic precedence resolution:
- Device-specific - Affects single device by serial
- Type-specific - Affects all devices of a type (color, multizone, etc.)
- Location-based - Affects all devices in a location
- Group-based - Affects all devices in a group
- Global - Affects all devices
This allows fine-grained control over which devices experience which conditions.
Quick Start¶
Configure a simple scenario via Python API:
from lifx_emulator import create_color_light
from lifx_emulator.scenarios.manager import ScenarioConfig
device = create_color_light("d073d5000001")
# Drop 30% of GetColor packets
device.scenarios = ScenarioConfig(
drop_packets={"101": 0.3}
)
Or via REST API:
# Set global scenario - drop 100% of GetColor packets
curl -X PUT http://localhost:8080/api/scenarios/global \
-H "Content-Type: application/json" \
-d '{
"drop_packets": {"101": 1.0},
"response_delays": {},
"malformed_packets": [],
"invalid_field_values": [],
"firmware_version": null,
"partial_responses": [],
"send_unhandled": false
}'
Scenario Types¶
Packet Dropping¶
Simulate packet loss by dropping incoming packets:
from lifx_emulator.scenarios.manager import ScenarioConfig
# Drop 100% of GetColor packets
config = ScenarioConfig(drop_packets={"101": 1.0})
# Drop 30% probabilistically
config = ScenarioConfig(drop_packets={"101": 0.3})
# Drop multiple packet types
config = ScenarioConfig(drop_packets={"101": 1.0, "102": 0.5})
Response Delays¶
Add latency to responses to simulate slow networks:
# Add 500ms delay to all GetColor responses
config = ScenarioConfig(response_delays={"101": 0.5})
# Multiple delays
config = ScenarioConfig(response_delays={
"101": 0.5, # GetColor - 500ms
"102": 0.2, # SetColor - 200ms
"116": 1.0, # GetPower - 1000ms
})
Malformed Packets¶
Send corrupted/truncated packets to test error handling:
# Send truncated StateColor packets
config = ScenarioConfig(malformed_packets=[107])
# Multiple packet types
config = ScenarioConfig(malformed_packets=[107, 108, 110])
Invalid Field Values¶
Send packets with invalid field values (all 0xFF bytes):
Partial Responses¶
Send incomplete multizone/tile data:
Firmware Version Override¶
Simulate different firmware versions:
# Simulate older firmware
config = ScenarioConfig(firmware_version=(2, 60))
# Simulate newer firmware
config = ScenarioConfig(firmware_version=(3, 90))
Scenario Scope¶
Global Scenarios¶
Apply to all devices:
from lifx_emulator.scenarios.manager import HierarchicalScenarioManager
manager = HierarchicalScenarioManager()
manager.set_global_scenario(ScenarioConfig(
drop_packets={"101": 1.0}
))
# All devices now drop GetColor packets
Device-Specific Scenarios¶
Target individual devices by serial:
# Only device d073d5000001 experiences delays
manager.set_device_scenario(
"d073d5000001",
ScenarioConfig(response_delays={"101": 0.5})
)
Type-Specific Scenarios¶
Target all devices of a type:
# All color devices drop GetColor packets
manager.set_type_scenario(
"color",
ScenarioConfig(drop_packets={"101": 0.3})
)
# All multizone devices get 500ms delay
manager.set_type_scenario(
"multizone",
ScenarioConfig(response_delays={"502": 0.5})
)
# Supported types: color, multizone, extended_multizone, matrix, hev, infrared, basic
Location-Based Scenarios¶
Target all devices in a location:
# All devices in "Kitchen" experience delays
manager.set_location_scenario(
"Kitchen",
ScenarioConfig(response_delays={"101": 0.2})
)
Group-Based Scenarios¶
Target all devices in a group:
# All devices in "Bedroom Lights" group
manager.set_group_scenario(
"Bedroom Lights",
ScenarioConfig(drop_packets={"101": 0.5})
)
Scenario Precedence¶
When multiple scopes apply, precedence is:
- Device-specific (highest priority)
- Type-specific
- Location-based
- Group-based
- Global (lowest priority)
Example:
manager = HierarchicalScenarioManager()
# Global: drop 100% of GetColor
manager.set_global_scenario(
ScenarioConfig(drop_packets={"101": 1.0})
)
# Type: multizone devices get 500ms delay
manager.set_type_scenario(
"multizone",
ScenarioConfig(response_delays={"502": 0.5})
)
# Device: d073d5000001 drops 50% of SetColor
manager.set_device_scenario(
"d073d5000001",
ScenarioConfig(drop_packets={"102": 0.5})
)
# Result for d073d5000001:
# - Drop 100% of GetColor (from global)
# - Drop 50% of SetColor (from device, overrides global)
# - 500ms delay for packet 502 (from type if multizone)
REST API Examples¶
Full REST API documentation is in the Scenario Management API guide.
Get Current Scenario¶
# Get global scenario
curl http://localhost:8080/api/scenarios/global
# Get scenario for specific device
curl http://localhost:8080/api/scenarios/devices/d073d5000001
# Get scenario for device type
curl http://localhost:8080/api/scenarios/types/multizone
Update Scenarios¶
# Set global scenario
curl -X PUT http://localhost:8080/api/scenarios/global \
-H "Content-Type: application/json" \
-d '{
"drop_packets": {"101": 0.3},
"response_delays": {"101": 0.2},
"malformed_packets": [],
"invalid_field_values": [],
"firmware_version": null,
"partial_responses": [],
"send_unhandled": false
}'
# Set device-specific scenario
curl -X PUT http://localhost:8080/api/scenarios/devices/d073d5000001 \
-H "Content-Type: application/json" \
-d '{
"drop_packets": {"101": 1.0},
"response_delays": {},
"malformed_packets": [],
"invalid_field_values": [],
"firmware_version": [2, 60],
"partial_responses": [],
"send_unhandled": false
}'
Clear Scenarios¶
# Clear global scenario
curl -X DELETE http://localhost:8080/api/scenarios/global
# Clear device scenario
curl -X DELETE http://localhost:8080/api/scenarios/devices/d073d5000001
# Clear type scenario
curl -X DELETE http://localhost:8080/api/scenarios/types/multizone
Practical Testing Patterns¶
Testing Retry Logic¶
# Simulate flaky network - drop 30% of packets
config = ScenarioConfig(drop_packets={"101": 0.3})
# Your client should retry and eventually succeed
Testing Timeout Handling¶
# Add 2 second delay to simulate slow device
config = ScenarioConfig(response_delays={"101": 2.0})
# Test that client timeout is > 2 seconds
Testing Error Recovery¶
# Send malformed responses
config = ScenarioConfig(malformed_packets=[107])
# Test that client handles parse errors gracefully
Testing Firmware Compatibility¶
# Simulate older firmware
config = ScenarioConfig(firmware_version=(2, 60))
# Test client behavior with older firmware
# Simulate newer firmware
config = ScenarioConfig(firmware_version=(3, 90))
# Test client with newer features
Testing Concurrent Operations¶
# Create multiple devices with different scenarios
devices = [
create_color_light("d073d5000001"), # No delays
create_color_light("d073d5000002"), # 500ms delay
create_color_light("d073d5000003"), # Drop packets
]
manager.set_device_scenario(
"d073d5000002",
ScenarioConfig(response_delays={"101": 0.5})
)
manager.set_device_scenario(
"d073d5000003",
ScenarioConfig(drop_packets={"101": 0.5})
)
# Test client behavior with heterogeneous device conditions
Persistent Scenarios¶
Save scenarios across emulator restarts:
Scenarios are saved to ~/.lifx-emulator/scenarios.json.
API Reference¶
For complete API documentation, see:
- Scenario Management API Guide - REST API endpoints
- Testing Scenarios Guide - Configuration details
- Scenario Manager API - Python API
Common Packet Types¶
| Type | ID | Description |
|---|---|---|
| GetColor | 101 | Request device color |
| SetColor | 102 | Set device color |
| GetPower | 116 | Request power state |
| SetPower | 117 | Set power state |
| StateColor | 107 | Color state response |
| StatePower | 118 | Power state response |
| StateMultiZone | 506 | Multizone state |
| ExtendedStateMultiZone | 512 | Extended multizone state |
| Get64 | 514 | Get tile 64 |
| Set64 | 715 | Set tile 64 |
See Protocol Documentation for complete list.
Next Steps¶
- Scenario Management API - REST API reference
- Testing Scenarios Guide - Configuration details
- Integration Testing - Testing patterns