Keyboard Remote
Receive signals from a keyboard and use it as a remote control.
This integrationIntegrations connect and integrate Home Assistant with your devices, services, and more. [Learn more] allows you to use one or more keyboards as remote controls. It will fire keyboard_remote_command_received
events which can then be used in automation rules.
The evdev
package is used to interface with the keyboard and thus this is Linux only. It also means you can’t use your normal keyboard for this because evdev
will block it.
To enable the Keyboard Remote integrationIntegrations connect and integrate Home Assistant with your devices, services, and more. [Learn more], add it to your configuration.yaml
The configuration.yaml file is the main configuration file for Home Assistant. It lists the integrations to be loaded and their specific configurations. In some cases, the configuration needs to be edited manually directly in the configuration.yaml file. Most integrations can be configured in the UI. [Learn more] file.
After changing the configuration.yaml
The configuration.yaml file is the main configuration file for Home Assistant. It lists the integrations to be loaded and their specific configurations. In some cases, the configuration needs to be edited manually directly in the configuration.yaml file. Most integrations can be configured in the UI. [Learn more] file, restart Home Assistant to apply the changes.
# Example configuration.yaml entry
keyboard_remote:
type: "key_up"
Configuration Variables
Possible values are key_up
, key_down
, and key_hold
. Be careful, key_hold
will fire a lot of events. This can be a list of types.
Emulate key hold events when key is held down. (Some input devices do not send these otherwise.)
Number of seconds to wait before sending first emulated key hold event
Number of seconds to wait before sending subsequent emulated key hold event
Path to the local event input device file that corresponds to the keyboard.
Either device_name
or device_descriptor
must be present in the configuration entry. Indicating a device name is useful in case of repeating disconnections and re-connections of the device (for example, a Bluetooth keyboard): the local input device file might change, thus breaking the configuration, while the name remains the same.
In case of presence of multiple devices of the same model, device_descriptor
must be used.
A list of possible device descriptors and names is reported in the debug log at startup when the device indicated in the configuration entry could not be found.
A full configuration for two Keyboard Remotes could look like the one below:
keyboard_remote:
- device_descriptor: '/dev/input/by-id/bluetooth-keyboard'
type: "key_down"
emulate_key_hold: true
emulate_key_hold_delay: 0.25
emulate_key_hold_repeat: 0.033
- device_descriptor: '/dev/input/event0'
type:
- 'key_up'
- 'key_down'
Or like the following for one keyboard:
keyboard_remote:
device_name: "Bluetooth Keyboard"
type: "key_down"
And an automation rule to breathe life into it:
automation:
alias: "Keyboard all lights on"
triggers:
- trigger: event
event_type: keyboard_remote_command_received
event_data:
device_descriptor: "/dev/input/event0"
key_code: 107 # inspect log to obtain desired keycode
type: key_down # only trigger on key_down events (optional)
actions:
- action: light.turn_on
target:
entity_id: light.all
device_descriptor
or device_name
may be specified in the trigger so the automation will be fired only for that keyboard. This is especially useful if you wish to use several Bluetooth remotes to control different devices. Omit them to ensure the same key triggers the automation for all keyboards/remotes.
key_code
should be set to the code generated by the key press, otherwise the trigger will fire on every key press.
type
can optionally be set to one of key_down
, key_up
, or key_hold
to limit the trigger to that specific event type.
Disconnections
This integration manages disconnections and re-connections of the keyboard, for example in the case of a Bluetooth device that turns off automatically to preserve battery.
If the keyboard disconnects, the integration will fire an event keyboard_remote_disconnected
.
When the keyboard reconnects, an event keyboard_remote_connected
will be fired.
Here’s an automation example that plays a sound through a media player whenever the keyboard connects/disconnects:
automation:
- alias: "Keyboard Connected"
triggers:
- trigger: event
event_type: keyboard_remote_connected
actions:
- action: media_player.play_media
target:
entity_id: media_player.speaker
data:
media_content_id: keyboard_connected.wav
media_content_type: music
- alias: "Bluetooth Keyboard Disconnected"
triggers:
- trigger: event
event_type: keyboard_remote_disconnected
event_data:
device_name: "00:58:56:4C:C0:91"
actions:
- action: media_player.play_media
target:
entity_id: media_player.speaker
data:
media_content_id: keyboard_disconnected.wav
media_content_type: music
Permissions
There might be permissions problems with the event input device file. If this is the case, the user that Home Assistant runs as must be allowed read and write permissions with:
sudo setfacl -m u:HASS_USER:rw /dev/input/event*
Where HASS_USER
is the user who runs Home Assistant.
If you want to make this permanent, you can use a udev rule that sets it for all event input devices. Add a file /etc/udev/rules.d/99-userdev-input.rules
containing:
KERNEL=="event*", SUBSYSTEM=="input", RUN+="/usr/bin/setfacl -m u:HASS_USER:rw $env{DEVNAME}"
You can check ACLs permissions with:
getfacl /dev/input/event*
Containers
If you are running Home Assistant Container, you need to pass the input device through to the container. You can pass the input device you want to use directly into the container with the --devices
flag. However, restarting the container or unplugging and replugging your keyboard will break this integration. This is because only the instance of the keyboard that existed when the container first started will be available inside the container.
Here is an incomplete example docker-compose.yml
that allows Home Assistant persistent access to input devices in a container:
version: '3.7'
services:
homeassistant:
image: ghcr.io/homeassistant/home-assistant:stable
volumes:
- config:/config/
- /dev/input:/dev/input/ # this is needed to read input events.
restart: unless-stopped
device_cgroup_rules:
# allow creation of /dev/input/* with mknod, this is not enough on its own and needs mknod to be called in the container
- 'c 13:* rmw'
devices:
# since input id may change, pass them all in
- "/dev/input/"
...