tbkeys
is an add-on for Thunderbird that uses Mousetrap to bind key sequences to custom commands.
The tbkeys-lite version of the addon can also be installed from addons.thunderbird.net by searching for "tbkeys-lite" in the Thunderbird addons manager or by downloading the xpi file from this page and following the steps above.
The default key bindings for the main window are modeled on GMail's key bindings.
Key | Function |
---|---|
c | Compose new message |
r | Reply |
a | Reply all |
f | Forward |
# | Delete |
u | Refresh mail. If a message tab is open, close it. |
j | Next message |
k | Previous message |
o | Open message |
x | Archive message |
To customize key bindings, modify the "key bindings" entries in the add-on's preferences pane which can be accessed from the add-on's entry in the Add-ons Manager ("Add-ons" in the Thunderbird menu). Here are some things to consider when setting key bindings:
shift
.ctrl+j ctrl+k
) is not supported.
Single keys with modifiers may be mapped to override the built-in shortcuts but not sequences.A few different styles of commands can be specified for key bindings. They are:
cmd:<command_name>
where <command_name>
is a command that Thunderbird can execute with goDoCommand()
.
Most command names can be found in the main command set file of the Thunderbird source code.func:<func_name>
where <func_name>
is a function defined on the Thunderbird window object.
That function is called without any arguments.tbkeys:<func_name>
where <func_name>
is the name of a custom function written in tbkeys.
Currently, the only available custom function is closeMessageAndRefresh
which closes the open tab if it is not the first tab and then refreshes all accounts.
This behavior mimics the behavior of the GMail keybinding u
.unset
.
When an unset
keybinding is triggered, nothing happens.
This can be useful unbinding built-in Thunderbird key bindings which you do not wish to trigger by accident.memsg:<extensionID>:<message>
where <extensionID>
is the ID of the Thunderbird extension to which to send a message and <message>
is a string message to send to the extension using the browser.runtime.sendMessage()
MailExtension API.
Currently, only string messages are supported because tbkeys
stores its commands as strings, though that restriction could possibly be relaxed in the future.eval()
when the key binding is triggered.
Any entry not matching the prefixes of the other command types is treated as an eval command.
NOTE: eval commands are not available in tbkeys-lite and will function the same as unset commands instead.Here are some examples of eval commands for commonly desired key bindings:
window.document.getElementById('tabmail-tabs').advanceSelectedTab(1, true)
window.document.getElementById('tabmail-tabs').advanceSelectedTab(-1, true)
func:CloseTabOrWindow
window.document.getElementById('threadTree').scrollByLines(1)
window.document.getElementById('threadTree').scrollByLines(-1)
window.gTabmail.currentAboutMessage.getMessagePaneBrowser().contentWindow.scrollBy(0, 100)
window.document.getElementById('messagepane').contentDocument.documentElement.getElementsByTagName('body')[0].scrollBy(0, 100)
window.gTabmail.currentAboutMessage.getMessagePaneBrowser().contentWindow.scrollBy(0, -100)
window.document.getElementById('messagepane').contentDocument.documentElement.getElementsByTagName('body')[0].scrollBy(0, -100)
window.goDoCommand('cmd_newFolder')
window.openSubscriptionsDialog(window.GetSelectedMsgFolders()[0])
The "Unset singles" button in the preferences pane can be used to unset Thunderbird's default single key bindings in the main window.
This function set all of Thunderbird's default single key shortcuts to unset
unless they are currently set in tbkey's preferences (that is, it won't overwrite tbkeys' existing settings for single key shortcuts).
tbkeys-lite is a version of tbkeys with the ability to execute arbitrary javascript removed.
Before installation, Thunderbird will prompt about the extension requiring permission to "Have full, unrestricted access to Thunderbird, and your computer." The reason for this permission request is that tbkeys must inject a key listener into the Thunderbird user interface in order to listen for key bindings. To do this, tbkeys uses the older Thunderbird extension interface that predates MailExtensions. This interface is what all extensions used prior to Thunderbird 68. The new MailExtensions APIs which provide tighter control on what extensions can do do not have a keyboard shortcut API. If you are interested in seeing a keyboard shortcut API added to Thunderbird, please consider contributing code to the project. Perhaps this ticket in the Thunderbird issue tracker could be a starting point.
To discuss the security considerations related to tbkeys further, it is necessary to review its implementation.
As mentioned in the intro, tbkeys relies on the Mousetrap library for managing the keybindings.
The bulk of the logic of tbkeys is in implementation.js which is a MailExtension experiment.
implementation.js
sets up the experiment API which can be called by tbkey's standard (restricted in scope) MailExtension to bind keyboard shortcuts to functions (including a null function for unbinding) and to messages to send to other extensions.
implementation.js
also loads Mousetrap into each Thunderbird window, tweaks the conditions upon which Mousetrap captures a key even to account for Thunderbird specific UI elements, and defines the function that executes what the user specifies for each key binding.
That is all that implementation.js
does.
It does not access the local file system or any message data and does not access the network.
One of the command modes tbkeys supports is eval.
This mode uses eval()
to execute arbitrary code provided by the user in implementation.js
with full access to Thunderbird's internals.
If one does not need to bind to arbitrary code, perhaps there is some security gained by using tbkeys-lite which does not support eval commands.
tbkeys-lite is the version published on Thunderbird's Add-ons page.
Add-ons published there undergo an independent manual review.
Having that barrier of review between yourself and the developer provides an added layer of security.