diff --git a/.github/workflows/lint.yaml b/.github/workflows/lint.yaml new file mode 100644 index 0000000..4dfdbdb --- /dev/null +++ b/.github/workflows/lint.yaml @@ -0,0 +1,32 @@ +name: "Lint" + +on: + push: + branches: + - "master" + pull_request: + branches: + - "master" + +jobs: + ruff: + name: "Ruff" + runs-on: "ubuntu-latest" + steps: + - name: "Checkout the repository" + uses: "actions/checkout@v4.2.2" + + - name: "Set up Python" + uses: actions/setup-python@v5.3.0 + with: + python-version: "3.12" + cache: "pip" + + - name: "Install requirements" + run: python3 -m pip install -r requirements.txt + + - name: "Lint" + run: python3 -m ruff check . + + - name: "Format" + run: python3 -m ruff format . --check diff --git a/custom_components/mattermost/__init__.py b/custom_components/mattermost/__init__.py index 1ea78b2..7477b77 100644 --- a/custom_components/mattermost/__init__.py +++ b/custom_components/mattermost/__init__.py @@ -3,14 +3,17 @@ from __future__ import annotations import logging +from typing import TYPE_CHECKING -from homeassistant.config_entries import ConfigEntry -from homeassistant.const import Platform, CONF_NAME -from homeassistant.core import HomeAssistant +from homeassistant.const import CONF_NAME, Platform from homeassistant.helpers import config_validation as cv -from homeassistant.helpers.typing import ConfigType -from .const import DOMAIN, DATA_HASS_CONFIG +from .const import DATA_HASS_CONFIG, DOMAIN + +if TYPE_CHECKING: + from homeassistant.config_entries import ConfigEntry + from homeassistant.core import HomeAssistant + from homeassistant.helpers.typing import ConfigType _LOGGER = logging.getLogger(__name__) @@ -38,13 +41,11 @@ async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool: async def async_unload_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool: """Shut down and unload a Mattermost instance and its config entry.""" - return await hass.config_entries.async_unload_platforms(entry, PLATFORMS) # # TODO Create ConfigEntry type alias with API object # # TODO Rename type alias and update all entry annotations -# type New_NameConfigEntry = ConfigEntry[MyApi] # noqa: F821 # # # # TODO Update entry annotation @@ -54,8 +55,5 @@ async def async_unload_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool: # # TODO 1. Create API instance # # TODO 2. Validate the API connection (and authentication) # # TODO 3. Store an API object for your platforms to access -# # entry.runtime_data = MyAPI(...) # -# await hass.config_entries.async_forward_entry_setups(entry, PLATFORMS) # -# return True diff --git a/custom_components/mattermost/config_flow.py b/custom_components/mattermost/config_flow.py index 2a71a1d..5e5fd68 100644 --- a/custom_components/mattermost/config_flow.py +++ b/custom_components/mattermost/config_flow.py @@ -6,11 +6,8 @@ from typing import Any import voluptuous as vol - from homeassistant.config_entries import ConfigFlow, ConfigFlowResult from homeassistant.const import CONF_NAME -from homeassistant.core import HomeAssistant -from homeassistant.exceptions import HomeAssistantError from .const import DOMAIN @@ -53,11 +50,9 @@ async def async_step_user( # # def __init__(self, host: str) -> None: # """Initialize.""" -# self.host = host # # async def authenticate(self, username: str, password: str) -> bool: # """Test if we can authenticate with the host.""" -# return True # # # async def validate_input(hass: HomeAssistant, data: dict[str, Any]) -> dict[str, Any]: @@ -70,10 +65,7 @@ async def async_step_user( # # If your PyPI package is not built with async, pass your methods # # to the executor: # # await hass.async_add_executor_job( -# # your_validate_func, data[CONF_USERNAME], data[CONF_PASSWORD] -# # ) # -# hub = PlaceholderHub(data[CONF_HOST]) # # if not await hub.authenticate(data[CONF_USERNAME], data[CONF_PASSWORD]): # raise InvalidAuth @@ -84,35 +76,19 @@ async def async_step_user( # # InvalidAuth # # # Return info that you want to store in the config entry. -# return {"title": "Name of the device"} # # # class ConfigFlow(ConfigFlow, domain=DOMAIN): # """Handle a config flow for Mattermost.""" # -# VERSION = 1 # # async def async_step_user( # self, user_input: dict[str, Any] | None = None # ) -> ConfigFlowResult: # """Handle the initial step.""" -# errors: dict[str, str] = {} # if user_input is not None: -# try: -# info = await validate_input(self.hass, user_input) -# except CannotConnect: -# errors["base"] = "cannot_connect" -# except InvalidAuth: -# errors["base"] = "invalid_auth" -# except Exception: -# _LOGGER.exception("Unexpected exception") -# errors["base"] = "unknown" -# else: -# return self.async_create_entry(title=info["title"], data=user_input) # # return self.async_show_form( -# step_id="user", data_schema=STEP_USER_DATA_SCHEMA, errors=errors -# ) # # # class CannotConnect(HomeAssistantError): diff --git a/ruff.toml b/ruff.toml new file mode 100644 index 0000000..e0d65f4 --- /dev/null +++ b/ruff.toml @@ -0,0 +1,26 @@ +# The contents of this file is based on https://github.com/home-assistant/core/blob/dev/pyproject.toml + +target-version = "py312" + +select = [ + "ALL", +] + +ignore = [ + "ANN101", # Missing type annotation for `self` in method + "ANN401", # Dynamically typed expressions (typing.Any) are disallowed + "D203", # no-blank-line-before-class (incompatible with formatter) + "D212", # multi-line-summary-first-line (incompatible with formatter) + "COM812", # incompatible with formatter + "ISC001", # incompatible with formatter + "EXE002", # incompatible with Windows filesystem +] + +[flake8-pytest-style] +fixture-parentheses = false + +[pyupgrade] +keep-runtime-typing = true + +[mccabe] +max-complexity = 25 diff --git a/scripts/lint b/scripts/lint new file mode 100644 index 0000000..5d68d15 --- /dev/null +++ b/scripts/lint @@ -0,0 +1,8 @@ +#!/usr/bin/env bash + +set -e + +cd "$(dirname "$0")/.." + +ruff format . +ruff check . --fix