Python interface (via AppleScript) to Cultured Code's excellent Things app.
pythings uses the PyObjC Python/Objective-C bridge for communication with Things.
Python 3.7 or later on OS X, plus the ScriptingBridge PyObjC bindings:
pip install pyobjc-framework-ScriptingBridge
At the moment the library is seriously dumb.
Objects that currently work: Collections of all $objects, which support len(), iteration and indexing, and also expose their contents in the $objects attribute (these are resource intensive - see below)
- Projects
- Areas
- ToDos
Simple objects carrying the expected attributes for the object
- Project
- Area
- ToDo
As of yet only ToDos support modification, like so:
>>> import thingsinterface
>>> thingsinterface.ToDo
<class 'thingsinterface.things.ToDo'>
>>> a = thingsinterface.ToDo("Testing pythings", tags=["useless"], location="Today")
And a suitably named todo will appear in Today.
Instantiating a ToDo creates one in Things. To work with todos that already exist, wrap them instead:
>>> todo = thingsinterface.ToDo.from_id(things_id)
>>> todo.complete()
>>> todo.is_closed()
True
A todo's status can also be set with cancel() and read with is_cancelled(). The integers Things uses internally live in the Status enum.
Stuff that doesn't work yet:
- Contacts
- Lists (largely will be used for internal status setting/project use)
Names are snake_case throughout, apart from the ScriptingBridge selectors the library calls through to. If you used an earlier version:
| Was | Now |
|---|---|
STATUS_MAP["closed"] |
Status.CLOSED |
ToDo.fromSBObject(obj) |
ToDo.from_sb_object(obj) |
ToDo(todo_obj=obj) |
ToDo.from_sb_object(obj) |
ToDo._getTodoByID(id) |
ToDo.from_id(id) |
Area.toDos |
Area.todos |
getThings() |
get_things() |
Projects now hold wrapped Project objects rather than raw ScriptingBridge ones, which makes building them as slow as querying every project's todos (see below). The projects, areas and todos attributes are read-only - iterate or index the collection instead of reassigning them.
Using the ScriptingBridge object will create a Python process that's visible in the dock. This is somewhat unavoidable.
The use of the ScriptingBridge object means that you must use a version of Python with this functionality available. No system Python 3 ships it, so install pyobjc-framework-ScriptingBridge (see Requirements above) into whichever interpreter you are using.
The Applescript interface is slow like Philip Glass on DXM. Querying all ToDos or all Projects will take minutes for mature Things profiles. Querying all projects with their constituent todos takes 7 minutes on my computer, because this will query all historical information. This is a prime candidate for storing objects in some other format keyed by id.
The Applescript interface is also a massive hog while it's being slow - CPU use will stick at 100% for a while while stuff is being queried.