Technical Guide

ดึงข้อมูล Solar ผ่าน Modbus-TCP
จาก Huawei SmartLogger

คู่มือฉบับสมบูรณ์: เชื่อมต่อ SmartLogger3000A → ดึงข้อมูลพลังงานแสงอาทิตย์ → ส่งต่อผ่าน MQTT ครบจบในบทความเดียว

โดย Artron Innovative | มิถุนายน 2569 | อ่าน ~12 นาที

สารบัญ

  1. ภาพรวม — SmartLogger คืออะไร?
  2. สถาปัตยกรรมการเชื่อมต่อ
  3. Hardware Specs ที่ต้องรู้
  4. Register Map — พิกัดข้อมูลทุกตัว
  5. Python Code ดึงข้อมูลจริง
  6. ส่งข้อมูลออก MQTT
  7. ทางเลือก: FusionSolar Northbound API
  8. Troubleshooting ปัญหาที่พบบ่อย

1 ภาพรวม — SmartLogger คืออะไร?

Huawei SmartLogger3000A คือ Data Concentrator สำหรับโรงไฟฟ้าโซลาร์ ทำหน้าที่รวบรวมข้อมูลจาก Inverter, มิเตอร์, และเซ็นเซอร์สภาพอากาศ แล้วเปิดช่องทางให้ระบบภายนอกเข้าถึงได้

รองรับ 80 อุปกรณ์
เชื่อมต่อ Inverter, Smart Meter, Weather Station ได้สูงสุด 80 ตัวต่อ Logger 1 เครื่อง
🔌
หลายช่องทางสื่อสาร
WAN/LAN (GbE), RS485 × 3 พอร์ต, 4G LTE (บางรุ่น) ครอบคลุมทั้ง TCP และ RTU
📊
Aggregate ข้อมูลให้
ไม่ต้อง poll ทีละ Inverter — SmartLogger รวมค่ากำลังไฟ, พลังงาน, สถานะของทั้ง plant ไว้ที่เดียว
💡
ทำไมต้อง Modbus-TCP? — เพราะเป็นโปรโตคอลมาตรฐานอุตสาหกรรมที่ SmartLogger รองรับโดยตรงบน port 502 ไม่ต้องพึ่ง cloud, latency ต่ำ (real-time), และควบคุมได้เต็มที่ว่าจะดึงข้อมูลอะไร เมื่อไหร่

2 สถาปัตยกรรมการเชื่อมต่อ

ข้อมูลไหลจาก SmartLogger ผ่าน 3 ขั้นตอน: Poll → Transform → Publish

Hardware
SmartLogger
Modbus-TCP :502
Middleware
Python Script
pymodbus + paho-mqtt
Transport
MQTT Broker
JSON payload
Destination
Platform
Dashboard / DB

Addressing — ใครเป็นใครบน Modbus

Unit IDอุปกรณ์หมายเหตุ
0SmartLogger (Plant Level)ข้อมูลรวมทั้ง plant — ใช้ตัวนี้เป็นหลัก
1–247Inverter, Meter, EMIอุปกรณ์แต่ละตัวที่ต่อพ่วงผ่าน RS485
⚠️
SmartLogger ≠ SDongle — SDongle ของ Huawei ไม่ forward Modbus-TCP ไปถึง Inverter (ยืนยันจาก Huawei Support) ถ้าต้องการดึงข้อมูลระดับ Inverter ผ่าน Modbus ต้องใช้ SmartLogger เท่านั้น

3 Hardware Specs ที่ต้องรู้

ข้อมูลทางเทคนิคสำคัญของ SmartLogger3000A สำหรับการ integrate

รายการรายละเอียด
Model VariantsA01EU, A03EU (MBUS/PLC), A01CN, A00GL, A01AU
EthernetWAN + LAN — 10/100/1000 Mbps (RJ45)
RS4853 พอร์ต COM — Modbus-RTU / IEC 60870-5-103
Modbus-TCP Port502 (ค่า default)
อุปกรณ์สูงสุด80 ตัว / logger (150 inverters ผ่าน MBUS บนรุ่น A03)
อุณหภูมิใช้งาน-40°C ถึง +60°C
กินไฟ8W (ปกติ) / 15W (สูงสุด)
IP RatingIP20 (ติดตั้งในตู้)

4 Register Map — พิกัดข้อมูลทุกตัว

Register ที่ใช้บ่อยที่สุดสำหรับ monitoring ระดับ Plant (Unit ID = 0)

กำลังผลิตและพลังงาน

RegisterCountชื่อหน่วยScaleType
320642Active Power (รวม plant)kW×0.001I32 (signed)
320662Reactive Power (รวม plant)kVar×0.001I32 (signed)
320782Daily Energy YieldkWh×0.01U32
320802Monthly Energy YieldkWh×0.01U32
320822Annual Energy YieldkWh×0.01U32
320842Total Energy Yield (ตลอดอายุ)kWh×0.01U32

กริดและสถานะ

RegisterCountชื่อหน่วยScaleType
320701Grid FrequencyHz×0.01U16
320711Grid Voltage Phase AV×0.1U16
320721Grid Voltage Phase BV×0.1U16
320731Grid Voltage Phase CV×0.1U16
320742Grid Current Phase AA×0.01I32 (signed)
320762Grid Current Phase BA×0.01I32 (signed)
320861Inverter Count (Online)×1U16
320891Plant Status×1U16
320911Internal Temperature°C×0.1I16 (signed)
📐
วิธีอ่านค่า: ข้อมูล 32-bit (I32/U32) ใช้ 2 registers ติดกัน เรียงแบบ Big-Endian — register แรกเป็น high word, register ที่สองเป็น low word ค่าที่อ่านได้ต้อง คูณ scale factor เช่น register 32064 อ่านได้ 150420 → ×0.001 = 150.42 kW

5 Python Code ดึงข้อมูลจริง

ใช้ pymodbus เชื่อมต่อ SmartLogger ผ่าน Modbus-TCP แล้วอ่านค่า register

ติดตั้ง Dependencies

Terminalbash
pip install pymodbus paho-mqtt

ทดสอบ Modbus Connection

test_modbus.pyPython
from pymodbus.client import ModbusTcpClient

# ===== ตั้งค่า =====
LOGGER_IP = "192.168.1.100"  # เปลี่ยนเป็น IP SmartLogger
PORT       = 502
UNIT_ID    = 1               # SmartLogger aggregate

# Register ที่จะอ่าน: (address, count, name, unit, scale, signed)
REGISTERS = [
    (32064, 2, "Active Power",      "kW",  0.001, True),
    (32078, 2, "Daily Energy",      "kWh", 0.01,  False),
    (32084, 2, "Total Energy",      "kWh", 0.01,  False),
    (32070, 1, "Grid Frequency",    "Hz",  0.01,  False),
    (32071, 1, "Voltage Phase A",   "V",   0.1,   False),
    (32089, 1, "Plant Status",      "",    1,     False),
]

def read_value(client, addr, count, signed):
    result = client.read_holding_registers(addr, count, slave=UNIT_ID)
    if result.isError():
        return None
    if count == 1:
        val = result.registers[0]
        return val - 65536 if signed and val > 32767 else val
    raw = (result.registers[0] << 16) | result.registers[1]
    return raw - 4294967296 if signed and raw > 2147483647 else raw

# ===== Main =====
client = ModbusTcpClient(LOGGER_IP, port=PORT, timeout=5)
if not client.connect():
    print("ERROR: ไม่สามารถเชื่อมต่อ SmartLogger ได้")
    exit(1)

print(f"เชื่อมต่อ {LOGGER_IP}:{PORT} สำเร็จ\n")
for addr, count, name, unit, scale, signed in REGISTERS:
    raw = read_value(client, addr, count, signed)
    if raw is not None:
        print(f"  {name:20s} = {raw * scale:>12.2f} {unit}")
    else:
        print(f"  {name:20s} = ERROR")

client.close()
ผลลัพธ์ตัวอย่าง:
Active Power = 150.42 kW
Daily Energy = 450.20 kWh
Grid Frequency = 50.01 Hz

6 ส่งข้อมูลออก MQTT

เมื่อดึงข้อมูลได้แล้ว ขั้นตอนต่อไปคือแปลงเป็น JSON แล้ว publish ไปยัง MQTT Broker

MQTT Topic Format

Topic PatternMQTT
solar/{building_id}/data

# ตัวอย่าง:
solar/building_1/data
solar/building_2/data

JSON Payload

ตัวอย่าง payloadJSON
{
  "ts": "2026-06-15T10:30:00+07:00",
  "building": "building_1",
  "active_power_kw": 150.42,
  "daily_energy_kwh": 450.20,
  "total_energy_kwh": 125430.80,
  "grid_voltage_a": 230.5,
  "grid_voltage_b": 231.2,
  "grid_voltage_c": 229.8,
  "grid_frequency_hz": 50.01,
  "inverter_online": 5,
  "plant_status": 1
}

Production Script (ย่อ)

mqtt_publish.pyPython
import json, time
from datetime import datetime, timezone, timedelta
from pymodbus.client import ModbusTcpClient
import paho.mqtt.client as mqtt

TZ = timezone(timedelta(hours=7))

# ===== Config =====
LOGGER_IP    = "192.168.1.100"
MQTT_BROKER  = "broker.vekin.tech"
BUILDING     = "building_1"
POLL_INTERVAL = 60  # วินาที

# ===== Connect =====
mb = ModbusTcpClient(LOGGER_IP, port=502, timeout=5)
mq = mqtt.Client(client_id=f"solar-{BUILDING}")
mq.connect(MQTT_BROKER, 1883)
mq.loop_start()
mb.connect()

while True:
    data = poll_all_registers(mb)  # ฟังก์ชันจากตัวอย่างด้านบน
    data["ts"] = datetime.now(TZ).isoformat()
    data["building"] = BUILDING

    mq.publish(f"solar/{BUILDING}/data", json.dumps(data), qos=1)
    print(f"[{data['ts']}] {data['active_power_kw']} kW")
    time.sleep(POLL_INTERVAL)

7 ทางเลือก: FusionSolar Northbound API

นอกจาก Modbus แล้ว Huawei ยังมี Cloud API ให้ดึงข้อมูลผ่าน Internet ได้

Modbus-TCP (Local)
  • ✅ Real-time (≤1 วินาที)
  • ✅ ไม่ต้องพึ่ง Internet
  • ✅ ไม่มี Rate limit
  • ✅ ได้ register ละเอียดทุกตัว
  • ⚠️ ต้องอยู่ใน LAN เดียวกัน
  • ⚠️ ไม่มี encryption
FusionSolar API (Cloud)
  • ✅ เข้าถึงจากที่ไหนก็ได้
  • ✅ HTTPS encrypted
  • ✅ ไม่ต้อง config network
  • ⚠️ ข้อมูลช้า 5-15 นาที
  • ⚠️ Rate limit เข้มงวด
  • ⚠️ ต้องมี Northbound account

FusionSolar API Overview

รายการรายละเอียด
Base URLhttps://{region}.fusionsolar.huawei.com/thirdData/
AuthenticationPOST /thirdData/login → ได้ xsrf-token จาก response header
Real-time Data/thirdData/getStationRealKpi (ข้อมูลทุก 5 นาที)
Device List/thirdData/getDevList → รายชื่อ Inverter, Meter ทั้งหมด
Rate LimitLogin 5 ครั้ง/10 นาที · Data ~1 call/5 นาที · 1 session เท่านั้น
ขอ AccountSystem → Company Management → Northbound Management → Add
🔄
แนะนำ: ใช้ทั้งสองทาง — Modbus-TCP เป็น primary (real-time, low latency) และ FusionSolar API เป็น fallback/validation ในกรณีที่ middleware offline หรือต้อง cross-check ข้อมูลกับ cloud

8 Troubleshooting ปัญหาที่พบบ่อย

ปัญหาที่เจอบ่อยในการเชื่อมต่อ Modbus-TCP กับ SmartLogger และวิธีแก้ไข

🔴
Connection Timeout
เชื่อมต่อไม่ได้เลย — ตรวจสอบ: (1) IP ถูกต้องไหม (2) อยู่ใน VLAN/subnet เดียวกัน (3) เปิด Modbus-TCP ใน WebUI ของ SmartLogger แล้วหรือยัง (Settings → Comm. Param. → Modbus-TCP → Enable)
🟡
Exception 0x02 — Illegal Data Address
Register address ผิด หรือจำนวน count เกินขอบเขต — ตรวจสอบว่า address ตรงกับ firmware version ของ SmartLogger (ดูจาก Interface Definitions document)
🟡
Exception 0x06 — Slave Device Busy
SmartLogger กำลังประมวลผลคำสั่งอื่น — เว้น 10 วินาทีแล้วลองใหม่ อาจเกิดจาก FusionSolar cloud กำลัง sync อยู่
🟡
อ่านค่าได้ แต่เป็น 0 ทั้งหมด
ปกติสำหรับเวลากลางคืน (ไม่มีแสงอาทิตย์) — ตรวจสอบ Plant Status (register 32089): ถ้าเป็น 0 = standby ถ้าเป็น 1 = normal operation
💡
Unit ID Mismatch
ถ้าต้องการข้อมูลรวมทั้ง plant ใช้ Unit ID = 1 (SmartLogger) แต่ถ้าต้องการข้อมูลเฉพาะ Inverter ตัวใดตัวหนึ่ง ต้องเปลี่ยนเป็น ID ของ Inverter นั้น (เช่น 2, 3, 4)
🔒
Security ที่ต้องระวัง
Modbus-TCP ไม่มี encryption หรือ authentication — ใครที่อยู่ใน LAN เดียวกันสามารถอ่าน/เขียน register ได้ทั้งหมด ควร: (1) แยก VLAN สำหรับ OT devices (2) ตั้ง firewall rule เปิด port 502 เฉพาะ IP ของ middleware (3) ไม่เปิดออก Internet โดยตรง