newsletter
-
I configured different note types to show in different colors. Zettelkasten has a few different kinds of notes, and quickly being able to see, by color, which it is, has been helpful.
-
I added the ability to change the order of notes. This was needed to be able to create structure notes with links in specific order.
-
I added the ability to give links a text description. This is what allowed me to experiment with articulating how two ideas relate to each other. I wrote more about the evolution of this feature in Linking (and how it has evolved) in Smart Notes.
-
I documented how I did a redirect to my old archived site for pages that I have not yet migrated to the new blog in Poor man’s redirect in a static site.
-
I started a “photo blog” documenting my runs and how my life improves from them.
-
Micro.blog makes it easy to create a website that feels like a home.
I can share and develop my interests. I can structure content with categories and pages. Others can come have a look. Comment if they wish. And you can see conversations that I’ve had with visitors.
-
It makes blogging fun. It is easy to publish and you can get comments from the community on your posts.
Newsletter January 2025: Inspired and Motivated by New Laptop and Reading
New Laptop
I got a new laptop this month. It was almost 10 years since I bought my previous one. I mainly needed a new one to be able to smoothly browse certain websites and for better performance when editing videos.
When installing the latest version of Fedora on it, I took the time to clean up my dotfiles. Since I jumped quite many Fedora versions, my often used tool rlselect had stopped working. I figured out the problem and documented the fix in Replacing Ctrl-R in Bash without TIOCSTI.
That blog post came naturally to me. I was trying to find a solution to a problem. I found other people having the same problem. When I found a solution, I felt the need to share it to contribute to the discussion and hopefully help someone else. I even wrote a custom version of the blog post tailored to an issue on GitHub.
Bootstrapping
I came across Bootstrappable Builds. Bootstrapping is an interesting problem that I’ve mainly come across in my work on RLMeta. They write that
To gain trust in our computing platforms, we need to be able to tell how each part was produced from source.
I started thinking how this would apply to RLMeta. The RLMeta “binary” is a Python file. So it needs Python to bootstrap itself. I’m not sure if that qualifies as a problem according to Bootstrappable.
The “binary” is not really human readable, so it is not feasible to inspect it. On the other hand, the source code says exactly how it is produced, and we can verify that it produces itself.
One way to figure out if this is a problem or not is to see if it is vulnerable to the “Trusting Trust” attack. The article Reflections on Rusting Trust talks about how to make this attack in the Rust compiler. I don’t fully understand it, but it could be interesting to try with RLMeta.
XXIIVV
I came across XXIIVV. There are so many things in there that interest me.
One of those things is the idea that in order to be able to run our software many, many years from now, we need to target a small virtual machine that we can re-implement in a weekend. You can find more on this in devlog and the transcript of the talk Weathering Software Winter.
One thing that cause our software to break is when the things that it depend on change or go away. For that reason, I’m reluctant to pull in third party dependencies when building software. But what if the language our software is written in disappears? That is less likely than third party dependencies changing, but there is still a risk. Especially in the long run.
But if we can not depend on third party software or languages, we have to implement the whole software stack ourselves. That is a lot of work. There is probably a balance where the trade-off of depending on something is worth it. And that balance differs depending on our goals with the software. However, my feeling is that many things that we pull in third party dependencies for, we can quite easily implement ourselves. And get rid of the bloat of the 80% of the third party dependency that we don’t use. In addition to getting rid of bloat, it also increases understandability. We don’t need to figure out how a third party dependency work, we just need to figure out how a much smaller set of our code works.
Another area where preserving software is of interest to me is my website. About half a year ago, I moved to Micro.blog. Some of my posts now only exists there. The platform gives me some things that I like such as ease of posting and interaction with others. But what if Micro.blog goes away? What happens to my words? I think I need to go back to having the source code for my website in a git repo. Then I should be able to compile my website for different targets. One for publishing online. It might be an export to Micro.blog so that I can continue to use some of its features. But it might also be a pdf export. That way I can print the pdf and have my whole website preserved as a physical book in my bookshelf. That will most likely live for much longer than any technology. And of course, compiling my website should depend on as few dependencies as possible. Perhaps even target a small VM as XXIIVV does it?
A Note on Reading
I was able to read and write about the topics above partly because of a realization that I had earlier this month:
Today’s realization is that you can get important things done by consistently working on them for 15 minutes at the start of every day.
By doing it at the start of the day, you ensure that it gets done. And the rest of the day you don’t need to be stressed about not working on your important thing, because you already have.
I want to read more. But it is easier to just scroll through my feeds and read headlines. What I’ve tried now is to bookmark things that look interesting. Then I spend some time in the mornings to carefully read those pieces. It’s been a quite positive experience for me. I’ve also used that trick to get more boring tasks done. It might not work if you are a night person though.
Newsletter November 2024: A New Project
Compared to last month, this month I did some programming in my spare time. I had fewer commitments, and my mind started thinking about various programming projects. We also got the first snowfall of the season and I got to enjoy a run in it:
A New Code Editor
The programming project that I started working on is code editor that is a mix of a text editor and a structured editor. It is all text, but parsers and pretty printers allow you to work with a tree structure and not think too much about syntax. The code is available on GitHub, and here is what it looks like when editing a JSON document:
I got the idea for this project when trying out Black. Black automatically formats Python code for you so that you don’t have to think about it. I’ve been interested in structured editors for some time, but my feeling is that they are not user friendly because they limit what you can type. Then I came up with this idea of an editor that constantly parses what you type. If the parse is successful, it pretty prints it for you and provides you with edit operations on the AST. But it is all still just text, so you can type whatever. In the worst case, the parse fails and you have to fix it manually.
So far, it looks quite promising. And most importantly, I’m having fun experimenting. The most likely scenario is that the project will not be a success, but I will learn something and have fun doing so. But you never know. One day, one of these projects just might turn into something that is invaluable.
TDD
This month I also watched a presentation by Kent Beck called TDD: Theme & Variations. For me, it was a nice refresher on the origins of TDD.
One thing that I appreciate with TDD, that I partially had forgotten, is how it reduces anxiety. Kent reminded me of it in the presentation. When all tests are passing and you can’t think of any more tests to write, you are done, and you know that it works. That reduces anxiety a lot.
Newsletter October 2024: Primitive Obsession?
Normally I do something related to programming in my spare time every month. I read something that I find interesting and want to share. Or I have some thought related to programming that I want to share. This is the first month since I started these monthly updates in June 2019 that I’ve got nothing of that. I’ve been occupied with other things, and I’ve also done quite a bit of programming at work. Perhaps that has satisfied my interest for programming.
One thing that I’ve done a lot at work this month is wrapping simple data structures in classes. Instead of passing around lists and dictionaries, I’ve created classes holding that data and only serialized it at the edges of the application. Every time I have done this, I wish I had done it sooner. It’s so good. And in nine times out of ten, those classes have attracted some functionality that fits perfectly. They have provided one place to put functionality instead of scattering it throughout the codebase.
What am I talking about? Let me give an example.
Imagine that we talk to a user service that has an API something like this:
service.get_all_users() -> ["user1", "user2"]
service.set_users_in_group("group1", ["user1", "user2"]) -> OK
The API works with users represented as list of strings. Now we want to write a function that applies some domain logic to assign users to groups. It is so easy and tempting to write something like this:
def update_r_users(service)
r_users = []
for user in service.get_all_users():
if "r" in user:
r_users.append(user)
service.set_users_in_group("users_with_r_in_name", r_users)
One problem with this code is that it mixes calls to the user service with domain logic, so is is difficult to test domain logic without invoking the service. It’s also more difficult to reason about.
What if we instead did this:
def update_r_users(service)
service.set_users_in_group(
"users_with_r_in_name",
Users.from_service(service.get_all_users()).filter_name("r").serialize()
)
class Users:
@classmethod
def from_service(cls, users):
return cls(users)
def __init__(self, users):
self.users = users
def filter_name(self, text):
return Users([
user
for user in self.users
if text in user
])
def serialize(self):
return self.users
This is what I mean by wrapping simple data structures in classes. Why is this better?
First of all, I think update_r_users
now reads a lot better. The filtering
logic is no longer mixed with the calls to the service.
This comes at the cost of writing the Users
class which is quite long
for the relative functionality that it provides. In the beginning, I often find
it hard to motivate myself to write these classes. It feels like a lots of
boilerplate code for not much benefit. However, I often find that these
sort of classes attract functionality, at which point they start to become
more useful.
Another thing that they do is encapsulate the data format from the user service. Say that the API of the service changes. There is now more information about users:
service.get_all_users() -> [{"name": "user1", "age": 21}, {"name": "user2", "age": 43}]
service.set_users_in_group("group1", ["user1", "user2"]) -> OK
We can update the User
class accordingly:
class Users:
@classmethod
def from_service(cls, users):
return cls(users)
def __init__(self, users):
self.users = users
def filter_name(self, text):
return Users([
user
for user in self.users
if text in user["name"]
])
def serialize(self):
return [user["name"] for user in self.users]
The update_r_users
stays the same. We control the API of Users
. Our
application can safely depend on it. And we can change the internals.
I couldn’t find a name for this sort of pattern. My first though was that it was a way to avoid primitive obsession. And it is. But it feels like more than that. Bill suggested that it might be just “good old encapsulation”. Dan said that it depends on the context and that it could be an anti-corruption layer in DDD terms. What would you call it?
Anyway, I’ve been doing this sort of thing a lot this month, and I thought it was worth sharing.
Newsletter September 2024: Bash Redirects and Reading
This month I read How to Use a Zettelkasten to Write Stories Packed with Emotion. It inspired me to write something using that technique. The topic that came to mind was Bash redirects. It resulted in the blog post Bash Redirects Explained.
I also started reading How Children Learn by John Holt. He says that children are naturally interested in exploring the world. I started thinking about what environments kill exploration. I though that fear of doing something wrong will discourage exploration. Then I made a parallel to a common practice in software development: pull requests. I thought that pull requests discourage experiments because changes can only propagate after approval, and the idea behind pull requests is to only approve “good” changes. First of all, the learning opportunities of mistakes are gone. Second of all, you might loose interest in experimenting because you are afraid of making a mistake. You build a culture of discouraging making mistakes. I though that a better approach is to focus on making the cost of mistakes small so that we can do lots of them and learn from them.
I also read Debugging Teams by Ben Collins-Sussman and Brian Fitzpatrick. They talk about the myth of the genius programmer and that all great things are built by teams. I believe that is true, but sometimes I have a hard time to acknowledge it because I also enjoy working by myself.
Newsletter August 2024: Smart Notes and Blogging
In August I had my last week of summer vacation. I read a book that made me want to improve my note taking tool, I did some programming on hobby projects, and I migrated my blog to a new platform. All while doing many runs.
A System for Writing
I read A System for Writing by Bob Doto. This review is what made me buy the book:
When I first tried to get my head around Zettelkasten, I consulted Sönke Ahrens’ extremely useful book How to Take Smart Notes. This was—and still is—seen as the book to read on the subject. I predict A System for Writing will replace it.
I liked Sönke’s book, and I was curious to learn more about this topic from a source that seemed credible.
I got some new insights about the Zettelkasten method. In particular the idea that it is important to articulate how two ideas relate. I’ve previously mostly connected ideas without context. The connection was obvious when I made it, but most likely less obvious when I come back to it.
I tried to research this a bit more and found the article Backlinking Is Not Very Useful – Often Even Harmful:
A good link context explains what you can expect if you follow the link. But it can also explain the nature of the relationship between both notes.
I wanted to try this out.
Smart Notes
I use my Smart Notes app to take notes using the Zettelkasten method. When I studied the method more, I got some new ideas that I implemented:
One-File Programs
I continued to work on One-File Programs.
I worked on an engine app that can automatically reload other apps when they change. This gives faster feedback, especially when working on graphical applications. It is similar to an approach I’ve written about previously in How to get fast feedback on graphical code?
I also worked on the no scrollbars app. I wanted to see if we can get rid of scrollbars in some GUI elements. The idea is to make items larger around the area of the mouse so that they can more easily get selected. Here is one screenshot:
I want do continue work with this repo, but the rest of the time this month, I spent on my blog.
Micro.blog
I found out about Micro.blog and moved my blog to it.
Some reflections on Micro.blog:
Newsletter July 2024: Note Making Re-Visited
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/july-2024/.
Newsletter June 2024: Quines and Smalltalk
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/june-2024/.
May 2024 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/may-2024/.
April 2024 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/april-2024/.
March 2024 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/march-2024/.
February 2024 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/february-2024/.
January 2024 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/january-2024/.
December 2023 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/december-2023/.
November 2023 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/november-2023/.
October 2023 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/october-2023/.
September 2023 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/september-2023/.
August 2023 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/august-2023/.
July 2023 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/july-2023/.
June 2023 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/june-2023/.
May 2023 Update
This post has not yet been imported to my new blog.
In the meantime, you can read it here: http://archive.rickardlindberg.me/writing/newsletter/may-2023/.