Skip to content

Latest commit

 

History

History
65 lines (57 loc) · 3.37 KB

EXPLANATION.md

File metadata and controls

65 lines (57 loc) · 3.37 KB

How Updates Work

There are two parts: the part that checks for new versions of the discord/discord-ptb/discord-canary desktop apps and the part that updates versions.json when a new version is found. Both parts use update.py, but the first is run on my GCE instance while the second is run from the update workflow.

Checking for Updates

Every 30 minutes, update.py check is run on my GCE instance. It gets the latest versions of each app from Discord's website (by following the download link and parsing the final URL) and compares them to the ones in versions.json. For every app where the version in versions.json does not match the latest version, it sends a repository_dispatch event to this repository. The name of the app (one of discord, discord-ptb, or discord-canary) is included in the event payload to make things easier on the other end.

The NixOS configuration for my GCE instance is public, and the service configuration can be found here.

Updating versions.json

The repository_dispatch event triggers the update workflow which runs update.py update $pname (where $pname is the name of the app included in the payload). It gets the latest version of that app (again using Discord's website), and also downloads it to get its hash (using nix-prefetch-url). It then updates versions.json with the new version/url/sha256, builds the package as a sanity check, and commits and pushes the changes.

Implementation Notes

  • The original implementation only relied on GitHub Actions; the workflow was set to run every 30 minutes and took care of checking for updates as well as updating versions.json. Unfortunately, the scheduling turned out to be highly inconsistent, with several hours going by before the workflow ran for the first time. Given that going through the process of setting up the runner, cloning the repository, etc., just to check for new versions seemed really inefficient anyway, I ended up splitting the update process into two parts instead of spending more time trying to get the action to run more consistently. The added complexity is unfortunate but seemed worth it in this case.
  • The instance that checks for updates actually keeps its own copy of versions.json locally, which differs slightly from the one in this repository in that it only contains versions, e.g.:
    {
      "discord": "0.0.17",
      "discord-canary": "0.0.135",
      "discord-ptb": "0.0.29"
    }
    If this file does not exist when update.py check is run it will be created based on the one in this repository. Like before, this adds complexity but seems worth it; if the script pulled the latest versions from the repository every time, then a situation where the update workflow failed for whatever reason could lead to hundreds of failed runs before anyone noticed.
  • update.py check triggers the update workflow once per version update, so in the unlikely case that two packages have new versions at the same time it would send two repository_dispatches (so that each of the two version updates get their own commits).