- *Siren*
- *Outdoor Camera / Presence*. Reports last event, consult picture and video from event/camera.
- *Doorbell*
+- *Smoke Detector*
See https://www.netatmo.com/ for details on their product.
All these channels except at-home are read only.
+### Netatmo Smart Smoke Detector
+
+All these channels are read only.
+
+**Supported channels for the Smoke Detector thing:**
+
+| Channel Group | Channel Id | Item Type | Description |
+|---------------|--------------|--------------|--------------------------------------------------|
+| signal | strength | Number | Signal strength (0 for no signal, 1 for weak...) |
+| signal | value | Number:Power | Signal strength in dBm |
+| timestamp | last-seen | DateTime | Last time the module reported its presence |
+| last-event | type | String | Type of event |
+| last-event | time | DateTime | Moment of the last event for this person |
+| last-event | subtype | String | Sub-type of event |
+| last-event | message | String | Last event message from this person |
+
## Configuration Examples
public static final String OPTION_PERSON = "-person";
public static final String OPTION_ROOM = "-room";
public static final String OPTION_THERMOSTAT = "-thermostat";
+ public static final String OPTION_SMOKE = "-smoke";
public static final Set<String> GROUP_VARIATIONS = Set.of(OPTION_EXTENDED, OPTION_OUTSIDE, OPTION_DOORBELL,
- OPTION_PERSON, OPTION_ROOM, OPTION_THERMOSTAT);
+ OPTION_PERSON, OPTION_ROOM, OPTION_THERMOSTAT, OPTION_SMOKE);
+
public static final String GROUP_TYPE_TIMESTAMP_EXTENDED = GROUP_TIMESTAMP + OPTION_EXTENDED;
public static final String GROUP_TYPE_BATTERY_EXTENDED = GROUP_BATTERY + OPTION_EXTENDED;
public static final String GROUP_TYPE_PRESSURE_EXTENDED = GROUP_PRESSURE + OPTION_EXTENDED;
public static final String GROUP_DOORBELL_LAST_EVENT = GROUP_LAST_EVENT + OPTION_DOORBELL;
public static final String GROUP_DOORBELL_SUB_EVENT = GROUP_SUB_EVENT + OPTION_DOORBELL;
public static final String GROUP_PERSON_LAST_EVENT = GROUP_LAST_EVENT + OPTION_PERSON;
+ public static final String GROUP_SMOKE_LAST_EVENT = GROUP_LAST_EVENT + OPTION_SMOKE;
public static final String GROUP_TYPE_ROOM_TEMPERATURE = GROUP_TEMPERATURE + OPTION_ROOM;
public static final String GROUP_TYPE_ROOM_PROPERTIES = GROUP_PROPERTIES + OPTION_ROOM;
public static final String GROUP_TYPE_TH_PROPERTIES = GROUP_PROPERTIES + OPTION_THERMOSTAT;
import org.openhab.binding.netatmo.internal.handler.capability.PersonCapability;
import org.openhab.binding.netatmo.internal.handler.capability.PresenceCapability;
import org.openhab.binding.netatmo.internal.handler.capability.RoomCapability;
+import org.openhab.binding.netatmo.internal.handler.capability.SmokeCapability;
import org.openhab.binding.netatmo.internal.handler.capability.WeatherCapability;
import org.openhab.binding.netatmo.internal.handler.channelhelper.ChannelHelper;
import org.openhab.binding.netatmo.internal.providers.NetatmoDescriptionProvider;
newCap = new PersonCapability(handler, stateDescriptionProvider, helpers);
} else if (capability == CameraCapability.class) {
newCap = new CameraCapability(handler, stateDescriptionProvider, helpers);
+ } else if (capability == SmokeCapability.class) {
+ newCap = new SmokeCapability(handler, stateDescriptionProvider, helpers);
} else if (capability == PresenceCapability.class) {
newCap = new PresenceCapability(handler, stateDescriptionProvider, helpers);
} else if (capability == MeasureCapability.class) {
throw new NetatmoException("home should not be null");
}
- public Collection<HomeEvent> getCameraEvents(String homeId, String deviceId, String deviceType)
+ public Collection<HomeEvent> getDeviceEvents(String homeId, String deviceId, String deviceType)
throws NetatmoException {
UriBuilder uriBuilder = getApiUriBuilder(SUB_PATH_GET_EVENTS, PARAM_HOME_ID, homeId, PARAM_DEVICE_ID, deviceId,
PARAM_DEVICES_TYPE, deviceType);
public static final ChannelGroup LOCATION = new ChannelGroup(LocationChannelHelper.class, GROUP_LOCATION);
public static final ChannelGroup BATTERY_EXT = new ChannelGroup(BatteryChannelHelper.class,
GROUP_TYPE_BATTERY_EXTENDED);
+ public static final ChannelGroup TIMESTAMP = new ChannelGroup(TimestampChannelHelper.class, GROUP_TIMESTAMP);
public static final ChannelGroup TSTAMP_EXT = new ChannelGroup(TimestampChannelHelper.class,
GROUP_TYPE_TIMESTAMP_EXTENDED);
public static final ChannelGroup TEMP_OUTSIDE_EXT = new ChannelGroup(TemperatureChannelHelper.class,
*/
@NonNullByDefault
public enum EventSubType {
- SD_CARD_MISSING(List.of(EventType.SD), 1),
- SD_CARD_INSERTED(List.of(EventType.SD), 2),
- SD_CARD_FORMATTED(List.of(EventType.SD), 3),
- SD_CARD_WORKING(List.of(EventType.SD), 4),
- SD_CARD_DEFECTIVE(List.of(EventType.SD), 5),
- SD_CARD_INCOMPATIBLE_SPEED(List.of(EventType.SD), 6),
- SD_CARD_INSUFFICIENT_SPACE(List.of(EventType.SD), 7),
- ALIM_INCORRECT_POWER(List.of(EventType.ALIM), 1),
- ALIM_CORRECT_POWER(List.of(EventType.ALIM), 2),
+ // SD Card sub events
+ SD_CARD_MISSING(1, EventType.SD),
+ SD_CARD_INSERTED(2, EventType.SD),
+ SD_CARD_FORMATTED(3, EventType.SD),
+ SD_CARD_WORKING(4, EventType.SD),
+ SD_CARD_DEFECTIVE(5, EventType.SD),
+ SD_CARD_INCOMPATIBLE_SPEED(6, EventType.SD),
+ SD_CARD_INSUFFICIENT_SPACE(7, EventType.SD),
+
+ // Alimentation sub events
+ ALIM_INCORRECT_POWER(1, EventType.ALIM),
+ ALIM_CORRECT_POWER(2, EventType.ALIM),
+
+ // Smoke detector sub events
+ DETECTION_CHAMBER_CLEAN(0, EventType.DETECTION_CHAMBER_STATUS),
+ DETECTION_CHAMBER_DIRTY(1, EventType.DETECTION_CHAMBER_STATUS),
+ BATTERY_LOW(0, EventType.BATTERY_STATUS),
+ BATTERY_VERY_LOW(1, EventType.BATTERY_STATUS),
+ SMOKE_CLEARED(0, EventType.SMOKE),
+ SMOKE_DETECTED(1, EventType.SMOKE),
+ SOUND_TEST_OK(0, EventType.SOUND_TEST),
+ SOUND_TEST_ERROR(1, EventType.SOUND_TEST),
+ DETECTOR_READY(0, EventType.TAMPERED),
+ DETECTOR_TAMPERED(1, EventType.TAMPERED),
+ WIFI_STATUS_OK(1, EventType.WIFI_STATUS),
+ WIFI_STATUS_ERROR(0, EventType.WIFI_STATUS),
// Artificially implemented by the binding subtypes
- PERSON_ARRIVAL(List.of(EventType.PERSON, EventType.PERSON_HOME), 1),
- PERSON_SEEN(List.of(EventType.PERSON), 2),
- PERSON_DEPARTURE(List.of(EventType.PERSON_AWAY), 1),
- MOVEMENT_HUMAN(List.of(EventType.MOVEMENT, EventType.HUMAN), 1),
- MOVEMENT_VEHICLE(List.of(EventType.MOVEMENT), 2),
- MOVEMENT_ANIMAL(List.of(EventType.MOVEMENT, EventType.ANIMAL), 3);
+ PERSON_ARRIVAL(1, EventType.PERSON, EventType.PERSON_HOME),
+ PERSON_SEEN(2, EventType.PERSON),
+ PERSON_DEPARTURE(1, EventType.PERSON_AWAY),
+ MOVEMENT_HUMAN(1, EventType.MOVEMENT, EventType.HUMAN),
+ MOVEMENT_VEHICLE(2, EventType.MOVEMENT),
+ MOVEMENT_ANIMAL(3, EventType.MOVEMENT, EventType.ANIMAL);
public final List<EventType> types;
public final int subType;
- EventSubType(List<EventType> types, int i) {
- this.types = types;
+ EventSubType(int i, EventType... types) {
+ this.types = List.of(types);
this.subType = i;
}
}
INCOMING_CALL(ModuleType.DOORBELL),
@SerializedName("missed_call") // When a call has not been answered by anyone
- MISSED_CALL(ModuleType.DOORBELL);
+ MISSED_CALL(ModuleType.DOORBELL),
+
+ @SerializedName("hush") // When the smoke detection is activated or deactivated
+ HUSH(ModuleType.SMOKE_DETECTOR),
+
+ @SerializedName("smoke") // When smoke is detected or smoke is cleared
+ SMOKE(ModuleType.SMOKE_DETECTOR),
+
+ @SerializedName("tampered") // When smoke detector is ready or tampered
+ TAMPERED(ModuleType.SMOKE_DETECTOR),
+
+ @SerializedName("wifi_status") // When wifi status is updated
+ WIFI_STATUS(ModuleType.SMOKE_DETECTOR),
+
+ @SerializedName("battery_status") // When battery status is too low
+ BATTERY_STATUS(ModuleType.SMOKE_DETECTOR),
+
+ @SerializedName("detection_chamber_status") // When the detection chamber is dusty or clean
+ DETECTION_CHAMBER_STATUS(ModuleType.SMOKE_DETECTOR),
+
+ @SerializedName("sound_test") // Sound test result
+ SOUND_TEST(ModuleType.SMOKE_DETECTOR),
+
+ @SerializedName("new_device")
+ NEW_DEVICE(ModuleType.HOME);
private final Set<ModuleType> appliesTo;
import org.openhab.binding.netatmo.internal.handler.capability.PersonCapability;
import org.openhab.binding.netatmo.internal.handler.capability.PresenceCapability;
import org.openhab.binding.netatmo.internal.handler.capability.RoomCapability;
+import org.openhab.binding.netatmo.internal.handler.capability.SmokeCapability;
import org.openhab.binding.netatmo.internal.handler.capability.WeatherCapability;
import org.openhab.binding.netatmo.internal.handler.channelhelper.AirQualityChannelHelper;
import org.openhab.binding.netatmo.internal.handler.channelhelper.CameraChannelHelper;
import org.openhab.binding.netatmo.internal.handler.channelhelper.EnergyChannelHelper;
+import org.openhab.binding.netatmo.internal.handler.channelhelper.EventChannelHelper;
import org.openhab.binding.netatmo.internal.handler.channelhelper.EventDoorbellChannelHelper;
import org.openhab.binding.netatmo.internal.handler.channelhelper.EventPersonChannelHelper;
import org.openhab.binding.netatmo.internal.handler.channelhelper.PersonChannelHelper;
import org.openhab.binding.netatmo.internal.handler.channelhelper.SetpointChannelHelper;
import org.openhab.binding.netatmo.internal.handler.channelhelper.SirenChannelHelper;
import org.openhab.binding.netatmo.internal.handler.channelhelper.Therm1ChannelHelper;
-import org.openhab.binding.netatmo.internal.handler.channelhelper.TimestampChannelHelper;
import org.openhab.binding.netatmo.internal.handler.channelhelper.WindChannelHelper;
import org.openhab.core.thing.ThingTypeUID;
ChannelGroup.EVENT, new ChannelGroup(CameraChannelHelper.class, GROUP_CAM_STATUS, GROUP_CAM_LIVE)),
SIREN(FeatureArea.SECURITY, "NIS", WELCOME, Set.of(ChannelHelperCapability.class), ChannelGroup.SIGNAL,
- ChannelGroup.BATTERY, new ChannelGroup(TimestampChannelHelper.class, GROUP_TIMESTAMP),
- new ChannelGroup(SirenChannelHelper.class, GROUP_SIREN)),
+ ChannelGroup.BATTERY, ChannelGroup.TIMESTAMP, new ChannelGroup(SirenChannelHelper.class, GROUP_SIREN)),
PRESENCE(FeatureArea.SECURITY, "NOC", HOME,
Set.of(EventCapability.class, PresenceCapability.class, ChannelHelperCapability.class), ChannelGroup.SIGNAL,
ROOM(FeatureArea.ENERGY, "NARoom", HOME, Set.of(RoomCapability.class, ChannelHelperCapability.class),
new ChannelGroup(RoomChannelHelper.class, GROUP_TYPE_ROOM_PROPERTIES, GROUP_TYPE_ROOM_TEMPERATURE),
- new ChannelGroup(SetpointChannelHelper.class, GROUP_SETPOINT));
+ new ChannelGroup(SetpointChannelHelper.class, GROUP_SETPOINT)),
+
+ SMOKE_DETECTOR(FeatureArea.SECURITY, "NSD", HOME, Set.of(SmokeCapability.class, ChannelHelperCapability.class),
+ ChannelGroup.SIGNAL, ChannelGroup.TIMESTAMP,
+ new ChannelGroup(EventChannelHelper.class, GROUP_SMOKE_LAST_EVENT));
public static final EnumSet<ModuleType> AS_SET = EnumSet.allOf(ModuleType.class);
public List<NAObject> updateReadings() {
List<NAObject> result = new ArrayList<>();
securityCapability.ifPresent(cap -> {
- Collection<HomeEvent> events = cap.getCameraEvents(handler.getId(), moduleType.apiName);
+ Collection<HomeEvent> events = cap.getDeviceEvents(handler.getId(), moduleType.apiName);
if (!events.isEmpty()) {
HomeEvent event = events.iterator().next();
result.add(event);
});
}
- public Collection<HomeEvent> getCameraEvents(String cameraId, String deviceType) {
+ public Collection<HomeEvent> getDeviceEvents(String cameraId, String deviceType) {
return getApi().map(api -> {
try {
- return api.getCameraEvents(handler.getId(), cameraId, deviceType);
+ return api.getDeviceEvents(handler.getId(), cameraId, deviceType);
} catch (NetatmoException e) {
logger.warn("Error retrieving last events of camera '{}' : {}", cameraId, e.getMessage());
return null;
--- /dev/null
+/**
+ * Copyright (c) 2010-2022 Contributors to the openHAB project
+ *
+ * See the NOTICE file(s) distributed with this work for additional
+ * information.
+ *
+ * This program and the accompanying materials are made available under the
+ * terms of the Eclipse Public License 2.0 which is available at
+ * http://www.eclipse.org/legal/epl-2.0
+ *
+ * SPDX-License-Identifier: EPL-2.0
+ */
+package org.openhab.binding.netatmo.internal.handler.capability;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.List;
+
+import org.eclipse.jdt.annotation.NonNullByDefault;
+import org.openhab.binding.netatmo.internal.api.dto.HomeEvent;
+import org.openhab.binding.netatmo.internal.api.dto.NAObject;
+import org.openhab.binding.netatmo.internal.handler.CommonInterface;
+import org.openhab.binding.netatmo.internal.handler.channelhelper.ChannelHelper;
+import org.openhab.binding.netatmo.internal.providers.NetatmoDescriptionProvider;
+
+/**
+ * {@link SmokeCapability} gives the ability to handle Smoke detector specifics
+ *
+ * @author Gaël L'hopital - Initial contribution
+ *
+ */
+@NonNullByDefault
+public class SmokeCapability extends HomeSecurityThingCapability {
+
+ public SmokeCapability(CommonInterface handler, NetatmoDescriptionProvider descriptionProvider,
+ List<ChannelHelper> channelHelpers) {
+ super(handler, descriptionProvider, channelHelpers);
+ }
+
+ @Override
+ public List<NAObject> updateReadings() {
+ List<NAObject> result = new ArrayList<>();
+ securityCapability.ifPresent(cap -> {
+ Collection<HomeEvent> events = cap.getDeviceEvents(handler.getId(), moduleType.apiName);
+ if (!events.isEmpty()) {
+ result.add(events.iterator().next());
+ }
+ });
+ return result;
+ }
+}
channel-group-type.netatmo.last-event-person.channel.snapshot-url.description = URL for the picture of the last event for this person.
channel-group-type.netatmo.last-event-person.channel.time.label = Person Timestamp
channel-group-type.netatmo.last-event-person.channel.time.description = Moment of the last event for this person.
+channel-group-type.netatmo.last-event-smoke.label = Last Event
+channel-group-type.netatmo.last-event-smoke.channel.time.label = Event Timestamp
+channel-group-type.netatmo.last-event-smoke.channel.time.description = Moment when event occurred.
channel-group-type.netatmo.last-event.label = Last Event
channel-group-type.netatmo.last-event.channel.local-video-url.label = Video Local URL
channel-group-type.netatmo.last-event.channel.local-video-url.description = Local URL of the event recording.
channel-type.netatmo.event-subtype.state.option.MOVEMENT_HUMAN = Human seen
channel-type.netatmo.event-subtype.state.option.MOVEMENT_VEHICLE = Car seen
channel-type.netatmo.event-subtype.state.option.MOVEMENT_ANIMAL = Animal seen
+channel-type.netatmo.event-subtype.state.option.SOUND_TEST_OK = Alarm test successful
+channel-type.netatmo.event-subtype.state.option.SOUND_TEST_ERROR = Alarm test failed
+channel-type.netatmo.event-subtype.state.option.DETECTOR_READY = Smoke detector installed
+channel-type.netatmo.event-subtype.state.option.DETECTOR_TAMPERED = Smoke detector tampered
+channel-type.netatmo.event-subtype.state.option.DETECTION_CHAMBER_CLEAN = Detection chamber clean
+channel-type.netatmo.event-subtype.state.option.DETECTION_CHAMBER_DIRTY = Detection chamber dusty
+channel-type.netatmo.event-subtype.state.option.BATTERY_LOW = Battery low
+channel-type.netatmo.event-subtype.state.option.BATTERY_VERY_LOW = Battery very low
+channel-type.netatmo.event-subtype.state.option.SMOKE_CLEARED = Smoke cleared
+channel-type.netatmo.event-subtype.state.option.SMOKE_DETECTED = Smoke detected
+channel-type.netatmo.event-subtype.state.option.WIFI_STATUS_OK = Wi-Fi status ok
+channel-type.netatmo.event-subtype.state.option.WIFI_STATUS_ERROR = Wi-Fi status error
channel-type.netatmo.event-type.label = Event Type
channel-type.netatmo.event-type.description = Description of the event.
channel-type.netatmo.event-type.state.option.PERSON = Face detected
channel-type.netatmo.event-type.state.option.ACCEPTED_CALL = Call is incoming
channel-type.netatmo.event-type.state.option.INCOMING_CALL = Call has been answered by a user
channel-type.netatmo.event-type.state.option.MISSED_CALL = Call has not been answered by anyone
+channel-type.netatmo.event-type.state.option.HUSH = Smoke detector status
+channel-type.netatmo.event-type.state.option.SMOKE = Smoke detection
+channel-type.netatmo.event-type.state.option.TAMPERED = Smoke Detector tamper
+channel-type.netatmo.event-type.state.option.WIFI_STATUS = Wifi status
+channel-type.netatmo.event-type.state.option.BATTERY_STATUS = Battery status
+channel-type.netatmo.event-type.state.option.DETECTION_CHAMBER_STATUS = Detection chamber status
+channel-type.netatmo.event-type.state.option.SOUND_TEST = Sound test
+channel-type.netatmo.event-type.state.option.NEW_DEVICE = A device has been added
channel-type.netatmo.floodlight-mode.label = Floodlight
channel-type.netatmo.floodlight-mode.description = State of the floodlight (On/Off/Auto)
channel-type.netatmo.floodlight-mode.state.option.ON = On
thing-type.netatmo.room.description = A room in your house.
thing-type.netatmo.siren.label = Siren Module
thing-type.netatmo.siren.description = The Netatmo Smart Indoor Siren.
+thing-type.netatmo.smoke-detector.label = Smoke Detector
+thing-type.netatmo.smoke-detector.description = The Netatmo Smart Smoke Detector.
thing-type.netatmo.thermostat.label = Thermostat Module
thing-type.netatmo.thermostat.description = The Thermostat device placed in a given room.
thing-type.netatmo.valve.label = Radiator valve
<option value="ACCEPTED_CALL">Call is incoming</option>
<option value="INCOMING_CALL">Call has been answered by a user</option>
<option value="MISSED_CALL">Call has not been answered by anyone</option>
+ <option value="HUSH">Smoke detector status</option>
+ <option value="SMOKE">Smoke detection</option>
+ <option value="TAMPERED">Smoke Detector tamper</option>
+ <option value="WIFI_STATUS">Wifi status</option>
+ <option value="BATTERY_STATUS">Battery status</option>
+ <option value="DETECTION_CHAMBER_STATUS">Detection chamber status</option>
+ <option value="SOUND_TEST">Sound test</option>
+ <option value="NEW_DEVICE">A device has been added</option>
</options>
</state>
</channel-type>
<option value="MOVEMENT_HUMAN">Human seen</option>
<option value="MOVEMENT_VEHICLE">Car seen</option>
<option value="MOVEMENT_ANIMAL">Animal seen</option>
+ <option value="SOUND_TEST_OK">Alarm test successful</option>
+ <option value="SOUND_TEST_ERROR">Alarm test failed</option>
+ <option value="DETECTOR_READY">Smoke detector installed</option>
+ <option value="DETECTOR_TAMPERED">Smoke detector tampered</option>
+ <option value="DETECTION_CHAMBER_CLEAN">Detection chamber clean</option>
+ <option value="DETECTION_CHAMBER_DIRTY">Detection chamber dusty</option>
+ <option value="BATTERY_LOW">Battery low</option>
+ <option value="BATTERY_VERY_LOW">Battery very low</option>
+ <option value="SMOKE_CLEARED">Smoke cleared</option>
+ <option value="SMOKE_DETECTED">Smoke detected</option>
+ <option value="WIFI_STATUS_OK">Wi-Fi status ok</option>
+ <option value="WIFI_STATUS_ERROR">Wi-Fi status error</option>
</options>
</state>
</channel-type>
</channels>
</channel-group-type>
+ <channel-group-type id="last-event-smoke">
+ <label>Last Event</label>
+ <channels>
+ <channel id="type" typeId="event-type"/>
+ <channel id="time" typeId="timestamp">
+ <label>Event Timestamp</label>
+ <description>Moment when event occurred.</description>
+ </channel>
+ <channel id="subtype" typeId="event-subtype"/>
+ <channel id="message" typeId="message"/>
+ </channels>
+ </channel-group-type>
+
<channel-group-type id="last-event-person">
<label>Last Event</label>
<channels>