├── .gitignore ├── DOCKER.env.enc ├── README.md ├── appdaemon └── dashboards │ ├── Cameras.dash │ ├── Home.dash │ ├── Music.dash │ ├── Security.dash │ └── Vacuum.dash ├── decrypt.sh ├── docker-compose.yml ├── encrypt.sh ├── googletracker ├── .dockerignore ├── Dockerfile └── track.py ├── home-assistant ├── configuration.yaml ├── custom_components │ └── unifi │ │ ├── .translations │ │ ├── bg.json │ │ ├── ca.json │ │ ├── cs.json │ │ ├── da.json │ │ ├── de.json │ │ ├── en.json │ │ ├── es-419.json │ │ ├── es.json │ │ ├── fr.json │ │ ├── hr.json │ │ ├── hu.json │ │ ├── it.json │ │ ├── ko.json │ │ ├── lb.json │ │ ├── nl.json │ │ ├── nn.json │ │ ├── no.json │ │ ├── pl.json │ │ ├── pt-BR.json │ │ ├── pt.json │ │ ├── ro.json │ │ ├── ru.json │ │ ├── sl.json │ │ ├── sv.json │ │ ├── th.json │ │ ├── tr.json │ │ ├── zh-Hans.json │ │ └── zh-Hant.json │ │ ├── __init__.py │ │ ├── config_flow.py │ │ ├── const.py │ │ ├── controller.py │ │ ├── device_tracker.py │ │ ├── errors.py │ │ ├── manifest.json │ │ ├── sensor.py │ │ ├── strings.json │ │ └── switch.py ├── customize.yaml ├── groups.yaml ├── packages │ ├── battery_alert.yaml │ ├── cloud.yaml │ ├── crawl_space.yaml │ ├── deck │ │ ├── cameras.yaml │ │ ├── deck_lights.yaml │ │ └── deck_sensors.yaml │ ├── dining_room.yaml │ ├── dog_sitter.yaml │ ├── foyer.yaml │ ├── garage │ │ ├── button_panel.yaml │ │ ├── night_lights.yaml │ │ └── notifications.yaml │ ├── guest_mode.yaml │ ├── guest_room.yaml │ ├── half_bath.yaml │ ├── hall.yaml │ ├── kitchen │ │ ├── cabinet_lights.yaml │ │ ├── kitchen_lights.yaml │ │ └── kitchen_sensors.yaml │ ├── laundry_room.yaml │ ├── living_room │ │ ├── fireplace.yaml │ │ ├── living_room_lamps.yaml │ │ ├── living_room_lights.yaml │ │ ├── living_room_sensors.yaml │ │ ├── music.yaml │ │ └── tv.yaml │ ├── locks │ │ └── index.yaml │ ├── lukes_room.yaml │ ├── master │ │ ├── bedside_lamps.yaml │ │ ├── closet.yaml │ │ ├── master_bath.yaml │ │ └── master_bedroom.yaml │ ├── media │ │ ├── auto_cool.yaml │ │ └── media_sensors.yaml │ ├── pantry.yaml │ ├── play_room.yaml │ ├── porch.yaml │ ├── presence.yaml │ ├── scenes │ │ └── away.yaml │ ├── security │ │ ├── alarm.yaml │ │ ├── baby_monitor.yaml │ │ ├── smoke_alarm.yaml │ │ └── status.yaml │ ├── sensors │ │ ├── index.yaml │ │ ├── sonoff_s31.yaml │ │ ├── xiaomi_batteries.yaml │ │ ├── xiaomi_sensors.yaml │ │ └── zway_batteries.yaml │ ├── switches │ │ └── zway.yaml │ ├── thermostats.yaml │ ├── vacation_mode.yaml │ ├── vacuum.yaml │ ├── water_leak_sensors.yaml │ ├── weather.yaml │ ├── yard │ │ └── cameras.yaml │ └── zwave_lights.yaml ├── scripts.yaml ├── secrets.yaml.enc └── www │ ├── ali.png │ ├── blake.png │ └── custom_ui │ └── oauth.html ├── ignition.json ├── ignition.yml ├── iptables-rules-save ├── mosquitto └── mosquitto.conf ├── motion ├── Dockerfile ├── conf.d │ └── back.conf ├── mask.pgm ├── motion.conf ├── on_event_start.sh └── on_picture_save.sh ├── mqttlogger ├── .dockerignore ├── Dockerfile └── logmqtt.sh ├── nginx ├── Dockerfile ├── cameras │ ├── asset-manifest.json │ ├── favicon.ico │ ├── index.html │ ├── manifest.json │ ├── service-worker.js │ └── static │ │ ├── css │ │ ├── main.c2957830.css │ │ └── main.c2957830.css.map │ │ └── js │ │ ├── main.fcde51b5.js │ │ └── main.fcde51b5.js.map ├── conf.d │ ├── blakeshome.conf │ ├── cameras.conf │ ├── dash.conf │ ├── hass.conf │ ├── hass_auth_script.js │ ├── netdata.conf │ ├── pihole.conf │ ├── portainer.conf │ ├── public.conf │ ├── tokens.template │ ├── unifi.conf │ └── vacuum.conf ├── html │ └── index.html ├── naxsi_core.rules ├── nginx.conf └── whitelist.rules ├── nvr_cleaner ├── Dockerfile └── cleaner ├── nvr_snapshot ├── Dockerfile └── watch_and_snapshot.sh ├── oauth2_proxy ├── authenticated_emails └── oauth2_proxy.cfg ├── pihole ├── Dockerfile ├── dnsmasq.d │ ├── 03-blakeshome.conf │ ├── 04-bypass.conf │ ├── 04-pihole-static-dhcp.conf │ └── 05-dhcp-settings.conf └── mqttpub.sh ├── unifi_backup ├── Dockerfile └── backup └── valetudo_maps ├── downstairs.json ├── downstairs_vac.json └── valetudo.conf /.gitignore: -------------------------------------------------------------------------------- 1 | .vscode 2 | home-assistant/secrets.yaml 3 | DOCKER.env 4 | -------------------------------------------------------------------------------- /DOCKER.env.enc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/blakeblackshear/blakeshome-config/afe682a9bfa84aba77b3bcc6ddf5894e5fec1ada/DOCKER.env.enc -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # DEPRECATED 2 | I have moved my configuration to [blakeblackshear/blakeshome-k8s](https://github.com/blakeblackshear/blakeshome-k8s) and run on k3os now that CoreOS is no longer supported. Also, in response to the move to UI-based configuration of HomeAssistant, I no longer manage my HomeAssistant config via github. 3 | 4 | ## Overview 5 | This is the my configuration for my home server. It serves the following functions: 6 | - nginx proxy 7 | - oauth2_proxy for authentication across all applications 8 | - homeassistant 9 | - appdaemon 10 | - mqtt (mosquitto) 11 | - ffmpeg based ip camera recording 12 | - motion detection for ip cameras 13 | - (future) tensorflow based object detection for cameras 14 | - pihole for adblocking and dhcp server 15 | - unifi controller for network gear 16 | - postgres (db for homeassistant) 17 | 18 | ## HomeAssistant 19 | My config isn't very organized. Still trying to decide what works best for me. 20 | ### Components 21 | - **Switches**: Homeseer Z-Wave dimmers + Cooper 5-button Scene Controller 22 | - **Bulbs**: Hue zigbee bulbs 23 | - **Sensors**: Xiaomi zigbee sensors 24 | - **Thermostats**: Ecobee 3 lite 25 | - **Smart Plugs**: Sonoff S31 flashed with Tasmota 26 | - **Led Strips**: H801 flashed with Tasmota 27 | - **Smart Locks**: Schlage Connect Z-Wave 28 | - **Whole Home Audio**: Google Chromecast 29 | - **Voice Control**: Google Home 30 | - **Media Control**: Harmony Hub 31 | - **Vacuum**: Xiaomi Mi Vacuum Gen1 (rooted) 32 | - **Lawn Mower**: Worx Landroid M 33 | - **Cameras**: Dahua IPC-HDW5231R-Z 34 | - **Presence Detection**: Google Location Sharing + DHCP Leases + Unifi Controller 35 | - **Notifications**: Twilio + HTML5 36 | - **Custom ESP8266 Devices**: 37 | - Fireplace 38 | - Smoke/CO Detector (Kidde SM120X/CO120X) 39 | - Garage Doors 40 | 41 | ### Automations 42 | 43 | - Turn on the outside lights when the garage opens after sunset for 5 minutes or until the back door is locked 44 | - Notify me if the garage is left open while we are not home and give me the option to close it 45 | - Sync the cabinet lighting with the kitchen lights, taking into consideration daytime vs nighttime 46 | - Make sure the fireplace is off if we are not home 47 | - Integrate the Harmony Hub with the status of the Chromecast audio to automatically switch inputs when music starts, and stopping playback when switching to another activity 48 | - Unlock the back door when someone arrives home 49 | - Turn on closets, bathrooms, pantry, and laundry with motion 50 | - When it is hot in the media room, prompt to turn on the media room a/c if we are near home at 7pm 51 | - Standard lighting scenes for when we are not home and when we arrive, taking into account day vs night 52 | - Arm the alarm system when we are not home 53 | - Set off the alarm if the garage opens 54 | - Disarm the alarm when we arrive or when a valid code is entered on the smart locks 55 | - Ensure the doors are locked if we are away, and notify me if they cant be locked automatically 56 | - Baby monitor mode to send alerts if motion is detected inside the house if we are grabbing a drink at the neighbors after the kids go to bed 57 | - Notify me by text if the smoke or co alarms go off 58 | - Alert me if any battery devices drop below 25% 59 | - Dog sitter mode to notify if any motion sensors go off upstairs while we are on vacation even if the alarm is disarmed 60 | - Start the vacuum after the dog sitters lock the door if it hasnt already run in the past 24 hours 61 | - Guest mode to prevent some of the automations based on presence detection, automatically enabled when certain devices are present 62 | - Upstairs hall lamps turn on after sunrise, dim before sunset, and turn on with motion after 10pm 63 | - Notify Ali to switch over the laundry 5 minutes after it finishes if no motion has been detected. If she isn't home, wait until she gets home and then notify her 64 | - Turn on the porch light at sunset and off at sunrise 65 | - Vacation mode to randomly turn lights on and off while we are gone 66 | - Enable/disable vacation mode when we are both more than 50km away 67 | - Set the thermostats to away/home when vacation mode is turned on/off 68 | - Start the vacuum when Ali leaves to take the kids to school in the mornings 69 | - Start the vacuum when Ali arrives at the gym 70 | - Ask about starting the vacuum when we are not home on the weekends, and the vacuum hasnt run in the past 24 hours 71 | - Notify me if any of the water leak detectors detect water 72 | 73 | ## Other Stuff 74 | ### Mount data drive in CoreOS 75 | ``` 76 | sudo parted /dev/sdc mklabel gpt 77 | sudo parted -a opt /dev/sdc mkpart primary ext4 0% 100% 78 | lsblk 79 | sudo mkfs.xfs -L data /dev/sdc1 80 | sudo mkdir -p /mnt/data 81 | UUID=8200b18e-7943-4924-b458-81be1887602a /mnt/data xfs defaults 0 2 82 | sudo mount -a 83 | ``` 84 | 85 | -------------------------------------------------------------------------------- /appdaemon/dashboards/Cameras.dash: -------------------------------------------------------------------------------- 1 | ## 2 | ## Main arguments, all optional 3 | ## 4 | title: Home Panel 5 | widget_dimensions: [120, 120] 6 | widget_margins: [5, 5] 7 | columns: 10 8 | 9 | backyard: 10 | widget_type: camera 11 | entity_picture: https://cameras.blakeshome.com/nvr/back.jpg 12 | refresh: 60 13 | 14 | layout: 15 | - backyard(10x6) -------------------------------------------------------------------------------- /appdaemon/dashboards/Home.dash: -------------------------------------------------------------------------------- 1 | ## 2 | ## Main arguments, all optional 3 | ## 4 | title: Home Panel 5 | widget_dimensions: [125, 125] 6 | widget_margins: [5, 5] 7 | columns: 9 8 | 9 | clock: 10 | widget_type: clock 11 | 12 | blake_presence: 13 | widget_type: device_tracker 14 | title: Blake 15 | device: blake_phone_mqtt 16 | 17 | ali_presence: 18 | widget_type: device_tracker 19 | title: Ali 20 | device: ali_phone_mqtt 21 | 22 | living_music: 23 | widget_type: media_player 24 | title: Living Room Music 25 | entity: media_player.living_room_2 26 | 27 | back_door_lock: 28 | widget_type: lock 29 | title: Back Door 30 | entity: lock.back_door_lock 31 | 32 | front_door_lock: 33 | widget_type: lock 34 | title: Front Door 35 | entity: lock.front_door_lock 36 | 37 | blake_garage: 38 | widget_type: cover 39 | title: Blake Garage 40 | icon_on: mdi-garage-open 41 | icon_off: mdi-garage 42 | entity: cover.blake_s_garage_door 43 | 44 | ali_garage: 45 | widget_type: cover 46 | title: Ali Garage 47 | icon_on: mdi-garage-open 48 | icon_off: mdi-garage 49 | entity: cover.ali_s_garage_door 50 | 51 | entitypicture2: 52 | widget_type: entitypicture 53 | entity: media_player.living_room_2 54 | base_url: https://hass.blakeshome.com 55 | image_style: "top: 0; bottom: 0; left: 0; right: 0;" 56 | 57 | alarm: 58 | widget_type: alarm 59 | entity: alarm_control_panel.home_alarm 60 | 61 | music: 62 | widget_type: navigate 63 | title: Music 64 | dashboard: Music 65 | icon_active: mdi-music 66 | icon_inactive: mdi-music 67 | icon_active_style: "font-size: 500%;" 68 | icon_inactive_style: "font-size: 500%;" 69 | args: 70 | timeout: 10 71 | return: Home 72 | 73 | vacuum: 74 | widget_type: navigate 75 | title: Vacuum 76 | dashboard: Vacuum 77 | icon_active: mdi-robot-vacuum 78 | icon_inactive: mdi-robot-vacuum 79 | icon_active_style: "font-size: 500%;" 80 | icon_inactive_style: "font-size: 500%;" 81 | args: 82 | timeout: 10 83 | return: Home 84 | 85 | cameras: 86 | widget_type: navigate 87 | title: Cameras 88 | dashboard: Cameras 89 | icon_active: mdi-cctv 90 | icon_inactive: mdi-cctv 91 | icon_active_style: "font-size: 2000%;" 92 | icon_inactive_style: "font-size: 2000%;" 93 | args: 94 | timeout: 10 95 | return: Home 96 | 97 | security: 98 | widget_type: navigate 99 | title: Security 100 | dashboard: Security 101 | icon_active: mdi-security 102 | icon_inactive: mdi-security 103 | icon_active_style: "font-size: 2000%;" 104 | icon_inactive_style: "font-size: 2000%;" 105 | args: 106 | timeout: 10 107 | return: Home 108 | 109 | guestmode: 110 | widget_type: input_boolean 111 | title: Guest Mode 112 | icon_on: mdi-account-outline 113 | icon_off: mdi-account-outline 114 | icon_style_active: "font-size: 2000%;" 115 | icon_style_inactive: "font-size: 2000%;" 116 | entity: input_boolean.guest_mode 117 | 118 | weather_today: 119 | widget_type: weather 120 | title: Today 121 | show_forecast: 1 122 | prefer_icons: 1 123 | forecast_title: Today 124 | sensors: 125 | icon: sensor.dark_sky_icon 126 | precip_probability: sensor.dark_sky_precip_probability 127 | precip_intensity: sensor.dark_sky_precip_intensity 128 | precip_type: sensor.dark_sky_precip 129 | wind_speed: sensor.dark_sky_wind_speed 130 | wind_bearing: sensor.dark_sky_wind_bearing 131 | forecast_icon: sensor.dark_sky_icon_1 132 | forecast_temperature_min: sensor.dark_sky_daily_low_temperature_1 133 | forecast_temperature_max: sensor.dark_sky_daily_high_temperature_1 134 | forecast_precip_probability: sensor.dark_sky_precip_probability_1 135 | forecast_precip_type: sensor.dark_sky_precip_1 136 | 137 | layout: 138 | - spacer(7x1), sensor.outside_temperature, weather_today 139 | - 140 | - spacer, spacer, music, clock(3x1), vacuum 141 | - cameras(3x3),security(3x3),guestmode(3x3) -------------------------------------------------------------------------------- /appdaemon/dashboards/Music.dash: -------------------------------------------------------------------------------- 1 | ## 2 | ## Main arguments, all optional 3 | ## 4 | title: Home Panel 5 | widget_dimensions: [120, 120] 6 | widget_margins: [5, 5] 7 | columns: 10 8 | 9 | clock: 10 | widget_type: clock 11 | 12 | living_music: 13 | widget_type: media_player 14 | title: Living Room Music 15 | entity: media_player.living_room_2 16 | 17 | entitypicture2: 18 | widget_type: entitypicture 19 | entity: media_player.living_room_2 20 | base_url: https://hass.blakeshome.com 21 | image_style: "top: 0; bottom: 0; left: 0; right: 0;" 22 | 23 | alarm: 24 | widget_type: alarm 25 | entity: alarm_control_panel.home_alarm 26 | 27 | layout: 28 | - living_music(3x3), entitypicture2(4x3) -------------------------------------------------------------------------------- /appdaemon/dashboards/Security.dash: -------------------------------------------------------------------------------- 1 | ## 2 | ## Main arguments, all optional 3 | ## 4 | title: Home Panel 5 | widget_dimensions: [120, 120] 6 | widget_margins: [5, 5] 7 | columns: 10 8 | 9 | alarm: 10 | widget_type: alarm 11 | entity: alarm_control_panel.home_alarm 12 | 13 | blake_presence: 14 | widget_type: device_tracker 15 | title: Blake 16 | device: blake_phone_mqtt 17 | 18 | ali_presence: 19 | widget_type: device_tracker 20 | title: Ali 21 | device: ali_phone_mqtt 22 | 23 | layout: 24 | - sensor.locked_up, blake_presence, ali_presence 25 | - alarm,binary_sensor.smoke_detector,binary_sensor.co_detector,binary_sensor.back_door,binary_sensor.front_door,binary_sensor.pantry_motion,binary_sensor.half_bath_motion,binary_sensor.dining_motion,binary_sensor.kitchen_motion,binary_sensor.living_room_motion 26 | - lock.back_door_lock,lock.front_door_lock,binary_sensor.laundry_room_motion,binary_sensor.hall_motion,binary_sensor.boys_doors_motion,binary_sensor.master_closet_motion,binary_sensor.blake_bedside_motion,binary_sensor.ali_bedside_motion,binary_sensor.backyard_camera_motion,binary_sensor.playroom_motion 27 | - binary_sensor.living_room_shutter_1,binary_sensor.living_room_shutter_2,binary_sensor.living_room_shutter_3,binary_sensor.living_room_shutter_4,binary_sensor.living_room_shutter_5,binary_sensor.living_room_shutter_6,binary_sensor.living_room_shutter_7,binary_sensor.dining_room_shutter_1,binary_sensor.dining_room_shutter_2,binary_sensor.play_room_shutter_1 28 | - binary_sensor.play_room_shutter_2,cover.ali_s_garage_door,cover.blake_s_garage_door -------------------------------------------------------------------------------- /appdaemon/dashboards/Vacuum.dash: -------------------------------------------------------------------------------- 1 | ## 2 | ## Main arguments, all optional 3 | ## 4 | title: Home Panel 5 | widget_dimensions: [120, 120] 6 | widget_margins: [5, 5] 7 | columns: 10 8 | 9 | vacuum: 10 | widget_type: switch 11 | title: Vacuum 12 | entity: vacuum.xiaomi_vacuum_cleaner 13 | icon_style_active: "font-size: 500%; color: #aaff00" 14 | icon_style_inactive: "font-size: 500%" 15 | icon_on: mdi-google-circles-group 16 | icon_off: mdi-broom 17 | 18 | battery: 19 | title: Battery 20 | widget_type: sensor 21 | units: "%" 22 | entity: vacuum.xiaomi_vacuum_cleaner.battery_level 23 | 24 | fan_speed: 25 | title: Fan Speed 26 | widget_type: sensor 27 | entity: vacuum.xiaomi_vacuum_cleaner.fan_speed 28 | 29 | status: 30 | widget_type: sensor 31 | entity: vacuum.xiaomi_vacuum_cleaner.status 32 | 33 | layout: 34 | - vacuum(2x2) 35 | - status, battery, fan_speed -------------------------------------------------------------------------------- /decrypt.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | DIR=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd ) 4 | 5 | if [ -z ${BLAKESHOME_PASS+x} ]; then 6 | read -s -p "Password:" BLAKESHOME_PASS 7 | export BLAKESHOME_PASS 8 | fi 9 | 10 | /usr/bin/openssl enc -aes-256-cbc -d -salt -in $DIR/home-assistant/secrets.yaml.enc -out $DIR/home-assistant/secrets.yaml -pass env:BLAKESHOME_PASS 11 | /usr/bin/openssl enc -aes-256-cbc -d -salt -in $DIR/DOCKER.env.enc -out $DIR/DOCKER.env -pass env:BLAKESHOME_PASS 12 | -------------------------------------------------------------------------------- /encrypt.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | DIR=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd ) 4 | 5 | if [ -z ${BLAKESHOME_PASS+x} ]; then 6 | read -s -p "Password:" BLAKESHOME_PASS 7 | export BLAKESHOME_PASS 8 | fi 9 | 10 | /usr/bin/openssl enc -aes-256-cbc -salt -in $DIR/home-assistant/secrets.yaml -out $DIR/home-assistant/secrets.yaml.enc -pass env:BLAKESHOME_PASS 11 | /usr/bin/openssl enc -aes-256-cbc -salt -in $DIR/DOCKER.env -out $DIR/DOCKER.env.enc -pass env:BLAKESHOME_PASS 12 | -------------------------------------------------------------------------------- /googletracker/.dockerignore: -------------------------------------------------------------------------------- 1 | Dockerfile -------------------------------------------------------------------------------- /googletracker/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM python:3.5 2 | 3 | RUN pip3 install --no-cache-dir locationsharinglib==0.3.0 paho-mqtt geopy 4 | 5 | COPY . . 6 | 7 | CMD [ "python", "-u", "track.py" ] -------------------------------------------------------------------------------- /googletracker/track.py: -------------------------------------------------------------------------------- 1 | import os, datetime, json, time 2 | from locationsharinglib import Service 3 | import paho.mqtt.client as mqtt 4 | from geopy.distance import vincenty 5 | 6 | email = os.environ['EMAIL'] 7 | password = os.environ['PASSWORD'] 8 | mqtt_server = os.environ['MQTT_SERVER'] 9 | poll_interval = os.environ['POLL_INTERVAL'] 10 | home_latitude = os.environ['HOME_LATITUDE'] 11 | home_longitude = os.environ['HOME_LONGITUDE'] 12 | 13 | print("Pulling locations for", email) 14 | 15 | client = mqtt.Client() 16 | client.connect(mqtt_server, 1883, 60) 17 | client.loop_start() 18 | 19 | print("Connected to", mqtt_server) 20 | 21 | service = Service(email, password) 22 | 23 | home = (float(home_latitude), float(home_longitude)) 24 | 25 | while True: 26 | people = service.get_all_people() 27 | print("Found "+str(len(people))+" people.") 28 | for person in people: 29 | # ignore locations that are not at least accurate within 1000 meters 30 | if person._accuracy > 1000: 31 | continue 32 | mqtt_topic = 'google/location/' + person.full_name.lower().replace(" ","_") 33 | mqtt_data = { 34 | "latitude": person.latitude, 35 | "longitude": person.longitude, 36 | "datetime": int(person.datetime.timestamp()), 37 | "gps_accuracy": person._accuracy 38 | } 39 | 40 | # if home is within the accuracy radius, assume home 41 | # if vincenty(home,(person.latitude, person.longitude)).meters < person._accuracy: 42 | # mqtt_data["latitude"] = home[0] 43 | # mqtt_data["longitude"] = home[1] 44 | 45 | print(mqtt_topic, mqtt_data) 46 | client.publish(mqtt_topic, json.dumps(mqtt_data), retain=False) 47 | 48 | time.sleep(float(poll_interval)) 49 | -------------------------------------------------------------------------------- /home-assistant/configuration.yaml: -------------------------------------------------------------------------------- 1 | homeassistant: 2 | # Name of the location where Home Assistant is running 3 | name: Blakeshome 4 | # Location required to calculate the time the sun rises and sets 5 | latitude: !secret blakeshome_latitude 6 | longitude: !secret blakeshome_longitude 7 | # Impacts weather/sunrise data (altitude above sea level in meters) 8 | elevation: 229 9 | # metric for Metric, imperial for Imperial 10 | unit_system: imperial 11 | # Pick yours from here: http://en.wikipedia.org/wiki/List_of_tz_database_time_zones 12 | time_zone: America/Chicago 13 | 14 | customize: !include customize.yaml 15 | packages: !include_dir_named packages 16 | 17 | # Enables the frontend 18 | frontend: 19 | extra_html_url: /local/custom_ui/oauth.html 20 | extra_html_url_es5: /local/custom_ui/oauth.html 21 | 22 | # Enables configuration UI 23 | config: 24 | 25 | http: 26 | base_url: https://hass.blakeshome.com 27 | use_x_forwarded_for: True 28 | trusted_proxies: 29 | - 127.0.0.1 30 | 31 | # Checks for available updates 32 | # Note: This component will send some information about your system to 33 | # the developers to assist with development of Home Assistant. 34 | # For more information, please see: 35 | # https://home-assistant.io/blog/2016/10/25/explaining-the-updater/ 36 | updater: 37 | 38 | # Discover some devices automatically 39 | discovery: 40 | ignore: 41 | - plex_mediaserver 42 | 43 | # Allows you to issue voice commands from the frontend in enabled browsers 44 | conversation: 45 | 46 | # Enables support for tracking state changes over time 47 | history: 48 | 49 | # View all events in a logbook 50 | logbook: 51 | exclude: 52 | entities: 53 | - sensor.date 54 | - sensor.date_time 55 | - sensor.time 56 | - sensor.time_date 57 | - sensor.time_utc 58 | - automation.update_battery_status_group_members 59 | - automation.battery_notification 60 | - automation.battery_notification_clear 61 | - automation.battery_sensor_from_attributes 62 | - automation.clear_mqtt_topic 63 | - automation.filter_out_blake_s_location_updates_that_are_old_and_republish 64 | - automation.filter_out_ali_s_location_updates_that_are_old_and_republish 65 | - automation.update_blake_last_seen_from_unifi 66 | - automation.update_ali_last_seen_from_unifi 67 | 68 | recorder: 69 | db_url: !secret postgres_url 70 | 71 | system_health: 72 | 73 | # Track the sun 74 | sun: 75 | 76 | # Text to speech 77 | tts: 78 | - platform: google_translate 79 | 80 | # MQTT 81 | mqtt: 82 | broker: mqtt.blakeshome.com 83 | birth_message: 84 | topic: 'hass/status' 85 | payload: 'online' 86 | retain: true 87 | will_message: 88 | topic: 'hass/status' 89 | payload: 'offline' 90 | retain: true 91 | discovery: true 92 | discovery_prefix: hass 93 | 94 | map: 95 | 96 | emulated_hue: 97 | 98 | vacuum: 99 | - platform: xiaomi_miio 100 | host: 192.168.2.36 101 | token: !secret xiaomi_vacuum_token 102 | 103 | cover: 104 | - platform: mqtt 105 | name: "Blake's Garage Door" 106 | command_topic: "taproot/garage/blake/set" 107 | state_topic: "taproot/garage/blake/status" 108 | - platform: mqtt 109 | name: "Ali's Garage Door" 110 | command_topic: "taproot/garage/ali/set" 111 | state_topic: "taproot/garage/ali/status" 112 | 113 | ecobee: 114 | api_key: !secret ecobee_api_key 115 | 116 | group: !include groups.yaml 117 | script: !include scripts.yaml 118 | 119 | sensor: 120 | - platform: time_date 121 | display_options: 122 | - 'time' 123 | - 'date' 124 | - 'date_time' 125 | - 'time_date' 126 | - 'time_utc' 127 | - platform: darksky 128 | api_key: !secret dark_sky_secret 129 | forecast: 130 | - 1 131 | monitored_conditions: 132 | - summary 133 | - temperature 134 | - apparent_temperature 135 | - humidity 136 | - precip_probability 137 | - precip_intensity 138 | - precip_type 139 | - wind_speed 140 | - wind_bearing 141 | - pressure 142 | - icon 143 | 144 | twilio: 145 | account_sid: !secret twilio_account_sid 146 | auth_token: !secret twilio_auth_token 147 | 148 | telegram_bot: 149 | - platform: webhooks 150 | api_key: !secret telegram_api_key 151 | trusted_networks: 152 | - 149.154.160.0/20 153 | - 91.108.4.0/22 154 | allowed_chat_ids: 155 | - 707447684 156 | 157 | notify: 158 | - name: blake_telegram 159 | platform: telegram 160 | chat_id: 707447684 161 | - name: html5 162 | platform: html5 163 | gcm_api_key: !secret google_messaging_server_key 164 | gcm_sender_id: !secret google_messaging_sender_id 165 | - name: blakeshome_call 166 | platform: twilio_call 167 | from_number: !secret twilio_phone_number 168 | - name: blakeshome_sms 169 | platform: twilio_sms 170 | from_number: !secret twilio_phone_number 171 | 172 | panel_custom: 173 | - name: frigate 174 | sidebar_title: Frigate 175 | sidebar_icon: mdi:cctv 176 | # This is the url that will load the panel 177 | url_path: frigate 178 | # Location where the panel is hosted during development 179 | js_url: https://cameras.blakeshome.com/static/js/main.fcde51b5.js 180 | # We want to load in an iframe to work around limitations in React 181 | embed_iframe: true 182 | # This will be available as prop `panel.config`. 183 | config: 184 | api_url: https://cameras.blakeshome.com 185 | camera_streams: back -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/bg.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "\u0421\u0430\u0439\u0442\u044a\u0442 \u0435 \u0432\u0435\u0447\u0435 \u043a\u043e\u043d\u0444\u0438\u0433\u0443\u0440\u0438\u0440\u0430\u043d", 5 | "user_privilege": "\u041f\u043e\u0442\u0440\u0435\u0431\u0438\u0442\u0435\u043b\u044f\u0442 \u0442\u0440\u044f\u0431\u0432\u0430 \u0434\u0430 \u0435 \u0430\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0442\u043e\u0440" 6 | }, 7 | "error": { 8 | "faulty_credentials": "\u041d\u0435\u0432\u0430\u043b\u0438\u0434\u043d\u0438 \u0438\u0434\u0435\u043d\u0442\u0438\u0444\u0438\u043a\u0430\u0446\u0438\u043e\u043d\u043d\u0438 \u0434\u0430\u043d\u043d\u0438", 9 | "service_unavailable": "\u041d\u044f\u043c\u0430 \u043d\u0430\u043b\u0438\u0447\u043d\u0430 \u0443\u0441\u043b\u0443\u0433\u0430" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "\u0410\u0434\u0440\u0435\u0441", 15 | "password": "\u041f\u0430\u0440\u043e\u043b\u0430", 16 | "port": "\u041f\u043e\u0440\u0442", 17 | "site": "Site ID", 18 | "username": "\u041f\u043e\u0442\u0440\u0435\u0431\u0438\u0442\u0435\u043b\u0441\u043a\u043e \u0438\u043c\u0435", 19 | "verify_ssl": "\u041a\u043e\u043d\u0442\u0440\u043e\u043b\u0435\u0440\u044a\u0442 \u0438\u0437\u043f\u043e\u043b\u0437\u0432\u0430 \u043d\u0430\u0434\u0435\u0436\u0434\u0435\u043d \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442" 20 | }, 21 | "title": "\u041d\u0430\u0441\u0442\u0440\u043e\u0439\u0432\u0430\u043d\u0435 \u043d\u0430 UniFi \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u0435\u0440" 22 | } 23 | }, 24 | "title": "UniFi \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u0435\u0440" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "\u0412\u0440\u0435\u043c\u0435 \u0432 \u0441\u0435\u043a\u0443\u043d\u0434\u0438 \u043e\u0442 \u043f\u043e\u0441\u043b\u0435\u0434\u043d\u043e\u0442\u043e \u0432\u0438\u0436\u0434\u0430\u043d\u0435 \u0437\u0430 \u0434\u0430 \u0441\u0435 \u0441\u0447\u0435\u0442\u0435 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u043e, \u043a\u0430\u0442\u043e \u043e\u0442\u0441\u044a\u0441\u0442\u0432\u0430\u0449\u043e", 31 | "track_clients": "\u041f\u0440\u043e\u0441\u043b\u0435\u0434\u044f\u0432\u0430\u043d\u0435 \u043d\u0430 \u043c\u0440\u0435\u0436\u043e\u0432\u0438 \u043a\u043b\u0438\u0435\u043d\u0442\u0438", 32 | "track_devices": "\u041f\u0440\u043e\u0441\u043b\u0435\u0434\u044f\u0432\u0430\u043d\u0435 \u043d\u0430 \u043c\u0440\u0435\u0436\u043e\u0432\u0438 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430 (Ubiquiti \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430)", 33 | "track_wired_clients": "\u0412\u043a\u043b\u044e\u0447\u0435\u0442\u0435 \u043d\u0430 \u043a\u043b\u0438\u0435\u043d\u0442\u0438 \u0441\u0432\u044a\u0440\u0437\u0430\u043d\u0438 \u0441 \u043a\u0430\u0431\u0435\u043b" 34 | } 35 | } 36 | } 37 | } 38 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/ca.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "El lloc del controlador ja est\u00e0 configurat", 5 | "user_privilege": "L'usuari ha de ser administrador" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Credencials d'usuari incorrectes", 9 | "service_unavailable": "Servei no disponible" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Amfitri\u00f3", 15 | "password": "Contrasenya", 16 | "port": "Port", 17 | "site": "ID del lloc", 18 | "username": "Nom d'usuari", 19 | "verify_ssl": "El controlador est\u00e0 utilitzant un certificat adequat" 20 | }, 21 | "title": "Configuraci\u00f3 del controlador UniFi" 22 | } 23 | }, 24 | "title": "Controlador UniFi" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Temps (en segons) des de s'ha vist per \u00faltima vegada fins que es considera a fora", 31 | "track_clients": "Segueix clients de la xarxa", 32 | "track_devices": "Segueix dispositius de la xarxa (dispositius Ubiquiti)", 33 | "track_wired_clients": "Inclou clients de xarxa per cable" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "un", 39 | "other": "altre" 40 | } 41 | }, 42 | "statistics_sensors": { 43 | "data": { 44 | "allow_bandwidth_sensors": "Crea sensors d'\u00fas d'ample de banda per a clients de la xarxa" 45 | } 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/cs.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "\u0158adi\u010d je ji\u017e nakonfigurov\u00e1n", 5 | "user_privilege": "U\u017eivatel mus\u00ed b\u00fdt spr\u00e1vcem" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Chybn\u00e9 p\u0159ihla\u0161ovac\u00ed \u00fadaje", 9 | "service_unavailable": "Slu\u017eba nen\u00ed dostupn\u00e1" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Hostitel", 15 | "password": "Heslo", 16 | "port": "Port", 17 | "site": "ID s\u00edt\u011b", 18 | "username": "U\u017eivatelsk\u00e9 jm\u00e9no", 19 | "verify_ssl": "\u0158adi\u010d pou\u017e\u00edv\u00e1 spr\u00e1vn\u00fd certifik\u00e1t" 20 | }, 21 | "title": "Nastaven\u00ed UniFi \u0159adi\u010de" 22 | } 23 | }, 24 | "title": "UniFi \u0159adi\u010d" 25 | } 26 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/da.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Controller site er allerede konfigureret", 5 | "user_privilege": "Bruger skal v\u00e6re administrator" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Ugyldige legitimationsoplysninger", 9 | "service_unavailable": "Service utilg\u00e6ngelig" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "V\u00e6rt", 15 | "password": "Adgangskode", 16 | "port": "Port", 17 | "site": "Site ID", 18 | "username": "Brugernavn", 19 | "verify_ssl": "Controller bruger korrekt certifikat" 20 | }, 21 | "title": "Konfigurer UniFi Controller" 22 | } 23 | }, 24 | "title": "UniFi Controller" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Tid i sekunder fra sidst set indtil betragtet som v\u00e6k", 31 | "track_clients": "Spor netv\u00e6rksklienter", 32 | "track_devices": "Spor netv\u00e6rksenheder (Ubiquiti-enheder)", 33 | "track_wired_clients": "Inkluder kablede netv\u00e6rksklienter" 34 | } 35 | }, 36 | "statistics_sensors": { 37 | "data": { 38 | "allow_bandwidth_sensors": "Opret b\u00e5ndbredde sensorer for netv\u00e6rksklienter" 39 | } 40 | } 41 | } 42 | } 43 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/de.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Controller-Site ist bereits konfiguriert", 5 | "user_privilege": "Der Benutzer muss Administrator sein" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Ung\u00fcltige Anmeldeinformationen", 9 | "service_unavailable": "Kein Dienst verf\u00fcgbar" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Host", 15 | "password": "Passwort", 16 | "port": "Port", 17 | "site": "Site-ID", 18 | "username": "Benutzername", 19 | "verify_ssl": "Controller mit ordnungsgem\u00e4ssem Zertifikat" 20 | }, 21 | "title": "UniFi-Controller einrichten" 22 | } 23 | }, 24 | "title": "UniFi-Controller" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Zeit in Sekunden vom letzten Gesehenen bis zur Entfernung", 31 | "track_clients": "Nachverfolgen von Netzwerkclients", 32 | "track_devices": "Verfolgen von Netzwerkger\u00e4ten (Ubiquiti-Ger\u00e4te)", 33 | "track_wired_clients": "Einbinden von kabelgebundenen Netzwerk-Clients" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "eins", 39 | "other": "andere" 40 | } 41 | }, 42 | "statistics_sensors": { 43 | "data": { 44 | "allow_bandwidth_sensors": "Erstellen von Bandbreiten-Nutzungssensoren f\u00fcr Netzwerk-Clients" 45 | } 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/en.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Controller site is already configured", 5 | "user_privilege": "User needs to be administrator" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Bad user credentials", 9 | "service_unavailable": "No service available" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Host", 15 | "password": "Password", 16 | "port": "Port", 17 | "site": "Site ID", 18 | "username": "User name", 19 | "verify_ssl": "Controller using proper certificate" 20 | }, 21 | "title": "Set up UniFi Controller" 22 | } 23 | }, 24 | "title": "UniFi Controller" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Time in seconds from last seen until considered away", 31 | "track_clients": "Track network clients", 32 | "track_devices": "Track network devices (Ubiquiti devices)", 33 | "track_wired_clients": "Include wired network clients" 34 | } 35 | }, 36 | "statistics_sensors": { 37 | "data": { 38 | "allow_bandwidth_sensors": "Create bandwidth usage sensors for network clients" 39 | } 40 | } 41 | } 42 | } 43 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/es-419.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "El sitio del controlador ya est\u00e1 configurado", 5 | "user_privilege": "El usuario necesita ser administrador" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Credenciales de usuario incorrectas", 9 | "service_unavailable": "No hay servicio disponible" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Host", 15 | "password": "Contrase\u00f1a", 16 | "port": "Puerto", 17 | "site": "ID del sitio", 18 | "username": "Nombre de usuario", 19 | "verify_ssl": "Controlador usando el certificado apropiado" 20 | }, 21 | "title": "Configurar el controlador UniFi" 22 | } 23 | }, 24 | "title": "Controlador UniFi" 25 | } 26 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/es.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "El sitio del controlador ya est\u00e1 configurado", 5 | "user_privilege": "El usuario debe ser administrador" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Credenciales de usuario incorrectas", 9 | "service_unavailable": "Servicio No disponible" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Host", 15 | "password": "Contrase\u00f1a", 16 | "port": "Puerto", 17 | "site": "ID del sitio", 18 | "username": "Nombre de usuario", 19 | "verify_ssl": "Controlador usando el certificado adecuado" 20 | }, 21 | "title": "Configurar el controlador UniFi" 22 | } 23 | }, 24 | "title": "Controlador UniFi" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Tiempo en segundos desde la \u00faltima vez que se vio hasta considerarlo desconectado", 31 | "track_clients": "Seguimiento de los clientes de red", 32 | "track_devices": "Rastree dispositivos de red (dispositivos Ubiquiti)", 33 | "track_wired_clients": "Incluir clientes de red cableada" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "uno", 39 | "other": "otro" 40 | } 41 | }, 42 | "statistics_sensors": { 43 | "data": { 44 | "allow_bandwidth_sensors": "Crear sensores para monitorizar uso de ancho de banda de clientes de red" 45 | } 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/fr.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Le contr\u00f4leur est d\u00e9j\u00e0 configur\u00e9", 5 | "user_privilege": "L'utilisateur doit \u00eatre administrateur" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Mauvaises informations d'identification de l'utilisateur", 9 | "service_unavailable": "Aucun service disponible" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "H\u00f4te", 15 | "password": "Mot de passe", 16 | "port": "Port", 17 | "site": "ID du site", 18 | "username": "Nom d'utilisateur", 19 | "verify_ssl": "Contr\u00f4leur utilisant un certificat appropri\u00e9" 20 | }, 21 | "title": "Configurer le contr\u00f4leur UniFi" 22 | } 23 | }, 24 | "title": "Contr\u00f4leur UniFi" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Temps en secondes depuis la derni\u00e8re vue avant de consid\u00e9rer comme absent", 31 | "track_clients": "Suivre les clients du r\u00e9seau", 32 | "track_devices": "Suivre les p\u00e9riph\u00e9riques r\u00e9seau (p\u00e9riph\u00e9riques Ubiquiti)", 33 | "track_wired_clients": "Inclure les clients du r\u00e9seau filaire" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "Vide", 39 | "other": "Vide" 40 | } 41 | }, 42 | "statistics_sensors": { 43 | "data": { 44 | "allow_bandwidth_sensors": "Cr\u00e9er des capteurs d'utilisation de la bande passante pour les clients r\u00e9seau" 45 | } 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/hr.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "step": { 4 | "user": { 5 | "data": { 6 | "host": "Host", 7 | "password": "Lozinka", 8 | "port": "Port", 9 | "username": "Korisni\u010dko ime" 10 | } 11 | } 12 | } 13 | } 14 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/hu.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "user_privilege": "A felhaszn\u00e1l\u00f3nak rendszergazd\u00e1nak kell lennie" 5 | }, 6 | "error": { 7 | "faulty_credentials": "Rossz felhaszn\u00e1l\u00f3i hiteles\u00edt\u0151 adatok", 8 | "service_unavailable": "Nincs el\u00e9rhet\u0151 szolg\u00e1ltat\u00e1s" 9 | }, 10 | "step": { 11 | "user": { 12 | "data": { 13 | "host": "Hoszt", 14 | "password": "Jelsz\u00f3", 15 | "port": "Port", 16 | "site": "Site azonos\u00edt\u00f3", 17 | "username": "Felhaszn\u00e1l\u00f3n\u00e9v", 18 | "verify_ssl": "Vez\u00e9rl\u0151 megfelel\u0151 tan\u00fas\u00edtv\u00e1nnyal" 19 | }, 20 | "title": "UniFi vez\u00e9rl\u0151 be\u00e1ll\u00edt\u00e1sa" 21 | } 22 | }, 23 | "title": "UniFi Vez\u00e9rl\u0151" 24 | } 25 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/it.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Il sito del Controller \u00e8 gi\u00e0 configurato", 5 | "user_privilege": "L'utente deve essere amministratore" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Credenziali utente non valide", 9 | "service_unavailable": "Servizio non disponibile" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Host", 15 | "password": "Password", 16 | "port": "Porta", 17 | "site": "ID del sito", 18 | "username": "Nome utente", 19 | "verify_ssl": "Il Controller sta utilizzando il certificato corretto" 20 | }, 21 | "title": "Configura l'UniFi Controller" 22 | } 23 | }, 24 | "title": "UniFi Controller" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Tempo in secondi dall'ultima volta che viene visto fino a quando non \u00e8 considerato lontano", 31 | "track_clients": "Traccia i client di rete", 32 | "track_devices": "Tracciare i dispositivi di rete (dispositivi Ubiquiti)", 33 | "track_wired_clients": "Includi i client di rete cablata" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "uno", 39 | "other": "altro" 40 | } 41 | }, 42 | "statistics_sensors": { 43 | "data": { 44 | "allow_bandwidth_sensors": "Creare sensori di utilizzo della larghezza di banda per i client di rete" 45 | } 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/ko.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "\ucee8\ud2b8\ub864\ub7ec \uc0ac\uc774\ud2b8\uac00 \uc774\ubbf8 \uad6c\uc131\ub418\uc5c8\uc2b5\ub2c8\ub2e4", 5 | "user_privilege": "\uc0ac\uc6a9\uc790\ub294 \uad00\ub9ac\uc790\uc5ec\uc57c \ud569\ub2c8\ub2e4" 6 | }, 7 | "error": { 8 | "faulty_credentials": "\uc0ac\uc6a9\uc790 \uc790\uaca9\uc99d\uba85\uc774 \uc798\ubabb\ub418\uc5c8\uc2b5\ub2c8\ub2e4", 9 | "service_unavailable": "\uc0ac\uc6a9\ud560 \uc218 \uc788\ub294 \uc11c\ube44\uc2a4\uac00 \uc5c6\uc2b5\ub2c8\ub2e4" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "\ud638\uc2a4\ud2b8", 15 | "password": "\ube44\ubc00\ubc88\ud638", 16 | "port": "\ud3ec\ud2b8", 17 | "site": "\uc0ac\uc774\ud2b8 ID", 18 | "username": "\uc0ac\uc6a9\uc790 \uc774\ub984", 19 | "verify_ssl": "\uc62c\ubc14\ub978 \uc778\uc99d\uc11c\ub97c \uc0ac\uc6a9\ud558\ub294 \ucee8\ud2b8\ub864\ub7ec" 20 | }, 21 | "title": "UniFi \ucee8\ud2b8\ub864\ub7ec \uc124\uc815" 22 | } 23 | }, 24 | "title": "UniFi \ucee8\ud2b8\ub864\ub7ec" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "\ub9c8\uc9c0\ub9c9\uc73c\ub85c \ud655\uc778\ub41c \uc2dc\uac04\ubd80\ud130 \uc678\ucd9c \uc0c1\ud0dc\ub85c \uac04\uc8fc\ub418\ub294 \uc2dc\uac04 (\ucd08)", 31 | "track_clients": "\ub124\ud2b8\uc6cc\ud06c \ud074\ub77c\uc774\uc5b8\ud2b8 \ucd94\uc801 \ub300\uc0c1", 32 | "track_devices": "\ub124\ud2b8\uc6cc\ud06c \uae30\uae30 \ucd94\uc801 (Ubiquiti \uae30\uae30)", 33 | "track_wired_clients": "\uc720\uc120 \ub124\ud2b8\uc6cc\ud06c \ud074\ub77c\uc774\uc5b8\ud2b8 \ud3ec\ud568" 34 | } 35 | }, 36 | "statistics_sensors": { 37 | "data": { 38 | "allow_bandwidth_sensors": "\ub124\ud2b8\uc6cc\ud06c \ud074\ub77c\uc774\uc5b8\ud2b8\ub97c \uc704\ud55c \ub300\uc5ed\ud3ed \uc0ac\uc6a9\ub7c9 \uc13c\uc11c \uc0dd\uc131\ud558\uae30" 39 | } 40 | } 41 | } 42 | } 43 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/lb.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Kontroller Site ass scho konfigur\u00e9iert", 5 | "user_privilege": "Benotzer muss een Administrator sinn" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Ong\u00eblteg Login Informatioune", 9 | "service_unavailable": "Keen Service disponibel" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Host", 15 | "password": "Passwuert", 16 | "port": "Port", 17 | "site": "Site ID", 18 | "username": "Benotzer", 19 | "verify_ssl": "Kontroller benotzt g\u00ebltegen Zertifikat" 20 | }, 21 | "title": "Unifi Kontroller ariichten" 22 | } 23 | }, 24 | "title": "Unifi Kontroller" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Z\u00e4it a Sekonne vum leschten Z\u00e4itpunkt un bis den Apparat als \u00ebnnerwee consider\u00e9iert g\u00ebtt", 31 | "track_clients": "Netzwierk Cliente verfollegen", 32 | "track_devices": "Netzwierk Apparater (Ubiquiti Apparater) verfollegen", 33 | "track_wired_clients": "Kabel Netzwierk Cliente abez\u00e9ien" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "Een", 39 | "other": "M\u00e9i" 40 | } 41 | }, 42 | "statistics_sensors": { 43 | "data": { 44 | "allow_bandwidth_sensors": "Bandbreet Benotzung Sensore fir Netzwierk Cliente erstellen" 45 | } 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/nl.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Controller site is al geconfigureerd", 5 | "user_privilege": "Gebruiker moet beheerder zijn" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Foutieve gebruikersgegevens", 9 | "service_unavailable": "Geen service beschikbaar" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Host", 15 | "password": "Wachtwoord", 16 | "port": "Poort", 17 | "site": "Site ID", 18 | "username": "Gebruikersnaam", 19 | "verify_ssl": "Controller gebruik van het juiste certificaat" 20 | }, 21 | "title": "Stel de UniFi-controller in" 22 | } 23 | }, 24 | "title": "UniFi-controller" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Tijd in seconden vanaf laatst gezien tot beschouwd als weg", 31 | "track_clients": "Volg netwerkclients", 32 | "track_devices": "Netwerkapparaten volgen (Ubiquiti-apparaten)", 33 | "track_wired_clients": "Inclusief bedrade netwerkcli\u00ebnten" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "Leeg", 39 | "other": "Leeg" 40 | } 41 | }, 42 | "statistics_sensors": { 43 | "data": { 44 | "allow_bandwidth_sensors": "Maak bandbreedtegebruiksensoren voor netwerkclients" 45 | } 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/nn.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "step": { 4 | "user": { 5 | "data": { 6 | "username": "Brukarnamn" 7 | } 8 | } 9 | } 10 | } 11 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/no.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Kontroller nettstedet er allerede konfigurert", 5 | "user_privilege": "Bruker m\u00e5 v\u00e6re administrator" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Ugyldig brukerlegitimasjon", 9 | "service_unavailable": "Ingen tjeneste tilgjengelig" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Vert", 15 | "password": "Passord", 16 | "port": "Port", 17 | "site": "Nettsted-ID", 18 | "username": "Brukernavn", 19 | "verify_ssl": "Kontroller bruker riktig sertifikat" 20 | }, 21 | "title": "Sett opp UniFi kontroller" 22 | } 23 | }, 24 | "title": "UniFi kontroller" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Tid i sekunder fra sist sett til den ble ansett borte", 31 | "track_clients": "Spor nettverksklienter", 32 | "track_devices": "Spore nettverksenheter (Ubiquiti-enheter)", 33 | "track_wired_clients": "Inkluder kablede nettverksklienter" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "en", 39 | "other": "andre" 40 | } 41 | }, 42 | "statistics_sensors": { 43 | "data": { 44 | "allow_bandwidth_sensors": "Opprett b\u00e5ndbreddesensorer for nettverksklienter" 45 | } 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/pl.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Witryna kontrolera jest ju\u017c skonfigurowana", 5 | "user_privilege": "U\u017cytkownik musi by\u0107 administratorem" 6 | }, 7 | "error": { 8 | "faulty_credentials": "B\u0142\u0119dne dane uwierzytelniaj\u0105ce", 9 | "service_unavailable": "Brak dost\u0119pnych us\u0142ug" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Host", 15 | "password": "Has\u0142o", 16 | "port": "Port", 17 | "site": "Identyfikator witryny", 18 | "username": "Nazwa u\u017cytkownika", 19 | "verify_ssl": "Kontroler u\u017cywa prawid\u0142owego certyfikatu" 20 | }, 21 | "title": "Konfiguracja kontrolera UniFi" 22 | } 23 | }, 24 | "title": "Kontroler UniFi" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Czas w sekundach od momentu, kiedy ostatnio widziano, a\u017c do momentu, kiedy uznano go za nieobecny.", 31 | "track_clients": "\u015aled\u017a klient\u00f3w sieciowych", 32 | "track_devices": "\u015aled\u017a urz\u0105dzenia sieciowe (urz\u0105dzenia Ubiquiti)", 33 | "track_wired_clients": "Uwzgl\u0119dnij klient\u00f3w sieci przewodowej" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "few": "Kilka", 39 | "many": "Wiele", 40 | "one": "Jeden", 41 | "other": "Inne" 42 | } 43 | }, 44 | "statistics_sensors": { 45 | "data": { 46 | "allow_bandwidth_sensors": "Stw\u00f3rz sensory wykorzystania przepustowo\u015bci przez klient\u00f3w sieciowych" 47 | } 48 | } 49 | } 50 | } 51 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/pt-BR.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "O site de controle j\u00e1 est\u00e1 configurado", 5 | "user_privilege": "O usu\u00e1rio precisa ser administrador" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Credenciais do usu\u00e1rio inv\u00e1lidas", 9 | "service_unavailable": "Servi\u00e7o indispon\u00edvel" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Host", 15 | "password": "Senha", 16 | "port": "Porta", 17 | "site": "ID do site", 18 | "username": "Usu\u00e1rio", 19 | "verify_ssl": "Controlador usando certificado apropriado" 20 | }, 21 | "title": "Configurar o Controlador UniFi" 22 | } 23 | }, 24 | "title": "Controlador UniFi" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Tempo em segundos desde a \u00faltima vez que foi visto at\u00e9 ser considerado afastado", 31 | "track_clients": "Rastrear clientes da rede", 32 | "track_devices": "Rastrear dispositivos de rede (dispositivos Ubiquiti)", 33 | "track_wired_clients": "Incluir clientes de rede com fio" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "um", 39 | "other": "uns" 40 | } 41 | } 42 | } 43 | } 44 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/pt.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "O site do controlador j\u00e1 se encontra configurado", 5 | "user_privilege": "Utilizador tem que ser administrador" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Credenciais do utilizador erradas", 9 | "service_unavailable": "Nenhum servi\u00e7o dispon\u00edvel" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Servidor", 15 | "password": "Palavra-passe", 16 | "port": "Porto", 17 | "site": "Site ID", 18 | "username": "Nome do utilizador", 19 | "verify_ssl": "Controlador com certificados adequados" 20 | }, 21 | "title": "Configurar o controlador UniFi" 22 | } 23 | }, 24 | "title": "Controlador UniFi" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "Tempo em segundos desde a \u00faltima vez que foi visto at\u00e9 ser considerado afastado", 31 | "track_clients": "Acompanhar clientes da rede", 32 | "track_devices": "Acompanhar dispositivos de rede (dispositivos Ubiquiti)", 33 | "track_wired_clients": "Incluir clientes da rede cablada" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "one": "Vazio", 39 | "other": "Vazios" 40 | } 41 | }, 42 | "statistics_sensors": { 43 | "data": { 44 | "allow_bandwidth_sensors": "Criar sensores de uso de largura de banda para clientes da rede" 45 | } 46 | } 47 | } 48 | } 49 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/ro.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "user_privilege": "Utilizatorul trebuie s\u0103 fie administrator" 5 | }, 6 | "error": { 7 | "faulty_credentials": "Credentiale utilizator invalide", 8 | "service_unavailable": "Nici un serviciu disponibil" 9 | }, 10 | "step": { 11 | "user": { 12 | "data": { 13 | "host": "Gazd\u0103", 14 | "password": "Parol\u0103", 15 | "port": "Port", 16 | "username": "Nume de utilizator", 17 | "verify_ssl": "Controler utiliz\u00e2nd certificatul adecvat" 18 | }, 19 | "title": "Configura\u021bi un controler UniFi" 20 | } 21 | }, 22 | "title": "Controler UniFi" 23 | } 24 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/ru.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "\u041d\u0430\u0441\u0442\u0440\u043e\u0439\u043a\u0430 \u0443\u0436\u0435 \u0432\u044b\u043f\u043e\u043b\u043d\u0435\u043d\u0430.", 5 | "user_privilege": "\u041f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c \u0434\u043e\u043b\u0436\u0435\u043d \u0431\u044b\u0442\u044c \u0430\u0434\u043c\u0438\u043d\u0438\u0441\u0442\u0440\u0430\u0442\u043e\u0440\u043e\u043c." 6 | }, 7 | "error": { 8 | "faulty_credentials": "\u041d\u0435\u0432\u0435\u0440\u043d\u044b\u0435 \u0443\u0447\u0435\u0442\u043d\u044b\u0435 \u0434\u0430\u043d\u043d\u044b\u0435.", 9 | "service_unavailable": "\u0421\u043b\u0443\u0436\u0431\u0430 \u043d\u0435 \u0434\u043e\u0441\u0442\u0443\u043f\u043d\u0430." 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "\u0425\u043e\u0441\u0442", 15 | "password": "\u041f\u0430\u0440\u043e\u043b\u044c", 16 | "port": "\u041f\u043e\u0440\u0442", 17 | "site": "ID \u0441\u0430\u0439\u0442\u0430", 18 | "username": "\u041b\u043e\u0433\u0438\u043d", 19 | "verify_ssl": "\u041a\u043e\u043d\u0442\u0440\u043e\u043b\u043b\u0435\u0440 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u044b\u0439 \u0441\u0435\u0440\u0442\u0438\u0444\u0438\u043a\u0430\u0442" 20 | }, 21 | "title": "UniFi Controller" 22 | } 23 | }, 24 | "title": "UniFi Controller" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "\u0412\u0440\u0435\u043c\u044f \u043e\u0442 \u043f\u043e\u0441\u043b\u0435\u0434\u043d\u0435\u0433\u043e \u0441\u0435\u0430\u043d\u0441\u0430 \u0441\u0432\u044f\u0437\u0438 \u0441 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u043e\u043c (\u0441\u0435\u043a.), \u043f\u043e \u0438\u0441\u0442\u0435\u0447\u0435\u043d\u0438\u044e \u043a\u043e\u0442\u043e\u0440\u043e\u0433\u043e \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u043e \u043f\u043e\u043b\u0443\u0447\u0438\u0442 \u0441\u0442\u0430\u0442\u0443\u0441 \"\u041d\u0435 \u0434\u043e\u043c\u0430\".", 31 | "track_clients": "\u041e\u0442\u0441\u043b\u0435\u0436\u0438\u0432\u0430\u043d\u0438\u0435 \u043a\u043b\u0438\u0435\u043d\u0442\u043e\u0432 \u0441\u0435\u0442\u0438", 32 | "track_devices": "\u041e\u0442\u0441\u043b\u0435\u0436\u0438\u0432\u0430\u043d\u0438\u0435 \u0441\u0435\u0442\u0435\u0432\u044b\u0445 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432 (\u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430 Ubiquiti)", 33 | "track_wired_clients": "\u0412\u043a\u043b\u044e\u0447\u0438\u0442\u044c \u043a\u043b\u0438\u0435\u043d\u0442\u043e\u0432 \u043f\u0440\u043e\u0432\u043e\u0434\u043d\u043e\u0439 \u0441\u0435\u0442\u0438" 34 | } 35 | }, 36 | "statistics_sensors": { 37 | "data": { 38 | "allow_bandwidth_sensors": "\u0421\u043e\u0437\u0434\u0430\u0432\u0430\u0442\u044c \u0434\u0430\u0442\u0447\u0438\u043a\u0438 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u044f \u043f\u043e\u043b\u043e\u0441\u044b \u043f\u0440\u043e\u043f\u0443\u0441\u043a\u0430\u043d\u0438\u044f \u0434\u043b\u044f \u0441\u0435\u0442\u0435\u0432\u044b\u0445 \u043a\u043b\u0438\u0435\u043d\u0442\u043e\u0432" 39 | } 40 | } 41 | } 42 | } 43 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/sl.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Nadzornik je \u017ee konfiguriran", 5 | "user_privilege": "Uporabnik mora biti skrbnik" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Napa\u010dni uporabni\u0161ki podatki", 9 | "service_unavailable": "Nobena storitev ni na voljo" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "Gostitelj", 15 | "password": "Geslo", 16 | "port": "Vrata", 17 | "site": "Mesto ID", 18 | "username": "Uporabni\u0161ko ime", 19 | "verify_ssl": "Kontroler uporablja ustrezen certifikat" 20 | }, 21 | "title": "Nastavi UniFi Controller" 22 | } 23 | }, 24 | "title": "UniFi Krmilnik" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "\u010cas v sekundah od zadnjega videnja na omre\u017eju do odsotnosti", 31 | "track_clients": "Sledite odjemalcem omre\u017eja", 32 | "track_devices": "Sledite omre\u017enim napravam (naprave Ubiquiti)", 33 | "track_wired_clients": "Vklju\u010dite kliente iz o\u017ei\u010denega omre\u017eja" 34 | } 35 | }, 36 | "init": { 37 | "data": { 38 | "few": "NEKAJ", 39 | "one": "ENA", 40 | "other": "OSTALO", 41 | "two": "DVA" 42 | } 43 | }, 44 | "statistics_sensors": { 45 | "data": { 46 | "allow_bandwidth_sensors": "Ustvarite senzorje porabe pasovne \u0161irine za omre\u017ene odjemalce" 47 | } 48 | } 49 | } 50 | } 51 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/sv.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "Controller-platsen \u00e4r redan konfigurerad", 5 | "user_privilege": "Anv\u00e4ndaren m\u00e5ste vara administrat\u00f6r" 6 | }, 7 | "error": { 8 | "faulty_credentials": "Felaktiga anv\u00e4ndaruppgifter", 9 | "service_unavailable": "Ingen tj\u00e4nst tillg\u00e4nglig" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "V\u00e4rddatorn", 15 | "password": "L\u00f6senord", 16 | "port": "Port", 17 | "site": "Plats-ID", 18 | "username": "Anv\u00e4ndarnamn", 19 | "verify_ssl": "Controller med korrekt certifikat" 20 | }, 21 | "title": "Konfigurera UniFi Controller" 22 | } 23 | }, 24 | "title": "UniFi Controller" 25 | } 26 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/th.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "step": { 4 | "user": { 5 | "data": { 6 | "host": "\u0e42\u0e2e\u0e2a\u0e15\u0e4c", 7 | "password": "\u0e23\u0e2b\u0e31\u0e2a\u0e1c\u0e48\u0e32\u0e19" 8 | }, 9 | "title": "\u0e15\u0e31\u0e49\u0e07\u0e04\u0e48\u0e32 UniFi Controller" 10 | } 11 | } 12 | } 13 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/tr.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "step": { 4 | "user": { 5 | "data": { 6 | "password": "Parola", 7 | "username": "Kullan\u0131c\u0131 ad\u0131" 8 | } 9 | } 10 | } 11 | } 12 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/zh-Hans.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "\u63a7\u5236\u5668\u7ad9\u70b9\u5df2\u914d\u7f6e\u5b8c\u6210", 5 | "user_privilege": "\u7528\u6237\u987b\u4e3a\u7ba1\u7406\u5458" 6 | }, 7 | "error": { 8 | "faulty_credentials": "\u9519\u8bef\u7684\u7528\u6237\u51ed\u636e", 9 | "service_unavailable": "\u6ca1\u6709\u53ef\u7528\u7684\u670d\u52a1" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "\u4e3b\u673a", 15 | "password": "\u5bc6\u7801", 16 | "port": "\u7aef\u53e3", 17 | "site": "\u7ad9\u70b9 ID", 18 | "username": "\u7528\u6237\u540d", 19 | "verify_ssl": "\u4f7f\u7528\u6b63\u786e\u8bc1\u4e66\u7684\u63a7\u5236\u5668" 20 | }, 21 | "title": "\u914d\u7f6e UniFi \u63a7\u5236\u5668" 22 | } 23 | }, 24 | "title": "UniFi \u63a7\u5236\u5668" 25 | } 26 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/.translations/zh-Hant.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "abort": { 4 | "already_configured": "\u63a7\u5236\u5668\u4f4d\u5740\u5df2\u7d93\u8a2d\u5b9a", 5 | "user_privilege": "\u4f7f\u7528\u8005\u5fc5\u9808\u70ba\u7ba1\u7406\u54e1\u8eab\u4efd" 6 | }, 7 | "error": { 8 | "faulty_credentials": "\u4f7f\u7528\u8005\u6191\u8b49\u7121\u6548", 9 | "service_unavailable": "\u7121\u670d\u52d9\u53ef\u7528" 10 | }, 11 | "step": { 12 | "user": { 13 | "data": { 14 | "host": "\u4e3b\u6a5f\u7aef", 15 | "password": "\u5bc6\u78bc", 16 | "port": "\u901a\u8a0a\u57e0", 17 | "site": "\u4f4d\u5740 ID", 18 | "username": "\u4f7f\u7528\u8005\u540d\u7a31", 19 | "verify_ssl": "\u63a7\u5236\u5668\u4f7f\u7528\u9a57\u8b49" 20 | }, 21 | "title": "\u8a2d\u5b9a UniFi \u63a7\u5236\u5668" 22 | } 23 | }, 24 | "title": "UniFi \u63a7\u5236\u5668" 25 | }, 26 | "options": { 27 | "step": { 28 | "device_tracker": { 29 | "data": { 30 | "detection_time": "\u6700\u7d42\u51fa\u73fe\u5f8c\u8996\u70ba\u96e2\u958b\u7684\u6642\u9593\uff08\u4ee5\u79d2\u70ba\u55ae\u4f4d\uff09", 31 | "track_clients": "\u8ffd\u8e64\u7db2\u8def\u5ba2\u6236\u7aef", 32 | "track_devices": "\u8ffd\u8e64\u7db2\u8def\u8a2d\u5099\uff08Ubiquiti \u8a2d\u5099\uff09", 33 | "track_wired_clients": "\u5305\u542b\u6709\u7dda\u7db2\u8def\u5ba2\u6236\u7aef" 34 | } 35 | }, 36 | "statistics_sensors": { 37 | "data": { 38 | "allow_bandwidth_sensors": "\u65b0\u589e\u7db2\u8def\u5ba2\u6236\u7aef\u983b\u5bec\u7528\u91cf\u611f\u61c9\u5668" 39 | } 40 | } 41 | } 42 | } 43 | } -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/__init__.py: -------------------------------------------------------------------------------- 1 | """Support for devices connected to UniFi POE.""" 2 | import voluptuous as vol 3 | 4 | from homeassistant.const import CONF_HOST 5 | from homeassistant.core import callback 6 | from homeassistant.helpers.device_registry import CONNECTION_NETWORK_MAC 7 | 8 | import homeassistant.helpers.config_validation as cv 9 | 10 | from .config_flow import get_controller_id_from_config_entry 11 | from .const import ( 12 | ATTR_MANUFACTURER, 13 | CONF_BLOCK_CLIENT, 14 | CONF_DETECTION_TIME, 15 | CONF_DONT_TRACK_CLIENTS, 16 | CONF_DONT_TRACK_DEVICES, 17 | CONF_DONT_TRACK_WIRED_CLIENTS, 18 | CONF_SITE_ID, 19 | CONF_SSID_FILTER, 20 | DOMAIN, 21 | UNIFI_CONFIG, 22 | UNIFI_WIRELESS_CLIENTS, 23 | ) 24 | from .controller import UniFiController 25 | 26 | SAVE_DELAY = 10 27 | STORAGE_KEY = "unifi_data" 28 | STORAGE_VERSION = 1 29 | 30 | CONF_CONTROLLERS = "controllers" 31 | 32 | CONTROLLER_SCHEMA = vol.Schema( 33 | { 34 | vol.Required(CONF_HOST): cv.string, 35 | vol.Required(CONF_SITE_ID): cv.string, 36 | vol.Optional(CONF_BLOCK_CLIENT, default=[]): vol.All( 37 | cv.ensure_list, [cv.string] 38 | ), 39 | vol.Optional(CONF_DONT_TRACK_CLIENTS): cv.boolean, 40 | vol.Optional(CONF_DONT_TRACK_DEVICES): cv.boolean, 41 | vol.Optional(CONF_DONT_TRACK_WIRED_CLIENTS): cv.boolean, 42 | vol.Optional(CONF_DETECTION_TIME): cv.positive_int, 43 | vol.Optional(CONF_SSID_FILTER): vol.All(cv.ensure_list, [cv.string]), 44 | } 45 | ) 46 | 47 | CONFIG_SCHEMA = vol.Schema( 48 | { 49 | DOMAIN: vol.Schema( 50 | { 51 | vol.Required(CONF_CONTROLLERS): vol.All( 52 | cv.ensure_list, [CONTROLLER_SCHEMA] 53 | ) 54 | } 55 | ) 56 | }, 57 | extra=vol.ALLOW_EXTRA, 58 | ) 59 | 60 | 61 | async def async_setup(hass, config): 62 | """Component doesn't support configuration through configuration.yaml.""" 63 | hass.data[UNIFI_CONFIG] = [] 64 | 65 | if DOMAIN in config: 66 | hass.data[UNIFI_CONFIG] = config[DOMAIN][CONF_CONTROLLERS] 67 | 68 | hass.data[UNIFI_WIRELESS_CLIENTS] = wireless_clients = UnifiWirelessClients(hass) 69 | await wireless_clients.async_load() 70 | 71 | return True 72 | 73 | 74 | async def async_setup_entry(hass, config_entry): 75 | """Set up the UniFi component.""" 76 | if DOMAIN not in hass.data: 77 | hass.data[DOMAIN] = {} 78 | 79 | controller = UniFiController(hass, config_entry) 80 | 81 | if not await controller.async_setup(): 82 | return False 83 | 84 | controller_id = get_controller_id_from_config_entry(config_entry) 85 | hass.data[DOMAIN][controller_id] = controller 86 | 87 | if controller.mac is None: 88 | return True 89 | 90 | device_registry = await hass.helpers.device_registry.async_get_registry() 91 | device_registry.async_get_or_create( 92 | config_entry_id=config_entry.entry_id, 93 | connections={(CONNECTION_NETWORK_MAC, controller.mac)}, 94 | manufacturer=ATTR_MANUFACTURER, 95 | model="UniFi Controller", 96 | name="UniFi Controller", 97 | # sw_version=config.raw['swversion'], 98 | ) 99 | 100 | return True 101 | 102 | 103 | async def async_unload_entry(hass, config_entry): 104 | """Unload a config entry.""" 105 | controller_id = get_controller_id_from_config_entry(config_entry) 106 | controller = hass.data[DOMAIN].pop(controller_id) 107 | return await controller.async_reset() 108 | 109 | 110 | class UnifiWirelessClients: 111 | """Class to store clients known to be wireless. 112 | 113 | This is needed since wireless devices going offline might get marked as wired by UniFi. 114 | """ 115 | 116 | def __init__(self, hass): 117 | """Set up client storage.""" 118 | self.hass = hass 119 | self.data = {} 120 | self._store = hass.helpers.storage.Store(STORAGE_VERSION, STORAGE_KEY) 121 | 122 | async def async_load(self): 123 | """Load data from file.""" 124 | data = await self._store.async_load() 125 | 126 | if data is not None: 127 | self.data = data 128 | 129 | @callback 130 | def get_data(self, config_entry): 131 | """Get data related to a specific controller.""" 132 | controller_id = get_controller_id_from_config_entry(config_entry) 133 | data = self.data.get(controller_id, {"wireless_devices": []}) 134 | return set(data["wireless_devices"]) 135 | 136 | @callback 137 | def update_data(self, data, config_entry): 138 | """Update data and schedule to save to file.""" 139 | controller_id = get_controller_id_from_config_entry(config_entry) 140 | self.data[controller_id] = {"wireless_devices": list(data)} 141 | 142 | self._store.async_delay_save(self._data_to_save, SAVE_DELAY) 143 | 144 | @callback 145 | def _data_to_save(self): 146 | """Return data of UniFi wireless clients to store in a file.""" 147 | return self.data 148 | -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/const.py: -------------------------------------------------------------------------------- 1 | """Constants for the UniFi component.""" 2 | import logging 3 | 4 | LOGGER = logging.getLogger(__package__) 5 | DOMAIN = "unifi" 6 | 7 | CONTROLLER_ID = "{host}-{site}" 8 | 9 | CONF_CONTROLLER = "controller" 10 | CONF_SITE_ID = "site" 11 | 12 | UNIFI_CONFIG = "unifi_config" 13 | UNIFI_WIRELESS_CLIENTS = "unifi_wireless_clients" 14 | 15 | CONF_ALLOW_BANDWIDTH_SENSORS = "allow_bandwidth_sensors" 16 | CONF_BLOCK_CLIENT = "block_client" 17 | CONF_DETECTION_TIME = "detection_time" 18 | CONF_TRACK_CLIENTS = "track_clients" 19 | CONF_TRACK_DEVICES = "track_devices" 20 | CONF_TRACK_WIRED_CLIENTS = "track_wired_clients" 21 | CONF_SSID_FILTER = "ssid_filter" 22 | 23 | CONF_DONT_TRACK_CLIENTS = "dont_track_clients" 24 | CONF_DONT_TRACK_DEVICES = "dont_track_devices" 25 | CONF_DONT_TRACK_WIRED_CLIENTS = "dont_track_wired_clients" 26 | 27 | DEFAULT_ALLOW_BANDWIDTH_SENSORS = False 28 | DEFAULT_BLOCK_CLIENTS = [] 29 | DEFAULT_TRACK_CLIENTS = True 30 | DEFAULT_TRACK_DEVICES = True 31 | DEFAULT_TRACK_WIRED_CLIENTS = True 32 | DEFAULT_DETECTION_TIME = 300 33 | DEFAULT_SSID_FILTER = [] 34 | 35 | ATTR_MANUFACTURER = "Ubiquiti Networks" 36 | -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/errors.py: -------------------------------------------------------------------------------- 1 | """Errors for the UniFi component.""" 2 | from homeassistant.exceptions import HomeAssistantError 3 | 4 | 5 | class UnifiException(HomeAssistantError): 6 | """Base class for UniFi exceptions.""" 7 | 8 | 9 | class AlreadyConfigured(UnifiException): 10 | """Controller is already configured.""" 11 | 12 | 13 | class AuthenticationRequired(UnifiException): 14 | """Unknown error occurred.""" 15 | 16 | 17 | class CannotConnect(UnifiException): 18 | """Unable to connect to the controller.""" 19 | 20 | 21 | class LoginRequired(UnifiException): 22 | """Component got logged out.""" 23 | 24 | 25 | class UserLevel(UnifiException): 26 | """User level too low.""" 27 | -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "domain": "unifi", 3 | "name": "Unifi", 4 | "config_flow": true, 5 | "documentation": "https://www.home-assistant.io/integrations/unifi", 6 | "requirements": [ 7 | "aiounifi==11" 8 | ], 9 | "dependencies": [], 10 | "codeowners": [ 11 | "@kane610" 12 | ] 13 | } 14 | -------------------------------------------------------------------------------- /home-assistant/custom_components/unifi/strings.json: -------------------------------------------------------------------------------- 1 | { 2 | "config": { 3 | "title": "UniFi Controller", 4 | "step": { 5 | "user": { 6 | "title": "Set up UniFi Controller", 7 | "data": { 8 | "host": "Host", 9 | "username": "User name", 10 | "password": "Password", 11 | "port": "Port", 12 | "site": "Site ID", 13 | "verify_ssl": "Controller using proper certificate" 14 | } 15 | } 16 | }, 17 | "error": { 18 | "faulty_credentials": "Bad user credentials", 19 | "service_unavailable": "No service available" 20 | }, 21 | "abort": { 22 | "already_configured": "Controller site is already configured", 23 | "user_privilege": "User needs to be administrator" 24 | } 25 | }, 26 | "options": { 27 | "step": { 28 | "init": { 29 | "data": {} 30 | }, 31 | "device_tracker": { 32 | "data": { 33 | "detection_time": "Time in seconds from last seen until considered away", 34 | "track_clients": "Track network clients", 35 | "track_devices": "Track network devices (Ubiquiti devices)", 36 | "track_wired_clients": "Include wired network clients" 37 | } 38 | }, 39 | "statistics_sensors": { 40 | "data": { 41 | "allow_bandwidth_sensors": "Create bandwidth usage sensors for network clients" 42 | } 43 | } 44 | } 45 | } 46 | } -------------------------------------------------------------------------------- /home-assistant/customize.yaml: -------------------------------------------------------------------------------- 1 | media_player.theater_room: 2 | hidden: true 3 | 4 | media_player.denon_avrx1300w: 5 | friendly_name: Media Room Receiver 6 | 7 | group.garage_doors: 8 | aliases: 9 | - Garage 10 | 11 | cover.blake_s_garage_door: 12 | device_class: garage 13 | 14 | cover.ali_s_garage_door: 15 | device_class: garage 16 | 17 | group.master_lamps: 18 | hidden: true 19 | 20 | group.all_automations: 21 | hidden: true 22 | 23 | vacuum.xiaomi_vacuum_cleaner: 24 | friendly_name: Downstairs Vacuum 25 | 26 | remote.living_room: 27 | friendly_name: Living Room TV 28 | 29 | sensor.back_door_lock_battery: 30 | icon: mdi:battery 31 | sensor.front_door_lock_battery: 32 | icon: mdi:battery 33 | sensor.back_door_sensor_battery: 34 | icon: mdi:battery 35 | sensor.front_door_sensor_battery: 36 | icon: mdi:battery 37 | -------------------------------------------------------------------------------- /home-assistant/packages/cloud.yaml: -------------------------------------------------------------------------------- 1 | cloud: 2 | google_actions: 3 | filter: 4 | exclude_domains: 5 | - group 6 | - media_player 7 | exclude_entities: 8 | - switch.back_panel_button_3 9 | - switch.back_panel_button_4 10 | - switch.back_panel_button_5 11 | - switch.sonoff3491 -------------------------------------------------------------------------------- /home-assistant/packages/crawl_space.yaml: -------------------------------------------------------------------------------- 1 | sensor: 2 | - platform: "mqtt" 3 | name: Crawl Space Temperature 4 | state_topic: "zigbee/0x00158d00023a7f7d" 5 | availability_topic: "zigbee/bridge/state" 6 | unit_of_measurement: "°F" 7 | icon: "mdi:thermometer" 8 | value_template: "{{ ((float(value_json.temperature) * 9 / 5 ) + 32) | round(1) }}" 9 | - platform: "mqtt" 10 | name: Crawl Space Humidity 11 | state_topic: "zigbee/0x00158d00023a7f7d" 12 | availability_topic: "zigbee/bridge/state" 13 | unit_of_measurement: "%" 14 | icon: "mdi:water-percent" 15 | value_template: "{{ value_json.humidity }}" 16 | - platform: "mqtt" 17 | name: Crawl Space Pressure 18 | state_topic: "zigbee/0x00158d00023a7f7d" 19 | availability_topic: "zigbee/bridge/state" 20 | unit_of_measurement: "Pa" 21 | icon: "mdi:gauge" 22 | value_template: "{{ value_json.pressure }}" -------------------------------------------------------------------------------- /home-assistant/packages/deck/cameras.yaml: -------------------------------------------------------------------------------- 1 | camera: 2 | - name: Backyard Camera 3 | platform: generic 4 | still_image_url: https://cameras.blakeshome.com/nvr/back.jpg 5 | - platform: mqtt 6 | name: Backyard Last Person 7 | topic: frigate/back/snapshot 8 | binary_sensor: 9 | - name: Backyard Person 10 | platform: mqtt 11 | state_topic: "frigate/back/objects" 12 | value_template: '{{ value_json.person }}' 13 | device_class: motion 14 | availability_topic: "frigate/available" 15 | 16 | script: 17 | play_backyard_camera: 18 | alias: Stream backyard camera 19 | sequence: 20 | - service: media_player.play_media 21 | data: 22 | entity_id: media_player.living_room 23 | media_content_id: https://cameras.blakeshome.com/cameras/back.m3u8 24 | media_content_type: application/vnd.apple.mpegurl 25 | 26 | automation: 27 | - alias: Turn on the outside lights when a person is detected at night 28 | trigger: 29 | platform: state 30 | entity_id: binary_sensor.backyard_person 31 | from: 'off' 32 | to: 'on' 33 | condition: 34 | condition: or 35 | conditions: 36 | - condition: time 37 | after: '22:00:00' 38 | - condition: sun 39 | before: sunrise 40 | action: 41 | - service: scene.turn_on 42 | entity_id: scene.backyard_night_active 43 | - alias: Turn off the outside lights when no people are detected at night 44 | trigger: 45 | platform: state 46 | entity_id: binary_sensor.backyard_person 47 | from: 'on' 48 | to: 'off' 49 | for: 50 | seconds: 5 51 | condition: 52 | condition: or 53 | conditions: 54 | - condition: time 55 | after: '22:00:00' 56 | - condition: sun 57 | before: sunrise 58 | action: 59 | - service: scene.turn_on 60 | entity_id: scene.backyard_night_normal 61 | - alias: Alert me if a person is detected while armed away 62 | trigger: 63 | platform: state 64 | entity_id: binary_sensor.backyard_person 65 | from: 'off' 66 | to: 'on' 67 | condition: 68 | - condition: state 69 | entity_id: alarm_control_panel.home_alarm 70 | state: armed_away 71 | action: 72 | # - delay: '00:00:30' 73 | # - condition: state 74 | # entity_id: alarm_control_panel.home_alarm 75 | # state: armed_away 76 | - service: notify.blake_telegram 77 | data: 78 | message: "A person was detected in the backyard." 79 | data: 80 | photo: 81 | - url: http://192.168.2.186:5000/back/best_person.jpg 82 | caption: A person was detected in the backyard. -------------------------------------------------------------------------------- /home-assistant/packages/deck/deck_lights.yaml: -------------------------------------------------------------------------------- 1 | scene: 2 | - name: Backyard Night Active 3 | entities: 4 | light.deck_string_lights: 5 | state: on 6 | brightness_pct: 75 7 | light.driveway_lights: 8 | state: on 9 | brightness_pct: 75 10 | light.deck_recessed_lights: 11 | state: on 12 | brightness_pct: 75 13 | - name: Backyard Night Normal 14 | entities: 15 | light.deck_string_lights: off 16 | light.deck_recessed_lights: off 17 | light.driveway_lights: 18 | state: on 19 | brightness: 50 20 | 21 | automation: 22 | - alias: Turn off string lights when back button 3 turns off 23 | trigger: 24 | - platform: state 25 | entity_id: switch.back_panel_button_3 26 | from: 'on' 27 | to: 'off' 28 | action: 29 | - service: light.turn_off 30 | entity_id: 31 | - light.deck_string_lights 32 | 33 | - alias: Turn on string lights when back button 3 turns on 34 | trigger: 35 | - platform: state 36 | entity_id: switch.back_panel_button_3 37 | from: 'off' 38 | to: 'on' 39 | action: 40 | - service: light.turn_on 41 | entity_id: 42 | - light.deck_string_lights 43 | data: 44 | brightness_pct: 35 45 | 46 | - alias: Turn off back button 3 when lights turn off 47 | trigger: 48 | - platform: state 49 | entity_id: light.deck_string_lights 50 | from: 'on' 51 | to: 'off' 52 | action: 53 | - service: switch.turn_off 54 | entity_id: 55 | - switch.back_panel_button_3 56 | 57 | - alias: Turn on back button 3 when lights turn on 58 | trigger: 59 | - platform: state 60 | entity_id: light.deck_string_lights 61 | from: 'off' 62 | to: 'on' 63 | action: 64 | - service: switch.turn_on 65 | entity_id: 66 | - switch.back_panel_button_3 -------------------------------------------------------------------------------- /home-assistant/packages/deck/deck_sensors.yaml: -------------------------------------------------------------------------------- 1 | sensor: 2 | - platform: "mqtt" 3 | name: Outside Temperature 4 | state_topic: "zigbee/0x00158d0001ab4496" 5 | availability_topic: "zigbee/bridge/state" 6 | unit_of_measurement: "°F" 7 | icon: "mdi:thermometer" 8 | value_template: "{{ ((float(value_json.temperature) * 9 / 5 ) + 32) | round(1) }}" 9 | - platform: "mqtt" 10 | name: Outside Humidity 11 | state_topic: "zigbee/0x00158d0001ab4496" 12 | availability_topic: "zigbee/bridge/state" 13 | unit_of_measurement: "%" 14 | icon: "mdi:water-percent" 15 | value_template: "{{ value_json.humidity }}" 16 | - platform: "mqtt" 17 | name: Outside Pressure 18 | state_topic: "zigbee/0x00158d0001ab4496" 19 | availability_topic: "zigbee/bridge/state" 20 | unit_of_measurement: "Pa" 21 | icon: "mdi:gauge" 22 | value_template: "{{ value_json.pressure }}" -------------------------------------------------------------------------------- /home-assistant/packages/dining_room.yaml: -------------------------------------------------------------------------------- 1 | light: 2 | - platform: mqtt 3 | schema: json 4 | name: Dining Room Lights 5 | state_topic: "homeassistant_hub/light/dining_room/state" 6 | availability_topic: "homeassistant_hub/status" 7 | brightness: true 8 | command_topic: "homeassistant_hub/light/dining_room/set" 9 | 10 | binary_sensor: 11 | - platform: "mqtt" 12 | name: Dining Room Shutter 1 13 | state_topic: "zigbee/0x00158d0001b1b1a3" 14 | availability_topic: "zigbee/bridge/state" 15 | payload_on: false 16 | payload_off: true 17 | value_template: "{{ value_json.contact }}" 18 | device_class: "window" 19 | - platform: "mqtt" 20 | name: Dining Room Shutter 2 21 | state_topic: "zigbee/0x00158d0001b7812e" 22 | availability_topic: "zigbee/bridge/state" 23 | payload_on: false 24 | payload_off: true 25 | value_template: "{{ value_json.contact }}" 26 | device_class: "window" 27 | - platform: "mqtt" 28 | name: Dining Motion 29 | state_topic: "zigbee/0x00158d0002b95dca" 30 | availability_topic: "zigbee/bridge/state" 31 | payload_on: true 32 | payload_off: false 33 | value_template: "{{ value_json.occupancy }}" 34 | device_class: "motion" 35 | 36 | sensor: 37 | - platform: "mqtt" 38 | name: Dining Illuminance 39 | state_topic: "zigbee/0x00158d0002b95dca" 40 | availability_topic: "zigbee/bridge/state" 41 | unit_of_measurement: "lx" 42 | device_class: "illuminance" 43 | value_template: "{{ value_json.illuminance }}" -------------------------------------------------------------------------------- /home-assistant/packages/dog_sitter.yaml: -------------------------------------------------------------------------------- 1 | # [x] just disarm the downstairs, motion sensors upstairs should still alert me 2 | # [ ] if no motion after period of time, rearm and ensure doors are locked. maybe play a TTS message 30 seconds in advance. 3 | # [ ] keypad unlock with usercode 3 should disarm 4 | # [ ] keypad lock should activate alarm again 5 | # [ ] keypad unlock should activate light scene, keypad lock should deactivate light scene 6 | 7 | 8 | input_boolean: 9 | dog_sitter: 10 | name: Dog Sitter Mode 11 | initial: off 12 | icon: mdi:dog-side 13 | 14 | automation: 15 | - alias: 'Motion detected upstairs' 16 | trigger: 17 | - platform: state 18 | entity_id: group.upstairs_motion_sensors 19 | to: 'on' 20 | condition: 21 | condition: state 22 | entity_id: input_boolean.dog_sitter 23 | state: 'on' 24 | action: 25 | - service: notify.blake_telegram 26 | data: 27 | title: Dog Sitter Mode 28 | message: Motion detected upstairs 29 | 30 | - alias: Run vacuum when locked with keypad in dog sitter mode 31 | trigger: 32 | - platform: state 33 | entity_id: sensor.back_door_last_action 34 | to: 'Keypad Lock' 35 | for: 36 | minutes: 1 37 | - platform: state 38 | entity_id: sensor.front_door_last_action 39 | to: 'Keypad Lock' 40 | for: 41 | minutes: 1 42 | condition: 43 | - condition: state 44 | entity_id: lock.back_door_lock 45 | state: 'locked' 46 | - condition: state 47 | entity_id: lock.front_door_lock 48 | state: 'locked' 49 | - condition: state 50 | entity_id: input_boolean.dog_sitter 51 | state: 'on' 52 | - condition: numeric_state 53 | entity_id: sensor.vacuum_time_in_the_last_24_hours 54 | below: 1 55 | - condition: state 56 | entity_id: vacuum.xiaomi_vacuum_cleaner 57 | state: 'docked' 58 | action: 59 | - service: notify.blake_telegram 60 | data_template: 61 | message: "Running the vacuum after dog sitter visit." 62 | - service: vacuum.start 63 | data: 64 | entity_id: vacuum.xiaomi_vacuum_cleaner -------------------------------------------------------------------------------- /home-assistant/packages/foyer.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Front Door 4 | state_topic: "zigbee/0x00158d0002b7de52" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: false 7 | payload_off: true 8 | value_template: "{{ value_json.contact }}" 9 | device_class: "door" -------------------------------------------------------------------------------- /home-assistant/packages/garage/button_panel.yaml: -------------------------------------------------------------------------------- 1 | automation: 2 | - alias: Open blake's garage door when button turns on 3 | trigger: 4 | - platform: state 5 | entity_id: switch.back_panel_button_4 6 | from: 'off' 7 | to: 'on' 8 | action: 9 | - service: cover.open_cover 10 | entity_id: 11 | - cover.blake_s_garage_door 12 | - alias: Close blake's garage door when the button turns off 13 | trigger: 14 | platform: state 15 | entity_id: switch.back_panel_button_4 16 | from: 'on' 17 | to: 'off' 18 | action: 19 | - service: cover.close_cover 20 | entity_id: 21 | - cover.blake_s_garage_door 22 | - alias: Turn off button when blake's garage door is closed 23 | trigger: 24 | - platform: state 25 | entity_id: cover.blake_s_garage_door 26 | from: 'open' 27 | to: 'closed' 28 | action: 29 | - service: switch.turn_off 30 | entity_id: 31 | - switch.back_panel_button_4 32 | - alias: Turn on button when blake's garage door is opened 33 | trigger: 34 | - platform: state 35 | entity_id: cover.blake_s_garage_door 36 | from: 'closed' 37 | to: 'open' 38 | action: 39 | - service: switch.turn_on 40 | entity_id: 41 | - switch.back_panel_button_4 42 | 43 | 44 | - alias: Open ali's garage door when button turns on 45 | trigger: 46 | - platform: state 47 | entity_id: switch.back_panel_button_5 48 | from: 'off' 49 | to: 'on' 50 | action: 51 | - service: cover.open_cover 52 | entity_id: 53 | - cover.ali_s_garage_door 54 | - alias: Close ali's garage door when the button turns off 55 | trigger: 56 | platform: state 57 | entity_id: switch.back_panel_button_5 58 | from: 'on' 59 | to: 'off' 60 | action: 61 | - service: cover.close_cover 62 | entity_id: 63 | - cover.ali_s_garage_door 64 | - alias: Turn off button when ali's garage door is closed 65 | trigger: 66 | - platform: state 67 | entity_id: cover.ali_s_garage_door 68 | from: 'open' 69 | to: 'closed' 70 | action: 71 | - service: switch.turn_off 72 | entity_id: 73 | - switch.back_panel_button_5 74 | - alias: Turn on button when ali's garage door is opened 75 | trigger: 76 | - platform: state 77 | entity_id: cover.ali_s_garage_door 78 | from: 'closed' 79 | to: 'open' 80 | action: 81 | - service: switch.turn_on 82 | entity_id: 83 | - switch.back_panel_button_5 -------------------------------------------------------------------------------- /home-assistant/packages/garage/night_lights.yaml: -------------------------------------------------------------------------------- 1 | timer: 2 | outside_lights_after_dark: 3 | duration: '00:05:00' 4 | 5 | automation: 6 | - alias: Turn on the outside lights if the garage opens at night 7 | trigger: 8 | - platform: state 9 | entity_id: cover.ali_s_garage_door 10 | from: 'closed' 11 | to: 'open' 12 | - platform: state 13 | entity_id: cover.blake_s_garage_door 14 | from: 'closed' 15 | to: 'open' 16 | condition: 17 | condition: sun 18 | after: sunset 19 | action: 20 | - service: scene.turn_on 21 | entity_id: scene.backyard_night_active 22 | - service: timer.start 23 | entity_id: timer.outside_lights_after_dark 24 | 25 | - alias: Turn off the outside lights after the timer expires at night 26 | trigger: 27 | platform: event 28 | event_type: timer.finished 29 | event_data: 30 | entity_id: timer.outside_lights_after_dark 31 | action: 32 | - wait_template: "{{ is_state('binary_sensor.backyard_person', 'off') }}" 33 | timeout: '00:10:00' 34 | continue_on_timeout: 'false' 35 | - service: scene.turn_on 36 | entity_id: scene.backyard_night_normal 37 | 38 | - alias: Turn off the outside lights if the door locks when the timer is running 39 | trigger: 40 | - platform: mqtt 41 | topic: "homeassistant_hub/lock/back_door/state" 42 | condition: 43 | - condition: state 44 | entity_id: timer.outside_lights_after_dark 45 | state: 'active' 46 | - condition: template 47 | value_template: "{{ 'Manual Lock' == trigger.payload_json.notification }}" 48 | action: 49 | - service: timer.finish 50 | entity_id: timer.outside_lights_after_dark 51 | -------------------------------------------------------------------------------- /home-assistant/packages/garage/notifications.yaml: -------------------------------------------------------------------------------- 1 | automation: 2 | - alias: Notify if the garage doors are open 3 | trigger: 4 | - platform: state 5 | entity_id: group.people 6 | to: 'not_home' 7 | for: 8 | minutes: 5 9 | condition: 10 | - condition: state 11 | entity_id: group.garage_doors 12 | state: open 13 | action: 14 | - service: notify.blake_telegram 15 | data: 16 | message: "The garage is open, but nobody is home!" 17 | data: 18 | inline_keyboard: 19 | - 'Close Garage:/close_garage' 20 | 21 | - alias: Close garage from notification 22 | trigger: 23 | - platform: event 24 | event_type: telegram_callback 25 | event_data: 26 | data: '/close_garage' 27 | action: 28 | - service: cover.close_cover 29 | entity_id: 30 | - cover.blake_s_garage_door 31 | - cover.ali_s_garage_door -------------------------------------------------------------------------------- /home-assistant/packages/guest_mode.yaml: -------------------------------------------------------------------------------- 1 | input_boolean: 2 | guest_mode: 3 | name: Guest Mode 4 | initial: off 5 | icon: mdi:account-plus 6 | 7 | automation: 8 | - alias: Turn on guest mode when guests are present 9 | trigger: 10 | - platform: state 11 | entity_id: group.guests 12 | to: 'home' 13 | action: 14 | - service: input_boolean.turn_on 15 | entity_id: input_boolean.guest_mode 16 | - alias: Turn off guest mode when guests are not present 17 | trigger: 18 | - platform: state 19 | entity_id: group.guests 20 | to: 'not_home' 21 | action: 22 | - service: input_boolean.turn_off 23 | entity_id: input_boolean.guest_mode 24 | -------------------------------------------------------------------------------- /home-assistant/packages/guest_room.yaml: -------------------------------------------------------------------------------- 1 | sensor: 2 | - platform: "mqtt" 3 | name: Guest Room Temperature 4 | state_topic: "zigbee/0x00158d0001c1647d" 5 | availability_topic: "zigbee/bridge/state" 6 | unit_of_measurement: "°F" 7 | icon: "mdi:thermometer" 8 | value_template: "{{ ((float(value_json.temperature) * 9 / 5 ) + 32) | round(1) }}" 9 | - platform: "mqtt" 10 | name: Guest Room Humidity 11 | state_topic: "zigbee/0x00158d0001c1647d" 12 | availability_topic: "zigbee/bridge/state" 13 | unit_of_measurement: "%" 14 | icon: "mdi:water-percent" 15 | value_template: "{{ value_json.humidity }}" -------------------------------------------------------------------------------- /home-assistant/packages/half_bath.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Half Bath Motion 4 | state_topic: "zigbee/0x00158d0001ad44f0" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.occupancy }}" 9 | device_class: "motion" 10 | 11 | automation: 12 | - alias: Turn on half bath light with motion 13 | trigger: 14 | platform: state 15 | entity_id: binary_sensor.half_bath_motion 16 | to: 'on' 17 | action: 18 | - service: timer.cancel 19 | entity_id: timer.half_bath_lights 20 | - service: light.turn_on 21 | entity_id: light.half_bath_bathroom_light 22 | 23 | - alias: Start half bath light timer with no motion 24 | trigger: 25 | platform: state 26 | entity_id: binary_sensor.half_bath_motion 27 | to: 'off' 28 | for: 29 | minutes: 10 30 | action: 31 | service: light.turn_off 32 | entity_id: light.half_bath_bathroom_light -------------------------------------------------------------------------------- /home-assistant/packages/hall.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Boys Doors Motion 4 | state_topic: "zigbee/0x00158d0001b15d3d" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.occupancy }}" 9 | device_class: "motion" 10 | - platform: "mqtt" 11 | name: Hall Motion 12 | state_topic: "zigbee/0x00158d0001d66c8d" 13 | availability_topic: "zigbee/bridge/state" 14 | payload_on: true 15 | payload_off: false 16 | value_template: "{{ value_json.occupancy }}" 17 | device_class: "motion" 18 | 19 | -------------------------------------------------------------------------------- /home-assistant/packages/kitchen/kitchen_lights.yaml: -------------------------------------------------------------------------------- 1 | automation: 2 | - alias: Turn on kitchen lights with double tap up 3 | trigger: 4 | - platform: mqtt 5 | topic: 'homeassistant_hub/scene_activated/17/1/3' 6 | - platform: mqtt 7 | topic: 'homeassistant_hub/scene_activated/16/1/3' 8 | - platform: mqtt 9 | topic: 'homeassistant_hub/scene_activated/15/1/3' 10 | action: 11 | service: light.turn_on 12 | entity_id: light.kitchen_lights 13 | - alias: Turn off kitchen lights with double tap down 14 | trigger: 15 | - platform: mqtt 16 | topic: 'homeassistant_hub/scene_activated/17/2/3' 17 | - platform: mqtt 18 | topic: 'homeassistant_hub/scene_activated/16/2/3' 19 | - platform: mqtt 20 | topic: 'homeassistant_hub/scene_activated/15/2/3' 21 | action: 22 | service: light.turn_off 23 | entity_id: light.kitchen_lights -------------------------------------------------------------------------------- /home-assistant/packages/kitchen/kitchen_sensors.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Kitchen Motion 4 | state_topic: "zigbee/0x00158d0002b4233f" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.occupancy }}" 9 | device_class: "motion" 10 | 11 | sensor: 12 | - platform: "mqtt" 13 | name: Kitchen Illuminance 14 | state_topic: "zigbee/0x00158d0002b4233f" 15 | availability_topic: "zigbee/bridge/state" 16 | unit_of_measurement: "lx" 17 | device_class: "illuminance" 18 | value_template: "{{ value_json.illuminance }}" 19 | - platform: "mqtt" 20 | name: Kitchen Temperature 21 | state_topic: "zigbee/0x00158d0002323855" 22 | availability_topic: "zigbee/bridge/state" 23 | unit_of_measurement: "°F" 24 | icon: "mdi:thermometer" 25 | value_template: "{{ ((float(value_json.temperature) * 9 / 5 ) + 32) | round(1) }}" 26 | - platform: "mqtt" 27 | name: Kitchen Humidity 28 | state_topic: "zigbee/0x00158d0002323855" 29 | availability_topic: "zigbee/bridge/state" 30 | unit_of_measurement: "%" 31 | icon: "mdi:water-percent" 32 | value_template: "{{ value_json.humidity }}" 33 | - platform: "mqtt" 34 | name: Kitchen Pressure 35 | state_topic: "zigbee/0x00158d0002323855" 36 | availability_topic: "zigbee/bridge/state" 37 | unit_of_measurement: "Pa" 38 | icon: "mdi:gauge" 39 | value_template: "{{ value_json.pressure }}" -------------------------------------------------------------------------------- /home-assistant/packages/laundry_room.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Laundry Room Motion 4 | state_topic: "zigbee/0x00158d0001215452" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.occupancy }}" 9 | device_class: "motion" 10 | 11 | automation: 12 | - alias: Turn on laundry light with motion 13 | trigger: 14 | platform: state 15 | entity_id: binary_sensor.laundry_room_motion 16 | to: 'on' 17 | action: 18 | - service: light.turn_on 19 | entity_id: light.laundry_room_light 20 | - service: input_datetime.set_datetime 21 | entity_id: input_datetime.laundry_last_motion 22 | data_template: 23 | time: '{{ (as_timestamp(now()) | timestamp_custom("%H:%M:%S", true)) }}' 24 | date: '{{ (as_timestamp(now()) | timestamp_custom("%Y-%m-%d", true)) }}' 25 | 26 | - alias: Turn off laundry light with no motion 27 | trigger: 28 | platform: state 29 | entity_id: binary_sensor.laundry_room_motion 30 | to: 'off' 31 | for: 32 | minutes: 1 33 | action: 34 | - service: light.turn_off 35 | entity_id: light.laundry_room_light 36 | - service: input_datetime.set_datetime 37 | entity_id: input_datetime.laundry_last_motion 38 | data_template: 39 | time: '{{ (as_timestamp(now()) | timestamp_custom("%H:%M:%S", true)) }}' 40 | date: '{{ (as_timestamp(now()) | timestamp_custom("%Y-%m-%d", true)) }}' 41 | 42 | - alias: Mark laundry finished when washer idle for 3 minutes 43 | trigger: 44 | platform: state 45 | entity_id: sensor.clothes_washer_status 46 | from: 'Washing' 47 | to: 'Idle' 48 | for: 49 | minutes: 3 50 | action: 51 | - service: input_datetime.set_datetime 52 | entity_id: input_datetime.washer_finish_time 53 | data_template: 54 | time: '{{ (as_timestamp(now()) | timestamp_custom("%H:%M:%S", true)) }}' 55 | date: '{{ (as_timestamp(now()) | timestamp_custom("%Y-%m-%d", true)) }}' 56 | 57 | - alias: Remind Ali to switch laundry over if needed when arriving home 58 | trigger: 59 | - platform: state 60 | entity_id: device_tracker.ali_phone_mqtt 61 | to: 'home' 62 | for: 63 | minutes: 5 64 | condition: 65 | condition: state 66 | entity_id: sensor.laundry_needs_changeover 67 | state: 'True' 68 | action: 69 | - service: notify.html5_ali_phone 70 | data: 71 | message: "Don't forget to change the laundry over." 72 | 73 | - alias: Remind Ali to switch laundry over when home 74 | trigger: 75 | - platform: state 76 | entity_id: sensor.laundry_needs_changeover 77 | to: 'True' 78 | for: 79 | minutes: 10 80 | condition: 81 | condition: state 82 | entity_id: device_tracker.ali_phone_mqtt 83 | state: 'home' 84 | action: 85 | - service: notify.html5_ali_phone 86 | data: 87 | message: "Don't forget to change the laundry over." 88 | 89 | sensor: 90 | - platform: mqtt 91 | name: "Clothes Washer Energy" 92 | state_topic: "tasmota/tele/7D1D93/SENSOR" 93 | value_template: '{{ value_json["ENERGY"]["Today"] }}' 94 | unit_of_measurement: "kWh" 95 | - platform: mqtt 96 | name: "Clothes Washer Power" 97 | state_topic: "tasmota/tele/7D1D93/SENSOR" 98 | value_template: '{{ value_json["ENERGY"]["Power"] }}' 99 | unit_of_measurement: "W" 100 | - platform: mqtt 101 | name: "Clothes Washer Voltage" 102 | state_topic: "tasmota/tele/7D1D93/SENSOR" 103 | value_template: '{{ value_json["ENERGY"]["Voltage"] }}' 104 | unit_of_measurement: "V" 105 | - platform: mqtt 106 | name: "Clothes Washer Current" 107 | state_topic: "tasmota/tele/7D1D93/SENSOR" 108 | value_template: '{{ value_json["ENERGY"]["Current"] }}' 109 | unit_of_measurement: "A" 110 | - platform: template 111 | sensors: 112 | clothes_washer_status: 113 | friendly_name: "Clothes Washer Status" 114 | value_template: >- 115 | {% if states.sensor.clothes_washer_current.state|float > 0.02 %} 116 | Washing 117 | {% else %} 118 | Idle 119 | {% endif %} 120 | icon_template: 'mdi:washing-machine' 121 | laundry_needs_changeover: 122 | friendly_name: "Laundry Needs Changeover" 123 | value_template: '{{ states.input_datetime.washer_finish_time.attributes.timestamp > states.input_datetime.laundry_last_motion.attributes.timestamp }}' 124 | 125 | input_datetime: 126 | washer_finish_time: 127 | name: Washer finish time 128 | has_date: true 129 | has_time: true 130 | laundry_last_motion: 131 | name: Laundry last motion 132 | has_date: true 133 | has_time: true 134 | 135 | -------------------------------------------------------------------------------- /home-assistant/packages/living_room/fireplace.yaml: -------------------------------------------------------------------------------- 1 | switch: 2 | - name: Fireplace 3 | platform: mqtt 4 | command_topic: "taproot/fireplace/set" 5 | state_topic: "taproot/fireplace/status" 6 | availability_topic: "taproot/fireplace/available" 7 | icon: "mdi:fire" 8 | 9 | automation: 10 | - alias: Turn off the fireplace when we leave 11 | trigger: 12 | - platform: state 13 | entity_id: group.people 14 | to: 'not_home' 15 | action: 16 | - service: switch.turn_off 17 | entity_id: 18 | - switch.fireplace -------------------------------------------------------------------------------- /home-assistant/packages/living_room/living_room_lamps.yaml: -------------------------------------------------------------------------------- 1 | light: 2 | - platform: mqtt 3 | schema: json 4 | name: Living Room Back Lamp 5 | state_topic: "zigbee/0x001788010344dd8e" 6 | availability_topic: "zigbee/bridge/state" 7 | brightness: true 8 | command_topic: "zigbee/0x001788010344dd8e/set" 9 | - platform: mqtt 10 | schema: json 11 | name: Living Room Front Lamp 12 | state_topic: "zigbee/0x00178801030453ea" 13 | availability_topic: "zigbee/bridge/state" 14 | brightness: true 15 | command_topic: "zigbee/0x00178801030453ea/set" -------------------------------------------------------------------------------- /home-assistant/packages/living_room/living_room_lights.yaml: -------------------------------------------------------------------------------- 1 | automation: 2 | - alias: Activate goodnight scene after 8 on foyer back double tap down 3 | trigger: 4 | - platform: mqtt 5 | topic: 'homeassistant_hub/scene_activated/20/2/3' 6 | condition: 7 | condition: or 8 | conditions: 9 | - condition: time 10 | after: '20:00:00' 11 | - condition: time 12 | before: '04:00:00' 13 | action: 14 | - service: scene.turn_on 15 | entity_id: scene.goodnight 16 | - service: lock.lock 17 | entity_id: 18 | - lock.back_door_lock 19 | - lock.front_door_lock 20 | - wait_template: "{{ is_state('binary_sensor.backyard_person', 'off') }}" 21 | timeout: '00:10:00' 22 | continue_on_timeout: 'false' 23 | - service: cover.close_cover 24 | entity_id: 25 | - cover.blake_s_garage_door 26 | - cover.ali_s_garage_door -------------------------------------------------------------------------------- /home-assistant/packages/living_room/living_room_sensors.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Living Room Motion 4 | state_topic: "zigbee/0x00158d0001d54b06" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.occupancy }}" 9 | device_class: "motion" 10 | - platform: "mqtt" 11 | name: Back Door 12 | state_topic: "zigbee/0x00158d0001bf484f" 13 | availability_topic: "zigbee/bridge/state" 14 | payload_on: false 15 | payload_off: true 16 | value_template: "{{ value_json.contact }}" 17 | device_class: "door" 18 | - platform: "mqtt" 19 | name: Living Room Shutter 1 20 | state_topic: "zigbee/0x00158d0001b1b801" 21 | availability_topic: "zigbee/bridge/state" 22 | payload_on: false 23 | payload_off: true 24 | value_template: "{{ value_json.contact }}" 25 | device_class: "window" 26 | - platform: "mqtt" 27 | name: Living Room Shutter 2 28 | state_topic: "zigbee/0x00158d0001dcc9bd" 29 | availability_topic: "zigbee/bridge/state" 30 | payload_on: false 31 | payload_off: true 32 | value_template: "{{ value_json.contact }}" 33 | device_class: "window" 34 | - platform: "mqtt" 35 | name: Living Room Shutter 3 36 | state_topic: "zigbee/0x00158d0001ab59ab" 37 | availability_topic: "zigbee/bridge/state" 38 | payload_on: false 39 | payload_off: true 40 | value_template: "{{ value_json.contact }}" 41 | device_class: "window" 42 | - platform: "mqtt" 43 | name: Living Room Shutter 4 44 | state_topic: "zigbee/0x00158d0001ab67c2" 45 | availability_topic: "zigbee/bridge/state" 46 | payload_on: false 47 | payload_off: true 48 | value_template: "{{ value_json.contact }}" 49 | device_class: "window" 50 | - platform: "mqtt" 51 | name: Living Room Shutter 5 52 | state_topic: "zigbee/0x00158d0001b71164" 53 | availability_topic: "zigbee/bridge/state" 54 | payload_on: false 55 | payload_off: true 56 | value_template: "{{ value_json.contact }}" 57 | device_class: "window" 58 | - platform: "mqtt" 59 | name: Living Room Shutter 6 60 | state_topic: "zigbee/0x00158d0001b1b8be" 61 | availability_topic: "zigbee/bridge/state" 62 | payload_on: false 63 | payload_off: true 64 | value_template: "{{ value_json.contact }}" 65 | device_class: "window" 66 | - platform: "mqtt" 67 | name: Living Room Shutter 7 68 | state_topic: "zigbee/0x00158d0001dcba28" 69 | availability_topic: "zigbee/bridge/state" 70 | payload_on: false 71 | payload_off: true 72 | value_template: "{{ value_json.contact }}" 73 | device_class: "window" 74 | -------------------------------------------------------------------------------- /home-assistant/packages/living_room/music.yaml: -------------------------------------------------------------------------------- 1 | automation: 2 | - alias: Set the harmony to listen to music when the living room chromecast starts playing 3 | trigger: 4 | - platform: state 5 | entity_id: media_player.living_room_2 6 | to: 'playing' 7 | - platform: state 8 | entity_id: media_player.living_room_and_deck 9 | to: 'playing' 10 | condition: 11 | condition: template 12 | value_template: '{{ not is_state_attr("remote.living_room", "current_activity", "Listen to Music") }}' 13 | action: 14 | - service: remote.turn_on 15 | data: 16 | entity_id: remote.living_room 17 | activity: 'Listen to Music' 18 | - alias: Turn off the harmony if on Listen to Music and the audio stops playing 19 | trigger: 20 | - platform: state 21 | entity_id: media_player.living_room_2 22 | to: 'off' 23 | - platform: state 24 | entity_id: media_player.living_room_and_deck 25 | to: 'off' 26 | condition: 27 | condition: and 28 | conditions: 29 | - condition: template 30 | value_template: '{{ is_state_attr("remote.living_room", "current_activity", "Listen to Music") }}' 31 | - condition: state 32 | entity_id: media_player.living_room_2 33 | state: 'off' 34 | - condition: state 35 | entity_id: media_player.living_room_and_deck 36 | state: 'off' 37 | action: 38 | - service: remote.turn_off 39 | data: 40 | entity_id: remote.living_room 41 | - alias: Turn off the music if the harmony remote switches away from Listen to Music 42 | trigger: 43 | - platform: state 44 | entity_id: remote.living_room 45 | from: 'on' 46 | to: 'off' 47 | - platform: template 48 | value_template: '{{ is_state_attr("remote.living_room", "current_activity", "Play a Game") }}' 49 | action: 50 | - service: media_player.turn_off 51 | entity_id: media_player.living_room_2 -------------------------------------------------------------------------------- /home-assistant/packages/living_room/tv.yaml: -------------------------------------------------------------------------------- 1 | switch: 2 | - platform: rest 3 | name: Downstairs TV 4 | resource: http://192.168.2.224:5000/device/0/power 5 | body_on: '{"state":"on"}' 6 | body_off: '{"state":"off"}' 7 | is_on_template: '{{ value_json.state == "starting" or value_json.state == "on" }}' 8 | - platform: rest 9 | name: Downstairs Shield 10 | resource: http://192.168.2.224:5000/device/4/power 11 | body_on: '{"state":"on"}' 12 | body_off: '{"state":"off"}' 13 | is_on_template: '{{ value_json.state == "starting" or value_json.state == "on" }}' 14 | 15 | automation: 16 | - alias: Turn off the tv when the harmony turns off 17 | trigger: 18 | - platform: state 19 | entity_id: remote.living_room 20 | from: 'on' 21 | to: 'off' 22 | action: 23 | - service: switch.turn_off 24 | entity_id: 25 | - switch.downstairs_tv 26 | - alias: Turn off the tv when switching to Listen to Music 27 | trigger: 28 | - platform: template 29 | value_template: '{{ is_state_attr("remote.living_room", "current_activity", "Listen to Music") }}' 30 | action: 31 | - service: switch.turn_off 32 | entity_id: 33 | - switch.downstairs_tv 34 | - alias: Turn on the tv when switching to Play a Game 35 | trigger: 36 | - platform: template 37 | value_template: '{{ is_state_attr("remote.living_room", "current_activity", "Play a Game") }}' 38 | action: 39 | - service: switch.turn_on 40 | entity_id: 41 | - switch.downstairs_tv 42 | - alias: Turn off the harmony remote when the shield goes to sleep if in Play a Game mode 43 | trigger: 44 | - platform: state 45 | entity_id: switch.downstairs_shield 46 | from: 'on' 47 | to: 'off' 48 | condition: 49 | condition: template 50 | value_template: '{{ is_state_attr("remote.living_room", "current_activity", "Play a Game") }}' 51 | action: 52 | - service: remote.turn_off 53 | entity_id: 54 | - remote.living_room -------------------------------------------------------------------------------- /home-assistant/packages/locks/index.yaml: -------------------------------------------------------------------------------- 1 | lock: 2 | - platform: mqtt 3 | name: Back Door Lock 4 | state_topic: "homeassistant_hub/lock/back_door/state" 5 | command_topic: "homeassistant_hub/lock/back_door/set" 6 | value_template: '{{ value_json.state }}' 7 | - platform: mqtt 8 | name: Front Door Lock 9 | state_topic: "homeassistant_hub/lock/front_door/state" 10 | command_topic: "homeassistant_hub/lock/front_door/set" 11 | value_template: '{{ value_json.state }}' 12 | 13 | sensor: 14 | - platform: mqtt 15 | name: Back Door Last Action 16 | state_topic: homeassistant_hub/lock/back_door/state 17 | value_template: '{{ value_json.notification }}' 18 | availability_topic: homeassistant_hub/status 19 | json_attributes_topic: homeassistant_hub/lock/back_door/state 20 | - platform: mqtt 21 | name: Front Door Last Action 22 | state_topic: homeassistant_hub/lock/front_door/state 23 | value_template: '{{ value_json.notification }}' 24 | availability_topic: homeassistant_hub/status 25 | json_attributes_topic: homeassistant_hub/lock/front_door/state 26 | 27 | automation: 28 | - alias: Unlock back door when someone arrives 29 | trigger: 30 | - platform: state 31 | entity_id: device_tracker.blake_phone_mqtt 32 | to: 'home' 33 | - platform: state 34 | entity_id: device_tracker.ali_phone_mqtt 35 | to: 'home' 36 | condition: 37 | condition: time 38 | after: '08:00:00' 39 | before: '23:00:00' 40 | action: 41 | service: lock.unlock 42 | entity_id: lock.back_door_lock -------------------------------------------------------------------------------- /home-assistant/packages/lukes_room.yaml: -------------------------------------------------------------------------------- 1 | sensor: 2 | - platform: "mqtt" 3 | name: Lukes Room Temperature 4 | state_topic: "zigbee/0x00158d0002371319" 5 | availability_topic: "zigbee/bridge/state" 6 | unit_of_measurement: "°F" 7 | icon: "mdi:thermometer" 8 | value_template: "{{ ((float(value_json.temperature) * 9 / 5 ) + 32) | round(1) }}" 9 | - platform: "mqtt" 10 | name: Lukes Room Humidity 11 | state_topic: "zigbee/0x00158d0002371319" 12 | availability_topic: "zigbee/bridge/state" 13 | unit_of_measurement: "%" 14 | icon: "mdi:water-percent" 15 | value_template: "{{ value_json.humidity }}" 16 | - platform: "mqtt" 17 | name: Lukes Room Pressure 18 | state_topic: "zigbee/0x00158d0002371319" 19 | availability_topic: "zigbee/bridge/state" 20 | unit_of_measurement: "Pa" 21 | icon: "mdi:gauge" 22 | value_template: "{{ value_json.pressure }}" -------------------------------------------------------------------------------- /home-assistant/packages/master/bedside_lamps.yaml: -------------------------------------------------------------------------------- 1 | light: 2 | - platform: group 3 | name: Master Lamps 4 | entities: 5 | - light.master_blake_lamp 6 | - light.master_ali_lamp 7 | - platform: group 8 | name: Master Table Lamps 9 | entities: 10 | - light.master_table_right_lamp 11 | - light.master_table_left_lamp 12 | - platform: mqtt 13 | schema: json 14 | name: Master Table Right Lamp 15 | state_topic: "zigbee/0x000b57fffe2f0751" 16 | availability_topic: "zigbee/bridge/state" 17 | brightness: true 18 | command_topic: "zigbee/0x000b57fffe2f0751/set" 19 | - platform: mqtt 20 | schema: json 21 | name: Master Table Left Lamp 22 | state_topic: "zigbee/0x000b57fffe2e2fef" 23 | availability_topic: "zigbee/bridge/state" 24 | brightness: true 25 | command_topic: "zigbee/0x000b57fffe2e2fef/set" 26 | 27 | automation: 28 | - alias: Turn on master lamps at sunset 29 | trigger: 30 | platform: sun 31 | event: sunset 32 | action: 33 | service: light.turn_on 34 | entity_id: 35 | - light.master_table_lamps 36 | - light.master_lamps 37 | data: 38 | brightness_pct: 50 39 | - alias: Toggle Blake lamp 40 | trigger: 41 | platform: mqtt 42 | topic: 'zigbee/0x00158d00022449ea' 43 | condition: 44 | condition: template 45 | value_template: "{{ 'single' == trigger.payload_json.click }}" 46 | action: 47 | service: light.toggle 48 | entity_id: light.master_blake_lamp 49 | 50 | - alias: Toggle Ali lamp 51 | trigger: 52 | platform: mqtt 53 | topic: 'zigbee/0x00158d00019de5ec' 54 | condition: 55 | condition: template 56 | value_template: "{{ 'single' == trigger.payload_json.click }}" 57 | action: 58 | service: light.toggle 59 | entity_id: light.master_ali_lamp 60 | 61 | - alias: Toggle both lamps 62 | trigger: 63 | - platform: mqtt 64 | topic: 'zigbee/0x00158d00022449ea' 65 | - platform: mqtt 66 | topic: 'zigbee/0x00158d00019de5ec' 67 | condition: 68 | condition: template 69 | value_template: "{{ 'double' == trigger.payload_json.click }}" 70 | action: 71 | service: light.toggle 72 | entity_id: light.master_lamps 73 | 74 | - alias: Turn off bathroom lights with triple tap 75 | trigger: 76 | - platform: mqtt 77 | topic: 'zigbee/0x00158d00022449ea' 78 | - platform: mqtt 79 | topic: 'zigbee/0x00158d00019de5ec' 80 | condition: 81 | condition: template 82 | value_template: "{{ 'triple' == trigger.payload_json.click }}" 83 | action: 84 | service: light.turn_off 85 | entity_id: 86 | - light.all_master_bath_lights 87 | - light.master_lamps 88 | - light.master_table_lamps 89 | - light.master_bedroom_light -------------------------------------------------------------------------------- /home-assistant/packages/master/closet.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Master Closet Motion 4 | state_topic: "zigbee/0x00158d0001b15d45" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.occupancy }}" 9 | device_class: "motion" 10 | 11 | automation: 12 | - alias: Turn on master closet lights with motion 13 | trigger: 14 | platform: state 15 | entity_id: binary_sensor.master_closet_motion 16 | to: 'on' 17 | action: 18 | - service: light.turn_on 19 | entity_id: light.master_closet_lights 20 | data_template: 21 | brightness: > 22 | {% if now().hour < 7 or now().hour > 22 %}60 23 | {% else %}250 24 | {% endif %} 25 | - alias: Turn off master closet lights with no motion 26 | trigger: 27 | platform: state 28 | entity_id: binary_sensor.master_closet_motion 29 | to: 'off' 30 | for: 31 | minutes: 2 32 | action: 33 | service: light.turn_off 34 | entity_id: light.master_closet_lights -------------------------------------------------------------------------------- /home-assistant/packages/master/master_bath.yaml: -------------------------------------------------------------------------------- 1 | light: 2 | - platform: group 3 | name: All Master Bath Lights 4 | entities: 5 | - light.master_bath_lights 6 | - light.master_closet_lights 7 | - light.master_shower_light 8 | 9 | sensor: 10 | - platform: "mqtt" 11 | name: Master Bath Temperature 12 | state_topic: "zigbee/0x00158d0001c164af" 13 | availability_topic: "zigbee/bridge/state" 14 | unit_of_measurement: "°F" 15 | icon: "mdi:thermometer" 16 | value_template: "{{ ((float(value_json.temperature) * 9 / 5 ) + 32) | round(1) }}" 17 | - platform: "mqtt" 18 | name: Master Bath Humidity 19 | state_topic: "zigbee/0x00158d0001c164af" 20 | availability_topic: "zigbee/bridge/state" 21 | unit_of_measurement: "%" 22 | icon: "mdi:water-percent" 23 | value_template: "{{ value_json.humidity }}" -------------------------------------------------------------------------------- /home-assistant/packages/master/master_bedroom.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Blake Bedside Motion 4 | state_topic: "zigbee/0x00158d0001b15d41" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.occupancy }}" 9 | device_class: "motion" 10 | - platform: "mqtt" 11 | name: Ali Bedside Motion 12 | state_topic: "zigbee/0x00158d0001e1845a" 13 | availability_topic: "zigbee/bridge/state" 14 | payload_on: true 15 | payload_off: false 16 | value_template: "{{ value_json.occupancy }}" 17 | device_class: "motion" -------------------------------------------------------------------------------- /home-assistant/packages/media/auto_cool.yaml: -------------------------------------------------------------------------------- 1 | automation: 2 | - alias: Prompt for cooling off the media room if its hot and we are in town 3 | trigger: 4 | platform: time 5 | at: '19:00' 6 | condition: 7 | condition: and 8 | conditions: 9 | - condition: numeric_state 10 | entity_id: proximity.blake_home 11 | below: '32000' 12 | - condition: numeric_state 13 | entity_id: sensor.media_temperature 14 | above: '74' 15 | - condition: state 16 | entity_id: climate.media 17 | state: 'off' 18 | action: 19 | service: notify.blake_telegram 20 | #target: ['specific device to notify'] 21 | data: 22 | message: "Should I cool down the media room?" 23 | data: 24 | inline_keyboard: 25 | - 'Yes:/cool_media' 26 | 27 | - alias: Cool media action clicked 28 | trigger: 29 | - platform: event 30 | event_type: telegram_callback 31 | event_data: 32 | data: '/cool_media' 33 | condition: 34 | condition: and 35 | conditions: 36 | - condition: numeric_state 37 | entity_id: sensor.media_temperature 38 | above: '74' 39 | - condition: state 40 | entity_id: climate.media 41 | state: 'off' 42 | action: 43 | - service: climate.set_operation_mode 44 | data: 45 | entity_id: climate.media 46 | operation_mode: 'cool' 47 | - service: climate.set_temperature 48 | data_template: 49 | temperature: 71 50 | entity_id: 51 | - climate.media 52 | 53 | - alias: Turn off media thermostat at 9:30pm 54 | trigger: 55 | platform: time 56 | at: '21:30' 57 | action: 58 | service: climate.set_operation_mode 59 | data: 60 | entity_id: climate.media 61 | operation_mode: 'off' 62 | -------------------------------------------------------------------------------- /home-assistant/packages/media/media_sensors.yaml: -------------------------------------------------------------------------------- 1 | sensor: 2 | - platform: "mqtt" 3 | name: Media Room Temperature 4 | state_topic: "zigbee/0x00158d00023235ed" 5 | availability_topic: "zigbee/bridge/state" 6 | unit_of_measurement: "°F" 7 | icon: "mdi:thermometer" 8 | value_template: "{{ ((float(value_json.temperature) * 9 / 5 ) + 32) | round(1) }}" 9 | - platform: "mqtt" 10 | name: Media Room Humidity 11 | state_topic: "zigbee/0x00158d00023235ed" 12 | availability_topic: "zigbee/bridge/state" 13 | unit_of_measurement: "%" 14 | icon: "mdi:water-percent" 15 | value_template: "{{ value_json.humidity }}" 16 | - platform: "mqtt" 17 | name: Media Room Pressure 18 | state_topic: "zigbee/0x00158d00023235ed" 19 | availability_topic: "zigbee/bridge/state" 20 | unit_of_measurement: "Pa" 21 | icon: "mdi:gauge" 22 | value_template: "{{ value_json.pressure }}" -------------------------------------------------------------------------------- /home-assistant/packages/pantry.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Pantry Motion 4 | state_topic: "zigbee/0x00158d0001a2ba1f" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.occupancy }}" 9 | device_class: "motion" 10 | 11 | light: 12 | - platform: mqtt 13 | name: Butlers Pantry Under Cabinet 14 | state_topic: "tasmota/stat/4BD477/RESULT" 15 | command_topic: "tasmota/cmnd/4BD477/POWER" 16 | state_value_template: "{{ value_json.POWER }}" 17 | brightness_state_topic: "tasmota/stat/4BD477/RESULT" 18 | brightness_command_topic: "tasmota/cmnd/4BD477/Dimmer" 19 | brightness_scale: 100 20 | brightness_value_template: "{{ value_json.Dimmer }}" 21 | white_value_state_topic: "tasmota/stat/4BD477/RESULT" 22 | white_value_command_topic: "tasmota/cmnd/4BD477/Channel5" 23 | white_value_scale: 100 24 | white_value_template: "{{ value_json.Channel[4] }}" 25 | rgb_command_topic: "tasmota/cmnd/4BD477/Color" 26 | rgb_command_template: "{{ '%02x%02x%02x' | format(red, green, blue)}}" 27 | rgb_state_topic: "tasmota/stat/4BD477/RESULT" 28 | rgb_value_template: "{{(value_json.Channel[0]*2.55)|int}},{{(value_json.Channel[1]*2.55)|int}},{{(value_json.Channel[2]*2.55)|int}}" 29 | effect_state_topic: "tasmota/stat/4BD477/RESULT" 30 | effect_command_topic: "tasmota/cmnd/4BD477/Scheme" 31 | effect_list: 32 | - 0 33 | - 1 34 | - 2 35 | - 3 36 | - 4 37 | retain: false 38 | qos: 1 39 | payload_on: "ON" 40 | payload_off: "OFF" 41 | - platform: mqtt 42 | name: Butlers Pantry Over Cabinet 43 | state_topic: "tasmota/stat/4BD4E3/RESULT" 44 | command_topic: "tasmota/cmnd/4BD4E3/POWER" 45 | state_value_template: "{{ value_json.POWER }}" 46 | brightness_state_topic: "tasmota/stat/4BD4E3/RESULT" 47 | brightness_command_topic: "tasmota/cmnd/4BD4E3/Dimmer" 48 | brightness_scale: 100 49 | brightness_value_template: "{{ value_json.Dimmer }}" 50 | white_value_state_topic: "tasmota/stat/4BD4E3/RESULT" 51 | white_value_command_topic: "tasmota/cmnd/4BD4E3/Channel5" 52 | white_value_scale: 100 53 | white_value_template: "{{ value_json.Channel[4] }}" 54 | rgb_command_topic: "tasmota/cmnd/4BD4E3/Color" 55 | rgb_command_template: "{{ '%02x%02x%02x' | format(red, green, blue)}}" 56 | rgb_state_topic: "tasmota/stat/4BD4E3/RESULT" 57 | rgb_value_template: "{{(value_json.Channel[0]*2.55)|int}},{{(value_json.Channel[1]*2.55)|int}},{{(value_json.Channel[2]*2.55)|int}}" 58 | effect_state_topic: "tasmota/stat/4BD4E3/RESULT" 59 | effect_command_topic: "tasmota/cmnd/4BD4E3/Scheme" 60 | effect_list: 61 | - 0 62 | - 1 63 | - 2 64 | - 3 65 | - 4 66 | retain: false 67 | qos: 1 68 | payload_on: "ON" 69 | payload_off: "OFF" 70 | 71 | automation: 72 | - alias: Turn on pantry light with motion 73 | trigger: 74 | platform: state 75 | entity_id: binary_sensor.pantry_motion 76 | to: 'on' 77 | action: 78 | service: light.turn_on 79 | entity_id: light.pantry_light 80 | 81 | - alias: Turn off pantry light with no motion 82 | trigger: 83 | platform: state 84 | entity_id: binary_sensor.pantry_motion 85 | to: 'off' 86 | for: 87 | minutes: 1 88 | action: 89 | service: light.turn_off 90 | entity_id: light.pantry_light -------------------------------------------------------------------------------- /home-assistant/packages/play_room.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Playroom Motion 4 | state_topic: "zigbee/0x00158d0001ad43f0" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.occupancy }}" 9 | device_class: "motion" 10 | - platform: "mqtt" 11 | name: Play Room Shutter 1 12 | state_topic: "zigbee/0x00158d0001dcba76" 13 | availability_topic: "zigbee/bridge/state" 14 | payload_on: false 15 | payload_off: true 16 | value_template: "{{ value_json.contact }}" 17 | device_class: "window" 18 | - platform: "mqtt" 19 | name: Play Room Shutter 2 20 | state_topic: "zigbee/0x00158d0001b780f8" 21 | availability_topic: "zigbee/bridge/state" 22 | payload_on: false 23 | payload_off: true 24 | value_template: "{{ value_json.contact }}" 25 | device_class: "window" 26 | 27 | automation: 28 | - alias: Turn on playroom light with motion 29 | trigger: 30 | platform: state 31 | entity_id: binary_sensor.playroom_motion 32 | to: 'on' 33 | action: 34 | - service: light.turn_on 35 | entity_id: light.playroom_light 36 | 37 | - alias: Turn off playroom lights with no motion for 10 min 38 | trigger: 39 | platform: state 40 | entity_id: binary_sensor.playroom_motion 41 | to: 'off' 42 | for: 43 | minutes: 10 44 | action: 45 | service: light.turn_off 46 | entity_id: light.playroom_light -------------------------------------------------------------------------------- /home-assistant/packages/porch.yaml: -------------------------------------------------------------------------------- 1 | automation: 2 | - alias: Turn on Outside Lights at Sunset 3 | trigger: 4 | platform: sun 5 | event: sunset 6 | action: 7 | - service: light.turn_on 8 | entity_id: light.porch_lights 9 | data: 10 | brightness_pct: 40 11 | - service: light.turn_on 12 | entity_id: light.driveway_lights 13 | data: 14 | brightness: 50 15 | 16 | - alias: Turn off Outside Lights at Sunrise 17 | trigger: 18 | platform: sun 19 | event: sunrise 20 | action: 21 | service: light.turn_off 22 | entity_id: 23 | - light.porch_lights 24 | - light.driveway_lights -------------------------------------------------------------------------------- /home-assistant/packages/security/baby_monitor.yaml: -------------------------------------------------------------------------------- 1 | input_boolean: 2 | baby_monitor: 3 | name: Baby Monitor Mode 4 | initial: off 5 | icon: mdi:baby-buggy 6 | 7 | automation: 8 | - alias: 'Motion detected in the house' 9 | trigger: 10 | - platform: state 11 | entity_id: binary_sensor.laundry_room_motion 12 | to: 'on' 13 | - platform: state 14 | entity_id: binary_sensor.hall_motion 15 | to: 'on' 16 | - platform: state 17 | entity_id: binary_sensor.master_closet_motion 18 | to: 'on' 19 | - platform: state 20 | entity_id: binary_sensor.motion_sensor_158d0001b15d41 21 | to: 'on' 22 | - platform: state 23 | entity_id: binary_sensor.motion_sensor_158d0001e1845a 24 | to: 'on' 25 | - platform: state 26 | entity_id: binary_sensor.half_bath_motion 27 | to: 'on' 28 | - platform: state 29 | entity_id: binary_sensor.pantry_motion 30 | to: 'on' 31 | - platform: state 32 | entity_id: binary_sensor.back_door 33 | to: 'on' 34 | - platform: state 35 | entity_id: binary_sensor.front_door 36 | to: 'on' 37 | - platform: state 38 | entity_id: binary_sensor.boys_doors_motion 39 | to: 'on' 40 | condition: 41 | condition: state 42 | entity_id: input_boolean.baby_monitor 43 | state: 'on' 44 | action: 45 | - service: notify.blake_telegram 46 | data_template: 47 | message: "{{ trigger.to_state.attributes.friendly_name }} has detected motion!" 48 | - service: notify.html5_ali_phone 49 | data_template: 50 | message: "{{ trigger.to_state.attributes.friendly_name }} has detected motion!" -------------------------------------------------------------------------------- /home-assistant/packages/security/smoke_alarm.yaml: -------------------------------------------------------------------------------- 1 | switch: 2 | - name: Smoke Alarm 3 | platform: mqtt 4 | command_topic: "taproot/alarm/set" 5 | state_topic: "taproot/alarm/status" 6 | payload_on: "ON" 7 | payload_off: "OFF" 8 | availability_topic: "taproot/smoke/available" 9 | icon: "mdi:alarm-bell" 10 | 11 | binary_sensor: 12 | - name: Smoke Detector 13 | platform: mqtt 14 | state_topic: "taproot/smoke/status" 15 | device_class: "smoke" 16 | availability_topic: "taproot/smoke/available" 17 | - name: CO Detector 18 | platform: mqtt 19 | state_topic: "taproot/co/status" 20 | device_class: "gas" 21 | availability_topic: "taproot/smoke/available" 22 | 23 | 24 | automation: 25 | - alias: Send a text message if the smoke alarm goes off 26 | trigger: 27 | - platform: state 28 | entity_id: binary_sensor.smoke_detector 29 | from: 'off' 30 | to: 'on' 31 | for: 32 | minutes: 1 33 | action: 34 | - service: notify.blakeshome_sms 35 | data_template: 36 | message: 'The smoke alarm is going off!' 37 | target: 38 | - !secret blake_phone_number 39 | - alias: Send a text message if the co alarm goes off 40 | trigger: 41 | - platform: state 42 | entity_id: binary_sensor.co_detector 43 | from: 'off' 44 | to: 'on' 45 | for: 46 | minutes: 1 47 | action: 48 | - service: notify.blakeshome_sms 49 | data_template: 50 | message: 'The carbon monoxide alarm is going off!' 51 | target: 52 | - !secret blake_phone_number 53 | - alias: Send a text message if the smoke or co alarms are unavailable 54 | trigger: 55 | - platform: state 56 | entity_id: binary_sensor.smoke_detector 57 | to: 'unavailable' 58 | - platform: state 59 | entity_id: binary_sensor.co_detector 60 | to: 'unavailable' 61 | action: 62 | - service: notify.blakeshome_sms 63 | data_template: 64 | message: 'The smoke or co alarms are disconnected.' 65 | target: 66 | - !secret blake_phone_number -------------------------------------------------------------------------------- /home-assistant/packages/security/status.yaml: -------------------------------------------------------------------------------- 1 | scene: 2 | - name: Lockup 3 | entities: 4 | lock.back_door_lock: locked 5 | lock.front_door_lock: locked 6 | cover.blake_s_garage_door: closed 7 | cover.ali_s_garage_door: closed 8 | 9 | sensor: 10 | platform: template 11 | sensors: 12 | locked_up: 13 | friendly_name: "Doors and Garage" 14 | value_template: >- 15 | {% if is_state('lock.back_door_lock', 'unlocked') or 16 | is_state('lock.front_door_lock','unlocked') or 17 | is_state('cover.blake_s_garage_door', 'open') or 18 | is_state('cover.ali_s_garage_door', 'open') %} 19 | Not Secured 20 | {% else %} 21 | Secured 22 | {% endif %} 23 | 24 | -------------------------------------------------------------------------------- /home-assistant/packages/sensors/index.yaml: -------------------------------------------------------------------------------- 1 | sensor: 2 | - platform: yr -------------------------------------------------------------------------------- /home-assistant/packages/sensors/sonoff_s31.yaml: -------------------------------------------------------------------------------- 1 | sensor: 2 | - platform: mqtt 3 | name: "Water Heater Energy" 4 | state_topic: "tele/sonoff-0AED33/SENSOR" 5 | value_template: '{{ value_json["ENERGY"]["Today"] }}' 6 | unit_of_measurement: "kWh" 7 | - platform: mqtt 8 | name: "Water Heater Power" 9 | state_topic: "tele/sonoff-0AED33/SENSOR" 10 | value_template: '{{ value_json["ENERGY"]["Power"] }}' 11 | unit_of_measurement: "W" 12 | - platform: mqtt 13 | name: "Water Heater Voltage" 14 | state_topic: "tele/sonoff-0AED33/SENSOR" 15 | value_template: '{{ value_json["ENERGY"]["Voltage"] }}' 16 | unit_of_measurement: "V" 17 | - platform: mqtt 18 | name: "Water Heater Current" 19 | state_topic: "tele/sonoff-0AED33/SENSOR" 20 | value_template: '{{ value_json["ENERGY"]["Current"] }}' 21 | unit_of_measurement: "A" 22 | 23 | - platform: mqtt 24 | name: "Dehumidifier Energy" 25 | state_topic: "tele/sonoff-3491/SENSOR" 26 | value_template: '{{ value_json["ENERGY"]["Today"] }}' 27 | unit_of_measurement: "kWh" 28 | - platform: mqtt 29 | name: "Dehumidifier Power" 30 | state_topic: "tele/sonoff-3491/SENSOR" 31 | value_template: '{{ value_json["ENERGY"]["Power"] }}' 32 | unit_of_measurement: "W" 33 | - platform: mqtt 34 | name: "Dehumidifier Voltage" 35 | state_topic: "tele/sonoff-3491/SENSOR" 36 | value_template: '{{ value_json["ENERGY"]["Voltage"] }}' 37 | unit_of_measurement: "V" 38 | - platform: mqtt 39 | name: "Dehumidifier Current" 40 | state_topic: "tele/sonoff-3491/SENSOR" 41 | value_template: '{{ value_json["ENERGY"]["Current"] }}' 42 | unit_of_measurement: "A" 43 | 44 | switch: 45 | - platform: mqtt 46 | name: "Christmas Tree" 47 | state_topic: "stat/7D1FF0/RESULT" 48 | value_template: "{{ value_json.POWER }}" 49 | command_topic: "cmnd/7D1FF0/POWER" 50 | availability_topic: "tele/7D1FF0/LWT" 51 | qos: 1 52 | payload_on: "ON" 53 | payload_off: "OFF" 54 | payload_available: "Online" 55 | payload_not_available: "Offline" 56 | retain: false -------------------------------------------------------------------------------- /home-assistant/packages/sensors/xiaomi_batteries.yaml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /home-assistant/packages/sensors/xiaomi_sensors.yaml: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/blakeblackshear/blakeshome-config/afe682a9bfa84aba77b3bcc6ddf5894e5fec1ada/home-assistant/packages/sensors/xiaomi_sensors.yaml -------------------------------------------------------------------------------- /home-assistant/packages/sensors/zway_batteries.yaml: -------------------------------------------------------------------------------- 1 | sensor: 2 | - platform: mqtt 3 | name: Front Door Lock Battery 4 | state_topic: "homeassistant_hub/sensor/front_door_lock_battery/state" 5 | availability_topic: homeassistant_hub/status 6 | unit_of_measurement: '%' 7 | value_template: '{{ value_json.state }}' 8 | - platform: mqtt 9 | name: Back Door Lock Battery 10 | state_topic: "homeassistant_hub/sensor/back_door_lock_battery/state" 11 | availability_topic: homeassistant_hub/status 12 | unit_of_measurement: '%' 13 | value_template: '{{ value_json.state }}' -------------------------------------------------------------------------------- /home-assistant/packages/switches/zway.yaml: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/blakeblackshear/blakeshome-config/afe682a9bfa84aba77b3bcc6ddf5894e5fec1ada/home-assistant/packages/switches/zway.yaml -------------------------------------------------------------------------------- /home-assistant/packages/thermostats.yaml: -------------------------------------------------------------------------------- 1 | ### 2 | # Downstairs: 3 | # When below 50 outside, heated to 72 during day and 70 at night. When over 60 outside, cooled to 74 during day and 69 at night. 4 | 5 | sensor: 6 | - platform: template 7 | sensors: 8 | target_down_temperature: 9 | friendly_name: Target Downstairs Temperature 10 | unit_of_measurement: "°F" 11 | value_template: >- 12 | {% set t = strptime(states('sensor.time'), '%H:%M') %} 13 | {% if states('climate.downstairs') == 'heat' -%} 14 | {%- if t.hour <6 or t.hour >=21 -%} 15 | 62 16 | {%- else -%} 17 | 72 18 | {%- endif -%} 19 | {%- elif states('climate.downstairs') == 'cool' -%} 20 | {%- if t.hour <6 or t.hour >=21 -%} 21 | 82 22 | {%- else -%} 23 | 74 24 | {%- endif -%} 25 | {%- endif %} 26 | target_up_temperature: 27 | friendly_name: Target Upstairs Temperature 28 | unit_of_measurement: "°F" 29 | value_template: >- 30 | {% set t = strptime(states('sensor.time'), '%H:%M') %} 31 | {% if states('climate.upstairs') == 'heat' -%} 32 | {%- if t.hour <8 or t.hour >=19 -%} 33 | 69 34 | {%- else -%} 35 | 71 36 | {%- endif -%} 37 | {%- elif states('climate.upstairs') == 'cool' -%} 38 | {%- if t.hour >=19 or t.hour <6 -%} 39 | 71 40 | {%- else -%} 41 | 74 42 | {%- endif -%} 43 | {%- endif %} 44 | automation: 45 | - alias: If outside temperature drops below 55, switch to Heat 46 | trigger: 47 | platform: numeric_state 48 | entity_id: sensor.outside_temperature 49 | below: 50 50 | action: 51 | - service: climate.set_hvac_mode 52 | data: 53 | hvac_mode: 'heat' 54 | entity_id: 55 | - climate.downstairs 56 | - climate.upstairs 57 | - alias: If outside temperature goes above 65, switch to Cool 58 | trigger: 59 | platform: numeric_state 60 | entity_id: sensor.outside_temperature 61 | above: 65 62 | action: 63 | - service: climate.set_hvac_mode 64 | data: 65 | hvac_mode: 'cool' 66 | entity_id: 67 | - climate.downstairs 68 | - climate.upstairs 69 | - alias: Set the downstairs thermostat to the target temperature 70 | trigger: 71 | platform: state 72 | entity_id: sensor.target_down_temperature 73 | condition: 74 | - condition: state 75 | entity_id: input_boolean.vacation_mode 76 | state: 'off' 77 | action: 78 | - service: climate.set_temperature 79 | data_template: 80 | temperature: "{{ states('sensor.target_down_temperature')|float }}" 81 | entity_id: 82 | - climate.downstairs 83 | - alias: Set the upstairs thermostat to the target temperature 84 | trigger: 85 | platform: state 86 | entity_id: sensor.target_up_temperature 87 | condition: 88 | - condition: state 89 | entity_id: input_boolean.vacation_mode 90 | state: 'off' 91 | action: 92 | - service: climate.set_temperature 93 | data_template: 94 | temperature: "{{ states('sensor.target_up_temperature')|float }}" 95 | entity_id: 96 | - climate.upstairs -------------------------------------------------------------------------------- /home-assistant/packages/vacation_mode.yaml: -------------------------------------------------------------------------------- 1 | light: 2 | - platform: group 3 | name: Foyer Lights 4 | entities: 5 | - light.foyer_front_light 6 | - light.foyer_back_light 7 | - platform: group 8 | name: Living Room Lights 9 | entities: 10 | - light.living_room_chandelier_light 11 | - light.living_room_recessed_lights 12 | 13 | input_boolean: 14 | vacation_mode: 15 | name: Vacation Mode 16 | initial: off 17 | icon: mdi:airplane 18 | 19 | group: 20 | random_away_lights: 21 | entities: 22 | - light.kitchen_lights 23 | - light.foyer_lights 24 | - light.playroom_lights 25 | - light.living_room_lights 26 | - light.master_lamps 27 | 28 | automation: 29 | ################################################################ 30 | ## Random lights on while sunset and vacation mode on 31 | ################################################################ 32 | - alias: Random Vacation Lights 33 | initial_state: True 34 | hide_entity: False 35 | 36 | trigger: 37 | - platform: time_pattern 38 | minutes: '/30' 39 | seconds: 00 40 | 41 | condition: 42 | - condition: state 43 | entity_id: input_boolean.vacation_mode 44 | state: 'on' 45 | 46 | action: 47 | - delay: "00:{{ '{:02}'.format(range(1, 29) | random | int) }}:00" 48 | 49 | - condition: state 50 | entity_id: input_boolean.vacation_mode 51 | state: 'on' 52 | 53 | - condition: or 54 | conditions: 55 | - condition: time 56 | before: "01:00:00" 57 | 58 | - condition: sun 59 | after: sunset 60 | after_offset: "-01:00:00" 61 | 62 | - condition: state 63 | entity_id: alarm_control_panel.home_alarm 64 | state: armed_away 65 | 66 | - service: homeassistant.toggle 67 | data_template: 68 | entity_id: "{{ state_attr('group.random_away_lights','entity_id') | random }}" 69 | 70 | ########################################################## 71 | ## Random Lights Off 72 | ########################################################## 73 | - alias: Random Lights Off At 1AM 74 | initial_state: True 75 | hide_entity: False 76 | 77 | trigger: 78 | - platform: time 79 | at: "01:00:00" 80 | 81 | condition: 82 | - condition: state 83 | entity_id: input_boolean.vacation_mode 84 | state: 'on' 85 | 86 | action: 87 | - service: homeassistant.turn_off 88 | entity_id: group.random_away_lights 89 | 90 | ########################################################## 91 | ## Random lights Off 92 | ########################################################## 93 | - alias: Random Lights Off 94 | initial_state: True 95 | hide_entity: False 96 | 97 | trigger: 98 | - platform: state 99 | entity_id: input_boolean.vacation_mode 100 | from: 'on' 101 | to: 'off' 102 | 103 | action: 104 | - service: homeassistant.turn_off 105 | entity_id: group.random_away_lights 106 | 107 | - alias: Turn on vacation mode if we are both more than 50 miles away 108 | trigger: 109 | - platform: numeric_state 110 | entity_id: proximity.blake_home 111 | above: '50000' 112 | for: 113 | minutes: 15 114 | - platform: numeric_state 115 | entity_id: proximity.ali_home 116 | above: '50000' 117 | for: 118 | minutes: 15 119 | condition: 120 | - condition: numeric_state 121 | entity_id: proximity.blake_home 122 | above: '50000' 123 | - condition: numeric_state 124 | entity_id: proximity.ali_home 125 | above: '50000' 126 | - condition: state 127 | entity_id: input_boolean.vacation_mode 128 | state: 'off' 129 | action: 130 | - service: input_boolean.turn_on 131 | entity_id: input_boolean.vacation_mode 132 | - service: notify.blake_telegram 133 | data: 134 | message: "Vacation mode enabled." 135 | 136 | - alias: Turn off vacation mode if either of us is less than 50 miles away 137 | trigger: 138 | - platform: numeric_state 139 | entity_id: proximity.blake_home 140 | below: '50000' 141 | for: 142 | minutes: 15 143 | - platform: numeric_state 144 | entity_id: proximity.ali_home 145 | below: '50000' 146 | for: 147 | minutes: 15 148 | condition: 149 | - condition: state 150 | entity_id: input_boolean.vacation_mode 151 | state: 'on' 152 | action: 153 | - service: input_boolean.turn_off 154 | entity_id: input_boolean.vacation_mode 155 | - service: notify.blake_telegram 156 | data: 157 | message: "Vacation mode disabled." 158 | 159 | - alias: Set the thermostats to vacation mode 160 | trigger: 161 | - platform: state 162 | entity_id: input_boolean.vacation_mode 163 | from: 'off' 164 | to: 'on' 165 | action: 166 | - service: climate.set_away_mode 167 | data: 168 | away_mode: 'yes' 169 | entity_id: 170 | - climate.downstairs 171 | - climate.upstairs 172 | 173 | - alias: Set the thermostats to normal mode 174 | trigger: 175 | - platform: state 176 | entity_id: input_boolean.vacation_mode 177 | from: 'on' 178 | to: 'off' 179 | action: 180 | - service: climate.set_away_mode 181 | data: 182 | away_mode: 'no' 183 | entity_id: 184 | - climate.downstairs 185 | - climate.upstairs -------------------------------------------------------------------------------- /home-assistant/packages/vacuum.yaml: -------------------------------------------------------------------------------- 1 | camera: 2 | - platform: mqtt 3 | name: Downstairs Vacuum Map 4 | topic: valetudo/downstairs/map 5 | 6 | sensor: 7 | - platform: history_stats 8 | name: Vacuum time in the last 24 hours 9 | entity_id: vacuum.xiaomi_vacuum_cleaner 10 | state: 'cleaning' 11 | type: time 12 | end: '{{ now() }}' 13 | duration: 14 | hours: 24 15 | 16 | automation: 17 | - alias: Run the vacuum if Ali is at the gym 18 | trigger: 19 | - platform: state 20 | entity_id: device_tracker.ali_phone_mqtt 21 | to: 'Gym' 22 | for: 23 | minutes: 10 24 | condition: 25 | condition: and 26 | conditions: 27 | - condition: time 28 | after: '09:30:00' 29 | before: '17:00:00' 30 | weekday: 31 | - mon 32 | - tue 33 | - wed 34 | - thu 35 | - fri 36 | - condition: template 37 | value_template: "{{ not is_state('device_tracker.blake_phone_mqtt', 'home') }}" 38 | action: 39 | service: vacuum.start 40 | data: 41 | entity_id: vacuum.xiaomi_vacuum_cleaner 42 | 43 | - alias: Run the vacuum when Ali leaves MWF 44 | trigger: 45 | - platform: state 46 | entity_id: device_tracker.ali_phone_mqtt 47 | from: 'home' 48 | condition: 49 | - condition: time 50 | after: '07:30:00' 51 | before: '09:30:00' 52 | weekday: 53 | - mon 54 | - wed 55 | - fri 56 | action: 57 | service: vacuum.start 58 | data: 59 | entity_id: vacuum.xiaomi_vacuum_cleaner 60 | 61 | - alias: Ask about running the vacuum if we are gone on the weekend 62 | trigger: 63 | - platform: state 64 | entity_id: group.people 65 | to: 'not_home' 66 | for: 67 | minutes: 7 68 | condition: 69 | - condition: state 70 | entity_id: vacuum.xiaomi_vacuum_cleaner 71 | state: 'docked' 72 | - condition: time 73 | weekday: 74 | - sat 75 | - sun 76 | - condition: numeric_state 77 | entity_id: sensor.vacuum_time_in_the_last_24_hours 78 | below: 1 79 | action: 80 | service: notify.blake_telegram 81 | #target: ['specific device to notify'] 82 | data: 83 | message: "Should I vacuum while you are gone?" 84 | data: 85 | inline_keyboard: 86 | - 'Yes:/run_vacuum' 87 | 88 | - alias: Run vacuum action clicked 89 | trigger: 90 | - platform: event 91 | event_type: telegram_callback 92 | event_data: 93 | data: '/run_vacuum' 94 | condition: 95 | - condition: state 96 | entity_id: vacuum.xiaomi_vacuum_cleaner 97 | state: 'docked' 98 | action: 99 | service: vacuum.start 100 | data: 101 | entity_id: vacuum.xiaomi_vacuum_cleaner 102 | -------------------------------------------------------------------------------- /home-assistant/packages/water_leak_sensors.yaml: -------------------------------------------------------------------------------- 1 | binary_sensor: 2 | - platform: "mqtt" 3 | name: Kitchen Sink Water Leak Detector 4 | state_topic: "zigbee/0x00158d0001d78a51" 5 | availability_topic: "zigbee/bridge/state" 6 | payload_on: true 7 | payload_off: false 8 | value_template: "{{ value_json.water_leak }}" 9 | device_class: "moisture" 10 | - platform: "mqtt" 11 | name: Clothes Washer Leak Detector 12 | state_topic: "zigbee/0x00158d00023738fc" 13 | availability_topic: "zigbee/bridge/state" 14 | payload_on: true 15 | payload_off: false 16 | value_template: "{{ value_json.water_leak }}" 17 | device_class: "moisture" 18 | - platform: "mqtt" 19 | name: Guest Bath Leak Detector 20 | state_topic: "zigbee/0x00158d0002379bac" 21 | availability_topic: "zigbee/bridge/state" 22 | payload_on: true 23 | payload_off: false 24 | value_template: "{{ value_json.water_leak }}" 25 | device_class: "moisture" 26 | - platform: "mqtt" 27 | name: Main HVAC Pan Water Detector 28 | state_topic: "zigbee/0x00158d000237390f" 29 | availability_topic: "zigbee/bridge/state" 30 | payload_on: true 31 | payload_off: false 32 | value_template: "{{ value_json.water_leak }}" 33 | device_class: "moisture" 34 | 35 | automation: 36 | - alias: Send a text message if a water leak is detected 37 | trigger: 38 | - platform: state 39 | entity_id: group.water_leak_detectors 40 | from: 'off' 41 | to: 'on' 42 | for: 43 | minutes: 1 44 | action: 45 | - service: notify.blakeshome_sms 46 | data_template: 47 | message: 'A water leak was detected!' 48 | target: 49 | - !secret blake_phone_number -------------------------------------------------------------------------------- /home-assistant/packages/weather.yaml: -------------------------------------------------------------------------------- 1 | # camera: 2 | # - name: Weather Radar 3 | # platform: generic 4 | # still_image_url: "https://radar.nashvillesevereweather.com/mosaic/nashville25_anim.gif?{{states('sensor.time_utc')}}" 5 | # limit_refetch_to_url_change: True 6 | # content_type: image/gif 7 | 8 | 9 | -------------------------------------------------------------------------------- /home-assistant/packages/yard/cameras.yaml: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/blakeblackshear/blakeshome-config/afe682a9bfa84aba77b3bcc6ddf5894e5fec1ada/home-assistant/packages/yard/cameras.yaml -------------------------------------------------------------------------------- /home-assistant/scripts.yaml: -------------------------------------------------------------------------------- 1 | clean_downstairs_vacuum: 2 | alias: Clean downstairs vacuum 3 | sequence: 4 | # This is written using the Script Syntax 5 | - service: vacuum.xiaomi_remote_control_start 6 | entity_id: vacuum.xiaomi_vacuum_cleaner 7 | - delay: 00:00:03 8 | - service: vacuum.xiaomi_remote_control_move_step 9 | data: 10 | entity_id: vacuum.xiaomi_vacuum_cleaner 11 | velocity: 0.29 12 | rotation: 0 13 | duration: 4000 -------------------------------------------------------------------------------- /home-assistant/secrets.yaml.enc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/blakeblackshear/blakeshome-config/afe682a9bfa84aba77b3bcc6ddf5894e5fec1ada/home-assistant/secrets.yaml.enc -------------------------------------------------------------------------------- /home-assistant/www/ali.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/blakeblackshear/blakeshome-config/afe682a9bfa84aba77b3bcc6ddf5894e5fec1ada/home-assistant/www/ali.png -------------------------------------------------------------------------------- /home-assistant/www/blake.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/blakeblackshear/blakeshome-config/afe682a9bfa84aba77b3bcc6ddf5894e5fec1ada/home-assistant/www/blake.png -------------------------------------------------------------------------------- /home-assistant/www/custom_ui/oauth.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /iptables-rules-save: -------------------------------------------------------------------------------- 1 | *filter 2 | :INPUT DROP [0:0] 3 | :FORWARD DROP [0:0] 4 | :OUTPUT ACCEPT [0:0] 5 | 6 | # Create chain for sshguard 7 | -N sshguard 8 | 9 | # Block sshguard ips 10 | -A INPUT -j sshguard 11 | 12 | # Accept all loopback (local) traffic: 13 | -A INPUT -i lo -j ACCEPT 14 | 15 | # Keep existing connections (like our SSH session) alive: 16 | -A INPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT 17 | 18 | # SSH 19 | -A INPUT -p tcp -m tcp --dport 22 -j ACCEPT 20 | 21 | # Nginx 22 | -A INPUT -p tcp -m tcp --dport 443 -j ACCEPT 23 | 24 | # Unifi controller 25 | -A INPUT -p tcp -m tcp --dport 8080 -j ACCEPT 26 | 27 | # Emulated hue 28 | -A INPUT -p tcp -m tcp --dport 8300 -j ACCEPT 29 | 30 | # Pihole 31 | -A INPUT -p tcp --dport 80 -j ACCEPT 32 | -A INPUT -p tcp --dport 53 -j ACCEPT 33 | -A INPUT -p udp --dport 53 -j ACCEPT 34 | -I INPUT -p udp --dport 67:68 --sport 67:68 -j ACCEPT 35 | 36 | # Zway MQTT Bridge 37 | -A INPUT -p tcp --dport 9009 -j ACCEPT 38 | 39 | # Allow multicast (for Xiaomi gateways) 40 | -I INPUT -p udp -j ACCEPT 41 | 42 | # Samba 43 | -A INPUT -p tcp --dport 139 -j ACCEPT 44 | -A INPUT -p tcp --dport 445 -j ACCEPT 45 | -A INPUT -p udp --dport 137 -j ACCEPT 46 | -A INPUT -p udp --dport 138 -j ACCEPT 47 | 48 | # Accept pings: 49 | -A INPUT -p icmp -m icmp --icmp-type 0 -j ACCEPT 50 | -A INPUT -p icmp -m icmp --icmp-type 3 -j ACCEPT 51 | -A INPUT -p icmp -m icmp --icmp-type 11 -j ACCEPT 52 | COMMIT 53 | -------------------------------------------------------------------------------- /mosquitto/mosquitto.conf: -------------------------------------------------------------------------------- 1 | persistence true 2 | persistence_location /mosquitto/data/ -------------------------------------------------------------------------------- /motion/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM motionproject/motion:latest 2 | 3 | RUN export DEBIAN_FRONTEND=noninteractive; \ 4 | export DEBCONF_NONINTERACTIVE_SEEN=true; \ 5 | apt-get update -qqy && apt-get install -qqy --option Dpkg::Options::="--force-confnew" --no-install-recommends \ 6 | mosquitto-clients jq && \ 7 | apt-get --quiet autoremove --yes && \ 8 | apt-get --quiet --yes clean && \ 9 | rm -rf /var/lib/apt/lists/* 10 | 11 | COPY on_event_start.sh /on_event_start.sh 12 | COPY on_picture_save.sh /on_picture_save.sh 13 | 14 | RUN chmod +x /on_*.sh 15 | 16 | VOLUME ["/data", "/usr/local/etc/motion"] 17 | -------------------------------------------------------------------------------- /motion/conf.d/back.conf: -------------------------------------------------------------------------------- 1 | camera_name back 2 | netcam_url rtsp://10.0.10.10:554/cam/realmonitor?channel=1&subtype=1 3 | mask_file /usr/local/etc/motion/mask.pgm -------------------------------------------------------------------------------- /motion/mask.pgm: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/blakeblackshear/blakeshome-config/afe682a9bfa84aba77b3bcc6ddf5894e5fec1ada/motion/mask.pgm -------------------------------------------------------------------------------- /motion/motion.conf: -------------------------------------------------------------------------------- 1 | # Rename this distribution example file to motion.conf 2 | # 3 | # This config file was generated by motion 4.2.1 4 | # Documentation: @prefix@/share/doc/motion/motion_guide.html 5 | # 6 | # This file contains only the basic configuration options to get a 7 | # system working. There are many more options available. Please 8 | # consult the documentation for the complete list of all options. 9 | # 10 | 11 | ############################################################ 12 | # System control configuration parameters 13 | ############################################################ 14 | 15 | # Start in daemon (background) mode and release terminal. 16 | daemon off 17 | 18 | # Start in Setup-Mode, daemon disabled. 19 | setup_mode off 20 | 21 | # File to store the process ID. 22 | ; pid_file value 23 | 24 | # File to write logs messages into. If not defined stderr and syslog is used. 25 | ; log_file value 26 | 27 | # Level of log messages [1..9] (EMG, ALR, CRT, ERR, WRN, NTC, INF, DBG, ALL). 28 | log_level 6 29 | 30 | # Target directory for pictures, snapshots and movies 31 | ; target_dir value 32 | 33 | # Video device (e.g. /dev/video0) to be used for capturing. 34 | # videodevice /dev/video0 35 | 36 | # Parameters to control video device. See motion_guide.html 37 | ; vid_control_params value 38 | 39 | # The full URL of the network camera stream. 40 | ; netcam_url value 41 | 42 | netcam_userpass viewer:test1234 43 | 44 | # Name of mmal camera (e.g. vc.ril.camera for pi camera). 45 | ; mmalcam_name value 46 | 47 | # Camera control parameters (see raspivid/raspistill tool documentation) 48 | ; mmalcam_control_params value 49 | 50 | ############################################################ 51 | # Image Processing configuration parameters 52 | ############################################################ 53 | 54 | # Image width in pixels. 55 | width 704 56 | 57 | # Image height in pixels. 58 | height 576 59 | 60 | # Maximum number of frames to be captured per second. 61 | framerate 2 62 | 63 | locate_motion_mode on 64 | 65 | ############################################################ 66 | # Motion detection configuration parameters 67 | ############################################################ 68 | 69 | # Always save pictures and movies even if there was no motion. 70 | emulate_motion off 71 | 72 | # Threshold for number of changed pixels that triggers motion. 73 | threshold 1500 74 | 75 | # Noise threshold for the motion detection. 76 | ; noise_level 32 77 | 78 | # Despeckle the image using (E/e)rode or (D/d)ilate or (l)abel. 79 | despeckle_filter EedDl 80 | 81 | # Number of images that must contain motion to trigger an event. 82 | minimum_motion_frames 2 83 | 84 | # Gap in seconds of no motion detected that triggers the end of an event. 85 | event_gap 60 86 | 87 | # The number of pre-captured (buffered) pictures from before motion. 88 | pre_capture 3 89 | 90 | # Number of frames to capture after motion is no longer detected. 91 | post_capture 0 92 | 93 | ############################################################ 94 | # Script execution configuration parameters 95 | ############################################################ 96 | 97 | # Command to be executed when an event starts. 98 | on_event_start /on_event_start.sh -c %$ -w %i -h %J -x %K -y %L 99 | 100 | # Command to be executed when an event ends. 101 | ; on_event_end value 102 | 103 | # Command to be executed when a movie file is closed. 104 | ; on_movie_end value 105 | 106 | on_picture_save /on_picture_save.sh -c %$ -f %f 107 | 108 | ############################################################ 109 | # Picture output configuration parameters 110 | ############################################################ 111 | 112 | # Output pictures when motion is detected 113 | picture_output best 114 | 115 | # File name(without extension) for pictures relative to target directory 116 | picture_filename %$-%Y%m%d%H%M%S-%q 117 | 118 | target_dir /nvr/motion 119 | 120 | ############################################################ 121 | # Movie output configuration parameters 122 | ############################################################ 123 | 124 | # Create movies of motion events. 125 | movie_output off 126 | 127 | # Maximum length of movie in seconds. 128 | movie_max_time 60 129 | 130 | # The encoding quality of the movie. (0=use bitrate. 1=worst quality, 100=best) 131 | movie_quality 45 132 | 133 | # Container/Codec to used for the movie. See motion_guide.html 134 | movie_codec mkv 135 | 136 | # File name(without extension) for movies relative to target directory 137 | movie_filename %t-%v-%Y%m%d%H%M%S 138 | 139 | ############################################################ 140 | # Webcontrol configuration parameters 141 | ############################################################ 142 | 143 | # Port number used for the webcontrol. 144 | webcontrol_port 0 145 | 146 | # Restrict webcontrol connections to the localhost. 147 | webcontrol_localhost on 148 | 149 | # Type of configuration options to allow via the webcontrol. 150 | webcontrol_parms 0 151 | 152 | ############################################################ 153 | # Live stream configuration parameters 154 | ############################################################ 155 | 156 | # The port number for the live stream. 157 | stream_port 0 158 | 159 | # Restrict stream connections to the localhost. 160 | stream_localhost on 161 | 162 | ############################################################## 163 | # Camera config files - One for each camera. 164 | ############################################################## 165 | ; camera @sysconfdir@/motion/camera1.conf 166 | ; camera @sysconfdir@/motion/camera2.conf 167 | ; camera @sysconfdir@/motion/camera3.conf 168 | ; camera @sysconfdir@/motion/camera4.conf 169 | 170 | ############################################################## 171 | # Directory to read '.conf' files for cameras. 172 | ############################################################## 173 | camera_dir /usr/local/etc/motion/conf.d -------------------------------------------------------------------------------- /motion/on_event_start.sh: -------------------------------------------------------------------------------- 1 | #! /bin/bash 2 | 3 | START_TIME=$(date +%s) 4 | 5 | while getopts c:w:h:x:y: option ; do 6 | case "${option}" in 7 | c ) 8 | CAMERA=${OPTARG} 9 | ;; 10 | w ) 11 | WIDTH=${OPTARG} 12 | ;; 13 | h ) 14 | HEIGHT=${OPTARG} 15 | ;; 16 | x ) 17 | POS_X=${OPTARG} 18 | ;; 19 | y ) 20 | POS_Y=${OPTARG} 21 | ;; 22 | esac 23 | done 24 | 25 | mkdir -p /nvr/motion/events/ 26 | 27 | cat < /nvr/motion/events/${CAMERA}-${START_TIME}.json 28 | {"start": ${START_TIME}, "end": END_TIME, "width": $WIDTH, "height": $HEIGHT, "x": $POS_X, "y": $POS_Y} 29 | EOF 30 | 31 | /usr/bin/mosquitto_pub -h mqtt -t cameras/${CAMERA}/motion -m 'ON' 32 | -------------------------------------------------------------------------------- /motion/on_picture_save.sh: -------------------------------------------------------------------------------- 1 | #! /bin/bash 2 | 3 | END_TIME=$(date +%s) 4 | 5 | while getopts c:f: option ; do 6 | case "${option}" in 7 | c ) 8 | CAMERA=${OPTARG} 9 | ;; 10 | f ) 11 | PICTURE=${OPTARG} 12 | ;; 13 | esac 14 | done 15 | 16 | # ensure the directory for json files exists 17 | mkdir -p /nvr/motion/events 18 | # ensure the directory for preview images exists 19 | mkdir -p /nvr/motion/preview 20 | 21 | # replace the END_TIME placeholder 22 | sed -i -e "s/END_TIME/${END_TIME}/g" /nvr/motion/events/${CAMERA}-*.json 23 | 24 | # get the start time from the json file 25 | start_time=$(jq -r '.start' < /nvr/motion/events/${CAMERA}-*.json) 26 | # move the picture file and use the start time as the name 27 | mv "${PICTURE}" /nvr/motion/preview/${start_time}-${CAMERA}.jpg 28 | 29 | # rename the json file now that it is valid 30 | mv /nvr/motion/events/${CAMERA}-${start_time}.json /nvr/motion/events/${start_time}-${CAMERA}.json 31 | 32 | /usr/bin/mosquitto_pub -h mqtt -t cameras/${CAMERA}/motion -m 'OFF' -------------------------------------------------------------------------------- /mqttlogger/.dockerignore: -------------------------------------------------------------------------------- 1 | Dockerfile -------------------------------------------------------------------------------- /mqttlogger/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM debian:stretch-slim 2 | 3 | RUN apt-get update && \ 4 | apt-get install -y mosquitto-clients && \ 5 | rm -rf /var/cache/apt/archives /var/lib/apt/lists/* 6 | 7 | COPY . . 8 | 9 | CMD [ "sh", "logmqtt.sh" ] -------------------------------------------------------------------------------- /mqttlogger/logmqtt.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | mosquitto_sub -h mqtt.blakeshome.com -v -t google/location/# -t network/dhcp/3c:28:6d:2a:f0:f4 -t network/dhcp/3c:28:6d:e3:ec:c4 -t location/# > /mqttlogger/mqtt_location.log -------------------------------------------------------------------------------- /nginx/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM nginx:stable 2 | 3 | LABEL maintainer="Blake Blackshear " 4 | 5 | ENV NAXSI_VERSION 0.56 6 | 7 | RUN set -x \ 8 | && apt-get update \ 9 | && apt-get install --no-install-recommends --no-install-suggests -y \ 10 | curl \ 11 | apt-transport-https \ 12 | ca-certificates \ 13 | build-essential \ 14 | libpcre3-dev 15 | 16 | RUN curl -fSL https://github.com/nbs-system/naxsi/archive/$NAXSI_VERSION.tar.gz -o naxsi.tar.gz \ 17 | && tar -zxC /usr/src -f naxsi.tar.gz \ 18 | && rm naxsi.tar.gz 19 | 20 | RUN export NGINX_SRC_VERSION=${NGINX_VERSION%-*} \ 21 | && curl -fSL https://nginx.org/download/nginx-$NGINX_SRC_VERSION.tar.gz -o nginx.tar.gz \ 22 | && tar -zxC /usr/src -f nginx.tar.gz \ 23 | && rm nginx.tar.gz \ 24 | && cd /usr/src/nginx-$NGINX_SRC_VERSION \ 25 | && ./configure --with-compat --add-dynamic-module=/usr/src/naxsi-$NAXSI_VERSION/naxsi_src --without-http_gzip_module \ 26 | && make modules \ 27 | && cp objs/ngx_http_naxsi_module.so /etc/nginx/modules \ 28 | && apt-get remove --purge --auto-remove -y apt-transport-https ca-certificates \ 29 | && rm -rf /var/lib/apt/lists/* \ 30 | && rm -rf /usr/src/naxsi-$NAXSI_VERSION \ 31 | && rm -rf /usr/src/nginx-$NGINX_SRC_VERSION -------------------------------------------------------------------------------- /nginx/cameras/asset-manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "main.css": "static/css/main.c2957830.css", 3 | "main.css.map": "static/css/main.c2957830.css.map", 4 | "main.js": "static/js/main.fcde51b5.js", 5 | "main.js.map": "static/js/main.fcde51b5.js.map" 6 | } -------------------------------------------------------------------------------- /nginx/cameras/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/blakeblackshear/blakeshome-config/afe682a9bfa84aba77b3bcc6ddf5894e5fec1ada/nginx/cameras/favicon.ico -------------------------------------------------------------------------------- /nginx/cameras/index.html: -------------------------------------------------------------------------------- 1 | Frigate
-------------------------------------------------------------------------------- /nginx/cameras/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "Frigate", 3 | "name": "Frigate NVR", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /nginx/cameras/service-worker.js: -------------------------------------------------------------------------------- 1 | "use strict";var precacheConfig=[["/index.html","5f6c9f2046e46356f2e22c3cb42397e0"],["/static/css/main.c2957830.css","06538e169818a8a103095365b243d5bf"],["/static/js/main.fcde51b5.js","4c3db0da7a061b067e2287c6d232742a"]],cacheName="sw-precache-v3-sw-precache-webpack-plugin-"+(self.registration?self.registration.scope:""),ignoreUrlParametersMatching=[/^utm_/],addDirectoryIndex=function(e,t){var n=new URL(e);return"/"===n.pathname.slice(-1)&&(n.pathname+=t),n.toString()},cleanResponse=function(t){return t.redirected?("body"in t?Promise.resolve(t.body):t.blob()).then(function(e){return new Response(e,{headers:t.headers,status:t.status,statusText:t.statusText})}):Promise.resolve(t)},createCacheKey=function(e,t,n,r){var a=new URL(e);return r&&a.pathname.match(r)||(a.search+=(a.search?"&":"")+encodeURIComponent(t)+"="+encodeURIComponent(n)),a.toString()},isPathWhitelisted=function(e,t){if(0===e.length)return!0;var n=new URL(t).pathname;return e.some(function(e){return n.match(e)})},stripIgnoredUrlParameters=function(e,n){var t=new URL(e);return t.hash="",t.search=t.search.slice(1).split("&").map(function(e){return e.split("=")}).filter(function(t){return n.every(function(e){return!e.test(t[0])})}).map(function(e){return e.join("=")}).join("&"),t.toString()},hashParamName="_sw-precache",urlsToCacheKeys=new Map(precacheConfig.map(function(e){var t=e[0],n=e[1],r=new URL(t,self.location),a=createCacheKey(r,hashParamName,n,/\.\w{8}\./);return[r.toString(),a]}));function setOfCachedUrls(e){return e.keys().then(function(e){return e.map(function(e){return e.url})}).then(function(e){return new Set(e)})}self.addEventListener("install",function(e){e.waitUntil(caches.open(cacheName).then(function(r){return setOfCachedUrls(r).then(function(n){return Promise.all(Array.from(urlsToCacheKeys.values()).map(function(t){if(!n.has(t)){var e=new Request(t,{credentials:"same-origin"});return fetch(e).then(function(e){if(!e.ok)throw new Error("Request for "+t+" returned a response with status "+e.status);return cleanResponse(e).then(function(e){return r.put(t,e)})})}}))})}).then(function(){return self.skipWaiting()}))}),self.addEventListener("activate",function(e){var n=new Set(urlsToCacheKeys.values());e.waitUntil(caches.open(cacheName).then(function(t){return t.keys().then(function(e){return Promise.all(e.map(function(e){if(!n.has(e.url))return t.delete(e)}))})}).then(function(){return self.clients.claim()}))}),self.addEventListener("fetch",function(t){if("GET"===t.request.method){var e,n=stripIgnoredUrlParameters(t.request.url,ignoreUrlParametersMatching),r="index.html";(e=urlsToCacheKeys.has(n))||(n=addDirectoryIndex(n,r),e=urlsToCacheKeys.has(n));var a="/index.html";!e&&"navigate"===t.request.mode&&isPathWhitelisted(["^(?!\\/__).*"],t.request.url)&&(n=new URL(a,self.location).toString(),e=urlsToCacheKeys.has(n)),e&&t.respondWith(caches.open(cacheName).then(function(e){return e.match(urlsToCacheKeys.get(n)).then(function(e){if(e)return e;throw Error("The cached response that was expected is missing.")})}).catch(function(e){return console.warn('Couldn\'t serve response for "%s" from cache: %O',t.request.url,e),fetch(t.request)}))}}); -------------------------------------------------------------------------------- /nginx/conf.d/blakeshome.conf: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443; 3 | server_name blakeshome.com; 4 | 5 | ssl_certificate /etc/ssl/private/blakeshome.com/fullchain.cer; 6 | ssl_certificate_key /etc/ssl/private/blakeshome.com/blakeshome.com.key; 7 | 8 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 9 | ssl on; 10 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 11 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 12 | ssl_prefer_server_ciphers on; 13 | ssl_session_cache shared:SSL:10m; 14 | 15 | location /oauth2/ { 16 | proxy_pass http://127.0.0.1:4180; 17 | proxy_set_header Host $host; 18 | proxy_set_header X-Real-IP $remote_addr; 19 | proxy_set_header X-Scheme $scheme; 20 | proxy_set_header X-Auth-Request-Redirect $arg_rd; 21 | } 22 | 23 | location / { 24 | SecRulesEnabled; 25 | #LearningMode; 26 | DeniedUrl "/403"; 27 | CheckRule "$SQL >= 8" BLOCK; 28 | CheckRule "$RFI >= 8" BLOCK; 29 | CheckRule "$TRAVERSAL >= 4" BLOCK; 30 | CheckRule "$EVADE >= 4" BLOCK; 31 | CheckRule "$XSS >= 8" BLOCK; 32 | include /etc/nginx/whitelist.rules; 33 | satisfy any; 34 | allow 192.168.2.0/24; 35 | deny all; 36 | auth_request /oauth2/auth; 37 | error_page 401 = /oauth2/sign_in; 38 | 39 | auth_request_set $user $upstream_http_x_auth_request_user; 40 | auth_request_set $email $upstream_http_x_auth_request_email; 41 | proxy_set_header X-User $user; 42 | proxy_set_header X-Email $email; 43 | 44 | proxy_set_header X-Real-IP $remote_addr; 45 | proxy_pass http://localhost:5050; 46 | proxy_set_header Host $host; 47 | proxy_http_version 1.1; 48 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 49 | proxy_set_header Upgrade $http_upgrade; 50 | proxy_set_header Connection "upgrade"; 51 | } 52 | 53 | location /hass { 54 | return 301 https://hass.blakeshome.com/; 55 | } 56 | 57 | location /nodered { 58 | return 301 https://nodered.blakeshome.com/; 59 | } 60 | 61 | location /portainer { 62 | return 301 https://portainer.blakeshome.com/; 63 | } 64 | 65 | location /pihole { 66 | return 301 https://pihole.blakeshome.com/; 67 | } 68 | 69 | location /cameras { 70 | return 301 https://cameras.blakeshome.com/; 71 | } 72 | 73 | location /dash { 74 | return 301 https://dash.blakeshome.com/; 75 | } 76 | 77 | location /netdata { 78 | return 301 https://netdata.blakeshome.com/; 79 | } 80 | 81 | location /vacuum { 82 | return 301 https://vacuum.blakeshome.com/; 83 | } 84 | 85 | location /403 { 86 | return 403 "Forbidden"; 87 | add_header Content-Type text/plain; 88 | } 89 | } -------------------------------------------------------------------------------- /nginx/conf.d/cameras.conf: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443; 3 | server_name cameras.blakeshome.com; 4 | 5 | ssl_certificate /etc/ssl/private/*.blakeshome.com/fullchain.cer; 6 | ssl_certificate_key /etc/ssl/private/*.blakeshome.com/*.blakeshome.com.key; 7 | 8 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 9 | ssl on; 10 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 11 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 12 | ssl_prefer_server_ciphers on; 13 | ssl_session_cache shared:SSL:10m; 14 | 15 | location @error401 { 16 | return 302 https://blakeshome.com/oauth2/sign_in?rd=/cameras; 17 | } 18 | 19 | location /oauth2/auth { 20 | internal; 21 | proxy_pass http://127.0.0.1:4180; 22 | proxy_set_header Host $host; 23 | proxy_set_header X-Real-IP $remote_addr; 24 | proxy_set_header X-Scheme $scheme; 25 | proxy_set_header X-Auth-Request-Redirect $arg_rd; 26 | } 27 | 28 | location / { 29 | satisfy any; 30 | allow 192.168.2.0/24; 31 | allow 172.18.0.0/16; 32 | deny all; 33 | auth_request /oauth2/auth; 34 | error_page 401 = @error401; 35 | 36 | add_header 'Cache-Control' 'no-cache'; 37 | add_header 'Access-Control-Allow-Origin' '*' always; 38 | add_header 'Access-Control-Expose-Headers' 'Content-Length'; 39 | if ($request_method = 'OPTIONS') { 40 | add_header 'Access-Control-Allow-Origin' '*'; 41 | add_header 'Access-Control-Max-Age' 1728000; 42 | add_header 'Content-Type' 'text/plain charset=UTF-8'; 43 | add_header 'Content-Length' 0; 44 | return 204; 45 | } 46 | 47 | root /var/www/cameras; 48 | } 49 | 50 | location /streams/ { 51 | satisfy any; 52 | allow 192.168.2.0/24; 53 | allow 172.18.0.0/16; 54 | deny all; 55 | auth_request /oauth2/auth; 56 | error_page 401 = @error401; 57 | 58 | add_header 'Cache-Control' 'no-cache'; 59 | add_header 'Access-Control-Allow-Origin' "$http_origin" always; 60 | add_header 'Access-Control-Allow-Credentials' 'true'; 61 | add_header 'Access-Control-Expose-Headers' 'Content-Length'; 62 | if ($request_method = 'OPTIONS') { 63 | add_header 'Access-Control-Allow-Origin' "$http_origin"; 64 | add_header 'Access-Control-Max-Age' 1728000; 65 | add_header 'Content-Type' 'text/plain charset=UTF-8'; 66 | add_header 'Content-Length' 0; 67 | return 204; 68 | } 69 | 70 | types { 71 | application/dash+xml mpd; 72 | application/vnd.apple.mpegurl m3u8; 73 | video/mp2t ts; 74 | image/jpeg jpg; 75 | } 76 | 77 | root /var/www/cameras; 78 | } 79 | 80 | location /cameras/ { 81 | satisfy any; 82 | allow 192.168.2.0/24; 83 | allow 172.18.0.0/16; 84 | deny all; 85 | auth_request /oauth2/auth; 86 | error_page 401 = @error401; 87 | 88 | add_header 'Cache-Control' 'no-cache'; 89 | add_header 'Access-Control-Allow-Origin' "$http_origin" always; 90 | add_header 'Access-Control-Allow-Credentials' 'true'; 91 | add_header 'Access-Control-Expose-Headers' 'Content-Length'; 92 | if ($request_method = 'OPTIONS') { 93 | add_header 'Access-Control-Allow-Origin' "$http_origin"; 94 | add_header 'Access-Control-Max-Age' 1728000; 95 | add_header 'Content-Type' 'text/plain charset=UTF-8'; 96 | add_header 'Content-Length' 0; 97 | return 204; 98 | } 99 | 100 | types { 101 | application/dash+xml mpd; 102 | application/vnd.apple.mpegurl m3u8; 103 | video/mp2t ts; 104 | image/jpeg jpg; 105 | } 106 | 107 | root /data; 108 | } 109 | 110 | location /nvr/ { 111 | satisfy any; 112 | allow 192.168.2.0/24; 113 | allow 172.18.0.0/16; 114 | deny all; 115 | auth_request /oauth2/auth; 116 | error_page 401 = @error401; 117 | 118 | add_header 'Access-Control-Allow-Origin' "$http_origin" always; 119 | add_header 'Access-Control-Allow-Credentials' 'true'; 120 | add_header 'Access-Control-Expose-Headers' 'Content-Length'; 121 | if ($request_method = 'OPTIONS') { 122 | add_header 'Access-Control-Allow-Origin' "$http_origin"; 123 | add_header 'Access-Control-Max-Age' 1728000; 124 | add_header 'Content-Type' 'text/plain charset=UTF-8'; 125 | add_header 'Content-Length' 0; 126 | return 204; 127 | } 128 | 129 | types { 130 | video/mp4 mp4; 131 | image/jpeg jpg; 132 | } 133 | 134 | autoindex on; 135 | autoindex_format json; 136 | root /data; 137 | } 138 | } 139 | -------------------------------------------------------------------------------- /nginx/conf.d/dash.conf: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443; 3 | server_name dash.blakeshome.com; 4 | 5 | ssl_certificate /etc/ssl/private/*.blakeshome.com/fullchain.cer; 6 | ssl_certificate_key /etc/ssl/private/*.blakeshome.com/*.blakeshome.com.key; 7 | 8 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 9 | ssl on; 10 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 11 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 12 | ssl_prefer_server_ciphers on; 13 | ssl_session_cache shared:SSL:10m; 14 | 15 | location @error401 { 16 | return 302 https://blakeshome.com/oauth2/sign_in?rd=/dash; 17 | } 18 | 19 | location /oauth2/auth { 20 | internal; 21 | proxy_pass http://127.0.0.1:4180; 22 | proxy_set_header Host $host; 23 | proxy_set_header X-Real-IP $remote_addr; 24 | proxy_set_header X-Scheme $scheme; 25 | proxy_set_header X-Auth-Request-Redirect $arg_rd; 26 | } 27 | 28 | location / { 29 | auth_request /oauth2/auth; 30 | error_page 401 = @error401; 31 | 32 | auth_request_set $user $upstream_http_x_auth_request_user; 33 | auth_request_set $email $upstream_http_x_auth_request_email; 34 | proxy_set_header X-User $user; 35 | proxy_set_header X-Email $email; 36 | 37 | proxy_set_header X-Real-IP $remote_addr; 38 | proxy_pass http://localhost:5050; 39 | proxy_set_header Host $host; 40 | proxy_http_version 1.1; 41 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 42 | proxy_set_header Upgrade $http_upgrade; 43 | proxy_set_header Connection "upgrade"; 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /nginx/conf.d/hass.conf: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443; 3 | server_name hass.blakeshome.com; 4 | 5 | ssl_certificate /etc/ssl/private/*.blakeshome.com/fullchain.cer; 6 | ssl_certificate_key /etc/ssl/private/*.blakeshome.com/*.blakeshome.com.key; 7 | 8 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 9 | ssl on; 10 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 11 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 12 | ssl_prefer_server_ciphers on; 13 | ssl_session_cache shared:SSL:10m; 14 | 15 | proxy_set_header X-Real-IP $remote_addr; 16 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 17 | proxy_set_header X-Forwarded-Host $host; 18 | proxy_set_header X-Forwarded-Port $server_port; 19 | 20 | location @error401 { 21 | return 401 "Not authorized"; 22 | } 23 | 24 | location /oauth2/auth { 25 | internal; 26 | proxy_pass http://127.0.0.1:4180; 27 | proxy_set_header Host $host; 28 | proxy_set_header X-Real-IP $remote_addr; 29 | proxy_set_header X-Scheme $scheme; 30 | proxy_set_header X-Auth-Request-Redirect $arg_rd; 31 | } 32 | 33 | location / { 34 | proxy_set_header X-Real-IP $remote_addr; 35 | proxy_pass http://localhost:8123; 36 | proxy_set_header Host $host; 37 | proxy_http_version 1.1; 38 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 39 | proxy_set_header Upgrade $http_upgrade; 40 | proxy_set_header Connection "upgrade"; 41 | 42 | # inject window.externalApp into documents 43 | sub_filter '' ''; 44 | sub_filter_once on; 45 | 46 | # redirect the frontend to use external auth when it attempts to authorize 47 | location /auth/authorize { 48 | auth_request /oauth2/auth; 49 | return 301 /?external_auth=1; 50 | } 51 | 52 | # endpoint for returning tokens with njs based on email 53 | location /api/get_token { 54 | auth_request /oauth2/auth; 55 | auth_request_set $email $upstream_http_x_auth_request_email; 56 | js_content get_token; 57 | } 58 | 59 | location /api { 60 | auth_request /oauth2/auth; 61 | proxy_pass http://localhost:8123; 62 | } 63 | 64 | location ^~ /api/google_assistant { 65 | auth_request off; 66 | proxy_pass http://localhost:8123; 67 | } 68 | 69 | location ^~ /api/tts_proxy/ { 70 | auth_request off; 71 | proxy_pass http://localhost:8123; 72 | } 73 | 74 | location ^~ /api/telegram_webhooks { 75 | auth_request off; 76 | proxy_pass http://localhost:8123; 77 | } 78 | 79 | location /api/notify.html5/callback { 80 | auth_request off; 81 | proxy_set_header Authorization $http_authorization; 82 | if ($http_authorization = "") { return 403; } 83 | proxy_pass http://localhost:8123; 84 | } 85 | } 86 | } -------------------------------------------------------------------------------- /nginx/conf.d/hass_auth_script.js: -------------------------------------------------------------------------------- 1 | var fs = require('fs'); 2 | var token_string = fs.readFileSync('/etc/nginx/tokens.json'); 3 | var tokens = JSON.parse(token_string); 4 | 5 | function get_token(r) { 6 | var email = r.variables["email"]; 7 | r.headersOut['Content-Type'] = 'text/plain'; 8 | if (email == '') { 9 | r.return(500, "No email found"); 10 | } 11 | var token = tokens[email]; 12 | if (token == undefined) { 13 | r.return(500, "No token found"); 14 | } 15 | return r.return(200, token); 16 | } 17 | -------------------------------------------------------------------------------- /nginx/conf.d/netdata.conf: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443; 3 | server_name netdata.blakeshome.com; 4 | 5 | ssl_certificate /etc/ssl/private/*.blakeshome.com/fullchain.cer; 6 | ssl_certificate_key /etc/ssl/private/*.blakeshome.com/*.blakeshome.com.key; 7 | 8 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 9 | ssl on; 10 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 11 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 12 | ssl_prefer_server_ciphers on; 13 | ssl_session_cache shared:SSL:10m; 14 | 15 | location @error401 { 16 | return 302 https://blakeshome.com/oauth2/sign_in?rd=/netdata; 17 | } 18 | 19 | location /oauth2/auth { 20 | internal; 21 | proxy_pass http://127.0.0.1:4180; 22 | proxy_set_header Host $host; 23 | proxy_set_header X-Real-IP $remote_addr; 24 | proxy_set_header X-Scheme $scheme; 25 | proxy_set_header X-Auth-Request-Redirect $arg_rd; 26 | } 27 | 28 | location / { 29 | auth_request /oauth2/auth; 30 | error_page 401 = @error401; 31 | 32 | auth_request_set $user $upstream_http_x_auth_request_user; 33 | auth_request_set $email $upstream_http_x_auth_request_email; 34 | proxy_set_header X-User $user; 35 | proxy_set_header X-Email $email; 36 | 37 | proxy_set_header X-Real-IP $remote_addr; 38 | proxy_pass http://localhost:19999; 39 | proxy_set_header Host $host; 40 | proxy_http_version 1.1; 41 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 42 | proxy_set_header Upgrade $http_upgrade; 43 | proxy_set_header Connection "upgrade"; 44 | } 45 | } -------------------------------------------------------------------------------- /nginx/conf.d/pihole.conf: -------------------------------------------------------------------------------- 1 | # disables logging for all the other domains 2 | # traffic comes from pihole resolving dns to this ip address 3 | server { 4 | listen 443 ssl default_server; 5 | server_name _; 6 | # needs a valid cert 7 | ssl_certificate /etc/ssl/private/blakeshome.com/fullchain.cer; 8 | ssl_certificate_key /etc/ssl/private/blakeshome.com/blakeshome.com.key; 9 | return 200 "Website Blocked"; 10 | add_header Content-Type text/plain; 11 | 12 | access_log off; 13 | error_log off; 14 | } 15 | 16 | server { 17 | listen 443; 18 | server_name pihole.blakeshome.com; 19 | 20 | ssl_certificate /etc/ssl/private/*.blakeshome.com/fullchain.cer; 21 | ssl_certificate_key /etc/ssl/private/*.blakeshome.com/*.blakeshome.com.key; 22 | 23 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 24 | ssl on; 25 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 26 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 27 | ssl_prefer_server_ciphers on; 28 | ssl_session_cache shared:SSL:10m; 29 | 30 | location @error401 { 31 | return 302 https://blakeshome.com/oauth2/sign_in?rd=/pihole; 32 | } 33 | 34 | location /oauth2/auth { 35 | internal; 36 | proxy_pass http://127.0.0.1:4180; 37 | proxy_set_header Host $host; 38 | proxy_set_header X-Real-IP $remote_addr; 39 | proxy_set_header X-Scheme $scheme; 40 | proxy_set_header X-Auth-Request-Redirect $arg_rd; 41 | } 42 | 43 | location / { 44 | auth_request /oauth2/auth; 45 | error_page 401 = @error401; 46 | 47 | auth_request_set $user $upstream_http_x_auth_request_user; 48 | auth_request_set $email $upstream_http_x_auth_request_email; 49 | proxy_set_header X-User $user; 50 | proxy_set_header X-Email $email; 51 | 52 | proxy_set_header X-Real-IP $remote_addr; 53 | proxy_pass http://localhost/admin/; 54 | proxy_set_header Host $host; 55 | proxy_http_version 1.1; 56 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 57 | proxy_set_header Upgrade $http_upgrade; 58 | proxy_set_header Connection "upgrade"; 59 | } 60 | } -------------------------------------------------------------------------------- /nginx/conf.d/portainer.conf: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443; 3 | server_name portainer.blakeshome.com; 4 | 5 | ssl_certificate /etc/ssl/private/*.blakeshome.com/fullchain.cer; 6 | ssl_certificate_key /etc/ssl/private/*.blakeshome.com/*.blakeshome.com.key; 7 | 8 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 9 | ssl on; 10 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 11 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 12 | ssl_prefer_server_ciphers on; 13 | ssl_session_cache shared:SSL:10m; 14 | 15 | location @error401 { 16 | return 302 https://blakeshome.com/oauth2/sign_in?rd=/portainer; 17 | } 18 | 19 | location /oauth2/auth { 20 | internal; 21 | proxy_pass http://127.0.0.1:4180; 22 | proxy_set_header Host $host; 23 | proxy_set_header X-Real-IP $remote_addr; 24 | proxy_set_header X-Scheme $scheme; 25 | proxy_set_header X-Auth-Request-Redirect $arg_rd; 26 | } 27 | 28 | location / { 29 | auth_request /oauth2/auth; 30 | error_page 401 = @error401; 31 | 32 | auth_request_set $user $upstream_http_x_auth_request_user; 33 | auth_request_set $email $upstream_http_x_auth_request_email; 34 | proxy_set_header X-User $user; 35 | proxy_set_header X-Email $email; 36 | 37 | proxy_set_header X-Real-IP $remote_addr; 38 | proxy_pass http://localhost:9000; 39 | proxy_set_header Host $host; 40 | proxy_http_version 1.1; 41 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 42 | proxy_set_header Upgrade $http_upgrade; 43 | proxy_set_header Connection "upgrade"; 44 | } 45 | } -------------------------------------------------------------------------------- /nginx/conf.d/public.conf: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443; 3 | server_name public.blakeshome.com; 4 | 5 | ssl_certificate /etc/ssl/private/*.blakeshome.com/fullchain.cer; 6 | ssl_certificate_key /etc/ssl/private/*.blakeshome.com/*.blakeshome.com.key; 7 | 8 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 9 | ssl on; 10 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 11 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 12 | ssl_prefer_server_ciphers on; 13 | ssl_session_cache shared:SSL:10m; 14 | 15 | 16 | location / { 17 | root /var/www/public; 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /nginx/conf.d/tokens.template: -------------------------------------------------------------------------------- 1 | { 2 | "blake.blackshear@gmail.com": "${BLAKE_TOKEN}", 3 | "ali.blackshear@gmail.com": "${ALI_TOKEN}" 4 | } -------------------------------------------------------------------------------- /nginx/conf.d/unifi.conf: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443; 3 | server_name unifi.blakeshome.com; 4 | 5 | ssl_certificate /etc/ssl/private/*.blakeshome.com/fullchain.cer; 6 | ssl_certificate_key /etc/ssl/private/*.blakeshome.com/*.blakeshome.com.key; 7 | 8 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 9 | ssl on; 10 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 11 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 12 | ssl_prefer_server_ciphers on; 13 | ssl_session_cache shared:SSL:10m; 14 | 15 | location / { 16 | proxy_set_header X-Real-IP $remote_addr; 17 | proxy_pass https://localhost:8443; 18 | proxy_set_header Host $host; 19 | proxy_http_version 1.1; 20 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 21 | proxy_set_header Upgrade $http_upgrade; 22 | proxy_set_header Connection "upgrade"; 23 | } 24 | } -------------------------------------------------------------------------------- /nginx/conf.d/vacuum.conf: -------------------------------------------------------------------------------- 1 | server { 2 | listen 443; 3 | server_name vacuum.blakeshome.com; 4 | 5 | ssl_certificate /etc/ssl/private/*.blakeshome.com/fullchain.cer; 6 | ssl_certificate_key /etc/ssl/private/*.blakeshome.com/*.blakeshome.com.key; 7 | 8 | add_header Strict-Transport-Security "max-age=31536000; includeSubdomains"; 9 | ssl on; 10 | ssl_protocols TLSv1 TLSv1.1 TLSv1.2; 11 | ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4"; 12 | ssl_prefer_server_ciphers on; 13 | ssl_session_cache shared:SSL:10m; 14 | 15 | location @error401 { 16 | return 302 https://blakeshome.com/oauth2/sign_in?rd=/vacuum; 17 | } 18 | 19 | location /oauth2/auth { 20 | internal; 21 | proxy_pass http://127.0.0.1:4180; 22 | proxy_set_header Host $host; 23 | proxy_set_header X-Real-IP $remote_addr; 24 | proxy_set_header X-Scheme $scheme; 25 | proxy_set_header X-Auth-Request-Redirect $arg_rd; 26 | } 27 | 28 | location / { 29 | auth_request /oauth2/auth; 30 | error_page 401 = @error401; 31 | 32 | auth_request_set $user $upstream_http_x_auth_request_user; 33 | auth_request_set $email $upstream_http_x_auth_request_email; 34 | proxy_set_header X-User $user; 35 | proxy_set_header X-Email $email; 36 | 37 | proxy_set_header X-Real-IP $remote_addr; 38 | proxy_pass http://192.168.2.36:80; 39 | proxy_set_header Host $host; 40 | proxy_http_version 1.1; 41 | proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 42 | proxy_set_header Upgrade $http_upgrade; 43 | proxy_set_header Connection "upgrade"; 44 | } 45 | } -------------------------------------------------------------------------------- /nginx/html/index.html: -------------------------------------------------------------------------------- 1 | Blakeshome -------------------------------------------------------------------------------- /nginx/naxsi_core.rules: -------------------------------------------------------------------------------- 1 | ################################## 2 | ## INTERNAL RULES IDS:1-999 ## 3 | ################################## 4 | #@MainRule "msg:weird request, unable to parse" id:1; 5 | #@MainRule "msg:request too big, stored on disk and not parsed" id:2; 6 | #@MainRule "msg:invalid hex encoding, null bytes" id:10; 7 | #@MainRule "msg:unknown content-type" id:11; 8 | #@MainRule "msg:invalid formatted url" id:12; 9 | #@MainRule "msg:invalid POST format" id:13; 10 | #@MainRule "msg:invalid POST boundary" id:14; 11 | #@MainRule "msg:invalid JSON" id:15; 12 | #@MainRule "msg:empty POST" id:16; 13 | #@MainRule "msg:libinjection_sql" id:17; 14 | #@MainRule "msg:libinjection_xss" id:18; 15 | 16 | ################################## 17 | ## SQL Injections IDs:1000-1099 ## 18 | ################################## 19 | MainRule "rx:select|union|update|delete|insert|table|from|ascii|hex|unhex|drop" "msg:sql keywords" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:4" id:1000; 20 | MainRule "str:\"" "msg:double quote" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:8,$XSS:8" id:1001; 21 | MainRule "str:0x" "msg:0x, possible hex encoding" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:2" id:1002; 22 | ## Hardcore rules 23 | MainRule "str:/*" "msg:mysql comment (/*)" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:8" id:1003; 24 | MainRule "str:*/" "msg:mysql comment (*/)" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:8" id:1004; 25 | MainRule "str:|" "msg:mysql keyword (|)" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:8" id:1005; 26 | MainRule "str:&&" "msg:mysql keyword (&&)" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:8" id:1006; 27 | ## end of hardcore rules 28 | MainRule "str:--" "msg:mysql comment (--)" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:4" id:1007; 29 | MainRule "str:;" "msg:semicolon" "mz:BODY|URL|ARGS" "s:$SQL:4,$XSS:8" id:1008; 30 | MainRule "str:=" "msg:equal sign in var, probable sql/xss" "mz:ARGS|BODY" "s:$SQL:2" id:1009; 31 | MainRule "str:(" "msg:open parenthesis, probable sql/xss" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$SQL:4,$XSS:8" id:1010; 32 | MainRule "str:)" "msg:close parenthesis, probable sql/xss" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$SQL:4,$XSS:8" id:1011; 33 | MainRule "str:'" "msg:simple quote" "mz:ARGS|BODY|URL|$HEADERS_VAR:Cookie" "s:$SQL:4,$XSS:8" id:1013; 34 | MainRule "str:," "msg:comma" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:4" id:1015; 35 | MainRule "str:#" "msg:mysql comment (#)" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:4" id:1016; 36 | MainRule "str:@@" "msg:double arobase (@@)" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$SQL:4" id:1017; 37 | 38 | ############################### 39 | ## OBVIOUS RFI IDs:1100-1199 ## 40 | ############################### 41 | MainRule "str:http://" "msg:http:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1100; 42 | MainRule "str:https://" "msg:https:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1101; 43 | MainRule "str:ftp://" "msg:ftp:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1102; 44 | MainRule "str:php://" "msg:php:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1103; 45 | MainRule "str:sftp://" "msg:sftp:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1104; 46 | MainRule "str:zlib://" "msg:zlib:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1105; 47 | MainRule "str:data://" "msg:data:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1106; 48 | MainRule "str:glob://" "msg:glob:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1107; 49 | MainRule "str:phar://" "msg:phar:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1108; 50 | MainRule "str:file://" "msg:file:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1109; 51 | MainRule "str:gopher://" "msg:gopher:// scheme" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$RFI:8" id:1110; 52 | 53 | ####################################### 54 | ## Directory traversal IDs:1200-1299 ## 55 | ####################################### 56 | MainRule "str:.." "msg:double dot" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$TRAVERSAL:4" id:1200; 57 | MainRule "str:/etc/passwd" "msg:obvious probe" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$TRAVERSAL:4" id:1202; 58 | MainRule "str:c:\\" "msg:obvious windows path" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$TRAVERSAL:4" id:1203; 59 | MainRule "str:cmd.exe" "msg:obvious probe" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$TRAVERSAL:4" id:1204; 60 | MainRule "str:\\" "msg:backslash" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$TRAVERSAL:4" id:1205; 61 | #MainRule "str:/" "msg:slash in args" "mz:ARGS|BODY|$HEADERS_VAR:Cookie" "s:$TRAVERSAL:2" id:1206; 62 | 63 | ######################################## 64 | ## Cross Site Scripting IDs:1300-1399 ## 65 | ######################################## 66 | MainRule "str:<" "msg:html open tag" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$XSS:8" id:1302; 67 | MainRule "str:>" "msg:html close tag" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$XSS:8" id:1303; 68 | MainRule "str:[" "msg:open square backet ([), possible js" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$XSS:4" id:1310; 69 | MainRule "str:]" "msg:close square bracket (]), possible js" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$XSS:4" id:1311; 70 | MainRule "str:~" "msg:tilde (~) character" "mz:BODY|URL|ARGS|$HEADERS_VAR:Cookie" "s:$XSS:4" id:1312; 71 | MainRule "str:`" "msg:grave accent (`)" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$XSS:8" id:1314; 72 | MainRule "rx:%[23]." "msg:double encoding" "mz:ARGS|URL|BODY|$HEADERS_VAR:Cookie" "s:$XSS:8" id:1315; 73 | 74 | #################################### 75 | ## Evading tricks IDs: 1400-1500 ## 76 | #################################### 77 | MainRule "str:&#" "msg:utf7/8 encoding" "mz:ARGS|BODY|URL|$HEADERS_VAR:Cookie" "s:$EVADE:4" id:1400; 78 | MainRule "str:%U" "msg:M$ encoding" "mz:ARGS|BODY|URL|$HEADERS_VAR:Cookie" "s:$EVADE:4" id:1401; 79 | 80 | ############################# 81 | ## File uploads: 1500-1600 ## 82 | ############################# 83 | MainRule "rx:\.ph|\.asp|\.ht" "msg:asp/php file upload" "mz:FILE_EXT" "s:$UPLOAD:8" id:1500; -------------------------------------------------------------------------------- /nginx/nginx.conf: -------------------------------------------------------------------------------- 1 | user nginx; 2 | worker_processes 1; 3 | 4 | error_log /var/log/nginx/error.log warn; 5 | pid /var/run/nginx.pid; 6 | 7 | load_module modules/ngx_http_naxsi_module.so; 8 | load_module modules/ngx_http_js_module.so; 9 | 10 | events { 11 | worker_connections 1024; 12 | } 13 | 14 | 15 | http { 16 | include /etc/nginx/mime.types; 17 | include /etc/nginx/naxsi_core.rules; 18 | js_include conf.d/hass_auth_script.js; 19 | js_set $hass_auth_script hass_auth_script; 20 | 21 | default_type application/octet-stream; 22 | 23 | log_format main '$remote_addr - $remote_user [$time_local] "$host" "$request" ' 24 | '$status $body_bytes_sent "$http_referer" ' 25 | '"$http_user_agent" "$http_x_forwarded_for"'; 26 | 27 | access_log /var/log/nginx/access.log main; 28 | 29 | sendfile on; 30 | #tcp_nopush on; 31 | 32 | keepalive_timeout 65; 33 | 34 | #gzip on; 35 | 36 | include /etc/nginx/conf.d/*.conf; 37 | } -------------------------------------------------------------------------------- /nginx/whitelist.rules: -------------------------------------------------------------------------------- 1 | BasicRule wl:0 "mz:$HEADERS_VAR:cookie"; -------------------------------------------------------------------------------- /nvr_cleaner/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM alpine:latest 2 | 3 | COPY cleaner /etc/periodic/hourly/cleaner 4 | 5 | RUN chmod +x /etc/periodic/hourly/cleaner 6 | 7 | VOLUME ["/data"] 8 | 9 | CMD ["crond", "-l", "2", "-f"] -------------------------------------------------------------------------------- /nvr_cleaner/cleaner: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | find /data -type f ${FIND_PARAMS} -delete -------------------------------------------------------------------------------- /nvr_snapshot/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM jrottenberg/ffmpeg:4.0-alpine 2 | 3 | RUN apk add inotify-tools bash 4 | 5 | VOLUME ["/data"] 6 | 7 | COPY watch_and_snapshot.sh /watch_and_snapshot.sh 8 | 9 | RUN chmod +x /watch_and_snapshot.sh 10 | 11 | ENTRYPOINT [ "/watch_and_snapshot.sh" ] -------------------------------------------------------------------------------- /nvr_snapshot/watch_and_snapshot.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | check_file (){ 4 | /usr/local/bin/ffprobe -v error -show_entries format=duration -of default=noprint_wrappers=1:nokey=1 $1; 5 | } 6 | 7 | archive_file (){ 8 | # grab the first 12 digits from the filename 9 | local date_string=$(echo "$1" |grep -Eo '[[:digit:]]{12}') 10 | # format them for folder archives ex: 2018/05/28 11 | local date_folders=$(date -d "$date_string" +'%Y/%m/%d/%H') 12 | # make sure the folders exist 13 | mkdir -p "${MONITORDIR}/${date_folders}" 14 | 15 | mv $1 "${MONITORDIR}/${date_folders}/" 16 | } 17 | 18 | check_and_archive_file (){ 19 | # test the file for errors 20 | if check_file "$1"; then 21 | # archive the good files 22 | archive_file "$1" 23 | else 24 | # delete the bad ones 25 | rm "$1" 26 | fi 27 | } 28 | 29 | check_existing_files (){ 30 | touch /data/dummy 31 | sleep 1 32 | find "${MONITORDIR}" -maxdepth 1 -type f -name "*.mp4" ! -newer /data/dummy | while read file; do check_and_archive_file "$file"; done 33 | } 34 | 35 | # create a directory for processed files 36 | mkdir -p "${MONITORDIR}/archive" 37 | 38 | # run ffprobe on all files in the directory that havent been modified in 1 second 39 | check_existing_files 40 | # run it again in case a new file was created in the meantime 41 | check_existing_files 42 | 43 | # look for files that are finished writing 44 | inotifywait -m "${MONITORDIR}" -e close_write | while read path action file 45 | do 46 | # just look for .mp4 files 47 | if [[ $file = *.mp4 ]]; then 48 | # make sure the file is good 49 | if ! check_file "${MONITORDIR}/${file}"; then 50 | # remove the file if its bad 51 | rm "${MONITORDIR}/${file}" 52 | continue 53 | fi 54 | 55 | # remove the extension 56 | noextension="${file%.*}" 57 | # remove any digits and dashes 58 | nodigits="${noextension//[[:digit:]]}" 59 | nodashes="${nodigits//-}" 60 | # pull out a single frame as a recent screenshot and save it with the computed name 61 | /usr/local/bin/ffmpeg -loglevel error -hide_banner -y -sseof -0.5 -i "${MONITORDIR}/${file}" -vframes 1 "${MONITORDIR}/${nodashes}.jpg" 62 | 63 | archive_file "${MONITORDIR}/${file}" 64 | fi 65 | done -------------------------------------------------------------------------------- /oauth2_proxy/authenticated_emails: -------------------------------------------------------------------------------- 1 | blake.blackshear@gmail.com 2 | ali.blackshear@gmail.com -------------------------------------------------------------------------------- /oauth2_proxy/oauth2_proxy.cfg: -------------------------------------------------------------------------------- 1 | ## OAuth2 Proxy Config File 2 | ## https://github.com/bitly/oauth2_proxy 3 | 4 | ## : to listen on for HTTP/HTTPS clients 5 | http_address = ":4180" 6 | # https_address = ":443" 7 | 8 | ## TLS Settings 9 | # tls_cert_file = "" 10 | # tls_key_file = "" 11 | 12 | ## the OAuth Redirect URL. 13 | # defaults to the "https://" + requested host header + "/oauth2/callback" 14 | redirect_url = "https://blakeshome.com/oauth2/callback" 15 | 16 | ## the http url(s) of the upstream endpoint. If multiple, routing is based on path 17 | # upstreams = [ 18 | # "http://127.0.0.1:8080/" 19 | # ] 20 | 21 | ## Log requests to stdout 22 | # request_logging = true 23 | 24 | ## pass HTTP Basic Auth, X-Forwarded-User and X-Forwarded-Email information to upstream 25 | # pass_basic_auth = true 26 | # pass_user_headers = true 27 | ## pass the request Host Header to upstream 28 | ## when disabled the upstream Host is used as the Host Header 29 | # pass_host_header = true 30 | 31 | ## Email Domains to allow authentication for (this authorizes any email on this domain) 32 | ## for more granular authorization use `authenticated_emails_file` 33 | ## To authorize any email addresses use "*" 34 | # email_domains = [ 35 | # "yourcompany.com" 36 | # ] 37 | 38 | ## The OAuth Client ID, Secret 39 | # client_id = "123456.apps.googleusercontent.com" 40 | # client_secret = "" 41 | 42 | ## Pass OAuth Access token to upstream via "X-Forwarded-Access-Token" 43 | # pass_access_token = false 44 | 45 | ## Authenticated Email Addresses File (one email per line) 46 | authenticated_emails_file = "/etc/oauth2_proxy/authenticated_emails" 47 | 48 | set_xauthrequest = true 49 | 50 | #proxy-prefix = "/api/__oauth2" 51 | 52 | ## Htpasswd File (optional) 53 | ## Additionally authenticate against a htpasswd file. Entries must be created with "htpasswd -s" for SHA encryption 54 | ## enabling exposes a username/login signin form 55 | # htpasswd_file = "" 56 | 57 | ## Templates 58 | ## optional directory with custom sign_in.html and error.html 59 | # custom_templates_dir = "" 60 | 61 | ## skip SSL checking for HTTPS requests 62 | # ssl_insecure_skip_verify = false 63 | 64 | 65 | ## Cookie Settings 66 | ## Name - the cookie name 67 | ## Secret - the seed string for secure cookies; should be 16, 24, or 32 bytes 68 | ## for use with an AES cipher when cookie_refresh or pass_access_token 69 | ## is set 70 | ## Domain - (optional) cookie domain to force cookies to (ie: .yourcompany.com) 71 | ## Expire - (duration) expire timeframe for cookie 72 | ## Refresh - (duration) refresh the cookie when duration has elapsed after cookie was initially set. 73 | ## Should be less than cookie_expire; set to 0 to disable. 74 | ## On refresh, OAuth token is re-validated. 75 | ## (ie: 1h means tokens are refreshed on request 1hr+ after it was set) 76 | ## Secure - secure cookies are only sent by the browser of a HTTPS connection (recommended) 77 | ## HttpOnly - httponly cookies are not readable by javascript (recommended) 78 | # cookie_name = "_oauth2_proxy" 79 | # cookie_secret = "" 80 | # cookie_domain = "" 81 | # cookie_expire = "168h" 82 | # cookie_refresh = "" 83 | # cookie_secure = true 84 | # cookie_httponly = true -------------------------------------------------------------------------------- /pihole/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM pihole/pihole:latest 2 | 3 | # install mosquitto clients to allow dhcp leases to be 4 | # published to mqtt 5 | RUN apt-get update && \ 6 | apt-get install -y mosquitto-clients && \ 7 | rm -rf /var/cache/apt/archives /var/lib/apt/lists/* 8 | 9 | # Prevent dhcp leases from being passed to the script on reboot. 10 | # This would make it look like all devices with dhcp leases just 11 | # made a dhcp request. 12 | # This may cause the same ip to be issued to multiple devices. 13 | # I could also read the dhcp leases file in my script and check 14 | # the expiration for the given IP. 15 | RUN ln -s /dev/null /etc/pihole/dhcp.leases -------------------------------------------------------------------------------- /pihole/dnsmasq.d/03-blakeshome.conf: -------------------------------------------------------------------------------- 1 | address=/blakeshome.com/192.168.2.2 2 | address=/mqtt.blakeshome.com/192.168.2.2 3 | address=/pihole.blakeshome.com/192.168.2.2 4 | address=/nodered.blakeshome.com/192.168.2.2 5 | address=/unifi.blakeshome.com/192.168.2.2 6 | address=/hass.blakeshome.com/192.168.2.2 7 | address=/dash.blakeshome.com/192.168.2.2 8 | address=/portainer.blakeshome.com/192.168.2.2 9 | address=/cameras.blakeshome.com/192.168.2.2 10 | address=/netdata.blakeshome.com/192.168.2.2 11 | address=/vacuum.blakeshome.com/192.168.2.2 12 | address=/public.blakeshome.com/192.168.2.2 -------------------------------------------------------------------------------- /pihole/dnsmasq.d/04-bypass.conf: -------------------------------------------------------------------------------- 1 | ## The contents here bypass pihole by mac address 2 | 3 | ## This will go straight to Googles DNS Servers. 4 | dhcp-option=tag:googlesdns1,6,8.8.8.8 5 | dhcp-option=tag:googlesdns2,6,8.8.4.4 6 | 7 | ## This will go straight to Opendns Servers. 8 | dhcp-option=tag:opendns1,6,208.67.222.220 9 | dhcp-option=tag:opendns2,6,208.67.222.222 10 | ## OpenDNS FamilyShield 11 | dhcp-option=tag:opendns3,6,208.67.222.123 12 | dhcp-option=tag:opendns4,6,208.67.220.123 13 | 14 | ## Level3 DNS 15 | dhcp-option=tag:Level3DNS1,6,4.2.2.1 16 | dhcp-option=tag:Level3DNS2,6,4.2.2.2 17 | 18 | ## Comodo Secure DNS 19 | dhcp-option=tag:ComodoSecureDNS,6,8.26.56.26 20 | dhcp-option=tag:ComodoSecureDNS,6,8.20.247.20 21 | 22 | ## Norton 23 | ## P1 - malware, phishing schemes, and scams. 24 | dhcp-option=tag:norton1,6,199.85.126.10 25 | dhcp-option=tag:norton2,6,199.85.127.10 26 | ## P2 - Pornography 27 | dhcp-option=tag:norton3,6,199.85.126.20 28 | dhcp-option=tag:norton4,6,199.85.127.20 29 | ## P3 - Security + Pornography + Other 30 | dhcp-option=tag:norton5,6,199.85.126.30 31 | dhcp-option=tag:norton6,6,199.85.127.30 32 | 33 | ######################################################################## 34 | 35 | ## Instructions 36 | ## First set your tag, and dns server. 37 | ## dhcp-option=tag:YOURTAGHERE,6,IPADDRESSOFDNSSERVER 38 | ## You then simply need to replace MA:CA:DD:R:ES:SS 39 | ## I have set up the standard DNS servertags above. 40 | ## Below are examples of how to set a mac address to bypass pihole. 41 | 42 | ## Your Device that goes to Google DNS 43 | #dhcp-host=MA:CA:DD:R:ES:SS,set:googlesdns1 44 | 45 | ## Your Device that goes to OpenDNS 46 | #dhcp-host=MA:CA:DD:R:ES:SS,set:opendns1 47 | 48 | ## Your Device that goes to custom DNS Server 49 | dhcp-host=3C:28:6D:E3:EC:C4,set:norton1 50 | dhcp-host=68:A8:6D:17:36:F4,set:norton1 -------------------------------------------------------------------------------- /pihole/dnsmasq.d/04-pihole-static-dhcp.conf: -------------------------------------------------------------------------------- 1 | # Set static ip addresses! 2 | # 3 | # dhcp-host=MACADDRESS,DEVICENAME,IPADDRESS,LEASETIME 4 | # 5 | # Example: 6 | # dhcp-host=11:22:33:44:55:66,fred,192.168.0.60,45m 7 | # 8 | # Example for when a machine has two hardware addresses 9 | ##dhcp-host=11:22:33:44:55:66,12:34:56:78:90:12,192.168.0.60 10 | 11 | dhcp-host=34:CE:00:E7:33:6D,192.168.2.36,xiaomi_vacuum 12 | dhcp-host=3C:28:6D:E3:EC:C4,192.168.2.192,ali_phone 13 | dhcp-host=3C:28:6D:2A:F0:F4,192.168.2.239,blake_phone -------------------------------------------------------------------------------- /pihole/dnsmasq.d/05-dhcp-settings.conf: -------------------------------------------------------------------------------- 1 | dhcp-script=/opt/mqttpub.sh -------------------------------------------------------------------------------- /pihole/mqttpub.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | op="${1:-op}" 4 | mac="${2:-mac}" 5 | ip="${3:-ip}" 6 | hostname="${4}" 7 | 8 | # dont report on deleted leases 9 | if [ $op = "del" ] 10 | then 11 | exit 0 12 | fi 13 | 14 | tstamp="`date '+%s'`" 15 | 16 | topic="network/dhcp/${mac}" 17 | 18 | payload=$(cat <