diff --git a/homeassistant/components/binary_sensor/nest.py b/homeassistant/components/binary_sensor/nest.py
index 008b6eed1e4e0423ca3df7f46361572c08e365c4..882ff142e8c14762e012ab5e2cb8fb2ebb7c7278 100644
--- a/homeassistant/components/binary_sensor/nest.py
+++ b/homeassistant/components/binary_sensor/nest.py
@@ -7,32 +7,31 @@ https://home-assistant.io/components/binary_sensor.nest/
 from itertools import chain
 import logging
 
-from homeassistant.components.binary_sensor import (BinarySensorDevice)
-from homeassistant.components.nest import DATA_NEST
-from homeassistant.components.sensor.nest import NestSensor
+from homeassistant.components.binary_sensor import BinarySensorDevice
+from homeassistant.components.nest import DATA_NEST, NestSensorDevice
 from homeassistant.const import CONF_MONITORED_CONDITIONS
 
 DEPENDENCIES = ['nest']
 
-BINARY_TYPES = ['online']
+BINARY_TYPES = {'online': 'connectivity'}
 
-CLIMATE_BINARY_TYPES = [
-    'fan',
-    'is_using_emergency_heat',
-    'is_locked',
-    'has_leaf',
-]
+CLIMATE_BINARY_TYPES = {
+    'fan': None,
+    'is_using_emergency_heat': 'heat',
+    'is_locked': None,
+    'has_leaf': None,
+}
 
-CAMERA_BINARY_TYPES = [
-    'motion_detected',
-    'sound_detected',
-    'person_detected',
-]
+CAMERA_BINARY_TYPES = {
+    'motion_detected': 'motion',
+    'sound_detected': 'sound',
+    'person_detected': 'occupancy',
+}
 
-STRUCTURE_BINARY_TYPES = [
-    'away',
-    # 'security_state', # wait for pending python-nest update
-]
+STRUCTURE_BINARY_TYPES = {
+    'away': None,
+    # 'security_state', # pending python-nest update
+}
 
 STRUCTURE_BINARY_STATE_MAP = {
     'away': {'away': True, 'home': False},
@@ -50,8 +49,8 @@ _BINARY_TYPES_DEPRECATED = [
     'hvac_emer_heat_state',
 ]
 
-_VALID_BINARY_SENSOR_TYPES = BINARY_TYPES + CLIMATE_BINARY_TYPES \
-    + CAMERA_BINARY_TYPES + STRUCTURE_BINARY_TYPES
+_VALID_BINARY_SENSOR_TYPES = {**BINARY_TYPES, **CLIMATE_BINARY_TYPES,
+                              **CAMERA_BINARY_TYPES, **STRUCTURE_BINARY_TYPES}
 
 _LOGGER = logging.getLogger(__name__)
 
@@ -105,7 +104,7 @@ def setup_platform(hass, config, add_devices, discovery_info=None):
     add_devices(sensors, True)
 
 
-class NestBinarySensor(NestSensor, BinarySensorDevice):
+class NestBinarySensor(NestSensorDevice, BinarySensorDevice):
     """Represents a Nest binary sensor."""
 
     @property
@@ -113,6 +112,11 @@ class NestBinarySensor(NestSensor, BinarySensorDevice):
         """Return true if the binary sensor is on."""
         return self._state
 
+    @property
+    def device_class(self):
+        """Return the device class of the binary sensor."""
+        return _VALID_BINARY_SENSOR_TYPES.get(self.variable)
+
     def update(self):
         """Retrieve latest state."""
         value = getattr(self.device, self.variable)
@@ -133,9 +137,9 @@ class NestActivityZoneSensor(NestBinarySensor):
         self._name = "{} {} activity".format(self._name, self.zone.name)
 
     @property
-    def name(self):
-        """Return the name of the nest, if any."""
-        return self._name
+    def device_class(self):
+        """Return the device class of the binary sensor."""
+        return 'motion'
 
     def update(self):
         """Retrieve latest state."""
diff --git a/homeassistant/components/nest.py b/homeassistant/components/nest.py
index 365f0593c8ddbede8bf6b50fdc1ee4b86954838b..16a0b80d1fd33d0c830b8b54145a4048d5cba6b0 100644
--- a/homeassistant/components/nest.py
+++ b/homeassistant/components/nest.py
@@ -15,7 +15,9 @@ from homeassistant.const import (
     CONF_MONITORED_CONDITIONS,
     EVENT_HOMEASSISTANT_START, EVENT_HOMEASSISTANT_STOP)
 from homeassistant.helpers import discovery, config_validation as cv
-from homeassistant.helpers.dispatcher import async_dispatcher_send
+from homeassistant.helpers.dispatcher import async_dispatcher_send, \
+    async_dispatcher_connect
+from homeassistant.helpers.entity import Entity
 
 REQUIREMENTS = ['python-nest==4.0.1']
 
@@ -272,3 +274,54 @@ class NestDevice(object):
         except socket.error:
             _LOGGER.error(
                 "Connection error logging into the nest web service.")
+
+
+class NestSensorDevice(Entity):
+    """Representation of a Nest sensor."""
+
+    def __init__(self, structure, device, variable):
+        """Initialize the sensor."""
+        self.structure = structure
+        self.variable = variable
+
+        if device is not None:
+            # device specific
+            self.device = device
+            self._name = "{} {}".format(self.device.name_long,
+                                        self.variable.replace('_', ' '))
+        else:
+            # structure only
+            self.device = structure
+            self._name = "{} {}".format(self.structure.name,
+                                        self.variable.replace('_', ' '))
+
+        self._state = None
+        self._unit = None
+
+    @property
+    def name(self):
+        """Return the name of the nest, if any."""
+        return self._name
+
+    @property
+    def unit_of_measurement(self):
+        """Return the unit the value is expressed in."""
+        return self._unit
+
+    @property
+    def should_poll(self):
+        """Do not need poll thanks using Nest streaming API."""
+        return False
+
+    def update(self):
+        """Do not use NestSensorDevice directly."""
+        raise NotImplementedError
+
+    async def async_added_to_hass(self):
+        """Register update signal handler."""
+        async def async_update_state():
+            """Update sensor state."""
+            await self.async_update_ha_state(True)
+
+        async_dispatcher_connect(self.hass, SIGNAL_NEST_UPDATE,
+                                 async_update_state)
diff --git a/homeassistant/components/sensor/nest.py b/homeassistant/components/sensor/nest.py
index 46a2206a9f78256ac7a8dd15f0049a1f78c12704..00d18c7fe105d217395d83946f8024becb5ffa7b 100644
--- a/homeassistant/components/sensor/nest.py
+++ b/homeassistant/components/sensor/nest.py
@@ -4,49 +4,44 @@ Support for Nest Thermostat Sensors.
 For more details about this platform, please refer to the documentation at
 https://home-assistant.io/components/sensor.nest/
 """
-from itertools import chain
 import logging
 
-from homeassistant.components.nest import DATA_NEST, SIGNAL_NEST_UPDATE
-from homeassistant.helpers.dispatcher import async_dispatcher_connect
-from homeassistant.helpers.entity import Entity
+from homeassistant.components.nest import DATA_NEST, NestSensorDevice
 from homeassistant.const import (
     TEMP_CELSIUS, TEMP_FAHRENHEIT, CONF_MONITORED_CONDITIONS,
-    DEVICE_CLASS_TEMPERATURE)
+    DEVICE_CLASS_TEMPERATURE, DEVICE_CLASS_HUMIDITY)
 
 DEPENDENCIES = ['nest']
 
-SENSOR_TYPES = ['humidity',
-                'operation_mode',
-                'hvac_state']
+SENSOR_TYPES = ['humidity', 'operation_mode', 'hvac_state']
 
-SENSOR_TYPES_DEPRECATED = ['last_ip',
-                           'local_ip',
-                           'last_connection']
-
-DEPRECATED_WEATHER_VARS = {'weather_humidity': 'humidity',
-                           'weather_temperature': 'temperature',
-                           'weather_condition': 'condition',
-                           'wind_speed': 'kph',
-                           'wind_direction': 'direction'}
+TEMP_SENSOR_TYPES = ['temperature', 'target']
 
-SENSOR_UNITS = {'humidity': '%', 'temperature': '°C'}
+PROTECT_SENSOR_TYPES = ['co_status', 'smoke_status', 'battery_health']
 
-PROTECT_VARS = ['co_status', 'smoke_status', 'battery_health']
+STRUCTURE_SENSOR_TYPES = ['eta']
 
-PROTECT_VARS_DEPRECATED = ['battery_level']
+_VALID_SENSOR_TYPES = SENSOR_TYPES + TEMP_SENSOR_TYPES + PROTECT_SENSOR_TYPES \
+                      + STRUCTURE_SENSOR_TYPES
 
-SENSOR_TEMP_TYPES = ['temperature', 'target']
+SENSOR_UNITS = {'humidity': '%'}
 
-STRUCTURE_SENSOR_TYPES = ['eta']
+SENSOR_DEVICE_CLASSES = {'humidity': DEVICE_CLASS_HUMIDITY}
 
 VARIABLE_NAME_MAPPING = {'eta': 'eta_begin', 'operation_mode': 'mode'}
 
-_SENSOR_TYPES_DEPRECATED = SENSOR_TYPES_DEPRECATED \
-    + list(DEPRECATED_WEATHER_VARS.keys()) + PROTECT_VARS_DEPRECATED
+SENSOR_TYPES_DEPRECATED = ['last_ip',
+                           'local_ip',
+                           'last_connection',
+                           'battery_level']
+
+DEPRECATED_WEATHER_VARS = ['weather_humidity',
+                           'weather_temperature',
+                           'weather_condition',
+                           'wind_speed',
+                           'wind_direction']
 
-_VALID_SENSOR_TYPES = SENSOR_TYPES + SENSOR_TEMP_TYPES + PROTECT_VARS  \
-    + STRUCTURE_SENSOR_TYPES
+_SENSOR_TYPES_DEPRECATED = SENSOR_TYPES_DEPRECATED + DEPRECATED_WEATHER_VARS
 
 _LOGGER = logging.getLogger(__name__)
 
@@ -76,7 +71,6 @@ def setup_platform(hass, config, add_devices, discovery_info=None):
                         "monitored_conditions. See "
                         "https://home-assistant.io/components/"
                         "binary_sensor.nest/ for valid options.")
-
             _LOGGER.error(wstr)
 
     all_sensors = []
@@ -84,70 +78,24 @@ def setup_platform(hass, config, add_devices, discovery_info=None):
         all_sensors += [NestBasicSensor(structure, None, variable)
                         for variable in conditions
                         if variable in STRUCTURE_SENSOR_TYPES]
-    for structure, device in chain(nest.thermostats(), nest.smoke_co_alarms()):
-        sensors = [NestBasicSensor(structure, device, variable)
-                   for variable in conditions
-                   if variable in SENSOR_TYPES and device.is_thermostat]
-        sensors += [NestTempSensor(structure, device, variable)
-                    for variable in conditions
-                    if variable in SENSOR_TEMP_TYPES and device.is_thermostat]
-        sensors += [NestProtectSensor(structure, device, variable)
-                    for variable in conditions
-                    if variable in PROTECT_VARS and device.is_smoke_co_alarm]
-        all_sensors.extend(sensors)
-
-    add_devices(all_sensors, True)
-
-
-class NestSensor(Entity):
-    """Representation of a Nest sensor."""
-
-    def __init__(self, structure, device, variable):
-        """Initialize the sensor."""
-        self.structure = structure
-        self.variable = variable
-
-        if device is not None:
-            # device specific
-            self.device = device
-            self._location = self.device.where
-            self._name = "{} {}".format(self.device.name_long,
-                                        self.variable.replace('_', ' '))
-        else:
-            # structure only
-            self.device = structure
-            self._name = "{} {}".format(self.structure.name,
-                                        self.variable.replace('_', ' '))
-
-        self._state = None
-        self._unit = None
-
-    @property
-    def name(self):
-        """Return the name of the nest, if any."""
-        return self._name
-
-    @property
-    def unit_of_measurement(self):
-        """Return the unit the value is expressed in."""
-        return self._unit
 
-    @property
-    def should_poll(self):
-        """Do not need poll thanks using Nest streaming API."""
-        return False
+    for structure, device in nest.thermostats():
+        all_sensors += [NestBasicSensor(structure, device, variable)
+                        for variable in conditions
+                        if variable in SENSOR_TYPES]
+        all_sensors += [NestTempSensor(structure, device, variable)
+                        for variable in conditions
+                        if variable in TEMP_SENSOR_TYPES]
 
-    async def async_added_to_hass(self):
-        """Register update signal handler."""
-        async def async_update_state():
-            """Update sensor state."""
-            await self.async_update_ha_state(True)
+    for structure, device in nest.smoke_co_alarms():
+        all_sensors += [NestBasicSensor(structure, device, variable)
+                        for variable in conditions
+                        if variable in PROTECT_SENSOR_TYPES]
 
-        async_dispatcher_connect(self.hass, SIGNAL_NEST_UPDATE,
-                                 async_update_state)
+    add_devices(all_sensors, True)
 
 
-class NestBasicSensor(NestSensor):
+class NestBasicSensor(NestSensorDevice):
     """Representation a basic Nest sensor."""
 
     @property
@@ -155,18 +103,26 @@ class NestBasicSensor(NestSensor):
         """Return the state of the sensor."""
         return self._state
 
+    @property
+    def device_class(self):
+        """Return the device class of the sensor."""
+        return SENSOR_DEVICE_CLASSES.get(self.variable)
+
     def update(self):
         """Retrieve latest state."""
-        self._unit = SENSOR_UNITS.get(self.variable, None)
+        self._unit = SENSOR_UNITS.get(self.variable)
 
         if self.variable in VARIABLE_NAME_MAPPING:
             self._state = getattr(self.device,
                                   VARIABLE_NAME_MAPPING[self.variable])
+        elif self.variable in PROTECT_SENSOR_TYPES:
+            # keep backward compatibility
+            self._state = getattr(self.device, self.variable).capitalize()
         else:
             self._state = getattr(self.device, self.variable)
 
 
-class NestTempSensor(NestSensor):
+class NestTempSensor(NestSensorDevice):
     """Representation of a Nest Temperature sensor."""
 
     @property
@@ -195,16 +151,3 @@ class NestTempSensor(NestSensor):
             self._state = "%s-%s" % (int(low), int(high))
         else:
             self._state = round(temp, 1)
-
-
-class NestProtectSensor(NestSensor):
-    """Return the state of nest protect."""
-
-    @property
-    def state(self):
-        """Return the state of the sensor."""
-        return self._state
-
-    def update(self):
-        """Retrieve latest state."""
-        self._state = getattr(self.device, self.variable).capitalize()