chiark / gitweb /
Playing with rich
authorColin Watson <cjwatson@debian.org>
Fri, 3 May 2024 15:31:23 +0000 (16:31 +0100)
committerColin Watson <cjwatson@debian.org>
Fri, 3 May 2024 15:31:23 +0000 (16:31 +0100)
content/playing-with-rich.md [new file with mode: 0644]

diff --git a/content/playing-with-rich.md b/content/playing-with-rich.md
new file mode 100644 (file)
index 0000000..29c4020
--- /dev/null
@@ -0,0 +1,74 @@
+Title: Playing with rich
+Slug: playing-with-rich
+Date: 2024-05-03 16:09:53 +01:00
+Category: columbiform
+Tags: columbiform, freexian, planet-debian, planet-ubuntu
+
+One of the things I do as a side project for Freexian is to work on various
+bits of business automation: accounting tools, programs to help contributors
+report their hours, invoicing, that kind of thing.  While it's not quite my
+usual beat, this makes quite a good side project as the tools involved are
+mostly rather sensible and easy to deal with (Python, git,
+[ledger](https://ledger-cli.org/), that sort of thing) and it's the kind of
+thing where I can dip into it for a day or so a week and feel like I'm
+making useful contributions.  The logic can be quite complex, but there's
+very little friction in the tools themselves.
+
+A recent case where I did run into some friction in the tools was with some
+commands that need to present small amounts of tabular data on the terminal,
+using [OSC
+8](https://gist.github.com/egmontkob/eb114294efbcd5adb1944c9f3cb5feda)
+hyperlinks if the terminal supports them: think customer-related information
+with some links to issues.  One of my colleagues had previously done this
+using a [hack](https://github.com/foutaise/texttable/issues/87) on top of
+[texttable](https://pypi.org/project/texttable/), which was perfectly fine
+as far as it went.  However, now I wanted to be able to add multiple links
+in a single table cell in some cases, and that was really going to stretch
+the limits of that approach: working out the width of the displayed text in
+the cell was going to take an annoying amount of bookkeeping.
+
+I started looking around to see whether any other approaches might be
+easier, without too much effort (remember that "a day or so a week" bit
+above).  [ansiwrap](https://pypi.org/project/ansiwrap/) looked somewhat
+promising, but it isn't currently packaged in Debian, and it would have
+still left me with the problem of figuring out how to integrate it into
+`texttable`, which looked like it would be quite complicated.  Then I
+remembered that I'd heard good things about
+[rich](https://pypi.org/project/rich/), and thought I'd take a look.
+
+`rich` turned out to be exactly what I wanted.  Instead of something like
+this based on the `texttable` hack above:
+
+    :::python
+    import shutil
+    from pyxian.texttable import UrlTable
+
+    termsize = shutil.get_terminal_size((80, 25))
+    table = UrlTable(max_width=termsize.columns)
+    table.set_deco(UrlTable.HEADER)
+    table.set_cols_align(["l"])
+    table.set_cols_dtype(["u"])
+    table.add_row(["Issue"])
+    table.add_row([(issue_url, f"#{issue_id}")]
+    print(table.draw())
+
+... now I can do this instead:
+
+    :::python
+    import rich
+    from rich import box
+    from rich.table import Table
+
+    table = Table(box=box.SIMPLE)
+    table.add_column("Issue")
+    table.add_row(f"[link={issue_url}]#{issue_id}[/link]")
+    rich.print(table)
+
+While this is a little shorter, the real bonus is that I can now just put
+multiple `[link]` tags in a single string, and it all just works.  No
+ceremony.  In fact, once the relevant bits of code passed type-checking
+(since the real code is a bit more complex than the samples above), it
+worked first time.  It's a pleasure to work with a library like that.
+
+It looks like I've only barely scratched the surface of `rich`, but I expect
+I'll reach for it more often now.