Add, list and complete tasks from Ulauncher, in any task list Evolution Data Server knows about: Google Tasks (through GNOME Online Accounts), CalDAV lists (Nextcloud, …) and local lists. The same lists show up in apps that use EDS, such as Evolution and Endeavour.
Due dates can be typed in English, French, German, Spanish or Italian, one or two of them at a time.
-
Ulauncher 5 (extension API 2)
-
Evolution Data Server and its GObject bindings. On Debian/Ubuntu:
sudo apt install evolution-data-server gir1.2-edataserver-1.2 gir1.2-ecal-2.0 gir1.2-ical-3.0 -
For Google Tasks: a Google account in Settings → Online Accounts, with Calendar enabled (task lists come with it).
In Ulauncher, open Preferences → Extensions → Add extension and paste:
https://github.com/lcharles/ulauncher-tasks
Ulauncher puts it in ~/.local/share/ulauncher/extensions/com.github.lcharles.ulauncher-tasks, the
"extension's folder" mentioned below.
| Type | To |
|---|---|
todo |
see your lists (last used first, with their open and overdue counts); Enter opens one |
todo #Courses |
see the open tasks of a list (lists with spaces: #Mes-tâches; #cou also works) |
todo #Courses milk |
add “milk” to it; you're back in the list, ready for the next item |
todo #Courses milk tomorrow :: semi-skimmed |
add with a due date and notes |
todo buy milk fri |
add, choosing the list from the results (last used first) |
todo today, todo next week |
tasks due then, across lists (today includes overdue ones) |
td, td milk |
the same, in the list you last added to |
todo # |
all lists, including excluded ones, and Refresh all lists from their servers |
Enter on a task marks it done, and Enter again undoes it. Alt+Enter copies its title.
Due dates understand things like tomorrow, fri, next monday, 14 oct, 14/10, in 3 days,
in the one or two languages chosen in the preferences:
| Language | Examples |
|---|---|
| English | tomorrow, fri, next monday, 14 oct, in 3 days |
| Français | demain, vendredi, lundi prochain, 14 octobre, dans 3 jours |
| Deutsch | morgen, Freitag, nächsten Montag, 14. Oktober, in 3 Tagen |
| Español | mañana, viernes, el lunes que viene, 14 de octubre, dentro de 3 días |
| Italiano | domani, venerdì, lunedì prossimo, 14 ottobre, tra 3 giorni |
Times are ignored: Google Tasks only stores a date.
New and completed tasks are saved in the background, so a slow server (Google uploads while saving) doesn't hold up Ulauncher. If a save fails, the next query shows it at the top.
- Tasks / Tasks (last list): the two keywords (
todo,td). - Excluded task lists: comma-separated names of lists to ignore (
todo #shows the names; Alt+Enter copies one). - Language and Second language: which languages due dates are typed in. Automatic follows your desktop's language (English if it isn't one of the five), and the second language defaults to English. When a word means different things in both, the first language wins.
- Date order: how to read
04/10: day first (DMY) or month first (MDY).
todo only shows "Loading…" or no lists. From the extension's folder, run:
/usr/bin/python3 tools/check_google_tasks.py
It checks Online Accounts, the task lists EDS sees, reading them, and the installed extension (started the way Ulauncher starts it, with a stack trace if it hangs). Use the system Python: conda or venv interpreters usually lack the GObject bindings. After installing or updating the extension, restart Ulauncher.
A change made on your phone or the web doesn't show yet. EDS syncs on its own every 30 minutes
or so. Refresh all lists from their servers at the bottom of todo # syncs now.
A Google list shows tasks that no longer exist on Google, even after a refresh. EDS only
asks Google for what changed since its last sync. If it hasn't synced a list for a long time
(months), Google may have forgotten the deletions in between, and EDS keeps the deleted tasks
forever. tools/show_tasks.py <word> shows what EDS holds for matching tasks. To make EDS
download one list again from scratch (nothing changes on Google, and the old copy is kept until
you delete it):
LIST='Courses' # the list's name, as shown by "todo"
LIST_UID=$(/usr/bin/python3 -c "
import sys, gi
gi.require_version('EDataServer', '1.2')
from gi.repository import EDataServer as E
r = E.SourceRegistry.new_sync(None)
print(next(s.get_uid() for s in r.list_sources(E.SOURCE_EXTENSION_TASK_LIST) if s.get_display_name() == sys.argv[1]))
" "$LIST")
DIR=~/.cache/evolution/tasks/$LIST_UID
ls -d "$DIR" || echo "no local copy found for $LIST"
systemctl --user stop evolution-calendar-factory # briefly stops calendar/task access for all apps
mv "$DIR" "$DIR.old"
systemctl --user start evolution-calendar-factoryThen use Refresh all lists from their servers (or wait for the next sync). Once the list looks
right, rm -rf "$DIR.old". To undo, stop the service, rm -rf "$DIR"; mv "$DIR.old" "$DIR", and
start it again. Don't name the variable UID: bash already uses it for your user id.
GPL-3.0-or-later. See LICENSE.


