How we went from JS to TS smoothly thanks to a Github Action

Julien Demangeon
swile-engineering
Published in
4 min readNov 8, 2022
Photo by Andrew Ruiz on Unsplash

Note: This post is co-authored by Grégory Houllier, who is the creator of the Github Action

The stability of applications has become essential. While automated tests offer increased security, it is welcome to add typing to our existing code.

Therefore, migrating from Javascript to Typescript has become a common task for most companies, and Swile is no exception.

That’s why we’ve developed a tool that allows us to track, mesure and analyse the type coverage of any project we’ve decided to migrate in our stack.

Why did we develop this tool?

Each codebase migration comes with its own challenges, line of code count, delivered service criticality and contribution frequency are the 3 criteria we chose to build our TypeScript migration strategy.

Medium/large codebase migration path

TypeScript can be incrementally adopted using JSDoc, checkJS and allowJs options. Theses options allow tsc (ie TypeScript Compiler) to report typing errors on pure JavaScript code.

{
"compilerOptions": {
"checkJs": true,
"allowJs": true
}
}

Adopting TypeScript without breaking our CI

Enabling type checks on a codebase can emit an important number of issues and fixing them in one go is not always an option.

In this context, we choose to track errors and include the typing improvement goal in our pull request review process.

Here’s the corresponding slides about TypeScript Migration Journey

How it works

At Swile, in companies, we use Github as a code version-control platform for all of our assets. It is unnecessary to detail the many features that Github offers. Nevertheless, one of the most interesting for us, developers, is called Github Actions.

Github Actions allow to automate almost everything, while having access to the Github API, directly in our development workflow.

So, we’ve choose to create a custom Github Action. Just as described in the schema bellow, the usage flow is quite simple.

As you can see, the only role of the “ts-migration-companion” Github Action described in this article is to turn the text output of the “tsc” build command into an error report.

Note: We could have integrated the build steps directly into our action. However, this means a loss of freedom in the implementation and it would be contrary to the Unix philosophy that I like so much “Do One Thing and Do It Well”

As a result, the comment that is posted on the corresponding PR is of the following form.

How to implement

The main advantage of Github Actions is that we can share them easily. By the way, there is even a dedicated marketplace with more than 15k actions at the moment.

The action we have developed is available here under the name ts-migration-companion-action.

Here’s an example of implementation, it simply follows the flow described above.

name: TS Migration Companion

on:
pull_request:
branches:
- master

permissions:
contents: read
packages: read
pull-requests: write
issues: write

jobs:
typescript-migration-companion:
runs-on: ubuntu-latest
steps:
- name: Create tsc-output directory
run: mkdir /tmp/tsc-output
- name: Checkout main branch
uses: actions/checkout@v3
with:
clean: false
ref: main
- name: Run npm install on main branch
run: npm ci
- name: Typecheck dependencies on main branch
run: npm run build > /tmp/tsc-output/main.txt
continue-on-error: true
- name: Checkout PR branch
uses: actions/checkout@v3
- name: Run npm install on PR branch
run: npm ci
- name: Typecheck dependencies on pr branch
run: npm run build > /tmp/tsc-output/pr.txt
continue-on-error: true
- uses: swile/ts-migration-companion-action
with:
master_tsc_output_path: /tmp/tsc-output/main.txt
pr_tsc_output_path: /tmp/tsc-output/pr.txt
tsc_rootdir: src

There are 3 parameters that can be provided to the action, here is a description below.

  • master_tsc_output_path: Absolute path to the master branch tsc output
  • pr_tsc_output_path: Absolute path to the PR branch tsc output
  • tsc_rootdir: The “basepath” we use to analyze outputs (usually “src”)

More information about the action can be found on the associated action repository. Feel free to contribute ! ;)

--

--