Automação IoT

Carregador de Veículo Elétrico com MQTT: OCPP vs MQTT e Recarga Solar em Casa

O OCPP conecta carregadores a sistemas de back-office, enquanto o MQTT os conecta ao restante da sua casa. Veja como os dois se complementam, qual caminho de integração serve ao seu wallbox e como montar uma recarga guiada pela energia solar sobre MQTT.

Wallbox residencial carregando um carro elétrico com painéis solares e diagrama de fluxo de energia para integração de carregador de veículo elétrico mqtt
Rode isso no seu próprio broker MQTTTenha um broker MQTT privado e gerenciado no plano Free e comece com exemplos de código prontos.
Teste grátis Exemplos de código Sem cartão de crédito

Integrar um carregador de veículo elétrico via MQTT permite que o seu wallbox participe do restante do sistema de energia da casa, por exemplo em uma residência com geração solar distribuída: carregar quando o sol brilha, pausar quando o forno e a bomba de calor estão ligados e mostrar seu status no mesmo painel que todo o resto. Este guia explica como OCPP e MQTT diferem, as três formas práticas de colocar um carregador no MQTT, um projeto de tópicos organizado e um controlador funcional de excedente solar em Python. Ao final, você saberá qual caminho combina com o seu carregador e como construir sobre ele com segurança.

OCPP e MQTT resolvem problemas diferentes

Muita gente pergunta se um carregador deve usar OCPP ou MQTT. Na prática, eles atendem relações diferentes, e uma boa instalação residencial frequentemente usa os dois.

OCPP (Open Charge Point Protocol) é a linguagem padrão entre um carregador e um Charging Station Management System (CSMS), o back-office que cuida de autorização, sessões e cobrança. O OCPP 1.6J e o 2.0.1 trafegam mensagens JSON sobre um WebSocket que o carregador abre até o CSMS. As mensagens incluem BootNotification, StatusNotification, MeterValues, início e fim de transação e SetChargingProfile para recarga inteligente. Cada carregador se conecta a um CSMS por vez.

MQTT é um protocolo publish/subscribe de uso geral. Um carregador ou uma bridge publica seu estado em um broker, e qualquer número de consumidores (painel, Home Assistant, gerenciador de energia, app de celular) assina sem que o carregador precise saber deles. Se o padrão é novo para você, a explicação sobre o que faz um broker MQTT cobre o básico.

Aspecto OCPP MQTT
Finalidade Carregador para back-office: sessões, autorização, cobrança, recarga inteligente Qualquer dispositivo para qualquer número de consumidores
Transporte WebSocket, o carregador se conecta a um CSMS TCP ou WebSocket até um broker, muitos assinantes
Esquema de mensagens Definido rigidamente por versão do OCPP Você projeta tópicos e payloads
Usuário típico Operadores de pontos de recarga, frotas, recarga no trabalho Automação residencial, gestão de energia, painéis
Controle Início/parada remotos, perfis de recarga O que o dispositivo ou a bridge expuser
Múltiplos consumidores Não, um CSMS por conexão Sim, nativamente

Se você opera carregadores públicos ou corporativos, OCPP até um CSMS é o núcleo certo. Se quer que um carregador residencial coopere com painéis solares, baterias e cargas da casa, o MQTT é a camada de integração prática, às vezes alimentada por OCPP nos bastidores.

Três formas de colocar um carregador de veículo elétrico no MQTT

1. MQTT nativo no carregador. Alguns carregadores, especialmente modelos de hardware aberto e voltados a entusiastas, publicam status e aceitam comandos diretamente via MQTT. Você informa host, porta e credenciais do broker na interface web do carregador. É o caminho mais simples quando disponível, mas os nomes de tópicos e os payloads variam de fabricante para fabricante.

2. Um servidor OCPP local que faz bridge para o MQTT. Muitos wallboxes comerciais falam apenas OCPP (além da nuvem do fabricante). Aponte a URL OCPP do carregador para um servidor OCPP local, por exemplo a integração OCPP do Home Assistant ou um CSMS de código aberto, e deixe esse servidor republicar status e medições em MQTT. Você mantém a semântica padrão do OCPP e ganha MQTT para todo o resto. A contrapartida é que os recursos da nuvem do fabricante podem deixar de funcionar enquanto o carregador conversa com o seu servidor.

3. Um gerenciador de energia no meio. Gerenciadores de energia de código aberto, como o evcc, conversam com muitos carregadores por seus protocolos nativos e publicam seu próprio estado em MQTT, incluindo potência da rede, potência fotovoltaica e potência de recarga por ponto de carga, além de aceitar mudanças de modo por tópicos MQTT. Esse costuma ser o caminho mais rápido para a recarga guiada pela energia solar, porque a lógica de controle já está pronta e testada.

Seja qual for o caminho, busque o mesmo resultado no broker: uma árvore de tópicos estável, que não muda se você trocar o carregador.

Projetando a árvore de tópicos MQTT do carregador

Separe estado de comandos, retenha o estado e nunca retenha comandos:

home/ev/charger1/state            retained  {"status":"charging","power_w":7210,"current_a":10.4,"phases":3,"session_kwh":12.8}
home/ev/charger1/status           retained  online / offline (Last Will)
home/ev/charger1/set/current_a    command   6..16
home/ev/charger1/set/enabled      command   true / false
home/energy/grid/telemetry        retained  {"net_w": -2350, ...}

Use valores de status no estilo OCPP (available, preparing, charging, suspended_ev, suspended_evse, finishing, faulted) mesmo quando a origem não for OCPP. Eles são bem conhecidos e distinguem "o carro está cheio" (suspended_ev) de "o carregador pausou" (suspended_evse), o que importa para as automações.

Reter um comando como set/current_a é um erro clássico: depois de uma queda de energia, o carregador ou a bridge se reconecta e executa de novo um valor antigo. Os comandos não devem ser retidos; a bridge publica o valor efetivo de volta no tópico de estado retido.

Um controlador de excedente solar em Python

O controlador abaixo assina o net_w do medidor da rede (negativo significa exportação, como publicado no tutorial de monitor de energia residencial) e o estado do carregador, e publica uma corrente de recarga que acompanha o excedente. Ele funciona com qualquer carregador ou bridge que aceite um setpoint de corrente em um tópico. Teste-o no servidor MQTT público com mensagens simuladas antes de conectar qualquer equipamento real.

pip install "paho-mqtt>=2.0"
import json
import time
import paho.mqtt.client as mqtt

PREFIX = "connectmq/demo/ev7k2"      # use seu próprio prefixo aleatório durante os testes
GRID_TOPIC = f"{PREFIX}/energy/grid/telemetry"
STATE_TOPIC = f"{PREFIX}/ev/charger1/state"
SET_CURRENT = f"{PREFIX}/ev/charger1/set/current_a"
SET_ENABLED = f"{PREFIX}/ev/charger1/set/enabled"

VOLTAGE = 230
PHASES = 1            # defina 3 para um carregador trifásico
MIN_A, MAX_A = 6, 16  # 6 A é a menor corrente na sinalização IEC 61851
START_MARGIN_W = 300  # exportação extra exigida antes de iniciar
UPDATE_EVERY = 30     # segundos entre mudanças de setpoint
STOP_AFTER = 300      # segundos abaixo do mínimo antes de pausar

state = {"net_w": None, "charger_current_a": 0.0, "status": "unknown"}
current_set = 0
below_since = None
last_update = 0.0


def on_connect(client, userdata, flags, reason_code, properties):
    print("Connected:", reason_code)
    client.subscribe(GRID_TOPIC, qos=1)
    client.subscribe(STATE_TOPIC, qos=1)


def on_message(client, userdata, msg):
    data = json.loads(msg.payload)
    if msg.topic == GRID_TOPIC:
        state["net_w"] = data.get("net_w")
    elif msg.topic == STATE_TOPIC:
        state["charger_current_a"] = data.get("current_a", 0.0)
        state["status"] = data.get("status", "unknown")


def control(client):
    global current_set, below_since, last_update
    if state["net_w"] is None or state["status"] in ("available", "faulted", "unknown"):
        return
    if time.time() - last_update < UPDATE_EVERY:
        return
    charger_w = state["charger_current_a"] * VOLTAGE * PHASES
    surplus_w = charger_w - state["net_w"]          # o que poderíamos usar sem importar da rede
    if current_set == 0:
        surplus_w -= START_MARGIN_W
    target = int(surplus_w // (VOLTAGE * PHASES))

    if target >= MIN_A:
        below_since = None
        target = min(target, MAX_A)
        if current_set == 0:
            client.publish(SET_ENABLED, "true", qos=1)
        if target != current_set:
            client.publish(SET_CURRENT, str(target), qos=1)
            print(f"surplus {surplus_w:.0f} W -> {target} A")
            current_set = target
    elif current_set > 0:
        below_since = below_since or time.time()
        if time.time() - below_since > STOP_AFTER:
            client.publish(SET_ENABLED, "false", qos=1)
            print("Not enough surplus, pausing")
            current_set = 0
        elif current_set != MIN_A:
            client.publish(SET_CURRENT, str(MIN_A), qos=1)
            current_set = MIN_A
    last_update = time.time()


client = mqtt.Client(mqtt.CallbackAPIVersion.VERSION2, client_id="ev-surplus-6619")
client.on_connect = on_connect
client.on_message = on_message
client.connect("broker.connectmq.com", 1883, keepalive=60)
client.loop_start()
while True:
    control(client)
    time.sleep(1)

Simule uma tarde ensolarada em outro terminal e veja o controlador reagir:

mosquitto_pub -h broker.connectmq.com -p 1883 -i ev-sim-1 -t "connectmq/demo/ev7k2/ev/charger1/state" -m '{"status":"suspended_evse","current_a":0}'
mosquitto_pub -h broker.connectmq.com -p 1883 -i ev-sim-2 -t "connectmq/demo/ev7k2/energy/grid/telemetry" -m '{"net_w":-2600}'

Com 2.600 W de exportação em uma única fase, o controlador começa em 10 A depois de descontar a margem de partida.

Regras de projeto para controlar o carregador com segurança

O hardware de recarga lida com correntes altas por horas, então seja conservador:

  1. Deixe o carregador impor seus próprios limites. Seu controlador apenas solicita um setpoint; o máximo configurado no carregador e as proteções da instalação devem continuar sendo a autoridade final.
  2. Mude os setpoints devagar. Mudanças frequentes de corrente e ciclos de liga/desliga castigam os contatores e alguns veículos. Um intervalo de atualização de 30 segundos e um atraso de parada de 5 minutos são bons pontos de partida.
  3. Respeite o mínimo de 6 A. Abaixo disso, pause a recarga em vez de solicitar uma corrente inválida.
  4. Trate a troca de fases com cuidado. Alternar entre monofásico e trifásico exige suporte do carregador e nunca deve acontecer com corrente fluindo.
  5. Falhe com segurança. Se o medidor da rede parar de enviar dados, pare de ajustar e volte para um estado fixo ou pausado. Use o status retido do Last Will do medidor para detectar isso.
  6. Nunca controle carregadores por um servidor MQTT público. Qualquer pessoa poderia publicar no seu tópico de comando. A área pública serve apenas para simulação.

Migrando para um broker privado

Quando a simulação se comportar bem, conecte o carregador real ou a bridge e o controlador a um broker privado com TLS e credenciais por cliente. Um broker MQTT gerenciado como a ConnectMQ mantém esse broker no ar sem um servidor para administrar e, como o carregador, o leitor do medidor e o controlador só fazem conexões de saída, nada precisa ser exposto no seu roteador. No portal da ConnectMQ, crie um broker, emita credenciais para cada cliente e conecte na porta 8883:

client = mqtt.Client(mqtt.CallbackAPIVersion.VERSION2, client_id="YOUR_CLIENT_ID")
client.username_pw_set("YOUR_USERNAME", "YOUR_PASSWORD")
client.tls_set()
client.connect("broker.connectmq.com", 8883, keepalive=60)

Em seguida, traga os dados de produção do monitoramento de inversor solar e de armazenamento do monitoramento de bateria residencial para decidir se o carro ou a bateria fica com o excedente primeiro. Com todos esses fluxos no mesmo broker, você tem a base para um gêmeo digital simples da instalação de energia. O guia de automação IoT mostra como esses fluxos de energia se encaixam em uma instalação residencial mais ampla, e o guia de broker MQTT na nuvem ajuda você a escolher onde hospedá-lo.

Conecte seu carregador à ConnectMQ

A ConnectMQ oferece à bridge do seu carregador, ao gerenciador de energia e aos painéis um broker privado com TLS, acesso via WebSocket para apps no navegador e um explorador de tópicos ao vivo para verificar cada mudança de estado. Crie um broker Serverless gratuito em app.connectmq.com, sem cartão de crédito.

Perguntas frequentes

Meu carregador residencial deve usar OCPP ou MQTT?

Use o que o carregador suporta nativamente para a conexão principal e use o MQTT como camada de integração para a automação residencial. Muitas instalações rodam OCPP até um servidor local e republicam em MQTT.

Posso usar OCPP e a nuvem do fabricante ao mesmo tempo?

Normalmente não, porque um carregador se conecta a um único backend OCPP. Apontá-lo para o seu próprio servidor costuma substituir o backend do fabricante, então verifique quais recursos você perderia.

Qual é a corrente mínima de recarga?

A sinalização de control pilot IEC 61851, usada pelos carregadores AC, tem mínimo de 6 A. Abaixo disso, o controlador deve pausar a recarga em vez de reduzir ainda mais a corrente.

Com que rapidez um controlador de excedente deve reagir?

A cada 30 a 60 segundos é um padrão sensato. Reações mais rápidas basicamente perseguem nuvens passageiras e causam acionamentos desnecessários.

Artigos relacionados

Guia de Configuração do Zigbee2MQTT: do Coordenador ao Painel

Instale o Zigbee2MQTT com Docker, configure o coordenador e a conexão MQTT, pareie e renomeie dispositivos, controle-os via MQTT e veja seus estados em um painel, testando primeiro no servidor MQTT público (gratuito).

8 min de leitura

Todos os artigos →

Seu broker MQTT privado está a poucos cliques de distância

Crie uma conta, receba as credenciais do seu broker e conecte seu primeiro dispositivo — sem servidores para instalar, atualizar ou escalar.