Files
kkelomatic_home/docs/redesign/structure-redesign-analysis.md
nearxos bf7bd56fe7 Initial commit: Home automation docs and CODESYS project
- Reorganized project: codesys/, docs/codesys|redesign|integration|reference/, scripts/
- CODESYS project and exports in codesys/
- Documentation index in docs/README.md
- Redesign and light naming configuration
- Water boiler control and safety design

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-02-07 21:52:46 +02:00

13 KiB
Raw Blame History

Room/Light Structure Redesign Analysis

Current Structure Analysis

Current Organization

Room-Centric Approach:

  • 15 rooms, each with 1 fb_switch instance
  • Each room controls up to 6 lights
  • Network variables organized by room name
  • Structure: l_masterBedroom.l_1, l_masterBedroom.l_2, etc.

Current Data Flow:

Room → fb_switch → 6 lights
Network Variable: l_masterBedroom (struct_lights with l_1 to l_6)

Current Issues

  1. Limited Scalability

    • Fixed 6 lights per room
    • Adding a 7th light requires structure changes
    • Some rooms may only need 1-2 lights (waste)
  2. Home Assistant Organization

    • HA entities: light.master_bedroom_l1, light.master_bedroom_l2
    • Not intuitive - hard to find lights
    • No grouping by function or zone
  3. Network Variable Efficiency

    • 15 room structures × 6 lights = 90 potential lights
    • Most rooms don't use all 6 lights
    • Wasted network bandwidth
  4. Maintenance Complexity

    • Changes require updating room structures
    • Hard to add new rooms
    • No clear naming convention
  5. MQTT Topic Structure

    • Topics like: homeassistant/light/master_bedroom_l1
    • Not standardized
    • Hard to discover and manage

Alternative Structures

Concept: All lights in a single flat structure, organized by unique IDs.

Data Structure:

TYPE struct_light :
STRUCT
    // Control
    on: BOOL;           // Turn ON command
    off: BOOL;          // Turn OFF command
    toggle: BOOL;       // Toggle command (for Zigbee)
    
    // Status
    state: BOOL;        // Current state
    relay_status: BOOL; // Actual relay status
    
    // Metadata (for reference, not in network var)
    room: STRING;       // Room name
    name: STRING;       // Light name
    zone: STRING;       // Zone (indoor/outdoor)
END_STRUCT
END_TYPE

TYPE struct_all_lights :
STRUCT
    // Master Bedroom
    master_bedroom_main: struct_light;
    master_bedroom_bedside: struct_light;
    master_bedroom_closet: struct_light;
    
    // Kitchen
    kitchen_ceiling: struct_light;
    kitchen_under_cabinet: struct_light;
    kitchen_island: struct_light;
    
    // Living Room
    living_room_main: struct_light;
    living_room_reading: struct_light;
    living_room_tv: struct_light;
    
    // Outdoor
    outdoor_front_porch: struct_light;
    outdoor_back_patio: struct_light;
    outdoor_side: struct_light;
    
    // ... all other lights
END_STRUCT
END_TYPE

Network Variable:

VAR_GLOBAL
    lights: struct_all_lights;  // All lights in one structure
END_VAR

Function Block:

FUNCTION_BLOCK fb_lightControl
VAR_INPUT
    light: struct_light;
    relay_output: BOOL;  // Direct relay output
END_VAR
VAR_OUTPUT
    relay_control: BOOL;
    light_status: struct_light;
END_VAR
// Implementation...
END_FUNCTION_BLOCK

Pros:

  • Each light is independent
  • Easy to add/remove lights
  • Clear naming: lights.kitchen_ceiling.on
  • Better for Home Assistant (one entity per light)
  • No wasted space
  • Easy to group in HA by room/zone

Cons:

  • ⚠️ Larger structure (but more efficient overall)
  • ⚠️ Need to update structure when adding lights

Home Assistant Organization:

light.kitchen_ceiling
light.kitchen_under_cabinet
light.master_bedroom_main
light.master_bedroom_bedside

MQTT Topics:

homeassistant/light/kitchen_ceiling/state
homeassistant/light/kitchen_ceiling/set
homeassistant/light/master_bedroom_main/state

Option 2: Hierarchical Room → Light Structure

Concept: Keep room structure but make it more flexible.

Data Structure:

TYPE struct_room :
STRUCT
    room_id: STRING;           // "master_bedroom"
    room_name: STRING;         // "Master Bedroom"
    zone: STRING;              // "indoor", "outdoor"
    
    // Flexible light array (up to 10 lights)
    lights: ARRAY[1..10] OF struct_light;
    light_count: INT;           // Actual number of lights
END_STRUCT
END_TYPE

TYPE struct_home :
STRUCT
    rooms: ARRAY[1..20] OF struct_room;
    room_count: INT;
END_STRUCT
END_TYPE

Pros:

  • Maintains room grouping
  • Flexible number of lights per room
  • Can add rooms easily

Cons:

  • ⚠️ More complex array handling
  • ⚠️ CODESYS arrays less efficient for network vars
  • ⚠️ Harder to access specific lights

Option 3: Zone-Based Structure

Concept: Organize by functional zones rather than rooms.

Data Structure:

TYPE struct_zone :
STRUCT
    zone_id: STRING;           // "indoor_main", "outdoor_security"
    zone_name: STRING;          // "Indoor Main", "Outdoor Security"
    
    // Lights in this zone
    lights: ARRAY[1..20] OF struct_light;
    light_count: INT;
END_STRUCT
END_TYPE

TYPE struct_home_zones :
STRUCT
    indoor_main: struct_zone;
    indoor_bedrooms: struct_zone;
    indoor_bathrooms: struct_zone;
    outdoor_security: struct_zone;
    outdoor_ambient: struct_zone;
END_STRUCT
END_TYPE

Zones:

  • Indoor Main: Kitchen, Living Room, Dining Room, Hallway
  • Indoor Bedrooms: All bedrooms
  • Indoor Bathrooms: All bathrooms
  • Outdoor Security: Front, Back, Side (security-focused)
  • Outdoor Ambient: Veranda, Patio (ambient lighting)

Pros:

  • Logical grouping for automation
  • Easy to control all security lights
  • Better for scheduling (indoor vs outdoor)

Cons:

  • ⚠️ Less intuitive for room-based control
  • ⚠️ Lights may belong to multiple zones conceptually

Option 4: Hybrid: Room + Light ID Structure (Best Balance)

Concept: Combine room organization with individual light control.

Data Structure:

TYPE struct_light_control :
STRUCT
    // Control
    on: BOOL;
    off: BOOL;
    toggle: BOOL;
    
    // Status
    state: BOOL;
    relay_status: BOOL;
    
    // Metadata (for HA, not in network var)
    light_id: STRING;      // Unique ID: "mb_main", "kit_ceiling"
    light_name: STRING;     // Display name: "Main Light", "Ceiling Light"
    room: STRING;           // Room: "master_bedroom", "kitchen"
    zone: STRING;           // Zone: "indoor", "outdoor"
    function: STRING;       // Function: "main", "task", "ambient", "security"
END_STRUCT
END_TYPE

// Organized by room for CODESYS, but flat for HA
TYPE struct_rooms :
STRUCT
    // Master Bedroom
    master_bedroom: STRUCT
        main: struct_light_control;
        bedside_left: struct_light_control;
        bedside_right: struct_light_control;
        closet: struct_light_control;
    END_STRUCT;
    
    // Kitchen
    kitchen: STRUCT
        ceiling: struct_light_control;
        under_cabinet: struct_light_control;
        island: struct_light_control;
    END_STRUCT;
    
    // ... other rooms
END_STRUCT
END_TYPE

Network Variable:

VAR_GLOBAL
    rooms: struct_rooms;  // Organized by room
END_VAR

Access Pattern:

  • CODESYS: rooms.kitchen.ceiling.on
  • Node-RED: Flatten to kitchen_ceiling for HA
  • Home Assistant: light.kitchen_ceiling

Pros:

  • Best of both worlds
  • Organized in CODESYS (by room)
  • Flat in Home Assistant (by light)
  • Easy to add lights to rooms
  • Clear naming convention

Cons:

  • ⚠️ Requires Node-RED transformation
  • ⚠️ Slightly more complex

Implementation

1. CODESYS Structure (Room-organized):

TYPE struct_light_control :
STRUCT
    on: BOOL;
    off: BOOL;
    toggle: BOOL;
    state: BOOL;
    relay_status: BOOL;
END_STRUCT
END_TYPE

TYPE struct_room_lights :
STRUCT
    main: struct_light_control;
    secondary: struct_light_control;
    task: struct_light_control;
    ambient: struct_light_control;
    accent: struct_light_control;
    security: struct_light_control;
END_STRUCT
END_TYPE

VAR_GLOBAL
    rooms: STRUCT
        master_bedroom: struct_room_lights;
        master_bathroom: struct_room_lights;
        bedroom_1: struct_room_lights;
        bedroom_2: struct_room_lights;
        bathroom: struct_room_lights;
        kitchen: struct_room_lights;
        living_room: struct_room_lights;
        dining_room: struct_room_lights;
        hallway: struct_room_lights;
        pantry: struct_room_lights;
        entrance: struct_room_lights;
        guest_wc: struct_room_lights;
        outdoor_veranda: struct_room_lights;
        outdoor_front: struct_room_lights;
        outdoor_side: struct_room_lights;
        outdoor_back: struct_room_lights;
    END_STRUCT;
END_VAR

2. Node-RED Transformation (Flatten for HA):

// Transform CODESYS structure to flat HA structure
function transformToHA(msg) {
    const rooms = msg.payload.rooms;
    const haLights = {};
    
    // Flatten structure
    for (const [roomName, roomLights] of Object.entries(rooms)) {
        for (const [lightName, lightControl] of Object.entries(roomLights)) {
            const lightId = `${roomName}_${lightName}`;
            haLights[lightId] = {
                on: lightControl.on,
                off: lightControl.off,
                state: lightControl.state,
                status: lightControl.relay_status,
                room: roomName,
                light: lightName
            };
        }
    }
    
    return { payload: haLights };
}

3. Home Assistant Configuration:

# Auto-discovery via MQTT
light:
  - platform: mqtt
    name: "Kitchen Main"
    unique_id: "kitchen_main"
    state_topic: "homeassistant/light/kitchen_main/state"
    command_topic: "homeassistant/light/kitchen_main/set"
    # ... config

4. MQTT Topic Structure:

homeassistant/light/{room}_{light}/state
homeassistant/light/{room}_{light}/set

Examples:
homeassistant/light/kitchen_main/state
homeassistant/light/master_bedroom_main/state
homeassistant/light/outdoor_front_security/state

Comparison Matrix

Aspect Current Option 1 (Flat) Option 2 (Hierarchical) Option 3 (Zone) Option 4 (Hybrid)
CODESYS Organization Room-based Flat Array-based Zone-based Room-based
HA Organization Room-based Flat Complex Zone-based Flat (transformed)
Scalability Poor Excellent Good Good Excellent
Maintainability Medium Excellent Medium Medium Excellent
Network Efficiency Poor Good Medium Medium Good
Naming Clarity Medium Excellent Medium Good Excellent
Implementation Complexity Low Medium High Medium Medium
Flexibility Low High High Medium High

Optimization Recommendations

1. Network Variable Optimization

Current: 15 rooms × 6 lights = 90 potential lights Optimized: Only include lights that exist

Example:

// Only define lights that exist
master_bedroom: STRUCT
    main: struct_light_control;
    bedside: struct_light_control;
    // No closet light if it doesn't exist
END_STRUCT;

2. Function-Based Naming

Instead of l_1, l_2, use descriptive names:

  • main - Main/primary light
  • secondary - Secondary light
  • task - Task lighting
  • ambient - Ambient/atmospheric
  • accent - Accent lighting
  • security - Security/outdoor

3. Metadata for Home Assistant

Add metadata structure (not in network var, but in Node-RED):

const lightMetadata = {
    "kitchen_main": {
        name: "Kitchen Main Light",
        room: "Kitchen",
        zone: "indoor",
        function: "main",
        icon: "mdi:ceiling-light"
    },
    // ... more lights
};

4. Grouping in Home Assistant

Use HA groups and areas:

# Automatically group by room
light:
  - platform: group
    name: "Kitchen Lights"
    entities:
      - light.kitchen_main
      - light.kitchen_under_cabinet
      - light.kitchen_island

# Use areas for room organization
areas:
  - name: "Kitchen"
    entities:
      - light.kitchen_main
      - light.kitchen_under_cabinet

Migration Strategy

Phase 1: Structure Redesign

  1. Define new data structures
  2. Create mapping from old to new
  3. Update function blocks

Phase 2: Node-RED Update

  1. Update network variable mapping
  2. Add transformation functions
  3. Update MQTT topics

Phase 3: Home Assistant Migration

  1. Create new entities with new structure
  2. Migrate automations
  3. Update dashboards

Phase 4: Testing & Validation

  1. Test all control paths
  2. Verify status feedback
  3. Test HA integration

Final Recommendation

Use Option 4 (Hybrid Structure) because:

  1. Best Organization: Room-based in CODESYS, flat in HA
  2. Scalability: Easy to add lights to any room
  3. Clarity: Descriptive names (kitchen_main vs l_1)
  4. Flexibility: Can group by room, zone, or function
  5. Efficiency: Only define lights that exist
  6. Maintainability: Clear structure, easy to understand

Key Improvements:

  • Replace l_1, l_2 with main, secondary, task, etc.
  • Use descriptive light IDs: kitchen_main, master_bedroom_bedside
  • Flatten structure in Node-RED for Home Assistant
  • Add metadata for better HA organization
  • Optimize network variables (only existing lights)

Next Steps:

  1. Review this analysis
  2. Choose structure option
  3. Plan migration
  4. Implement new structure
  5. Update Node-RED and HA