mirror of
https://github.com/JanDeDobbeleer/oh-my-posh.git
synced 2024-12-28 20:39:40 -08:00
150 lines
5.7 KiB
Markdown
150 lines
5.7 KiB
Markdown
|
---
|
|||
|
title: "What idiot wrote this code?"
|
|||
|
description: "It was me..."
|
|||
|
slug: idiots-everywhere
|
|||
|
authors:
|
|||
|
- name: Jan De Dobbeleer
|
|||
|
title: Maintainer
|
|||
|
url: https://github.com/jandedobbeleer
|
|||
|
image_url: https://avatars.githubusercontent.com/u/2492783?v=4
|
|||
|
tags: [weekly, ohmyposh]
|
|||
|
hide_table_of_contents: false
|
|||
|
---
|
|||
|
|
|||
|
It finally happened, **I introduced a bug** that only appears in 1 use case and it can’t be resolved as it’s the result of
|
|||
|
using an old and new version of Oh My posh at the same time. Who does that you might ask? Well, it can be because you’re
|
|||
|
using WSL on Windows, or VM’s on any system while sharing the same configuration cross installation.
|
|||
|
Not the main use-case, but also not exotic either.
|
|||
|
|
|||
|
## What happened?
|
|||
|
|
|||
|
In the beginning of the year, after what has been quite the struggle, I was finally able to deliver **the most important
|
|||
|
architectural update** since the introduction of the rewrite in Go. Because of this, a migration of old configs was needed
|
|||
|
so that no end user would have to go through the ordeal of figuring out what to map where, it's a very logical process
|
|||
|
and obviously computers are better at that.
|
|||
|
|
|||
|
To facilitate this, I added a config property called `version` which can be incremented when the configuration evolves
|
|||
|
and triggers an automatic migration when necessary. The logic to identify the need for migration is as follows:
|
|||
|
|
|||
|
```go
|
|||
|
if !env.Flags().Migrate && cfg.Version != configVersion {
|
|||
|
cfg.BackupAndMigrate(env)
|
|||
|
}
|
|||
|
```
|
|||
|
|
|||
|
If you're observant, you might already spot the issue now that you know the use-case. For those of us who like to read
|
|||
|
and not think, the result is rather straightforward as it will always run the migration, either when forced (because you
|
|||
|
can use `oh-my-posh config migrate` manually), or when the current config version doesn't match the required config
|
|||
|
version. _Simple, right?_ And this works according to expectations when updating Oh My Posh. The problem starts when you
|
|||
|
have a shared config, and use multiple versions of Oh My Posh on the same machine.
|
|||
|
|
|||
|
Imagine working using multiple shells, one is WSL Ubuntu with a version of Oh My Posh that's still on version 1
|
|||
|
(**S1**). One day, you update PowerShell in Windows to use the latest greatest, using version 2 (**S2**). Starting S2,
|
|||
|
**it automatically migrates the config to version 2**, moving the `template` property to the segment's model.
|
|||
|
|
|||
|
In practice, the following version 1 config:
|
|||
|
|
|||
|
```json
|
|||
|
{
|
|||
|
"$schema": "https://raw.githubusercontent.com/JanDeDobbeleer/oh-my-posh/main/themes/schema.json",
|
|||
|
"version": 1,
|
|||
|
"blocks": [
|
|||
|
{
|
|||
|
"type": "prompt",
|
|||
|
"alignment": "left",
|
|||
|
"segments": [
|
|||
|
{
|
|||
|
"background": "#9A348E",
|
|||
|
"foreground": "#ffffff",
|
|||
|
"leading_diamond": "\ue0b6",
|
|||
|
"properties": {
|
|||
|
// highlight-next-line
|
|||
|
"template": "{{ .UserName }} "
|
|||
|
},
|
|||
|
"style": "diamond",
|
|||
|
"type": "session"
|
|||
|
}
|
|||
|
]
|
|||
|
}
|
|||
|
]
|
|||
|
}
|
|||
|
```
|
|||
|
|
|||
|
Is migrated to:
|
|||
|
|
|||
|
```json
|
|||
|
{
|
|||
|
"$schema": "https://raw.githubusercontent.com/JanDeDobbeleer/oh-my-posh/main/themes/schema.json",
|
|||
|
"version": 2,
|
|||
|
"blocks": [
|
|||
|
{
|
|||
|
"type": "prompt",
|
|||
|
"alignment": "left",
|
|||
|
"segments": [
|
|||
|
{
|
|||
|
"background": "#9A348E",
|
|||
|
"foreground": "#ffffff",
|
|||
|
"leading_diamond": "\ue0b6",
|
|||
|
// highlight-next-line
|
|||
|
"template": "{{ .UserName }} ",
|
|||
|
"style": "diamond",
|
|||
|
"type": "session"
|
|||
|
}
|
|||
|
]
|
|||
|
}
|
|||
|
]
|
|||
|
}
|
|||
|
```
|
|||
|
|
|||
|
Awesome, no user interaction at all and _everything works as designed_. However, you now want to do something using S1, and
|
|||
|
due to the logic, Oh My Posh sees that `2 != 1` and **the migration is triggered for version 1**. The migration as such
|
|||
|
is non-breaking, but Oh My Posh doesn't know the `template` property on `segment` in this case. The end result of our
|
|||
|
config above is rather annoying as we're now left with this:
|
|||
|
|
|||
|
```json
|
|||
|
{
|
|||
|
"$schema": "https://raw.githubusercontent.com/JanDeDobbeleer/oh-my-posh/main/themes/schema.json",
|
|||
|
"version": 1,
|
|||
|
"blocks": [
|
|||
|
{
|
|||
|
"type": "prompt",
|
|||
|
"alignment": "left",
|
|||
|
"segments": [
|
|||
|
{
|
|||
|
"background": "#9A348E",
|
|||
|
"foreground": "#ffffff",
|
|||
|
"leading_diamond": "\ue0b6",
|
|||
|
"style": "diamond",
|
|||
|
"type": "session"
|
|||
|
}
|
|||
|
]
|
|||
|
}
|
|||
|
]
|
|||
|
}
|
|||
|
```
|
|||
|
|
|||
|
😱 the template is gone! Nothing to worry about just yet, Oh My Posh will use the default template so you will still see
|
|||
|
a prompt, and the migration also _creates a backup_ of your previously correct version 2 config. Up to this point you
|
|||
|
can still revert, it's unfortunate, but your local tweaks are still available. If you happen to continue working in S2 at
|
|||
|
this point however, it will once again trigger the migration to version 2 and **overwrite your backup with the faulty
|
|||
|
version 1 config**.
|
|||
|
|
|||
|
While the fix for this issue in code is trivial, it's impossible to push that to older versions. People will upgrade
|
|||
|
to the most recent version, and in this specific setup, this is potentially breaking. **The advice is to upgrade all versions
|
|||
|
at once**, so you only migrate once and there's no "old" version of Oh My Posh left to trigger this unwanted side-effect.
|
|||
|
|
|||
|
The actual fix for the issue can be found in [7.52.1][fix-version], but due to obvious reasons, it will only work
|
|||
|
going from version 2 to any new config version in the future.
|
|||
|
|
|||
|
```go
|
|||
|
if !env.Flags().Migrate && cfg.Version < configVersion {
|
|||
|
cfg.BackupAndMigrate(env)
|
|||
|
}
|
|||
|
```
|
|||
|
|
|||
|
While I try hard to come up with every possible edge case when validating this logic, sometimes things slip through.
|
|||
|
Even when looking at this one **I find it challenging not having considered that case**, but it still happened. The
|
|||
|
good news? It won't happen again 😅
|
|||
|
|
|||
|
[fix-version]: https://github.com/JanDeDobbeleer/oh-my-posh/releases/tag/v7.52.1
|