diff --git a/.coveragerc b/.coveragerc
index 7071312a99c21d58fb9e1ea186e1c00809b2e20e..7c35022c355a43f013184d61c81c6663f13c24a7 100644
--- a/.coveragerc
+++ b/.coveragerc
@@ -253,6 +253,7 @@ omit =
     homeassistant/components/github/sensor.py
     homeassistant/components/gitlab_ci/sensor.py
     homeassistant/components/gitter/sensor.py
+    homeassistant/components/glances/__init__.py
     homeassistant/components/glances/sensor.py
     homeassistant/components/gntp/notify.py
     homeassistant/components/goalfeed/*
diff --git a/CODEOWNERS b/CODEOWNERS
index 6e254c5a1d4688541052e1fa83fc024d51fd75fc..e1ff7b36ff154a78b88a31b3cd6a5b1f199f3d6b 100644
--- a/CODEOWNERS
+++ b/CODEOWNERS
@@ -110,7 +110,7 @@ homeassistant/components/geniushub/* @zxdavb
 homeassistant/components/geo_rss_events/* @exxamalte
 homeassistant/components/geonetnz_quakes/* @exxamalte
 homeassistant/components/gitter/* @fabaff
-homeassistant/components/glances/* @fabaff
+homeassistant/components/glances/* @fabaff @engrbm87
 homeassistant/components/gntp/* @robbiet480
 homeassistant/components/google_assistant/* @home-assistant/cloud
 homeassistant/components/google_cloud/* @lufton
diff --git a/homeassistant/components/glances/.translations/en.json b/homeassistant/components/glances/.translations/en.json
new file mode 100644
index 0000000000000000000000000000000000000000..1bd7275daeff156bdcc1aacb4f4dcc570d3a84dd
--- /dev/null
+++ b/homeassistant/components/glances/.translations/en.json
@@ -0,0 +1,37 @@
+{
+    "config": {
+        "title": "Glances",
+        "step": {
+            "user": {
+                "title": "Setup Glances",
+                "data": {
+                    "name": "Name",
+                    "host": "Host",
+                    "username": "Username",
+                    "password": "Password",
+                    "port": "Port",
+                    "version": "Glances API Version (2 or 3)",
+                    "ssl": "Use SSL/TLS to connect to the Glances system",
+                    "verify_ssl": "Verify the certification of the system"
+                }
+            }
+        },
+        "error": {
+            "cannot_connect": "Unable to connect to host",
+            "wrong_version": "Version not supported (2 or 3 only)"
+        },
+        "abort": {
+            "already_configured": "Host is already configured."
+        }
+    },
+    "options": {
+        "step": {
+            "init": {
+                "description": "Configure options for Glances",
+                "data": {
+                    "scan_interval": "Update frequency"
+                }
+            }
+        }
+    }
+}
\ No newline at end of file
diff --git a/homeassistant/components/glances/__init__.py b/homeassistant/components/glances/__init__.py
index b458d8788fcf7eca76370c16d8a834257c068d79..d09aa78253474d45720f32564e3e37e9d443cc31 100644
--- a/homeassistant/components/glances/__init__.py
+++ b/homeassistant/components/glances/__init__.py
@@ -1 +1,174 @@
-"""The glances component."""
+"""The Glances component."""
+from datetime import timedelta
+import logging
+
+from glances_api import Glances, exceptions
+import voluptuous as vol
+
+from homeassistant.config_entries import SOURCE_IMPORT
+from homeassistant.const import (
+    CONF_HOST,
+    CONF_NAME,
+    CONF_PASSWORD,
+    CONF_PORT,
+    CONF_SCAN_INTERVAL,
+    CONF_SSL,
+    CONF_USERNAME,
+    CONF_VERIFY_SSL,
+)
+from homeassistant.core import Config, HomeAssistant
+from homeassistant.exceptions import ConfigEntryNotReady
+from homeassistant.helpers.aiohttp_client import async_get_clientsession
+import homeassistant.helpers.config_validation as cv
+from homeassistant.helpers.dispatcher import async_dispatcher_send
+from homeassistant.helpers.event import async_track_time_interval
+
+from .const import (
+    CONF_VERSION,
+    DATA_UPDATED,
+    DEFAULT_HOST,
+    DEFAULT_NAME,
+    DEFAULT_PORT,
+    DEFAULT_SCAN_INTERVAL,
+    DEFAULT_VERSION,
+    DOMAIN,
+)
+
+_LOGGER = logging.getLogger(__name__)
+
+GLANCES_SCHEMA = vol.All(
+    vol.Schema(
+        {
+            vol.Required(CONF_HOST, default=DEFAULT_HOST): cv.string,
+            vol.Optional(CONF_PORT, default=DEFAULT_PORT): cv.port,
+            vol.Optional(CONF_NAME, default=DEFAULT_NAME): cv.string,
+            vol.Optional(CONF_USERNAME): cv.string,
+            vol.Optional(CONF_PASSWORD): cv.string,
+            vol.Optional(CONF_SSL, default=False): cv.boolean,
+            vol.Optional(CONF_VERIFY_SSL, default=True): cv.boolean,
+            vol.Optional(CONF_VERSION, default=DEFAULT_VERSION): vol.In([2, 3]),
+        }
+    )
+)
+
+CONFIG_SCHEMA = vol.Schema(
+    {DOMAIN: vol.All(cv.ensure_list, [GLANCES_SCHEMA])}, extra=vol.ALLOW_EXTRA
+)
+
+
+async def async_setup(hass: HomeAssistant, config: Config) -> bool:
+    """Configure Glances using config flow only."""
+    if DOMAIN in config:
+        for entry in config[DOMAIN]:
+            hass.async_create_task(
+                hass.config_entries.flow.async_init(
+                    DOMAIN, context={"source": SOURCE_IMPORT}, data=entry
+                )
+            )
+
+    return True
+
+
+async def async_setup_entry(hass, config_entry):
+    """Set up Glances from config entry."""
+    client = GlancesData(hass, config_entry)
+    hass.data.setdefault(DOMAIN, {})[config_entry.entry_id] = client
+    if not await client.async_setup():
+        return False
+
+    return True
+
+
+async def async_unload_entry(hass, config_entry):
+    """Unload a config entry."""
+    await hass.config_entries.async_forward_entry_unload(config_entry, "sensor")
+    hass.data[DOMAIN].pop(config_entry.entry_id)
+    return True
+
+
+class GlancesData:
+    """Get the latest data from Glances api."""
+
+    def __init__(self, hass, config_entry):
+        """Initialize the Glances data."""
+        self.hass = hass
+        self.config_entry = config_entry
+        self.api = None
+        self.unsub_timer = None
+        self.available = False
+
+    @property
+    def host(self):
+        """Return client host."""
+        return self.config_entry.data[CONF_HOST]
+
+    async def async_update(self):
+        """Get the latest data from the Glances REST API."""
+        try:
+            await self.api.get_data()
+            self.available = True
+        except exceptions.GlancesApiError:
+            _LOGGER.error("Unable to fetch data from Glances")
+            self.available = False
+        _LOGGER.debug("Glances data updated")
+        async_dispatcher_send(self.hass, DATA_UPDATED)
+
+    async def async_setup(self):
+        """Set up the Glances client."""
+        try:
+            self.api = get_api(self.hass, self.config_entry.data)
+            await self.api.get_data()
+            self.available = True
+            _LOGGER.debug("Successfully connected to Glances")
+
+        except exceptions.GlancesApiConnectionError:
+            _LOGGER.debug("Can not connect to Glances")
+            raise ConfigEntryNotReady
+
+        self.add_options()
+        self.set_scan_interval(self.config_entry.options[CONF_SCAN_INTERVAL])
+        self.config_entry.add_update_listener(self.async_options_updated)
+
+        self.hass.async_create_task(
+            self.hass.config_entries.async_forward_entry_setup(
+                self.config_entry, "sensor"
+            )
+        )
+        return True
+
+    def add_options(self):
+        """Add options for Glances integration."""
+        if not self.config_entry.options:
+            options = {CONF_SCAN_INTERVAL: DEFAULT_SCAN_INTERVAL}
+            self.hass.config_entries.async_update_entry(
+                self.config_entry, options=options
+            )
+
+    def set_scan_interval(self, scan_interval):
+        """Update scan interval."""
+
+        async def refresh(event_time):
+            """Get the latest data from Glances api."""
+            await self.async_update()
+
+        if self.unsub_timer is not None:
+            self.unsub_timer()
+        self.unsub_timer = async_track_time_interval(
+            self.hass, refresh, timedelta(seconds=scan_interval)
+        )
+
+    @staticmethod
+    async def async_options_updated(hass, entry):
+        """Triggered by config entry options updates."""
+        hass.data[DOMAIN][entry.entry_id].set_scan_interval(
+            entry.options[CONF_SCAN_INTERVAL]
+        )
+
+
+def get_api(hass, entry):
+    """Return the api from glances_api."""
+    params = entry.copy()
+    params.pop(CONF_NAME)
+    verify_ssl = params.pop(CONF_VERIFY_SSL)
+    session = async_get_clientsession(hass, verify_ssl)
+    return Glances(hass.loop, session, **params)
diff --git a/homeassistant/components/glances/config_flow.py b/homeassistant/components/glances/config_flow.py
new file mode 100644
index 0000000000000000000000000000000000000000..3c86fae0357350bd37e3fa944155d5b76223fd77
--- /dev/null
+++ b/homeassistant/components/glances/config_flow.py
@@ -0,0 +1,130 @@
+"""Config flow for Glances."""
+import glances_api
+import voluptuous as vol
+
+from homeassistant import config_entries, core, exceptions
+from homeassistant.const import (
+    CONF_HOST,
+    CONF_NAME,
+    CONF_PASSWORD,
+    CONF_PORT,
+    CONF_SCAN_INTERVAL,
+    CONF_SSL,
+    CONF_USERNAME,
+    CONF_VERIFY_SSL,
+)
+from homeassistant.core import callback
+
+from . import get_api
+from .const import (
+    CONF_VERSION,
+    DEFAULT_HOST,
+    DEFAULT_NAME,
+    DEFAULT_PORT,
+    DEFAULT_SCAN_INTERVAL,
+    DEFAULT_VERSION,
+    DOMAIN,
+    SUPPORTED_VERSIONS,
+)
+
+DATA_SCHEMA = vol.Schema(
+    {
+        vol.Required(CONF_NAME, default=DEFAULT_NAME): str,
+        vol.Required(CONF_HOST, default=DEFAULT_HOST): str,
+        vol.Optional(CONF_USERNAME): str,
+        vol.Optional(CONF_PASSWORD): str,
+        vol.Required(CONF_PORT, default=DEFAULT_PORT): int,
+        vol.Required(CONF_VERSION, default=DEFAULT_VERSION): int,
+        vol.Optional(CONF_SSL, default=False): bool,
+        vol.Optional(CONF_VERIFY_SSL, default=False): bool,
+    }
+)
+
+
+async def validate_input(hass: core.HomeAssistant, data):
+    """Validate the user input allows us to connect."""
+    for entry in hass.config_entries.async_entries(DOMAIN):
+        if entry.data[CONF_HOST] == data[CONF_HOST]:
+            raise AlreadyConfigured
+
+    if data[CONF_VERSION] not in SUPPORTED_VERSIONS:
+        raise WrongVersion
+    try:
+        api = get_api(hass, data)
+        await api.get_data()
+    except glances_api.exceptions.GlancesApiConnectionError:
+        raise CannotConnect
+
+
+class GlancesFlowHandler(config_entries.ConfigFlow, domain=DOMAIN):
+    """Handle a Glances config flow."""
+
+    VERSION = 1
+    CONNECTION_CLASS = config_entries.CONN_CLASS_LOCAL_POLL
+
+    @staticmethod
+    @callback
+    def async_get_options_flow(config_entry):
+        """Get the options flow for this handler."""
+        return GlancesOptionsFlowHandler(config_entry)
+
+    async def async_step_user(self, user_input=None):
+        """Handle the initial step."""
+        errors = {}
+        if user_input is not None:
+            try:
+                await validate_input(self.hass, user_input)
+                return self.async_create_entry(
+                    title=user_input[CONF_NAME], data=user_input
+                )
+            except AlreadyConfigured:
+                return self.async_abort(reason="already_configured")
+            except CannotConnect:
+                errors["base"] = "cannot_connect"
+            except WrongVersion:
+                errors[CONF_VERSION] = "wrong_version"
+
+        return self.async_show_form(
+            step_id="user", data_schema=DATA_SCHEMA, errors=errors
+        )
+
+    async def async_step_import(self, import_config):
+        """Import from Glances sensor config."""
+
+        return await self.async_step_user(user_input=import_config)
+
+
+class GlancesOptionsFlowHandler(config_entries.OptionsFlow):
+    """Handle Glances client options."""
+
+    def __init__(self, config_entry):
+        """Initialize Glances options flow."""
+        self.config_entry = config_entry
+
+    async def async_step_init(self, user_input=None):
+        """Manage the Glances options."""
+        if user_input is not None:
+            return self.async_create_entry(title="", data=user_input)
+
+        options = {
+            vol.Optional(
+                CONF_SCAN_INTERVAL,
+                default=self.config_entry.options.get(
+                    CONF_SCAN_INTERVAL, DEFAULT_SCAN_INTERVAL
+                ),
+            ): int
+        }
+
+        return self.async_show_form(step_id="init", data_schema=vol.Schema(options))
+
+
+class CannotConnect(exceptions.HomeAssistantError):
+    """Error to indicate we cannot connect."""
+
+
+class AlreadyConfigured(exceptions.HomeAssistantError):
+    """Error to indicate host is already configured."""
+
+
+class WrongVersion(exceptions.HomeAssistantError):
+    """Error to indicate the selected version is wrong."""
diff --git a/homeassistant/components/glances/const.py b/homeassistant/components/glances/const.py
new file mode 100644
index 0000000000000000000000000000000000000000..e47586ea245b5ce0a34d96e5737b77d32a5a54ac
--- /dev/null
+++ b/homeassistant/components/glances/const.py
@@ -0,0 +1,36 @@
+"""Constants for Glances component."""
+from homeassistant.const import TEMP_CELSIUS
+
+DOMAIN = "glances"
+CONF_VERSION = "version"
+
+DEFAULT_HOST = "localhost"
+DEFAULT_NAME = "Glances"
+DEFAULT_PORT = 61208
+DEFAULT_VERSION = 3
+DEFAULT_SCAN_INTERVAL = 60
+
+DATA_UPDATED = "glances_data_updated"
+SUPPORTED_VERSIONS = [2, 3]
+
+SENSOR_TYPES = {
+    "disk_use_percent": ["Disk used percent", "%", "mdi:harddisk"],
+    "disk_use": ["Disk used", "GiB", "mdi:harddisk"],
+    "disk_free": ["Disk free", "GiB", "mdi:harddisk"],
+    "memory_use_percent": ["RAM used percent", "%", "mdi:memory"],
+    "memory_use": ["RAM used", "MiB", "mdi:memory"],
+    "memory_free": ["RAM free", "MiB", "mdi:memory"],
+    "swap_use_percent": ["Swap used percent", "%", "mdi:memory"],
+    "swap_use": ["Swap used", "GiB", "mdi:memory"],
+    "swap_free": ["Swap free", "GiB", "mdi:memory"],
+    "processor_load": ["CPU load", "15 min", "mdi:memory"],
+    "process_running": ["Running", "Count", "mdi:memory"],
+    "process_total": ["Total", "Count", "mdi:memory"],
+    "process_thread": ["Thread", "Count", "mdi:memory"],
+    "process_sleeping": ["Sleeping", "Count", "mdi:memory"],
+    "cpu_use_percent": ["CPU used", "%", "mdi:memory"],
+    "cpu_temp": ["CPU Temp", TEMP_CELSIUS, "mdi:thermometer"],
+    "docker_active": ["Containers active", "", "mdi:docker"],
+    "docker_cpu_use": ["Containers CPU used", "%", "mdi:docker"],
+    "docker_memory_use": ["Containers RAM used", "MiB", "mdi:docker"],
+}
diff --git a/homeassistant/components/glances/manifest.json b/homeassistant/components/glances/manifest.json
index 775d208c1c48e524449369a5e2c0023312f7a331..6067b1a986860d131302604888fcda5b27e65889 100644
--- a/homeassistant/components/glances/manifest.json
+++ b/homeassistant/components/glances/manifest.json
@@ -1,12 +1,14 @@
 {
   "domain": "glances",
   "name": "Glances",
+  "config_flow": true,
   "documentation": "https://www.home-assistant.io/integrations/glances",
   "requirements": [
     "glances_api==0.2.0"
   ],
   "dependencies": [],
   "codeowners": [
-    "@fabaff"
+    "@fabaff",
+    "@engrbm87"
   ]
-}
+}
\ No newline at end of file
diff --git a/homeassistant/components/glances/sensor.py b/homeassistant/components/glances/sensor.py
index 90b4b386f37e52bdd43f2b591c32e4e8fd3d0a54..760958f0dee0da8a05d742bf57399ca59d16728f 100644
--- a/homeassistant/components/glances/sensor.py
+++ b/homeassistant/components/glances/sensor.py
@@ -1,114 +1,31 @@
 """Support gathering system information of hosts which are running glances."""
-from datetime import timedelta
 import logging
 
-import voluptuous as vol
-
-from homeassistant.components.sensor import PLATFORM_SCHEMA
-from homeassistant.const import (
-    CONF_HOST,
-    CONF_NAME,
-    CONF_PORT,
-    CONF_USERNAME,
-    CONF_PASSWORD,
-    CONF_SSL,
-    CONF_VERIFY_SSL,
-    CONF_RESOURCES,
-    STATE_UNAVAILABLE,
-    TEMP_CELSIUS,
-)
-from homeassistant.exceptions import PlatformNotReady
-from homeassistant.helpers.aiohttp_client import async_get_clientsession
-import homeassistant.helpers.config_validation as cv
+from homeassistant.const import CONF_NAME, STATE_UNAVAILABLE
+from homeassistant.core import callback
+from homeassistant.helpers.dispatcher import async_dispatcher_connect
 from homeassistant.helpers.entity import Entity
-from homeassistant.util import Throttle
-
-_LOGGER = logging.getLogger(__name__)
-
-CONF_VERSION = "version"
 
-DEFAULT_HOST = "localhost"
-DEFAULT_NAME = "Glances"
-DEFAULT_PORT = "61208"
-DEFAULT_VERSION = 2
+from .const import DATA_UPDATED, DOMAIN, SENSOR_TYPES
 
-MIN_TIME_BETWEEN_UPDATES = timedelta(minutes=1)
-
-SENSOR_TYPES = {
-    "disk_use_percent": ["Disk used percent", "%", "mdi:harddisk"],
-    "disk_use": ["Disk used", "GiB", "mdi:harddisk"],
-    "disk_free": ["Disk free", "GiB", "mdi:harddisk"],
-    "memory_use_percent": ["RAM used percent", "%", "mdi:memory"],
-    "memory_use": ["RAM used", "MiB", "mdi:memory"],
-    "memory_free": ["RAM free", "MiB", "mdi:memory"],
-    "swap_use_percent": ["Swap used percent", "%", "mdi:memory"],
-    "swap_use": ["Swap used", "GiB", "mdi:memory"],
-    "swap_free": ["Swap free", "GiB", "mdi:memory"],
-    "processor_load": ["CPU load", "15 min", "mdi:memory"],
-    "process_running": ["Running", "Count", "mdi:memory"],
-    "process_total": ["Total", "Count", "mdi:memory"],
-    "process_thread": ["Thread", "Count", "mdi:memory"],
-    "process_sleeping": ["Sleeping", "Count", "mdi:memory"],
-    "cpu_use_percent": ["CPU used", "%", "mdi:memory"],
-    "cpu_temp": ["CPU Temp", TEMP_CELSIUS, "mdi:thermometer"],
-    "docker_active": ["Containers active", "", "mdi:docker"],
-    "docker_cpu_use": ["Containers CPU used", "%", "mdi:docker"],
-    "docker_memory_use": ["Containers RAM used", "MiB", "mdi:docker"],
-}
-
-PLATFORM_SCHEMA = PLATFORM_SCHEMA.extend(
-    {
-        vol.Required(CONF_HOST, default=DEFAULT_HOST): cv.string,
-        vol.Optional(CONF_PORT, default=DEFAULT_PORT): cv.port,
-        vol.Optional(CONF_NAME, default=DEFAULT_NAME): cv.string,
-        vol.Optional(CONF_USERNAME): cv.string,
-        vol.Optional(CONF_PASSWORD): cv.string,
-        vol.Optional(CONF_SSL, default=False): cv.boolean,
-        vol.Optional(CONF_VERIFY_SSL, default=True): cv.boolean,
-        vol.Optional(CONF_RESOURCES, default=["disk_use"]): vol.All(
-            cv.ensure_list, [vol.In(SENSOR_TYPES)]
-        ),
-        vol.Optional(CONF_VERSION, default=DEFAULT_VERSION): vol.In([2, 3]),
-    }
-)
+_LOGGER = logging.getLogger(__name__)
 
 
 async def async_setup_platform(hass, config, async_add_entities, discovery_info=None):
-    """Set up the Glances sensors."""
-    from glances_api import Glances
-
-    name = config[CONF_NAME]
-    host = config[CONF_HOST]
-    port = config[CONF_PORT]
-    version = config[CONF_VERSION]
-    var_conf = config[CONF_RESOURCES]
-    username = config.get(CONF_USERNAME)
-    password = config.get(CONF_PASSWORD)
-    ssl = config[CONF_SSL]
-    verify_ssl = config[CONF_VERIFY_SSL]
-
-    session = async_get_clientsession(hass, verify_ssl)
-    glances = GlancesData(
-        Glances(
-            hass.loop,
-            session,
-            host=host,
-            port=port,
-            version=version,
-            username=username,
-            password=password,
-            ssl=ssl,
-        )
-    )
+    """Set up the Glances sensors is done through async_setup_entry."""
+    pass
 
-    await glances.async_update()
 
-    if glances.api.data is None:
-        raise PlatformNotReady
+async def async_setup_entry(hass, config_entry, async_add_entities):
+    """Set up the Glances sensors."""
 
+    glances_data = hass.data[DOMAIN][config_entry.entry_id]
+    name = config_entry.data[CONF_NAME]
     dev = []
-    for resource in var_conf:
-        dev.append(GlancesSensor(glances, name, resource))
+    for sensor_type in SENSOR_TYPES:
+        dev.append(
+            GlancesSensor(glances_data, name, SENSOR_TYPES[sensor_type][0], sensor_type)
+        )
 
     async_add_entities(dev, True)
 
@@ -116,9 +33,10 @@ async def async_setup_platform(hass, config, async_add_entities, discovery_info=
 class GlancesSensor(Entity):
     """Implementation of a Glances sensor."""
 
-    def __init__(self, glances, name, sensor_type):
+    def __init__(self, glances_data, name, sensor_name, sensor_type):
         """Initialize the sensor."""
-        self.glances = glances
+        self.glances_data = glances_data
+        self._sensor_name = sensor_name
         self._name = name
         self.type = sensor_type
         self._state = None
@@ -127,7 +45,12 @@ class GlancesSensor(Entity):
     @property
     def name(self):
         """Return the name of the sensor."""
-        return "{} {}".format(self._name, SENSOR_TYPES[self.type][0])
+        return f"{self._name} {self._sensor_name}"
+
+    @property
+    def unique_id(self):
+        """Set unique_id for sensor."""
+        return f"{self.glances_data.host}-{self.name}"
 
     @property
     def icon(self):
@@ -142,17 +65,31 @@ class GlancesSensor(Entity):
     @property
     def available(self):
         """Could the device be accessed during the last update call."""
-        return self.glances.available
+        return self.glances_data.available
 
     @property
     def state(self):
         """Return the state of the resources."""
         return self._state
 
+    @property
+    def should_poll(self):
+        """Return the polling requirement for this sensor."""
+        return False
+
+    async def async_added_to_hass(self):
+        """Handle entity which will be added."""
+        async_dispatcher_connect(
+            self.hass, DATA_UPDATED, self._schedule_immediate_update
+        )
+
+    @callback
+    def _schedule_immediate_update(self):
+        self.async_schedule_update_ha_state(True)
+
     async def async_update(self):
         """Get the latest data from REST API."""
-        await self.glances.async_update()
-        value = self.glances.api.data
+        value = self.glances_data.api.data
 
         if value is not None:
             if self.type == "disk_use_percent":
@@ -249,24 +186,3 @@ class GlancesSensor(Entity):
                         self._state = round(mem_use / 1024 ** 2, 1)
                 except KeyError:
                     self._state = STATE_UNAVAILABLE
-
-
-class GlancesData:
-    """The class for handling the data retrieval."""
-
-    def __init__(self, api):
-        """Initialize the data object."""
-        self.api = api
-        self.available = True
-
-    @Throttle(MIN_TIME_BETWEEN_UPDATES)
-    async def async_update(self):
-        """Get the latest data from the Glances REST API."""
-        from glances_api.exceptions import GlancesApiError
-
-        try:
-            await self.api.get_data()
-            self.available = True
-        except GlancesApiError:
-            _LOGGER.error("Unable to fetch data from Glances")
-            self.available = False
diff --git a/homeassistant/components/glances/strings.json b/homeassistant/components/glances/strings.json
new file mode 100644
index 0000000000000000000000000000000000000000..1bd7275daeff156bdcc1aacb4f4dcc570d3a84dd
--- /dev/null
+++ b/homeassistant/components/glances/strings.json
@@ -0,0 +1,37 @@
+{
+    "config": {
+        "title": "Glances",
+        "step": {
+            "user": {
+                "title": "Setup Glances",
+                "data": {
+                    "name": "Name",
+                    "host": "Host",
+                    "username": "Username",
+                    "password": "Password",
+                    "port": "Port",
+                    "version": "Glances API Version (2 or 3)",
+                    "ssl": "Use SSL/TLS to connect to the Glances system",
+                    "verify_ssl": "Verify the certification of the system"
+                }
+            }
+        },
+        "error": {
+            "cannot_connect": "Unable to connect to host",
+            "wrong_version": "Version not supported (2 or 3 only)"
+        },
+        "abort": {
+            "already_configured": "Host is already configured."
+        }
+    },
+    "options": {
+        "step": {
+            "init": {
+                "description": "Configure options for Glances",
+                "data": {
+                    "scan_interval": "Update frequency"
+                }
+            }
+        }
+    }
+}
\ No newline at end of file
diff --git a/homeassistant/generated/config_flows.py b/homeassistant/generated/config_flows.py
index 664e83fba33aeab72f74e13c0bb32080d51a1384..60aa610ec073f4a1ab270999fe83ea52e23dc9d1 100644
--- a/homeassistant/generated/config_flows.py
+++ b/homeassistant/generated/config_flows.py
@@ -22,6 +22,7 @@ FLOWS = [
     "esphome",
     "geofency",
     "geonetnz_quakes",
+    "glances",
     "gpslogger",
     "hangouts",
     "heos",
diff --git a/requirements_test_all.txt b/requirements_test_all.txt
index 7912de963abbf4a7339ec31d1de4f0a3ba049869..754a7d72a64c025cee30dfe44d065d1abfd43137 100644
--- a/requirements_test_all.txt
+++ b/requirements_test_all.txt
@@ -208,6 +208,9 @@ georss_qld_bushfire_alert_client==0.3
 # homeassistant.components.nmap_tracker
 getmac==0.8.1
 
+# homeassistant.components.glances
+glances_api==0.2.0
+
 # homeassistant.components.google
 google-api-python-client==1.6.4
 
diff --git a/tests/components/glances/__init__.py b/tests/components/glances/__init__.py
new file mode 100644
index 0000000000000000000000000000000000000000..488265f970b3234105695fdbfba332440122c955
--- /dev/null
+++ b/tests/components/glances/__init__.py
@@ -0,0 +1 @@
+"""Tests for Glances."""
diff --git a/tests/components/glances/test_config_flow.py b/tests/components/glances/test_config_flow.py
new file mode 100644
index 0000000000000000000000000000000000000000..e5be52e6b33783bc5925ce4fbb35b929e9a60f76
--- /dev/null
+++ b/tests/components/glances/test_config_flow.py
@@ -0,0 +1,102 @@
+"""Tests for Glances config flow."""
+from unittest.mock import patch
+
+from glances_api import Glances
+
+from homeassistant.components.glances import config_flow
+from homeassistant.components.glances.const import DOMAIN
+from homeassistant.const import CONF_SCAN_INTERVAL
+
+from tests.common import MockConfigEntry, mock_coro
+
+NAME = "Glances"
+HOST = "0.0.0.0"
+USERNAME = "username"
+PASSWORD = "password"
+PORT = 61208
+VERSION = 3
+SCAN_INTERVAL = 10
+
+DEMO_USER_INPUT = {
+    "name": NAME,
+    "host": HOST,
+    "username": USERNAME,
+    "password": PASSWORD,
+    "version": VERSION,
+    "port": PORT,
+    "ssl": False,
+    "verify_ssl": True,
+}
+
+
+def init_config_flow(hass):
+    """Init a configuration flow."""
+    flow = config_flow.GlancesFlowHandler()
+    flow.hass = hass
+    return flow
+
+
+async def test_form(hass):
+    """Test config entry configured successfully."""
+    flow = init_config_flow(hass)
+
+    with patch("glances_api.Glances"), patch.object(
+        Glances, "get_data", return_value=mock_coro()
+    ):
+
+        result = await flow.async_step_user(DEMO_USER_INPUT)
+
+    assert result["type"] == "create_entry"
+    assert result["title"] == NAME
+    assert result["data"] == DEMO_USER_INPUT
+
+
+async def test_form_cannot_connect(hass):
+    """Test to return error if we cannot connect."""
+    flow = init_config_flow(hass)
+
+    with patch("glances_api.Glances"):
+        result = await flow.async_step_user(DEMO_USER_INPUT)
+
+    assert result["type"] == "form"
+    assert result["errors"] == {"base": "cannot_connect"}
+
+
+async def test_form_wrong_version(hass):
+    """Test to check if wrong version is entered."""
+    flow = init_config_flow(hass)
+
+    user_input = DEMO_USER_INPUT.copy()
+    user_input.update(version=1)
+    result = await flow.async_step_user(user_input)
+
+    assert result["type"] == "form"
+    assert result["errors"] == {"version": "wrong_version"}
+
+
+async def test_form_already_configured(hass):
+    """Test host is already configured."""
+    entry = MockConfigEntry(
+        domain=DOMAIN, data=DEMO_USER_INPUT, options={CONF_SCAN_INTERVAL: 60}
+    )
+    entry.add_to_hass(hass)
+
+    flow = init_config_flow(hass)
+    result = await flow.async_step_user(DEMO_USER_INPUT)
+
+    assert result["type"] == "abort"
+    assert result["reason"] == "already_configured"
+
+
+async def test_options(hass):
+    """Test options for Glances."""
+    entry = MockConfigEntry(
+        domain=DOMAIN, data=DEMO_USER_INPUT, options={CONF_SCAN_INTERVAL: 60}
+    )
+    entry.add_to_hass(hass)
+    flow = init_config_flow(hass)
+    options_flow = flow.async_get_options_flow(entry)
+
+    result = await options_flow.async_step_init({CONF_SCAN_INTERVAL: 10})
+    assert result["type"] == "create_entry"
+    assert result["data"][CONF_SCAN_INTERVAL] == 10