Telega Manual (v0.8.291)

 Telega Manual

This version of the manual for bleeding edge telega from "master" branch running under bleeding edge TDLib from "master" branch. For release version of the manual switch to Telega Manual (release).

This file is automatically generated from by GitHub#ellit-org.el tool. Do not edit manually. Modify or comments in .el files instead.


telega is full featured unofficial client for Telegram platform for GNU Emacs.

telega is actively developed, for this reason, some features are not implemented, or they are present just as skeleton for future implementation. However, the core parts are mature enough so that it is possible to use telega on daily basis.

Join us at

If you enjoy telega, consider making a donation for unstoppable development, also see benefits you get being telega patron.


telega depends on the visual-fill-column and rainbow-identifiers packages. This dependency automatically installs if you install telega from MELPA or GNU Guix. Otherwise will you need to install these packages by hand.

telega is built on top of the official library provided by Telegram TDLib. Most distributions do not provide this package in their repositories, in which case you will have to install it manually by following the instructions.

GNU Guix, however, does have both telega and TDLib packaged. If you use GNU Guix you can skip directly to Installing from GNU Guix.

Also, you can use Docker to avoid complicated installation steps by using one of the provided docker images. See Running telega-server in docker for details.


  • GNU Emacs (at least 26.1 is required with svg support)
  • GNU make (known as gmake on BSD platforms)
  • GNU gperf (for building TDLib)
  • CMake (for building TDLib)
  • pkg-config (for building telega-server)

Optional dependencies:

  • Python (optional, for testing the telega-server)
  • GNU Guix (optional, if using the Guix installation method)
  • libappindicator3 (optional, to show telega icon/info in system tray)
  • dwebp (optional, to display Stickers)
  • tgs2png (optional, for Animated Stickers), sources are at

make is found in most of the modern machines. The other packages can be download with the system package manager (such as apt for Debian-based distributions, dnf for Fedora or pacman for Arch-based).

MacOS users

  1. If you are using Emacs For Mac OS X, or you installed Emacs by running $ brew cask install emacs, make sure you installed a recent enough version (>= emacs-27.1-mac-8.1, you can check your version by running $ brew info emacs-mac or $ brew cask info emacs-mac) with rsvg support ($ brew install emacs-mac --with-librsvg), or your Emacs may not display some media correctly, in this case consider switching to emacs-plus.
  2. If you are using Emacs-mac, or you installed Emacs by running $ brew install emacs-mac or $ brew cask install emacs-mac, your Emacs has bug dealing with complex svg, which leads to Emacs hangups. Compiling Emacs with rsvg support by running $ brew install emacs-mac --with-librsvg will fix this problem.

    NOTE: telega cannot display stickers correctly with emacs-mac, even when emacs-mac is compiled with rsvg support. If you want sticker support, please consider switching to emacs-plus.

  3. emacs-plus is the best choice to run telega.

Linux users

telega requires at least GNU Emacs 26.1 with optional, but highly recommended, svg support. If Emacs version is less then 27.1, then imagemagick is also required. Most distributions provide GNU Emacs compiled with these dependencies when installing GNU Emacs with GTK+ support (graphical).

Windows 10 users

See detailed description how to install telega under Windows 10.

Thanks to @ritsch_master

Building TDLib

TDLib is the library for building Telegram clients. It requires a large amount of memory to be built. Make sure you are using TDLib version greater or equal to 1.8.29.

On MacOS you can install a pre-built TDLib package using homebrew from Just run:

$ brew install tdlib --HEAD

On Linux, you will need to build TDLib from source. Use TDLib build instructions generator for comprehensive build instructions.

In general, you need to install all TDLib dependencies then get TDLib sources and compile them using CMake.

To get the source:

$ git clone

Move into the folder with $ cd ./td or wherever you checked out td.

Prepare a folder for building the library:

$ mkdir build && cd build && cmake ../

Build the sources:

$ make -jN

with N number of cores that should be used for the compilation (the optimal value is the number of physical cores on the machine).

Finally, to install the library system-wide:

$ sudo make install

It will install headers to /usr/local/include and library itself into /usr/local/lib. If you have TDLib installed in other location, don't forget to modify telega-server-libs-prefix before starting telega.

For Linux users, make sure /usr/local/lib is in your ldconfig cache, otherwise telega server build will fail.

Updating telega and TDLib

If you use telega from master and update it from time to time it might ask you to update/rebuild TDLib and telega-server. To update TDLib and rebuild telega-server do next:

  1. Fetch, rebuild and reinstall updated TDLib as described above
  2. On Linux run $ sudo ldconfig to refresh ldconfig cache
  3. Run $ make server-reinstall in the telega.el sources directory to rebuild and reinstall telega-server

Now you are ready to run updated telega.

Installing telega and TDLib from GNU Guix

telega and TDLib are both available in GNU Guix. If you have a resource constrained machine or would simply prefer to bypass compiling TDLib from source, this is a good option!

On Guix System:

$ guix package -i emacs-telega font-gnu-{unifont,freefont}

The latter two packages provide glyphs used by telega.

On "Foreign" Distributions:

  • Use the shell installer script, or install GNU Guix manually on-top of your current distribution. Installation Documentation
  • Enable fetching substitutes from the build server cache if you do not wish to build from source. Substitute Server Authorization
  • And finally, run:

    $ guix package -i emacs emacs-telega

It is easiest to use the version of Emacs installed from GNU Guix because it is modified with an autoloader to identify and automatically use Emacs packages installed from Guix. Alternatively, if you wish to use the bundle of Emacs provided by your distribution, you may install the telega elisp sources through MELPA and use Guix to provide the server binary precompiled.

Consult the official GNU Guix documentation for further questions. Issues related to the GUIX package must be accompanied by the GUIX label in the issue tracker.

Do note that since telega is actively maintained installations from Guix might at times lag behind master, but regular attempts to keep it updated will occur. If the version in Guix is too outdated or is missing a feature, please use the protocol for the issue tracker.

Installing telega from MELPA

telega is available from MELPA, so you can install it from there as usual package. This is a preferable method, because it will automatically handle all dependencies and provides autoloads.

For TDLib 1.8.0 release you might consider stable telega version. Stable telega version won't require you to rebuild TDLib until next TDLib 1.9.0 release, telega updates will work with 1.8.0. Stable telega is placed in MELPA Stable. Package configuration for telega from MELPA Stable might look like:

(add-to-list 'package-archives
             '("melpa-stable" . ""))
(add-to-list 'package-pinned-packages '(telega . "melpa-stable"))

telega from unstable MELPA is a bleeding edge of the telega development and telega updates might require also TDLib update/rebuild sometimes. However, it brings you all newer (probably incompatible with TDLib 1.8.0) functionality faster, no need to wait for TDLib 1.9.0 to access newer features.

Or you could use git repository with this melpa-style recipe for quelpa:

(quelpa '(telega :fetcher github
                 :repo "zevlg/telega.el"
                 :branch "master"
                 :files (:defaults "contrib" "etc" "server" "Makefile")))

Installing telega directly from GitHub

Make sure dependencies are installed with M-x package-install RET visual-fill-column RET and M-x package-install RET rainbow-identifiers RET.

Get the source:

$ git clone
$ cd telega.el
$ make compile

Finally load telega into Emacs using:

(use-package telega
  :load-path  "~/telega.el"
  :commands (telega)
  :defer t)

Or with:

(add-to-list 'load-path "~/telega.el")
(require 'telega)

The code should be put in the configuration file for Emacs, which usually is init.el, or emacs.el.

Running telega-server in docker

Pull latest telega-server image:

$ docker pull zevlg/telega-server:latest

Make telega know you want to use docker by adding this to your init.el:

(setq telega-use-docker t)

That's it, you are ready to get starting. However, you might anyway need to have local ffmpeg installation to utilize some telega features, such as playing audio/voice messages, capturing video/voice notes, etc.

Getting started

Start telega with M-x telega RET. The first time it will ask for the phone number you have associated with the Telegram network.

Some options affecting TDLib runtime:

  • User Option: telega-directory

    Directory for telega runtime files. Set this variable before loading telega, because other variables depends on telega-directory value.

Default value: "~/.telega"

  • User Option: telega-options-plist

    Plist of options to set. To use custom language pack (from "tdesktop" localization target), add :language_pack_id option. Only writable options can be set. See:

    Default value:

    (:online t :localization_target "tdesktop" :use_storage_optimizer
             :false :ignore_file_names :false)
  • User Option: telega-proxies

    List of proxies. Format is: (:server "<ADDRESS>" :port <PORT> :enable <BOOL> :type <PROXY-TYPE>)

    where PROXY-TYPE is one of:

    • (:@type "proxyTypeSocks5" :username <USER> :password <PASSWORD>)
    • (:@type "proxyTypeHttp" :username <USER> :password <PASSWORD> :httponly <BOOL>)
    • (:@type "proxyTypeMtproto" :secret <SECRET-STRING>)

    <BOOL> is either t or :false, nil is not valid value.

    Default value: nil

  • User Option: telega-my-location

    Set to non-nil to use this as location of me. Plist in form (:latitude <LAT> :longitude <LONG>) To publically expose this location set :is_location_visible to non-nil in telega-options-plist. Used to calculate distances from other peers to me.

    Default value: nil

    See also telega-my-location-mode to automatically update telega-my-location when you send location message to the "Saved Messages" using mobile Telegram client.

To list all available customizable user options use M-x customize-group RET telega RET command.

Settings for Emacs As Daemon

Some people starts Emacs in daemon mode, i.e. emacs --daemon. Such Emacs instance has no frames, frames are created when needed and connects to the daemon process.

telega autodetects values for some variables at load time by examining current frame parameters and window system possibilities. This won't work in daemon mode. You need to explicitly specify values for that variables. Most notable options are:

  • User Option: telega-use-images

    Non-nil to show images. Explicitly set it to non-nil if using Emacs as a service and want to create X frames to show images. See

    Set to imagemagick to use ImageMagick to handle images (not recommended).

  • User Option: telega-emoji-font-family

    Font to use for emoji image generation using telega-emoji-create-svg.

  • User Option: telega-emoji-use-images

    Non-nil to use images for emojis.

  • User Option: telega-online-status-function

    Function used to determine if user is online. Function should return non-nil if user is online, and nil if offline. See

Setting telega-use-images before loading telega is essential, because many other custom options depends on its value.

Telega glossary

Before start, please read TDLib glossary

telega tries to keep TDLib's terminology, however introduces some new terms specific to telega. All of them are used in the manual.

Root Buffer a.k.a. rootbuf
Buffer with list of chats, you see it just after M-x telega RET. Most of the time rootbuf term is used in the manual. See Root Buffer
Root View
Root Buffer can be shown in different ways. Way rootbuf is shown is called root view. See Root Buffer
Chat Buffer a.k.a. chatbuf
Buffer with chat contents. See Chat Buffer
Ordinary Emacs Button (see button.el). Some outlined area with text, that can be acted on. Pressing RET on the button, executes button action. There are many buttons of different kind in telega
Chat Button

Button referring to some chat. Action for such button is to open corresponding chatbuf.

rootbuf lists the chat buttons, such as:

{🎗Saved Messages            }📌  📹 Video (10s)               Fri✓
[Emacs | Emacs (english)     ]  @oldosfan: same                Fri
Telega Match Expression - S-expression to match telega objects such as chats or messages. See Telega Match Expressions for the details.
[Custom] Chat Filter

Named temex to filter chats in the rootbuf.

Custom chat filters are displayed as buttons above the chat list in the rootbuf, such as:

[243:📑Main      4890]  [51:Groups       4677]  [27:Channels      210]
[53:Contacts         ]  [0:Important         ]  [3:📑Archive      670]

Action for such buttons is to add corresponding temex to the active chat filter.

However, buttons that corresponds to a Telegram Folder, including "Main" and "Archive", substitutes folder in the active chat filter with new one at button.

  • User Option: telega-filter-button-width

    Width of the custom filter buttons. If integer, then use this number of chars. If float in range (0..1), then occupy this percents of telega-root-fill-column chars, but not less then 15 chars. If list, where first element is float, then use 1 and 2 list values as min and max values for a width calculation using telega-canonicalize-number.

    Default value: (0.25 17 25)

  • User Option: telega-filters-custom

    Alist of custom filters in form (NAME . TEMEX). NAME can be an i18n string, such as "lngfilterstypegroups". This filters are displayed as filter buttons at the top of rootbuf.

    Default value:

    (("Main" . main) ("Important" . important)
     ("Online" and (not saved-messages) (user is-online))
     ("lng_filters_type_groups" type basicgroup supergroup)
     ("lng_filters_type_channels" type channel)
     ("lng_filters_type_no_archived" . archive))
  • User Option: telega-filter-custom-expand

    Non-nil to expand custom filter when adding to active filters.

    Default value: t

  • User Option: telega-filter-custom-show-folders

    Non-nil to show telegram folders along the side with custom filters.

    Default value: t

Active Chat Filter

List of chat temexes applied to the chat list in rootbuf.

Only chats matching all temexes in the active chat filter are displayed in rootbuf. Active chat filter is displayed above the chat list in rootbuf, such as:


(telega-filter-active) returns active chat filter.

  • User Option: telega-filter-default

    Temex to filter chats by default.

    Default value: main

Chat Sort Criteria
List of symbols denoting how to sort chats. See Sorting Chats
Active Sort Criteria a.k.a. active sorter

Sort criteria applied to the chat list in rootbuf.

By default, chats are sorted according to internal Telegram order (except for chats with custom order).

In case active sorter is enabled, it is displayed above the chat list in rootbuf, such as:

-\---------------------(unread-count join-date)-----------------------
Me user a.k.a. me

User currently logged in, (telega-user-me) returns me.

me means you, not me.

Chat with me is also known as "Saved Messages".


S-Expression denoting an inserter. It could be a function, a symbol or a list to be evaluated.

Insexp evaluation results in content being inserted.

Telega prefix map

telega has prefix map for common telega commands, such as switching to rootbuf, switch to "Saved Messages", sending current buffer as file to a chat, switching accounts, opening chat or switching to some chat.

It is convenient to have it somewhere accessible from global-map, say C-c t. To do so use next code in your init.el:

(define-key global-map (kbd "C-c t") telega-prefix-map)

Or if telega is not accessible to autoload at start time, then use:

(add-hook 'telega-load-hook
          (lambda ()
            (define-key global-map (kbd "C-c t") telega-prefix-map)))

Telega prefix map bindings:

a (telega-account-switch)
Switch to the ACCOUNT-NAME.
b (telega-switch-buffer)
Interactively switch to CHAT's buffer. Switch only if CHAT is opened, i.e. has corresponding chatbuf.
c (telega-chat-with)
Start messaging with CHAT-OR-USER.
e (telega-edit-file-switch-buffer)
Interactively switch to BUFFER having telega-edit-file-mode.
i (telega-switch-important-chat)
Switch to important CHAT if any. If C-u is used, then select first chat if multiple chats are important.
f (telega-buffer-file-send)
Prepare FILE to be sent as document or photo to CHAT. If C-u is specified, then always send as a file. Otherwise FILE type is automatically detected. If called interactively, then file associated with current buffer is used as FILE. If current buffer is dired, then send all marked files.
s (telega-saved-messages)
Switch to "Saved Messages" chat buffer. If "Saved Messages" chat is not opened, then open it. If C-u is specified, then goto prompt otherwise keep the point, where it is.
t (telega)
Start telega.el Telegram client. Pop to root buffer. If C-u is specified, then do not pop to root buffer.
u (telega-switch-unread-chat)

Switch to next unread message in next unread CHAT. CHAT considered unread if matches telega-unread-chat-temex.

Customizable options:

  • User Option: telega-unread-chat-temex

    Chat Temex for telega-switch-unread-chat command.

    Default value: (and main unread)

w (telega-browse-url)
Open the URL. If URL can be opened directly inside telega, then do it. Invite links and link to users can be directly opened in telega. If IN-WEB-BROWSER is non-nil then force opening in web browser.

Root Buffer

rootbuf is the heart of the telega. Switch to rootbuf with M-x telega RET or use t (telega) binding from the Telega prefix map.

TODO: describe parts of the rootbuf: status, custom-filters, *folders, active chat filter, active chat sorter

rootbuf lists chats filtered by active chat filter. Press h, i, <down-mouse-3> <describe> (telega-describe-chat) to get detailed description of the chat at point.

Important customizable options:

  • User Option: telega-root-fill-column

    Maximum width to use in root buffer to display active filters and chats.

    Default value: 70

    This option is applied only if telega-root-auto-fill-mode is disabled. Default behaviour is to automatically adjust telega-root-fill-column to the width of the window displaying rootbuf.

  • User Option: telega-root-keep-cursor

    Non-nil to keep cursor at current chat, even if chat's order changes. Set to track, to move cursor to corresponding chat button, when chat buffers are switched, useful in side-by-side window setup for rootbuf and chatbuf.

    Consider setting switch-to-buffer-preserve-window-point to nil, to make telega-root-keep-cursor always work as expected.

    Default value: track

Rootbuf fast navigation

M-g prefix in rootbuf is used to jump across chat buttons:

M-g u (telega-root-next-unread)
Move point to the next chat with unread message.
M-g i (telega-root-next-important)

Move point to the next important chat.

Chat is important if matches telega-important-chat-temex temex.

M-g @, M-g m (telega-root-next-mention)
Move point to the next chat with mention.
M-g ! (telega-root-next-reaction)
Move point to the next chat with unread reaction.

Rootbuf view switching

Rootbuf view is the specific way how rootbuf is shown to the user. By default, list of the chats is shown, this is known as default root view.

v prefix in rootbuf is used to switch root views:

v a (telega-view-alternative-similar-channels)
View channels similar to the given CHAT.
s, v s (telega-view-search)
View QUERY search results.
v n (telega-view-nearby)
View contacts and chats nearby telega-my-location.
v v (telega-view-reset)
Reset rootview to the default value.
v 0 (telega-view-compact)
Compact view for the rootbuf.
v 1 (telega-view-one-line)
View chat list as one line.
v 2 (telega-view-two-lines)
View chat list as 2 lines.
v g (telega-view-grouping)

Group chats by telega-root-view-grouping-alist.

Customizable options:

  • User Option: telega-root-view-grouping-alist

    Alist of chat temexes for "grouping" root view. Car is name of the chats group, cdr is a chat temex to match chats.

    Default value: (("Important" . important))

  • User Option: telega-root-view-grouping-folders

    Non-nil to add Chat Folders in the grouping root view. Could be one of prepend, append or nil.

    Default value: append

  • User Option: telega-root-view-grouping-other-chats

    Non-nil to show other chats in the "grouping" root view.

    Default value: t

v F (telega-view-files)

View status of files known to telega. File can be in one of the state kinds: "downloading", "uploading", "partially-downloaded", "partially-uploaded", "downloaded". If C-u is specified, then query user about file state kinds to show. By default all kinds are shown.

If you use this view frequently, consider setting telega-chat-upload-attaches-ahead to nil, to avoid file duplications for "uploading" kind. See for details

Press d under downloaded filename to delete the file. Only files cached by TDLib in the telega-cache-dir can be deleted.

Customizable options:

  • User Option: telega-root-view-files-exclude-subdirs

    Alist specifying which subdirs to exclude when viewing files. car of each element is predicate matching file, and rest is list of subdirectories to ignore, i.e. if absolute file name contains any of the subdirectory in list, then file is ignored. Supported predicates: telega-file--downloading-p, telega-file--uploading-p, telega-file--downloaded-p, telega-file--uploaded-p, telega-file--partially-downloaded-p, telega-file--partially-uploaded-p

    Default value: ((telega-file--downloaded-p "thumbnails" "profile_photos"))

  • User Option: telega-chat-upload-attaches-ahead

    Non-nil to upload attachments ahead, before message actually sent. Having this non-nil "speedups" uploading, it is like files uploads instantly.

    Default value: t

v T (telega-view-top)

View top chats in all categories.

Customizable options:

  • User Option: telega-root-view-top-categories

    List of top categories with limits.

    Default value:

    (("Users" . 10) ("Groups" . 10) ("Channels" . 10) ("Bots" . 10)
     ("InlineBots" . 10) ("Calls" . 10) ("ForwardChats" . 10))
v S (telega-view-settings)
View and edit your Telegram settings.
v c (telega-view-contacts)
View contacts searched by QUERY. If QUERY is empty string, then show all contacts.
v C, c l (telega-view-calls)
View calls. If C-u is given, then view missed calls only.
v l (telega-view-last-messages)
View last messages in the chats.
v f (telega-view-folders)
View Telegram folders.
v d (telega-view-deleted-chats)
View recently deleted chats.
v * (telega-view-favorite-messages)
View favorite messages in all the chats.
v r (telega-view-recommended-channels)
View channels recommended to me.

Important customizable options:

  • User Option: telega-root-default-view-function

    Default view for the rootbuf.

    Default value: telega-view-default

    v v (telega-view-reset) uses this function to reset root view.

Voice/Video calls

Telegram provides nice voice/video calls.

TODO more documentation about voice/video calls support by telega.

c prefix in rootbuf is used to call VoIP commands:

c c (telega-chat-call)
Call to the user associated with the given private CHAT.
c a (telega-voip-accept)
Accept last incoming CALL. Discard active call if any.
c d (telega-voip-discard)
Discard the CALL. If called interactively then discard active call.
c b (telega-voip-buffer-show)
Show callbuf for the CALL.
v C, c l (telega-view-calls)
View calls. If C-u is given, then view missed calls only.

Telega Match Expressions

Telega Match Expression (temex in short) is a verbal expression to match TDLib objects. Temex uses S-exp notation similar to rx package for regexps.

Primitive Temex is a named predicate returning non-nil if matches some object. Primitive Temexes can be combined using and, or or not temexes, so temex is a logical combination of other temexes down to Primitive Temexes.

telega-match-gen-predicate can be used to generate predicate functions out of temex.

Chat Temex examples:

(return t)
Matches all chats.
(or saved-messages (type channel bot))
Matches bots/channels chats or "Saved Messages" chat.
(and unmuted (unread 10) (mention 1))
Matches unmuted chats with at least 10 unread messages and at least one message with unread mention.

Message Temex examples:

(sender me)
Matches all messages sent by me.
(or (prop :contains_unread_mention) unread-reactions)
Matches messages containing unread mention or reaction.
(and (chat (type channel)) (type text) (contains "\shello\s"))
Matches channel's text messages containing "hello" word.

List of temexes you can apply to any TDLib object:

(return RET)
Matches if RET is non-nil and return RET as a result.
(eval SEXP)
Matches if SEXP evaluates to non-nil, return result of evaluation.
Matches if any matcher in the TEMEX-LIST matches.
Matches if all matchers in the TEMEX-LIST matches. Also matches if TEMEX-LIST is empty.
(not TEMEX)
Matches if TEMEX does not match.
Matches if given TDLib object has non-nil PROPERTY.
Matches if PREDICATE called with TDLib object as argument returns non-nil.
(ids ID-LIST…)
Matches if TDLib object's id is in the ID-LIST.

List of Chat Temexes

Use telega-chat-match-p to match a chat.

(type CHAT-TYPE-LIST), / t (telega-filter-by-type)

Matches if chat type is one of CHAT-TYPE-LIST.

Every chat has a type. Type is one of:

  • private Private chat with a Telegram user
  • secret Secret chat with a Telegram user
  • bot Chat with a Telegram bot
  • basicgroup Small chat group, could be upgraded to supergroup
  • supergroup Chat group with all the chat possibilities
  • channel Supergroup with unlimited members, where only admins can post messages
(name REGEXP)
Matches if chat's title matches REGEXP.
(search QUERY), / s (telega-filter-by-search)
Matches if chat maches search QUERY.
nearby, / n (telega-filter-by-nearby)
Matches if chat is nearby telega-my-location.
(custom NAME), / C (telega-filter-by-custom)
Matches if custom filter with NAME matches.
(has-username [ USERNAME ])
Matches if chat has username associated with the chat. If USERNAME is specified, then match only if chat has exact USERNAME.
Matches if chat is a public chat. Chat is considered public if it has a username.
(unread [ N ]), / u (telega-filter-by-unread)
Matches if chat has at least N unread messages. By default N is 1. Also matches chats marked as unread.
(mention [ N ]), / m (telega-filter-by-mention)
Matches if chat has least N unread mentions. By default N is 1.
Matches if chat has disabled notifications.
Matches if chat is temporary muted.
unmuted, / y (telega-filter-by-unmuted)
Matches if chat has enabled notifications.
important, / i (telega-filter-by-important)
Matches if chat is important. Chat is important if it matches telega-important-chat-temex chat filter.
(me-is-owner [ OR-ADMIN ])
Matches if me is owner of the chat. Only basicgroup, supergroup and channel can be owned. If optional OR-ADMIN is specified, then match also if me is administrator in the chat.
Matches if me is member of the chat. Matches only basicgroup, supergroup or a channel.
Matches if me is anonymous in the chat.
(no term)
(has-avatar [ ANIMATED-P ]):: Matches if chat has chat photo. For non-nil ANIMATED-P match only if avatar is animated.
has-chatbuf, / b (telega-filter-by-has-chatbuf)
Matches if chat has corresponding chatbuf.
(permission PERM)
Matches if chat has PERM set in chat permissions. PERM could be one of listed in telega-chat--chat-permissions.
(my-permission PERM)
Matches if me has PERM permission in the chat. PERM could be one of in telega-chat--chat-permissions list or in telega-chat--admin-permissions list.
verified, / v (telega-filter-by-verified)
Matches if chat is verified.
(restriction SUFFIX-LIST…), / r (telega-filter-by-restriction)

Matches restricted chats. SUFFIX-LIST is a list of suffixes to filter on. Suffix can be one of:

  • "-all" - All platforms
  • "-ios" - For iOS devices
  • "-android" - For Android devices
  • "-wp" - Windows?

If SUFFIX-LIST is not specified, then match any restriction reason.

Chat restriction reason reported only if chat must be restricted by current client. See TDLib#1203

top, / T (telega-filter-by-top)
Matches if chat is in top usage.
Matches only "Saved Messages" chat.
Matches only "Replies" chat.
tracking, / SPC (telega-filter-by-tracking)
Matches if chat is in tracking buffers list.
(no term)
(last-message MSG-TEMEX):: Matches if chat has last message and last message matches MSG-TEMEX.
(chat-list LIST-NAME), / f (telega-filter-by-folder)
Matches if chat is in chat list named LIST-NAME. LIST-NAME is main or archive symbol, or string naming Chat Folder.
Matches if chat from "Main" chat list.
Matches if chat is archived, i.e. in "Archive" chat list.
Matches if chat is known, i.e. in "Main" or "Archive" chat list.
(folder FOLDER-NAME), / f (telega-filter-by-folder)
Matches if chat belongs to Folder named FOLDER-NAME.
Matches if chat has scheduled messages.
Matches if chat has active action bar.
Matches if chat has reply markup message.
Matches if statistics available for the chat.
Matches if chat is a supergroup and has a linked chat.
Matches if chat is a channel with a linked discussion group.
Matches if chat is a location-based supergroup.
inactive-supergroups , (telega-filter-by-inactive-supergroups)
Matches if chat is an inactive supergroup.
Matches if CHAT has non-nil default disable notification setting.
Matches if chat is fake or scam user or group.
(has-video-chat [ NON-EMPTY ])
Matches if chat contains a live video chat. If non-nil NON-EMPTY is specified, then match only if video chat is not empty.
Matches if chat has favorite messages.
Matches if chat has enabled message auto-delete or self-destruct timer. Return auto-deletion timer value.
Matches if chat is a broadcast group.
Matches if chat is a forum group.
Matches if chat has sponsored messages. BE AWARE: This filter will do blocking request for every chat.
Matches if chat has protected content.
Matches if chat allows choosing a message sender.
Matches if you can send or post messages to the chat. You don't need te be a chat member to be able to send messages. Chat might not be known (i.e. in your Main or Archive list) to post messages into it. Use is-known chat temex to check chat is known.
Matches if corresponding bot accepts inline requests.
(unread-reactions [ N ])
Matches if chat has least N unread reactions. By default N is 1.
(has-active-stories [ UNREAD-P ])
Matches if chat has non-expired stories available to you. If UNREAD-P is non-nil then match only if there is at least one unread non-expired story.
(active-stories-list LIST)
Matches if chat's active stories belongs to LIST. LIST is one of main or archive.
Matches if channel chat has pinned stories.
Matches if you can post a story into chat.
(my-boost [ N ])
Matches if supergroup or channel has least N my boosts. By default N is 1.
Matches non-bot private chat where corresponding user matches USER-TEMEX.
(bot-user USER-TEMEX)
Matches chat where corresponding bot user matches USER-TEMEX.
(is-blocked [ BLOCK-LIST ])
Matches chat if chat is blocked in by the BLOCK-LIST. BLOCK-LIST is one of blockListMain or blockListStories. By default blockListMain is used.
(boost-level [ N ])
Matches if chat's boost level is greater or equal to N. By default N is 1.

List of Message Temexes

Use telega-msg-match-p to match a message.


Matches if message's content type is one of MSG-TYPE-LIST.

Every message has a content type. Most notable message types are: Text, Animation, Audio, Document, Photo, Sticker, Video, VideoNote, VoiceNote, Location, etc.

Return non-nil if message has been viewed in the chat.
(unread-reactions [ N ])
Matches if message has at least N unread reactions. By default N is 1.
(has-chosen-reaction [ REACTION-TYPE ])
Matches if message has a reaction chosen by me.
Matches if message is a reply to some message.
Matches if message is a reply to a story.
Matches if message is a channel post that can be commented.
Matches if message is a forum topic message.
Matches if message belongs to or starts a messages thread.
(web-page [ PROPNAME ])
Matches messages with a webpage preview. If PROPNAME is specified, then match only message with a webpage having PROPNAME property.
(outgoing [ ANY-STATE-P ])
Matches if message is an outgoing message. This temex differs from (sender me), matching any outgoing messages, including anonymous messages to channels created by me.
Matches outgoing message failed to send.
(ignored [ REASON ])
Matches if message is an ignored message. If REASON is specified, then match only if has been ignored by REASON function.
(contains REGEXP )
Matches if message's text or caption contains REGEXP. Matching ignores case.
Matches if message's chat matches CHAT-TEMEX.
Matches if message's sender matches SENDER-TEMEX.
Matches deleted message.
Matches if message is the last message in chat.

List of User Temexes

Use telega-user-match-p to match a user.

Matches if user account is deleted.
Matches if user is a bot.
(status STATUS-LIST…)

Matches if user status is one of STATUS-LIST.

Each element in STATUS-LIST is one of: "Online", "Offline", "Recently", "LastWeek", "LastMonth" or "Empty"


Matches if user is online. Does not match bots, because bots are always online.

Same as (status "Online") user temex.

(contact [ MUTUAL-P ]), / c (telega-filter-by-contact)
Matches if user is in my contacts list. If MUTUAL-P is non-nil, then mach only if contact is mutual.
Matches if user is my close friend.
Matches if user has pinned stories.
(groups-in-common [ N ])
Matches if user has at least N groups in common with me. By default N is 1.
Matches if corresponding user is a telega patron.
Matches if corresponding user is a Telegram Premium user.
Matches if user can't be linked in forwarded messages.
Matches if user has business info.
Matches if user has birthdate set.
Matches if user has personal chat.
Matches if corresponding user set his current emoji status.
(username [ USERNAME-REGEXP ])
Matches if user's username matches USERNAME-REGEXP.
Matches if me has private chat with USER matching CHAT-TEMEX.
(is-blocked [ BLOCK-LIST ])
Matches user blocked by the BLOCK-LIST. BLOCK-LIST is one of blockListMain or blockListStories. By default blockListMain is used.

List of Message Sender Temexes

Use telega-sender-match-p to match a message sender.

Matches if sender is me.
(is-blocked [ BLOCK-LIST ])
Matches if sender is blocked in the BLOCK-LIST. BLOCK-LIST is one of blockListMain, blockListStories. By default blockListMain is used.
Matches if sender is a user matching USER-TEMEX.
Matches if sender is a chat matching CHAT-TEMEX.

List of Forum Topic Temexes

Use telega-topic-match-p to match a forum's topic.

(last-message MSG-TEMEX)
Matches if topic's last message matches MSG-TEMEX.
(mention [ N ])
Matches if topic has least N unread mentions. By default N is 1.
(unread-reactions [ N ])
Matches if topic has least N unread reactions. By default N is 1.
Matches if topic has disabled notifications.
Matches if topic is temporary muted.
(creator SENDER-TEMEX)
Matches if topic's creator matches SENDER-TEMEX.
Matches if topic's chat matches CHAT-TEMEX.
Matches if topic is a general topic in a chat.
Matches if topic has been created by me.
Matches if topic is closed.
Matches if topic is hidden. for General topic only.
Matches if last message in the chat is made to topic.

List of Story Temexes

Story Temexes are used to match Telegram Stories posted by users or channels.

Use telega-story-match-p to match a story.

Matches if story is sent by CHAT matching CHAT-TEMEX.
(contains REGEXP)
Matches if story's caption contains REGEXP.
Matches if story has been viewed.
Matches if story has video content.
Matches if story has photo content.

Some customizable options making use of Telega Match Expressions

  • User Option: telega-filter-default

    Temex to filter chats by default.

    Default value: main

  • User Option: telega-filters-custom

    Alist of custom filters in form (NAME . TEMEX). NAME can be an i18n string, such as "lngfilterstypegroups". This filters are displayed as filter buttons at the top of rootbuf.

    Default value:

    (("Main" . main) ("Important" . important)
     ("Online" and (not saved-messages) (user is-online))
     ("lng_filters_type_groups" type basicgroup supergroup)
     ("lng_filters_type_channels" type channel)
     ("lng_filters_type_no_archived" . archive))
  • User Option: telega-use-tracking-for

    Specifies Chat Temex for chats to be tracked with tracking.el. Make sure you have tracking.el loaded if this option is used. Only chats with corresponding opened chatbuf are tracked. Tracking notifications for telega buffers will use the `telega-tracking` face.

    Default value: nil

  • User Option: telega-rainbow-color-custom-for

    List of custom colors for chats. Each element is cons cell, where car is Chat Filter, and cdr is color.

    Default value: ((saved-messages))

  • User Option: telega-chat-group-messages-for

    Chat Filter for chats where to group messages by sender.

    Default value: (not (or saved-messages (type channel bot)))

  • User Option: telega-chat-show-deleted-messages-for

    Chat Filter for chats where to show deleted messages in chatbuf.

    Default value: nil

  • User Option: telega-root-view-grouping-alist

    Alist of chat temexes for "grouping" root view. Car is name of the chats group, cdr is a chat temex to match chats.

    Default value: (("Important" . important))

Chat Folders

Telegram has added a new feature that allows users to organise chats into Chat Folders.

Each folder can have unlimited number of pinned chats.

Before Telegram had support for Chat Folders, telega implemented custom chat label feature, resembling Chat Folders functionality. But now custom chat label feature is deprecated in favor to Chat Folders. Use M-x telega-folders-migrate-custom-labels RET to migrate your custom labels into Chat Folders.

F prefix in rootbuf is used to operate on Chat Folders:

F + (telega-folder-create)
Create new Telegram folder with name FOLDER-NAME.
F - (telega-folder-delete)
Delete Telegram folder with FOLDER-NAME. This won't delete any chat, just a folder.
F = (telega-folders-reorder)
Reorder Telegram folders to be in ORDERED-FOLDER-NAMES order.
F R (telega-folder-rename)
Assign new name and icon to the folder with FOLDER-NAME.
F I (telega-folder-set-icon)
For folder with FOLDER-NAME set new icon to NEW-ICON-NAME.
F a (telega-chat-add-to-folder)
Add CHAT to the Telegram folder named FOLDER-NAME. You can add chat to multiple folders.
F d (telega-chat-remove-from-folder)
Remove CHAT from the folder named FOLDER-NAME.

Customizable options for Chat Folders:

  • User Option: telega-root-view-grouping-folders

    Non-nil to add Chat Folders in the grouping root view. Could be one of prepend, append or nil.

    Default value: append

  • User Option: telega-folder-icons-alist

    Alist of symbols to be used as folder icons instead of telega-symbol-folder. See list of all available icon names in telega-folder-icon-names.

    Default value:

    (("All" . "💬") ("Unread" . "✅") ("Unmuted" . "🔔") ("Bots" . "🤖️")
     ("Channels" . "📢") ("Groups" . "👥") ("Private" . "👤")
     ("Setup" . "📋") ("Cat" . "🐱") ("Crown" . "👑") ("Favorite" . "⭐️")
     ("Flower" . "🌹") ("Game" . "🎮") ("Home" . "🏠") ("Love" . "❤️")
     ("Mask" . "🎭") ("Party" . "🍸") ("Sport" . "⚽️") ("Study" . "🎓")
     ("Trade" . "📊") ("Travel" . "🛫️") ("Work" . "💼") ("Airplane" . "✈️️")
     ("Book" . "📖") ("Like" . "👍") ("Money" . "💰") ("Note" . "🗒️"))
  • User Option: telega-chat-folders-insexp

    Inserter sexp for chat folders prefixing chat's title. While using this insexp telega-chat-folders is bound to the list of folder names to be inserted.

    Default value: telega-folders-insert-default

  • User Option: telega-chat-folders-exclude

    Exclude these folders from chat folders list to be displayed.

    Default value: ("Unread" "Personal")

  • User Option: telega-filter-custom-show-folders

    Non-nil to show telegram folders along the side with custom filters.

    Default value: t

Filtering chats

Chat Filters are used to match chats, same as regexps are used to match strings. Chat Filters uses S-exp notation similar to rx package for regexps. Consider Chat Filters as extremely powerful "Folders" functionality in official client.

Primitive Chat Filter is a specifier to match some property of the chat. Each primitive Chat Filter has name (elisp symbol) and corresponding function named telega--filter-<FILTER-NAME>. You can specify primitive Chat Filter in either way:

  2. ( <FILTER-NAME> <ARG1> [<ARG2> ...] )

Primitive Chat Filters are combined using and, or and not filters, forming final Chat Filter. So Chat Filter is a logical combination of other Chat Filters, down to primitive Chat Filters.

Chat Filter examples:

(return t)
Matches all chats
(or saved-messages (type channel bot))
Matches bots/channels chats or "Saved Messages" chat
(and unmuted (unread 10) (mention 1))
Matches unmuted chats with at least 10 unread messages and at least one message with unread mention

Matching is done using telega-chat-match-p function.

/ prefix in rootbuf is used for some useful filtering commands:

/ i (telega-filter-by-important)
Filter important chats.
/ o (telega-filter-by-online-status)
Filter private chats by its user online STATUS.
/ a (telega-filter-by-filter)
Interactively select a Chat filter to add to active filter.
/ e, / : (telega-filters-edit)
Edit and reapply filters list.
/ DEL, / d (telega-filters-pop-last)
Pop last N filters.
/ ! (telega-filters-negate)
Negate last filter. If C-u is specified, then negate whole active filter.
/ / (telega-filters-reset)
Reset active filter to the telega-filter-default.

For other chat filtering bindings see List of Chat Temexes

Sorting chats

It is possible to sort chats in rootbuf out of Telega built-in order. Sorting chats is done by some criteria. Built-in criterias are in telega-sort-criteria-alist. Do not insert criterias directly into telega-sort-criteria-alist, use define-telega-sorter instead.

\ prefix in rootbuf is used for sorting commands:

\ \ (telega-sort-reset)

Reset active sorter.

It is possible to add multiple criteria using telega-sort-reset with prefix argument C-u.

\ s, \ a (telega-sort-by-sorter)

Interactively add CRITERIA to active sorter. If prefix ARG is used, then add sort criteria, instead of overwriting currently active one.

Use this command to reset active sorter.

For other sorting keybindings see below.

Sorting criteria

unread-count, \ u (telega-sort-by-unread-count)
Sort chats by number of unread messages in chat.
title, \ t (telega-sort-by-title)

Sort chats alphabetically by chat title.

Thanks to

member-count, \ m (telega-sort-by-member-count)
Sort chats by number of members in the chat.
online-members, \ o (telega-sort-by-online-members)
Sort chats by number of online members.
join-date, \ j (telega-sort-by-join-date)
Sort chats by join date. Last joined chats goes first.
chatbuf-recency, \ v (telega-sort-by-chatbuf-recency)
Sort chats by chatbuf recency. Recently used chats goes first.
Sort chats by visibility in other window in DWIM style. See
Sort chats by nearby distance to me. See
Sort by number of chats in common. See
Sort by last seen activity. For private chats user's last seen date is taken. For other chats date of the last message is taken.

Customizable options making use of sorting criteria

  • User Option: telega-chat-completing-sort-criteria

    Criteria to sort chats in telega-completing-read-chat.

    Default value: (chatbuf-visibility chatbuf-recency)

  • User Option: telega-chat-switch-buffer-sort-criteria

    Criteria to sort open chats when switching with telega-switch-buffer.

    Default value: chatbuf-recency

Chat buffer

Chatbuf is a Emacs buffer showing some Telegram chat. Chatbuf consists of a list of chat messages and an input for your messages to send. Press i, <down-mouse-3> <describe> (telega-describe-message) to get detailed description of the message at point.

visual-line-mode and visual-fill-column-mode are enabled by default in chat buffers, to word-wrap and fill message content. You might want to tune visual-fill-column-extra-text-width custom option if message's header does not fit into telega-chat-fill-column for some reason.

Avoid setting truncate-lines to non-nil value in the chatbufs (and using modes that does so), unless you know what you are doing, you will get confusing results.

Note for RTL users: unlike rootbuf, chatbufs disables bidirectional display reordering by default, so RTL text will look reversed in chatbufs. To enable bidi in chatbufs customize your telega-chat-bidi-display-reordering user option.

Important customizable options:

  • User Option: telega-chat-fill-column

    Column to fill chat messages to.

    Default value: 70

  • User Option: telega-chat-use-date-breaks

    Non-nil to insert date break bar in chat buffers. Date break is a special mark separating two messages received on different days. Such as:

    MSG1                              <--- msg sent on 27dec
    -------(28 December 2020)------   <--- date break
    MSG2                              <--- msg sent on 28dec

    Default value: t

Chatbuf fast navigation

M-g prefix in chatbuf is used to jump across various chat messages:

M-g ! (telega-chatbuf-next-unread-reaction)
Goto next unread reaction in chat buffer.
M-g d (telega-chatbuf-goto-date)
Goto last message before DATE timestamp.
M-g < (telega-chatbuf-history-beginning)
Jump to the first message in the chat history.
M-g r, M-g > (telega-chatbuf-read-all)
Jump to the last message in the chat history and mark all messages as read.
M-g @, M-g m (telega-chatbuf-next-unread-mention)
Goto next unread mention in chat buffer. If there is no unread mentions, then search for last mention starting from message at point.
M-g u (telega-chatbuf-next-unread)
Goto next unread message in the chatbuf.
M-g ^, M-g P (telega-chatbuf-goto-pinned-message)
Goto next pinned message for the chatbuffer.
M-g x (telega-chatbuf-goto-pop-message)
Pop message from telega-chatbuf--messages-pop-ring and goto it.
M-g * (telega-chatbuf-next-favorite)
Goto next favorite message. See Favorite Messages for details.
M-g v (telega-chatbuf-goto-video-chat)
Goto video chat associated with the chat. See Video Chats for details.
M-g s (telega-chatbuf-inplace-search)
Search backward in the chatbuf. If C-u is given, then search forward instead. FROM-MSG specifies message from where to start searching. For non-interactive use cases only.
M-g n (telega-chatbuf-inplace-search-next)
Continue inplace searching with last search.
M-g p (telega-chatbuf-inplace-search-prev)
Continue searching.

Sending ordinary messages

Type a text in the chatbuf input and press RET to send the message. To insert newline in the middle of the input use ordinary C-j Emacs command. To preview resulting message before sending it, press M-RET (telega-chatbuf-input-preview).

You can apply markup to the input when sending message. This is controlled by number of C-u pressed before RET and value of the:

  • User Option: telega-chat-input-markups

    Markups to apply when sending input with RET. Each index in the list corresponds to the number of C-u supplied before RET, i.e. first element is used for ordinary RET, second is used for C-u RET, and third is for C-u C-u RET and so on. Supported markups are defined in the telega-chat-markup-functions.

    "markdown1" syntax is not recommended, it always treats underscore as starting point of italic emphasize even inside URLs, thats why "markdown1" is not included into telega-chat-input-markups by default.

    Default value: (nil "markdown2" "org")

Markup syntax table:

  markdown2 org markdown1
bold text **bold text** *bold text* *bold text*
italic text __italic text__ /italic text/ _italic text_
underline text UNSUPPORTED _underline text_ UNSUPPORTED
strike through ~~strike through~~ +strike through+ UNSUPPORTED
  ¦¦spoiler¦¦ ¦¦spoiler¦¦ UNSUPPORTED
inlined code `inlined code` ~inlined code~ `inlined code`
pre text ```pre text``` =pre text= UNSUPPORTED
text [text](http://www.url) [[http://www.url][text]] [text](http://www.url)
name [name](tg://user?id=<USER-ID>) [[tg://user?id=<USER-ID>][name]] [name](tg://user?id=<USER-ID>)

There is also "markdown1" syntax to insert multiline code blocks of specified languge:

first line of multiline preformatted code
second line
last line```

"markdown2" backquotes syntax to insert multiline code blocks is controlled by:

  • User Option: telega-markdown2-backquotes-as-precode

    Non-nil for markdown1 style syntax for ```. Non-nil activates syntax: ```<language-name> (not displayed) code code ```

    Default value: known

Org syntax for code blocks is NOT YET supported:

#+begin_src <language-name>
code line
next code line

Also, you can intermix various markups, using C-c C-a markup RET command.

Important customizable options:

  • User Option: telega-chat-input-markups

    Markups to apply when sending input with RET.

    Default value: (nil "markdown2" "org")

  • User Option: telega-chat-send-message-on-ret

    Customization for RET behaviour.

    Default value: always

  • User Option: telega-chat-markup-functions

    List of markups to use on C-c C-a markup RET.

    Default value:

    (("markdown2" . telega-markup-markdown2-fmt)
     ("org" . telega-markup-org-fmt) ("html" . telega-markup-html-fmt)
     ("markdown1" . telega-markup-markdown1-fmt))

Attaching media

You can attach various media into chatbuf input, using next bindings:

C-c C-a (telega-chatbuf-attach)
Attach something to the chatbuf input. C-u is passed directly to the attachment function. See telega-chat-attach-commands for available attachment types.
C-c C-f (telega-chatbuf-attach-media)
Attach FILENAME as media, detecting media type by FILENAME extension. If C-u is given, then attach as file. If AS-FILE-P is preview, then attach as file with preview. FILENAME must be a photo in this case.
C-c C-v (telega-chatbuf-attach-clipboard)
Attach clipboard image to the chatbuf as photo. If C-u is given, then attach clipboard as document.
C-c C-e (telega-chabuf-input-formatting-set)
Attach formatting to the region in the chatbuf input.

Text following attached media will be a media caption.

Attachment types to attach with C-c C-a (telega-chatbuf-attach) defined in telega-chat-attach-commands user option:

Attach FILENAME as photo to the chatbuf input.
Attach FILENAME as video to the chatbuf input.
Attach FILENAME as audio to the chatbuf input.
Attach photo marked with spoiler.
Attach video marked with spoiler.
Attach a file as self destructing photo. This attachment can be used only in private chats.
Attach a file as self destructing video. This attachment can be used only in private chats.
Attach a (circled) video note to the chatbuf input. If C-u is given, then attach existing file as video-note. Otherwise record video note inplace. telega-vvnote-video-record-args is used as arguments to ffmpeg to record video notes.
Attach a voice note to the chatbuf input. If C-u is given, then attach existing file as voice-note. Otherwise record voice note inplace. telega-vvnote-voice-cmd is used to record voice notes.
Attach FILENAME as document to the chatbuf input. If CONTENT-TYPE-DETECT-P is specified, then FILENAME's content type is automatically detected.
Attach GIF-FILE as animation to the chatbuf input.
Attach location to the chatbuf input. If C-u is given, then attach live location.
Attach poll to the chatbuf input. Can be used only in group chats. QUESTION - Title of the poll. ANONYMOUS-P - Non-nil to create anonymous poll. ALLOW-MULTIPLE-ANSWERS-P - Non-nil to allow multiple answers. OPTIONS - List of strings representing poll options.
Attach CONTACT user to the chatbuf input.
Attach a sticker. If C-u is given, then attach recent or favorite sticker. Otherwise choose a sticker from installed sticker sets.
Attach an animation. If C-u is given, then attach animation from a file, otherwise choose animation from list of saved animations.
Attach random dice roll message.
Attach screenshot to the chatbuf input. If numeric prefix arg N is given, then take screenshot in N seconds. If C-u is given, then take screenshot of the screen area. Multiple C-u increases delay before taking screenshot of the area. Uses telega-screenshot-function to take a screenshot.
Attach clipboard image to the chatbuf as photo. If C-u is given, then attach clipboard as document.
Attach MARKUP-TEXT using MARKUP-NAME into chatbuf. Using this type of attachment it is possible to intermix multiple markups in the chatbuf input. Markups are defined in the telega-chat-markup-functions user option.
Interactively attach new chat theme to the chat buffer.
Mark content as scheduled. Send following message at TIMESTAMP. If C-u is given and chat is private and online status of the corresponding user is known, then send message when user gets online.
Toggle disable-notification chat option for the subsequent chatbuf input. Use this attachment to disable/enable notification on the receiver side.
Toggle disable-notification chat option for the subsequent chatbuf input. Use this attachment to disable/enable notification on the receiver side.
Change telega-chat-send-link-preview-options for the following messages.
Set sender for the following message.
Interactively attach a custom emoji.
Attach explicit messages delimiter.
Interactively attach a code of the LANGUAGE into chatbuf input. For non-interactive code attach, use telega-mnz--chatbuf-attach-internal.

Special attachment types are disable-webpage-preview, scheduled, disable-notification or enable-notification. They do not attach anything, but changes options on how to send the message. Use scheduled to schedule messages, disable-notification or enable-notification to trigger notification on receiver side and disable-webpage-preview to disable rich web page previews for URLs in the message text.

Customizable options for attaching media:

  • User Option: telega-chat-upload-attaches-ahead

    Non-nil to upload attachments ahead, before message actually sent. Having this non-nil "speedups" uploading, it is like files uploads instantly.

    Default value: t

  • User Option: telega-chat-markup-functions

    List of markups to use on C-c C-a markup RET.

    Default value:

    (("markdown2" . telega-markup-markdown2-fmt)
     ("org" . telega-markup-org-fmt) ("html" . telega-markup-html-fmt)
     ("markdown1" . telega-markup-markdown1-fmt))

Replying to a message

To reply to a message, put point on the message you want to reply to and press r, <down-mouse-3> <reply> (telega-msg-reply).

Selected region at reply time will be a reply quote.

To cancel reply use C-c C-k, C-M-c, M-ESC (telega-chatbuf-cancel-dwim) binding. C-u prefix to this command will clear chatbuf's input along with canceling reply.

Editing previously sent message

To edit a given message, put point on the message you want to edit and press e, <down-mouse-3> <edit> (telega-msg-edit).

To cancel editing use the same command as for canceling reply to a message.

To edit your previously sent message press M-p (telega-chatbuf-edit-prev).

It is possible to edit a message using markup syntax. e, <down-mouse-3> <edit> (telega-msg-edit) accepts C-u prefix to specify markup syntax to be used for editing.

Forwarding messages

To forward a message, put cursor under the message which you want to forward and press f, <down-mouse-3> <forward> (telega-msg-forward-marked-or-at-point) and then select a Chat to forward a message to. To forward multiple messages at once, mark messages with the m, <down-mouse-3> <unmark>, <down-mouse-3> <mark> (telega-msg-mark-toggle) and then press f, <down-mouse-3> <forward> (telega-msg-forward-marked-or-at-point) on one of the messages.

There are few options how you can affect the way a message is forwarded:

  1. C-u f to forward a message copy, it will look like you sent a message.
  2. C-u C-u f To forward a message copy deleting or replacing caption it has. Use this to forward media message with your own caption.

Deleting messages

To delete a message, put cursor under the message you want to delete and press DEL, d, <down-mouse-3> <delete> (telega-msg-delete-marked-or-at-point).

As with forwarding messages, you can mark multiple messages to delete with m, <down-mouse-3> <unmark>, <down-mouse-3> <mark> (telega-msg-mark-toggle).

Also, you can ban/report message sender (and delete all messages from this sender in the chat) with B, <down-mouse-3> <ban-sender> (telega-msg-ban-sender) when cursor is under the message.

telega can keep deleted messages visible until chatbuf is killed. This is controlled using custom variable:

  • User Option: telega-chat-show-deleted-messages-for

    Chat Filter for chats where to show deleted messages in chatbuf.

    Default value: nil

For example, to show deleted messages in all chats except for "Saved Messages", use next:

(setq telega-chat-show-deleted-messages-for '(not saved-messages))

Scheduling messages and reminders

To schedule a message, press C-c C-a scheduled RET, select date and time to schedule message at, type text of a message and send it as always.

To reschedule a message, first list all scheduled messages in the chat with C-c / scheduled RET, then press e, <down-mouse-3> <edit> (telega-msg-edit) on the message you want to reschedule, remove previous "Schedule" attachment and add a new one at the beginning.

Message scheduled in "Saved Messages" chat is called reminder.

Whenever a scheduled message or reminder is sent, you get a special notification marked with a 📅, so you don't get caught off-guard by messages you planned in the past.

You can navigate your previous chatbuf input using commands:

M-p (telega-chatbuf-edit-prev)
Edit previously sent message. MARKUP-ARG could be used to select markup to edit message. See telega-msg-edit for details.
M-n (telega-chatbuf-edit-next)
Edit message sent next to currently editing. MARKUP-ARG could be used to select markup to edit message. See telega-msg-edit for details.
M-r (telega-chatbuf-input-search)

Search for REGEX in chat input history.

While searching input, you can use M-p (telega-chatbuf--input-search-input-prev) and M-n (telega-chatbuf--input-search-input-next) to cycle chatbuf input ring.

Completing input in chatbuf

Powerful company-mode can be used to complete input in the chatbuf with TAB (telega-chatbuf-complete-or-next-link).

telega provides few company backends, such as:


Complete emojis via :<emoji>: syntax. Completion is done using predefined set of emojis.

Customizable Options:

  • User Option: telega-company-emoji-fuzzy-match

    Non-nil to use fuzzy prefix matching. For example without fuzzy matches, prefix :jo will match only :joy:, :joy-cat: and :joystick:. With fuzzy matching enabled it will match also :flag-jo: and :black-jocker:.

    Default value: t

Same as telega-company-emoji, but uses Telegram cloud for the emojis completion.
Complete user mentions via @<username> syntax. Here is the screenshot, showing use of this backend: completing-usernames.jpg

Customizable options:

  • User Option: telega-company-username-prefer-name

    Preferred formatting argument to the telega-user-title to complete user. Frist giving non-nil result will be used.

    Default value: (username first-name last-name)

  • User Option: telega-company-username-show-avatars

    Non-nil to show avatars in the company annotation.

    Default value: nil

  • User Option: telega-company-username-markup

    Markup to use for usernames completion.

    Default value: nil

Complete common hashtags via #<hashtag> syntax.
Complete bot commands via /<botcmd> syntax. This backend does not complete if /<botcmd> syntax is used in the middle of the chatbuf input, only if /<botcmd> starts chatbuf input.
Complete language name for code blocks via ``` syntax.

List of company backends to be used for user input completion is controlled by:

  • User Option: telega-company-backends

    Company backends to use in chat buffers. Set to nil to disable company completions in chat buffers.

    Default value:

    (telega-company-emoji telega-company-telegram-emoji
                          telega-company-username telega-company-hashtag

You can use completion without enabling company-mode in the chat buffers, by explicitly pressing TAB (telega-chatbuf-complete-or-next-link) to perform completion at point.

On the other hand, company-mode detects input context and pops up completion candidates if completion at point is available. To enable company-mode in chat buffers use:

(add-hook 'telega-chat-mode-hook 'company-mode)

Consider also using company-posframe Emacs package (in MELPA), so chatbuf's contents remain untouched when completion menu pops above the chatbuf prompt.

If you don't like company-posframe, consider option:

  • User Option: telega-company-tooltip-always-below

    Non-nil to show company tooltip always below the point. Done by recentering point in the chatbuf.

    Default value: t

Using capf for input completions

It is possible to use standard Emacs capf (completion at point) functionality to perform completions in the chatbuf. You still need company.el package installed and loaded because telega uses it as engine.

capf is used by default if company-mode is disabled in the chatbuf, so to enable capf completions setup could look like:

(defun my-telega-chat-mode ()
  (require 'company)
  (add-hook 'completion-at-point-functions
            #'telega-chatbuf-complete-at-point nil 'local)

(add-hook 'telega-chat-mode-hook 'my-telega-chat-mode)

capf functionality is very limited comparing to company-mode completions, however, some users might still prefer capf.

Sending messages via bots

If chatbuf input starts with @<botname> <query> and mentioned bot support inline mode, then pressing TAB (telega-chatbuf-complete-or-next-link) will pop a special buffer with the inline results to the bot inline <query>, you can use these results to send a message via bot. Some useful bots with inline mode support are:

  • @gif To search and send animations
  • @pic, @bing To search and send pictures
  • @vid To search and send videos on YouTube
  • @foursquare - To find and send places around the world
  • etc

To find out is some bot supports inline mode or not, enter @<botname><SPC> in chatbuf input and press TAB (telega-chatbuf-complete-or-next-link). If momentary help is displayed, then this bot supports inline mode.

Customizable options for inline bots:

  • User Option: telega-known-inline-bots

    List of known bots for everyday use.

    Default value: ("@gif" "@youtube" "@pic")

  • User Option: telega-inline-query-window-select

    Non-nil to select window with inline query results.

    Default value: t

Filtering chat messages a.k.a. Shared Media

Message filtering means to show only some messages matching filter. Available message filters are: scheduled, search, by-sender, hashtag, topic, tag, photo, photo-video, url, doc, file, gif, audio, video, voice-note, video-note, voice-video-note, chat-photo, mention, unread-mention, unread-reaction, failed-to-send, pinned

Chatbuf uses next bindings for message filtering:

C-c / (telega-chatbuf-filter)
Enable chat message filtering MSG-FILTER.
C-c C-c (telega-chatbuf-filter-cancel)
Cancel current messages filtering. If point is at some message, then keep point on this message after reseting. If C-u is given, then cancel thread filtering as well.
C-c C-r (telega-chatbuf-inplace-search-query)
Inplace search backward for the QUERY. If C-u is given, search for the messages containing QUERY sent by specified sender. To navigate across searching results use M-g p and M-g n bindings.
C-c C-s (telega-chatbuf-inplace-search-query-forward)
Inplace search forward for the QUERY. If C-u is given, search for the messages containing QUERY sent by specified sender.

Inplace searching in text messages or media captions

Use C-c C-r (telega-chatbuf-inplace-search-query) or C-c C-s (telega-chatbuf-inplace-search-query-forward) to start searching while keeping history without applied filter, i.e. you can see surrounding messages.

Use M-g s (telega-chatbuf-inplace-search) or M-g n (telega-chatbuf-inplace-search-next) to continue searching.

Opening files using external programs

Document messages in Telegram has attached file in the message. By default telega opens that files inside Emacs using find-file function. Sometimes that is not desirable behaviour and you might want to open some files in external application. You can use org-open-file function for this. Behaviour is controlled by:

  • User Option: telega-open-file-function

    Function to use to open files associated with messages. Called with single argument - filename to open. Could be used to open files in external programs. Set it to org-open-file to use Org mode to open files.

    Default value: find-file

Setup to open some files in external applications might look like:

;; ("\\.pdf\\'" . default) is already member in `org-file-apps'
;; Use "xdg-open" to open files by default
(setcdr (assq t org-file-apps-gnu) 'browse-url-xdg-open)

(setq telega-open-file-function 'org-open-file)

On MacOS use browse-url-default-macosx-browser instead of browse-url-xdg-open.

If you also want to open non-document messages as file using telega-open-file-function consider:

  • User Option: telega-open-message-as-file

    List of message types to open as file using telega-open-file-function. Supported message types are: photo, video, audio, video-note, voice-note, animation. Document messages are always opens as file.

    Default value: nil

Another alternative to open some files using external programs is to use nice openwith Emacs package available in MELPA.

Browse URL with custom function

Also, you can open urls using custom functions:

  • User Option: telega-browse-url-alist

    Alist of custom url browse functions. Each element is in form: (PREDICATE-OR-REGEX . FUNCTION).

    Default value: nil

For example, to play youtube videos using mpv player, add this to config:

(defun my-watch-in-mpv (url)
  (async-shell-command (format "mpv -v %S" url)))

(add-to-list 'telega-browse-url-alist
             '("https?://\\(www\\.\\)?" . my-watch-in-mpv))
(add-to-list 'telega-browse-url-alist
             '("https?://" . my-watch-in-mpv))

Client side messages ignoring

In official telegram clients all messages in group chats are displayed even if message has been sent by blocked sender (user or chat). telega has client side message ignoring feature implemented. Ignoring messages can be done by adding function into telega-msg-ignore-predicates. This function must accept single argument - message, and return non-nil if messages should be ignored. You can use telega-match-gen-predicate to generate message predicates out of Telega Match Expressions. For example, to ignore messages from particular user with id=12345 you could add next code:

(defun my-telega-ignore-12345-user (msg)
  (telega-msg-match-p msg '(sender (ids 12345))))

(add-hook 'telega-msg-ignore-predicates 'my-telega-ignore-12345-user)

Or to ignore messages from blocked senders (users or chats), just add:

(add-hook 'telega-msg-ignore-predicates
          (telega-match-gen-predicate 'msg '(sender is-blocked)))

To view recently ignored messages use M-x telega-ignored-messages RET command.

Favorite messages

Any message in any chat can be marked with as favorite. Favorite messages are labeled with:

  • User Option: telega-symbol-favorite

    Symbol to use for favorite messages, bookmarks.

    Default value: "🔖"

To toggle message at point being favorite, press *, <down-mouse-3> <rm-favorite>, <down-mouse-3> <add-favorite> (telega-msg-favorite-toggle).

To jump to next favorite message in the chat buffer press M-g * (telega-chatbuf-next-favorite).

To view all favorite messages in all chats, enable "Favorite Messages" Root View, by pressing v * (telega-view-favorite-messages) in the root buffer.

Media Controls for media messages

Some media messages that are playing inside Emacs (such as "audio", "voice-note" or "video-note" messages) will have additional media control buttons to control media playback parameters:

[⏪] [⏩] [2×] [Stop] 

For fast access to media controls you can you next bindings:

0 (telega-msg--vvnote-stop)
Stop playing media message.
<, , (telega-msg--vvnote-rewind-10-backward)
Rewind 10 seconds backward.
>, . (telega-msg--vvnote-rewind-10-forward)
Rewind 10 seconds forward.
x (telega-msg--vvnote-play-speed-toggle)
Toggle playback speed for the media message. Only two modes are available: normal speed and x2 speed.
9, 8, 7, 6, 5, 4, 3, 2, 1 (telega-msg--vvnote-rewind-part)
Rewind to the N's 10 part of the message duration. I.e. if you press 7, then you will jump to 70% of the message duration.

To play/pause media messages use RET. Also, l, <down-mouse-3> <copy-link> (telega-msg-copy-link) command supports linking to the currently playing (or paused at) moment.

To reference a given moment in a media message (or in a reply to media message) use [HH:]MM:SS] syntax in the message's body/caption. Such timestamp marks will be automatically emphasised with a media timestamp text entity.

Forums and Topics

Telegram allows creating forums with multiple distinct topics. Use M-x telega-chat-create RET forum RET to create forums.

NOTE: forums and topics are not fully supported by telega at moment.

Video Chats

TODO: write me

Stickers / Animations

To display stickers telega uses dwebp utility to convert .webp stickers into png images that can be displayed by Emacs. dwebp utility is available on almost every system inside webp package.

Important customizable options for stickers:

  • User Option: telega-sticker-size

    Size for the sticker. car is height in chars to use. cdr is maximum width in chars to use.

    Default value: (4 . 24)

  • User Option: telega-sticker-set-download

    Non-nil to automatically download known sticker sets.

    Default value: nil

  • User Option: telega-sticker-favorite-background

    Background color for the favorite stickers. Can be nil, in this case favorite stickers are not outlined.

    Default value: "cornflower blue"

To play short animations inside Emacs telega uses ffmpeg utility. Playing animations inside Emacs is a bit heavy process, so be careful in choosing value for the telega-animation-play-inline.

Important customizable options for animations:

  • User Option: telega-animation-height

    Height in chars for animations.

    Default value: 5

  • User Option: telega-animation-play-inline

    Non-nil to play animation inside telega. If number, then play animation inline only if animation is shorter then this number of seconds.

    Default value: 10

  • User Option: telega-animation-download-saved

    Non-nil to automatically download saved animations.

    Default value: nil

Animated stickers

telega supports animated stickers using tgs2png utility from

Once tgs2png tool is installed into exec-path (check value for telega-sticker-animated-play after telega is started), you can play animated stickers by pressing RET on sticker.

Also telega-autoplay-mode can be used, to automatically animate messages containing animated stickers.

Favorite and recently used stickers

To attach your favorite or rencetly used sticker use C-u before C-c C-a sticker RET. Background for favorite stickers are filled with color:

  • User Option: telega-sticker-favorite-background

    Background color for the favorite stickers. Can be nil, in this case favorite stickers are not outlined.

    Default value: "cornflower blue"

To toggle sticker being favorite, press *, f (telega-sticker-toggle-favorite) while point is under sticker in the *Telega Sticker Set* buffer.

Or you can press S, <down-mouse-3> <save> (telega-msg-save) on the sticker message to add that sticker to the favorite stickers list.


There are multiple methods you can use to attach an animation:

  • C-c C-a animation RET to attach animation from the Saved Animations list.
  • C-c C-a gif RET to attach animation from a gif or mp4 file.
  • via @gif bot

To play animation message press RET on the message. Also, telega-autoplay-mode can be used to automatically play animation messages.

To explicitly add animation to Saved Animations list, press S, <down-mouse-3> <save> (telega-msg-save) on the corresponding animation message.


Telegram added Stories feature on its 10th birthday.

Story is a media content that user or channel shares outside chat contents. By default active and pinned stories are shown in a chatbuf's footer. This behaviour is controlled by custom options:

  • User Option: telega-story-show-active-stories-for

    Show active stories in the chatbuf's footer for chats matching this temex. If temex returns a number then limit number of shown active stories.

    Default value: (return 10)

  • User Option: telega-story-show-pinned-stories-for

    Show pinned stories in the chatbuf's footer for chats matching this temex. If temex returns a number then limit number of shown pinned stories.

    Default value: (return 10)

telega can preload media content for stories from users or channels of your interest. This is controlled by custom option:

  • User Option: telega-story-preload-for

    Preload stories media files for chats matching this temex.

    Default value: (user is-close-friend)

Stories can be matched using Telega Match Expressions.

Multiple accounts

telega support multiple accounts, however only single account can be active, i.e. you can't run account simultaneously, but you can switch between accounts. Notifications won't work for inactive accounts.

To switch accounts use a (telega-account-switch) from prefix map. To setup multiple accounts use:

  • User Option: telega-accounts

    List of the accounts to be used by telega. Each element is a list in form: (ACCOUNT-NAME CUSTOM-VAR1 VAL1 CUSTOM-VAR2 VAL2 …). At least telega-database-dir should be customized for each account.

    Default value: nil

    For example:

    (setq telega-accounts (list
      (list "zevlg" 'telega-database-dir telega-database-dir)
      (list "Evgen2" 'telega-database-dir
        (expand-file-name "evgen2" telega-database-dir))))

    Each account can have its own configuration using custom variables specified in account setup, and only telega-database-dir must be different for different accounts.

    Uninitialized account from telega-accounts will be initialized when you switch to it for the first time.

Minor Modes

telega ships with various minor modes you might consider to use.

Notifications for incoming messages

telega.el can notify you about incoming messages and calls via D-Bus notifications, however notifications are disabled by default.

Enable it with (telega-notifications-mode 1) or at telega load time:

(add-hook 'telega-load-hook 'telega-notifications-mode)

Message is triggered for messages matching:

  • User Option: telega-notifications-msg-temex

    Message temex to match messages that needs to be notified.

    Default value: (call telega-notifications-msg-notify-p)

You can use this option for custom notifications. For example to trigger notification for messages containing "keyword" (in addition to default behaviour) you can set telega-notifications-msg-temex to (or (call telega-notifications-msg-notify-p) (contains "keyword"))

By default notification triggers if telega-notifications-msg-notify-p predicate returns non-nil. It returns non-nil if next conditions are satisfied.

Do NOT pop notification if:

  1. Me is not member of the group chat, see
  2. Message is ignored by client side messages ignoring
  3. Chat is muted and message does not contain unread mention or mention notification is disabled for the chat
  4. Message already has been read (see telega-msg-seen-p)
  5. Message is older than 1 min (to avoid popping up messages on laptop wakeup)
  6. Message is currently observable in a chatbuf, i.e. chatbuf must be selected and focused.

To view recent notifications use M-x telega-notifications-history RET command.

See also Notifications using alert.el


Global minor mode to automatically adjust telega-root-fill-column to the width of the window displaying rootbuf.

telega-root-auto-fill-mode is enabled by default.


Minor mode to automatically adjust telega-chat-fill-column to the width of the window displaying chatbuf.

telega-chat-auto-fill-mode is enabled by default.


Global minor mode to display telega status in modeline.

Enable with (telega-mode-line-mode 1) or at telega load time:

(add-hook 'telega-load-hook 'telega-mode-line-mode)

Customizable options:

  • User Option: telega-mode-line-string-format

    Format in mode-line-format for telega-mode-line-string.

    Default value:

    ("   " (:eval (telega-mode-line-icon))
     (:eval (car (telega-account-current)))
     (:eval (telega-mode-line-online-status))
     (:eval (when telega-use-tracking-for (telega-mode-line-tracking)))
     (:eval (telega-mode-line-unread-unmuted))
     (:eval (telega-mode-line-mentions 'messages))
     (:eval (telega-mode-line-active-video-chats)))


Global minor mode to display telega status in system tray. This mode requires appindicator support in the telega-server. To add appindicator support to telega-server, please install libappindicator3-dev or libayatana-appindicator3-dev system package and rebuild telega-server with {{{kbd(M-x telega-server-build RET}}}.

Screenshot of system tray with enabled telega appindicator: screen-appindicator.png

Enable with (telega-appindicator-mode 1) or at telega load time:

(add-hook 'telega-load-hook 'telega-appindicator-mode)

Customizable options:

  • User Option: telega-appindicator-use-label

    Non-nil to add text labels to the icon. Otherwise use just icon to show info. labels are not supported by XEMBED based system trays, such as exwm-systemtray or polybar.

    Default value: nil

  • User Option: telega-appindicator-icon-colors

    Colors to use for offline/online appindicator icon. Alist with offline, online or connecting as key, and value in form (CIRCLE-COLOR TRIANGLE-COLOR ONLINE-CIRCLE-COLOR).

    Default value:

    ((offline "white" "black" nil) (online "#7739aa" "white" "#00ff00")
     (connecting "gray" "white" "white"))
  • User Option: telega-appindicator-show-account-name

    Non-nil to show current account name in appindicator label. Applied only if telega-appindicator-use-label is non-nil.

    Default value: t

  • User Option: telega-appindicator-show-mentions

    Non-nil to show number of mentions in appindicator label. Applied only if telega-appindicator-use-label is non-nil.

    Default value: t

  • User Option: telega-appindicator-labels

    List of number labels to use for the number of unread unmuted chats. Use this labels instead of plain number. Set to nil to use plain number.

    Default value:

    ("❶" "❷" "❸" "❹" "❺" "❻" "❼" "❽" "❾" "❿" "⓫" "⓬" "⓭" "⓮" "⓯" "⓰" "⓱"
     "⓲" "⓳" "⓴")


Global minor mode to automatically open content for incoming messages. Message automatically opens if it matches against telega-autoplay-msg-temex Message Temex and message's content is fully observable.

Enable with (telega-autoplay-mode 1) or at telega load time:

(add-hook 'telega-load-hook 'telega-autoplay-mode)

Customizable options:

  • User Option: telega-autoplay-msg-temex

    Message Temex for messages to automatically play content for.

    Default value: (type Animation Sticker AnimatedEmoji)

  • User Option: telega-autoplay-custom-emojis

    Non-nil to automatically play this number of custom emojis in the message.

    Default value: 10


Minor mode for chatbuf to squash messages into single one while nobody saw this.

Squashing mean adding contents of the new message to the previous message by editing contents of the previous message.

New message in a chat is squashed into your previous message only if all next conditions are met:

  1. Last message in chat is sent by you
  2. Nobody seen your last message
  3. Last and new message are both text messages
  4. Last message can be edited
  5. Last and new messages are not replying to any message
  6. Last message has no associated web-page
  7. New message has no messageSendOptions to avoid squashing scheduled messages or similar
  8. New message is sent within telega-squash-message-within-seconds seconds from last message


Major mode to view images in chatbuf. Same as image-mode, however has special bindings:

n (telega-image-next)
Show next image in chat.
p (telega-image-prev)
Show previous image in chat.

To view high resolution image in chatbuf with telega-image-mode press RET on the message with photo.


Minor mode to edit files from Telegram messages. In this mode C-x C-s will save file to Telegram cloud. To enable telega-edit-file-mode for files opened from message with RET, use:

(add-hook 'telega-open-file-hook 'telega-edit-file-mode)

While editing file press <menu-bar> <goto-message>, M-g t (telega-edit-file-goto-message) to go back to the file's message.

To switch between files opened from telega use e (telega-edit-file-switch-buffer) binding from the Telega prefix map.

To distinguish files opened from telega with ordinary files suffix is added to the buffer name. You can modify this suffix using user option:

  • User Option: telega-edit-file-buffer-name-function

    Function to return buffer name when telega-edit-file-mode is enabled. Function is called without arguments and should return a buffer name string. Inside a function you can use telega-edit-file-message<f> to get message associated with the file.

    Default value: telega-edit-file-buffer-name


jit-lock powered minor mode to highlight given regexp.

Similar to hi-lock, however supports jit-lock for highlighting dynamic content.


Emphasize telega patrons by drawing special elements (telega cat ears) above the patron's avatar, like: telega-patron-ava.png

In addition:

  • Display "Telega Patron Since: <date>" note in the patron's Chat/User description.
  • All Emacs Stories from telega patrons are automatically considered "Featured".

If you are already telega patron and not in the telega-patrons-alist list, please write me.

telega-patrons-mode is enabled by default.


telega-my-location is used by telega to calculate distance to me for location messages. Also, telega-my-location is used to search chats nearby me. So, having it set to correct value is essential. There is contrib/telega-live-location.el which uses geo.el to actualize telega-my-location, however it is not always possible to use it.

When telega-my-location-mode is enabled, your telega-my-location gets automatic update when you send location message into "Saved Messages" using mobile Telegram client.

Enable with (telega-my-location-mode 1) or at telega load time:

(add-hook 'telega-load-hook 'telega-my-location-mode)


Minor mode to display currently active live locations in the root buffer.

telega-active-locations-mode is enabled by default.

  • User Option: telega-active-locations-show-avatars

    Non-nil to show user avatars in chat buffer.

    Default value: nil

  • User Option: telega-active-locations-show-titles

    Non-nil to show sender/chat titles along the side with avatars.

    Default value: t


Minor mode to display currently active video chats in the root buffer. Also display number of active video chats in the modeline if telega-mode-line-mode is enabled.

telega-active-video-chats-mode is enabled by default.

Customizable options:

  • User Option: telega-active-video-chats-temex

    Chat Temex to match chat with active video chat.

    Default value: (and is-known (has-video-chat non-empty))


Minor mode to automatically recognize speech in a voice/video messages. Available only for the Telegram Premium users.

Enable with (telega-recognize-voice-message-mode 1) or at telega load time:

(add-hook 'telega-load-hook 'telega-recognize-voice-message-mode)

Customizable options:

  • User Option: telega-recognize-voice-message-temex

    Message Temex for messages to automatically recognize speech. Speech recognition is only applied to voice messages matching this Message Temex. Applied only if non-nil. For example, to recognize speech in a voice messages only in private chats, use (chat (type private)) Message Temex.

    Default value: nil


Minor chatbuf mode to automatically translate messages in the chat to your native language. Also translates chatbuf input from your native language to the chat's language.

Customizable options:

  • User Option: telega-auto-translate-probe-language-codes

    List of language codes to probe. Chat description is used to probe chat's language.

    Default value: nil

  • User Option: telega-translate-to-language-by-default

    Default language code for messages translation. If nil, then use language suggested by the server.

    Default value: nil

telega-auto-download-mode (WIP)

Global minor mode to automatically download media files. Auto-download settings depends on network type currently used by telega.

You can modify auto-download settings by changing network type with M-x telega-set-network-type RET command.

Enable auto-download with (telega-auto-download-mode 1) or at telega load time:

(add-hook 'telega-load-hook 'telega-auto-download-mode)

Customizable options:

  • User Option: telega-auto-download-settings-alist

    Alist with auto-download settings for different network types. car of the item is the network type symbol from telega-tdlib-network-type-alist, cdr is auto-download setting. Auto-download setting could be one of :disabled, :low, :medium or :high keyword denoting auto download preset or a plist with TDLib's autoDownloadSettings structure.

    Default value:

    ((roaming-mobile . :disabled) (mobile . :low) (wi-fi . :medium)
     (other . :high))


Mode to display close birthdays of the contacts.

telega-contact-birthdays-mode is enabled by default.

TODO telega-play-media-sequence-mode

Play media content in subsequent manner.


Mode to notify about VoIP call by playing sounds. telega-voip-sounds-mode is enabled by default. Disable it with:

(add-hook 'telega-load-hook (lambda () (telega-voip-sounds-mode -1)))

Contributed packages

contrib/ directory contains packages contributed to telega project.

telega-status-history.el – Global minore mode to save user's online status history

Saves online status history into telega-status-history-logs-dir directory.

telega-url-shorten.el – Makes urls look nicer

Minor mode for chatbuf to show shorter version for some URLs. For example, with telega-url-shorten-mode enabled in chatbuf, urls like:Душ

Will look like: telega-url-shorten.png

Can be enabled globally in all chats matching telega-url-shorten-mode-for chat temex (see below) with (global-telega-url-shorten-mode 1) or by adding:

(add-hook 'telega-load-hook 'global-telega-url-shorten-mode)

Depends on all-the-icons Emacs package.

Customizable options:

  • User Option: telega-url-shorten-use-images

    Non-nil to use images on graphics display.

    Default value: nil

  • User Option: telega-url-shorten-regexps Alist of patterns for URL shortening.

    To change :symbol or :svg-icon property for existing url shortening pattern use something like:

    (plist-put (cdr (assq '<LABEL> telega-url-shorten-regexps))
               :<PROP> <VALUE>)
  • User Option: telega-url-shorten-mode-for

    Chat filter for global-telega-url-shorten-mode. global-telega-url-shorten-mode enables urls shortening only for chats matching this chat filter.

    Default value: all

telega-alert.el – Notifications using alert.el

To enable notifications using alert.el use:

(telega-alert-mode 1)

Alerts for telega.el are fired with :mode 'telega-chat-mode value. You might use this to customize alert rules with alert-add-rule.

telega-dired-dwim.el – Attach files from dired in DWIM style

This package advises dired-do-copy to attach files into visible chatbuf.

In dired, mark files you want to attach and press C. If you have some chatbuf visible, marked files will be attached in that chatbuf.

telega-live-location.el – Manage live location in Telega using geo.el

Enable this mode with M-x global-telega-live-location-mode RET

This mode installs new live-geo-location chat attach type, use it with C-c C-a live-geo-location RET in the chatbuf.

This mode requires the geo.el library, available at

Take into account that using geo-simulate backend to fake geo location data is Telegram API ToS violation. See 1.4 in

telega-mnz.el – Highlight code blocks inside messages.

Global minor mode to highlight code blocks inside messages.

Can be enabled globally in all chats matching telega-mnz-mode-for (see below) chat temex with (global-telega-mnz-mode 1) or by adding:

(require 'telega-mnz)
(add-hook 'telega-load-hook 'global-telega-mnz-mode)

Optionally depends on language-detection Emacs package. If language-detection is available, then language could be detected automatically for code blocks without language explicitly specified. Install language-detection with M-x package-install RET language-detection RET

telega-mnz installs ' (telega-mnz-send-region-as-code) binding into telega prefix map to attach region as code to a chatbuf.

Also, telega-mnz installs code media attachment type, use it with C-c C-a code RET in chatbuf.

Customizable options:

  • User Option: telega-mnz-mode-for

    Chat temex for global-telega-mnz-mode. Global mnz mode enables telega-mnz-mode only for chats matching this chat temex.

    Default value: all

  • User Option: telega-mnz-entity-types

    List of entity types for which mnz performs highlighting.

    Default value: (textEntityTypePreCode)

  • User Option: telega-mnz-edit-code-block

    How to edit message containing mnz code blocks.

    Default value: query

  • User Option: telega-mnz-use-language-detection

    Non-nil to use language-detection for blocks without specified language. Could be also a number, meaning that language detection is done only for code larger then this number of chars.

    Default value: nil

  • User Option: telega-mnz-edit-display-buffer-action

    Action value when poping to code edit buffer. See docstring for display-buffer for the value meaning.

    Default value: ((display-buffer-below-selected))

telega-dashboard.el – Important telega chats in the Emacs dashboard

Display important telega chats in the Emacs dashboard. Enable it with:

(require 'telega-dashboard)
(add-to-list 'dashboard-items '(telega-chats . 5))

Screenshot of telega-dashboard in action: telega-dashboard.png

Customizable options:

  • User Option: telega-dashboard-chat-filter

    Chat Filter used to filter chats to display in the Emacs dashboard.

    Default value: (or mention (and unread unmuted))

  • User Option: telega-dashboard-chat-inserter

    Inserter for the chat button in the Emacs dashboard.

    Default value: telega-ins--chat-full

telega-emacs-stories.el – Display Emacs Stories in the dashboard

Emacs Stories: share your Emacs experience with other Emacs users.

Display recent Emacs Stories in the dashboard. Enable it with:

(require 'telega-emacs-stories)
(telega-emacs-stories-mode 1)
;; "Emacs Stories" rootview
(define-key telega-root-mode-map (kbd "v e") 'telega-view-emacs-stories)
;; Emacs Dashboard
(add-to-list 'dashboard-items '(telega-emacs-stories . 5))

Apart from dashboard, telega-emacs-stories provides "Emacs Stories" Root View. To enable this view execute M-x telega-view-emacs-stories RET in the root buffer.

If you see inappropriate content in some Emacs Story, please report this story by pressing ! (telega-emacs-stories-msg-report) on the story.

For best performance consider newest Emacs28 with :base_uri svg image property support.

Screenshots of telega-emacs-stories in action: emacs-stories-dashboard.png

And screenshot of "Emacs Stories" root view: emacs-stories-rootview.png

Customizable options:

  • User Option: telega-emacs-stories-show

    Show all or only unread stories.

    Default value: unread

  • User Option: telega-emacs-stories-height

    Height in chars for Emacs Stories buttons.

    Default value: 6

  • User Option: telega-emacs-stories-notify-if

    Pop notification on new story if stories chat matches this Chat Filter.

    Default value: (not unmuted)

  • User Option: telega-emacs-stories-preload-content

    Preload content when Emacs Story is inserted, so can be viewed instantly.

    Default value: t

  • User Option: telega-emacs-stories-root-view-count

    Number of Emacs Stories to show in "Emacs Stories" rootview.

    Default value: 12

  • User Option: telega-emacs-stories-root-view-keep-viewed

    Keep viewed stories in the "Emacs Stories" rootview. Non-nil to keep story in the root view after story is viewed.

    Default value: t

telega-transient.el – Transient (magit-like style) commands for telega

Use transient (magit-like style) commands in the telega. Enable it with:

(require 'telega-transient)
(telega-transient-mode 1)

Control keymaps for which to use transient with:

  • User Option: telega-transient-keymaps

    List of keymaps names to apply transient for.

    Default value:

    (telega-prefix-map telega-sort-map telega-filter-map
                       telega-describe-map telega-folder-map
                       telega-voip-map telega-root-fastnav-map
                       telega-root-view-map telega-chatbuf-fastnav-map)

telega-adblock.el – Block advertisement messages

Telegram channels often advertises another channels in annoying manner. Sometimes adverts has inappropriate content. This mode uses client side messages ignoring functionality to block such advert messages.

To enable advertisement blocking use:

(telega-adblock-mode 1)

Customizable options:

  • User Option: telega-adblock-for

    Chat Temex to match chats for which to apply adblock logic.

    Default value: (and (type channel) (not unmuted) (not verified))

  • User Option: telega-adblock-chat-order-if-last-message-ignored

    Custom chat order for chats with last message being ignored by adblock. Set to "1" to put chats with ignored last message to the bottom of the rootbuf.

    Default value: nil

  • User Option: telega-adblock-verbose

    Non-nil to show (in echo area) reason why message is ignored by adblock.

    Default value: nil

  • User Option: telega-adblock-max-distance

    Maximum string-distance for self-link. Used for heuristics to avoid blocking non-advert messages in some channels. Set it to less value if you see some advert messages not being blocked.

    Default value: 4

  • User Option: telega-adblock-same-link-count

    Number of links to the same resource. Used by telega-adblock-msg-multiple-same-links-p.

    Default value: 3

  • User Option: telega-adblock-block-msg-temex

    Message temex for telega-adblock-msg-by-temex-p predicate.

    Default value: nil

  • User Option: telega-adblock-allow-msg-temex

    Message's matching this temex will be allowed.

    Default value: (or is-reply-to-msg is-reply-to-story)

  • User Option: telega-adblock-predicates

    List of predicates to check message for advertisements. Each predicate accepts single argument - message. If any of predicates returns non-nil, then message contains advert.

    Default value:

    (telega-adblock-msg-by-temex-p telega-adblock-msg-forwarded-p

telega-channels-export.el – Export Telegam channels to OPML

Use M-x telega-channels-export RET to export public channels shown in the rootbuf (i.e. matching Active Chat Filter) into XML file of OPML format. Making it possible to import this file into any RSS reader that supports OPML.

Customizable options:

  • User Option: telega-channels-export-template

    URL template where single %s is substituteed with channel username. Use rsshub or rssbrdige (or whatever that supports Telegram) url.

    Default value: ""

telega-bridge-bot.el – Replace bridge bot user.

This package advises some telega functions to replace the message bridge bot (like @matrix_t2bot), to make it look like the user itself. Currently only works for matrix bridge bot, but can be extended to other bridges by adding more handlers to the telega-bridge-bot--counterparty-handler-plist .

Enable it with:

(require 'telega-bridge-bot)

and customize the telega-bridge-bot-bridge-info-plist to specify the relationship between the bridge bot and the chat.

For example, if you want to replace the bridge bot @matrix_t2bot in the Telegram chat @emacs_china, you can set the following:

(setq telega-bridge-bot-bridge-info-plist
      '(-1001773572820 ; id of the @emacs_china
        (420415423 ; id of the @matrix_t2bot
         ;; will fetch member info with this matrix room id
         (:type :matrix :chat-id "!"))))

If you want download avatar from matrix, you should also set telega-bridge-bot-matrix-access-token or set telega-bridge-bot-matrix-user then put the access token in .authinfo , the host should be and the user should be the same as telega-bridge-bot-matrix-user. This is required because only user in the room can access the member info.


Can't compile telega-server


Invalid TDLib version


[telega bug]

Q: I've got a lot of [telega bug] things in the rootbuf or chatbuf.

A: Set debug-on-error to non-nil and trigger the bug to get the backtrace buffer. Report this backtrace to github issues or to the telega.el Telegram Chat

Stickers are not shown

Q: Stickers are not fully shown, I see only outlines for some stickers, like on the screenshot: bad-stickers.jpg

A: If your Emacs does not have bultin WEBP format support. telega will use dwebp tool to convert stickers from WEBP format to the format supported by your Emacs. See Stickers / Animations for details. So, make sure dwebp tool is available on your machine.

Notifications does not work

Q: I've enabled telega-notifications-mode as described in the manual, but notifications still does not pop up.

A: Make sure your time is correct. Eval (telega-time-seconds) to get UTC time in your Emacs, it should be more or less the same as on