I wanted a solid platform to connect MySensors to OpenHab. I struggled getting messages to come back from OpenHab to MySensor with both the serial gateway and the MQTTGateway on 1.5.4. Finally I abandoned that approach and went to MySensors 2.0 MQTTClientGateway > Mosquito > OpenHab and it all works beautifully. I am posting my final setup so that maybe it will help others trying to accomplish the same thing. If I have omitted anything critical please reply and I will try to update this.
Controller
- Raspberry Pi (Jessie)
- Openhab 1.8
- make sure you org.openhab.binding.mqtt-1.8.1.jar in your addons directory
- 192.168.1.101
MQTT Broker
- Mosquito on same Raspberry Pi as OpenHab
- followed steps to install here https://mosquitto.org/2013/01/mosquitto-debian-repository/
- 192.168.1.101 running on port 1883 this needs to be set in both OpenHab.cfg and in GatewayW5100MQTTClient sketch (see below)
MQTT Client Gateway
- Genuine Arduino
- Gikfun Ethernet Shield W5100
- Addicore nRF24L01
- MySensors 2.0 https://github.com/mysensors/Arduino/archive/master.zip
- GatewayW5100MQTTClient from examples folder in zip
MySensors RelayActuator
- Arduino Nano clone
- Addicore nRF24L01
MQTT Client on my iPhone
- This is so useful for getting the messaging correct (both from OpenHab and Sensor)
- MQTT Inspector 1.0 is the one i used
GatewayW5100MQTTClient sketch I didn't change these lines but you need to note them. They form an important part of the message structure that your openhab items will need to subscribe to
// Set this nodes subscripe and publish topic prefix
#define MY_MQTT_PUBLISH_TOPIC_PREFIX "mygateway1-out"
#define MY_MQTT_SUBSCRIBE_TOPIC_PREFIX "mygateway1-in"
It is important to change the lines below so that the MySensors MQTT Client device is on your network and can communicate correctly. Use the same subnet as your other devices. You can get gateway information using ipconfig on windows..
// Enable MY_IP_ADDRESS here if you want a static ip address (no DHCP)
#define MY_IP_ADDRESS 192,168,1,87
// If using static ip you need to define Gateway and Subnet address as well
#define MY_IP_GATEWAY_ADDRESS 192,168,1,1
#define MY_IP_SUBNET_ADDRESS 255,255,255,0
Change these lines to point to your Mosquito MQTT Broker
// MQTT broker ip address or url. Define one or the other.
//#define MY_CONTROLLER_URL_ADDRESS "m20.cloudmqtt.com"
#define MY_CONTROLLER_IP_ADDRESS 192, 168, 1, 101
// The MQTT broker port to to open
#define MY_PORT 1883
openhab.cfg I probably should have called the broker mosquitto instead of mysensor but just note that this is the alias openhab will use to talk to the broker and can be anything you choose
# URL to the MQTT broker, e.g. tcp://localhost:1883 or ssl://localhost:8883
mqtt:mysensor.url=tcp://192.168.1.101:1883
# Optional. Client id (max 23 chars) to use when connecting to the broker.
# If not provided a default one is generated.
mqtt:mysensor.clientId=openhab
1closed0open.map this is in opt/openhab/configurations/transform
1=closed
0=open
mqtt.items
before each message is a symbol. < means openhab is subscribing to this topic. As such topics need to be prefixed with the values in your gateway. If you left the default use mygateway1-out prefix. I am not including the code I use to publish to the Garage Door item. > means openhab is publishing to this item. The default prefix here is mygateway1-in. Now the good news here is once everything gets connected and starts sending messages, you can use a MQTT client to watch for specifc messages by subscribing to both mygateway1-out/# and mygateway1-in/#. This is how i dialed in the values you see in my mqtt.items file.
String Garage_Door "Garage Door [%s]" (gGarage, Windows) {mqtt="<[mysensor:mygateway1-out/101/3/1/0/16:state:MAP(1closed0open.map)]"}
Switch MQTTTestSwitch "MQTT Test Switch" (gBasement) {mqtt=">[mysensor:mygateway1-in/2/2/0/0/2:command:ON:1],>[mysensor:mygateway1-in/2/2/0/0/2:command:OFF:0]"}
Modified RelayActuator Sketch from MySensors 2.0 examples
/**
* The MySensors Arduino library handles the wireless radio link and protocol
* between your home built sensors/actuators and HA controller of choice.
* The sensors forms a self healing radio network with optional repeaters. Each
* repeater and gateway builds a routing tables in EEPROM which keeps track of the
* network topology allowing messages to be routed to nodes.
*
* Created by Henrik Ekblad <henrik.ekblad@mysensors.org>
* Copyright (C) 2013-2015 Sensnology AB
* Full contributor list: https://github.com/mysensors/Arduino/graphs/contributors
*
* Documentation: http://www.mysensors.org
* Support Forum: http://forum.mysensors.org
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* version 2 as published by the Free Software Foundation.
*
*******************************
*
* REVISION HISTORY
* Version 1.0 - Henrik Ekblad
*
* DESCRIPTION
* Example sketch showing how to control physical relays.
* This example will remember relay state after power failure.
* http://www.mysensors.org/build/relay
*/
// Enable debug prints to serial monitor
#define MY_DEBUG
// Enable and select radio type attached
#define MY_RADIO_NRF24
//#define MY_RADIO_RFM69
// Enable repeater functionality for this node
// #define MY_REPEATER_FEATURE
#include <SPI.h>
#include <MySensors.h>
#define RELAY_1 3 // Arduino Digital I/O pin number for first relay (second on pin+1 etc)
#define NUMBER_OF_RELAYS 1 // Total number of attached relays
#define RELAY_ON 1 // GPIO value to write to turn on attached relay
#define RELAY_OFF 0 // GPIO value to write to turn off attached relay
#define LED_PIN 6
void before() {
}
void setup() {
// Then set relay pins in output mode
pinMode(LED_PIN, OUTPUT);
// Set relay to last known state (using eeprom storage)
digitalWrite(LED_PIN, LOW);
}
void presentation()
{
// Send the sketch version information to the gateway and Controller
sendSketchInfo("Relay", "1.0");
// Register all sensors to gw (they will be created as child devices)
present(2, S_LIGHT);
}
void loop()
{
}
void receive(const MyMessage &message) {
Serial.print("V_LIGHT=");
Serial.print(V_LIGHT);
Serial.print("got message of type ");
Serial.println(message.type);
// We only expect one type of message from controller. But we better check anyway.
if (message.type==V_LIGHT) {
// Change relay state
digitalWrite(LED_PIN, message.getBool()?RELAY_ON:RELAY_OFF);
// Store state in eeprom
saveState(message.sensor, message.getBool());
// Write some debug info
Serial.print("Incoming change for sensor:");
Serial.print(message.sensor);
Serial.print(", New status: ");
Serial.println(message.getBool());
}
}
One other thing to note is that the type of item can affect how it reacts to values. For example, originally my Garage Door item was of type contact and i kept getting messages in my openhab.log that said it could not set state because new value was NULL. I switched it to string and it worked.