Building a Static Documentation/Blog Generator with esbuild-scripts

In the last blog post, I talked about how I rebuild my website infrastructure to speed up the build time by 20x. However, it is only able to support a subset of my React websites. I also have some websites that are powered by Docusaurus that are unable to migrate to esbuild-scripts due to the lack of customized routing support. In this post, I am going to go over the process of developing abstractions for this feature.

Achieving 20x Build Speedup: Introducing esbuild-scripts

Since the release of esbuild that gives a theoretical 100x speedup, I always imagined adopting it to significantly improve the build time of my own websites. After some investigation and proof-of-concept work, I figured out how to write some minimal amount of code to use esbuild, an extremely fast but limited build tool, to bundle and generate minified JavaScript for static sites.

The end result is a 20x speedup on my personal website:

20x performance improvement

The Case for Squash and Merge

There are several things I have very passionate opinions on, like whether opening braces { should be on a new line, etc. (Answer: NO NO NO!) Merging in a pull request using squash and merge is among the list. However, unlike the braces argument which is largely aesthetic, I believe that the practice of squash and merge provides significant productivity boosts compared to merging by merge commit.

Squash and merge

Supporting the LLVM Backend for samlang

LLVM is a collection of compiler toolchain that allows you to target any instruction set from any source-level programming language. Once the source code has been lowered to LLVM IR, the LLVM toolchain can easily handle the tasks of optimization and emitting assembly code for all the supported architecture.

I was always planning to migrate the samlang backend to LLVM since Apple announced that future Macs would be running on ARM chips and I want the ability to run compiled samlang code natively. Such a plan finally came true this winter when I was stuck in Ithaca having nothing else to do.

Rewriting samlang in TypeScript

A lot has changed since my last blog post on my effort to make samlang run in browsers. The samlang demo site has been merged into the samlang documentation site as a demo tab. In addition, samlang can now emit optimized JavaScript code as its second target language. However, the most exciting changes come from a complete overhaul of the codebase: rewriting samlang in TypeScript.

Making samlang Run in Browsers


samlang is my favorite and most sophisticated side project. It is a functional programming language with an optimizing compiler that targets the X86 instruction set and a language server that can provide type query and autocompletion.

The compiler and the language server was written in Kotlin and compiled to JVM bytecode. It's worth noting that Kotlin has multiplatform support and can compile any Kotlin code into JVM bytecode and JavaScript with a single codebase. Therefore, it's theoretically possible to create a samlang build that can run in browsers.

The reality is always harsher than the theory. It takes a significant effort of refactoring to make this happen. In this blog post, I will explain these efforts and some of the tricky design decisions I made along the way.

One Year as Developer Lead

Almost a year ago, I started to perform developer lead responsibilities at Cornell DTI. My first major task was to grade part of developers at the end of the spring 2019 semester. A few days ago, I just finished grading all developers for their performance in the spring 2020 semester, wrapping up almost a year of work.

I came into the position thinking that developer lead has the easiest issues to deal with. I still believe this statement is true for me. However, I didn't realize that the easiest issues are still issues of a complex system full of Byzantine faults. Easy DevOps issues become exponentially harder to deal with when there is a people factor. Just like software engineering, sometimes it's all about compromises.

Therefore, I decided to write this blog post as both a reflection for myself and as documentation for future leads.

2016: A Year of No Significance

In the year of 2016, a school in Shanghai celebrated its 20th founding anniversary. Beyond this ceremony in December, its high school division students have made record-breaking college admission success: Engineering school admission in Ivy League had finally invalidated the 0 success rate record, and there was a student that made it into Columbia University after several years of hiatus.

However, compared to later years, it was quite an insignificant year, at least to the high school division. A year later, it would celebrate its 10th anniversary since it started the IBDP program. The college admission record in the next year also completely overshined the year of 2016. There were a few miniscale crises, but none of them had caused widespread dissent over a long period. Those small crises tend to be remembered less than a week. Yet, these events started to manifest themselves as symptoms of a larger problem, which might eventually lead to a spontaneous online protest that is beyond the imagination of school administrators.

Let's start with something small.

How to Implement Autocomplete

Implement autocomplete in 79 lines of code. Actually, it's not that easy.

Without the infrastructure discussed in this post, that code snippet mentioned here is useless.

I will walk through my journey to implement autocomplete in this blog post, using my programming language samlang as an example.

My Decade in Review

Following the lead of React and JavaScript god Dan Abramov, I decided to also publish my decade in review blog post.

I want to clarify that I intend to present the following content as plain facts. I will talk about the facts that certain events happened, and the facts that I thought and reacted to certain events in certain ways. You should treat them as a totally ordered set of boring logs rather than definitive guidance to something.

(To be friendlier to not-so-technical readers, I italicized all the technical jokes that are not essential to understand the story.)

Move Fast with Automation Powered Monorepo

In the last article The Road to Better Engineering, I promised that there will be a new post about my recent website re-architecturing effort. In the past week, I am working to gradually transform the website monorepo into a repository with latest technologies and reliable automation. At the time of writing this article, the transformation is complete and the repository has reached a state that I am mostly satisfied with.

The Road to Better Engineering

The Start#

About three years ago, a student club welcomes the largest influx of new members in its entire existence. It is considered as a milestone: it's a de facto recognition that it's becoming prominent. By that time, its product covers over 40% of the student base and the club is the place for future software engineers to go. The former president of the club publicly celebrated this, and he was thinking about how the club can continue to move fast without any overhead of bureaucracy.

If you have read my blog post before, you know what had happened. Beneath the promising sign of future prosperity, there were huge risks: the main product already hit the upper bound of the user count; the engineering team was not well-trained by the former president; more importantly, the codebase was in a hell state.

That club is called Computerization and that dumb former president was me.

Design Choice of samlang in Alpha


In the last summer, I developed my first programming language SAMPL. Measured against my technical skills at that time, it was a clear success. I was able to implement an interpreter and a compiler for a self-designed functional programming language with only the knowledge to implement an interpreter for a toy language in Cornell CS 3110. I was particularly proud of the module system and generics in that language.

Highlights in 2018 and Short-Term Plans in 2019

I won't write a reflection on what I did in 2018 because my resume and GitHub commit history are already self-evident. In the first part of this post, I will list some amazing things I created in 2018 for the purpose of summary, because some of the blog posts are long and I know you want to a TLDR version. I will then talk about some short-term plans that I hope to check off before my winter holiday ends.

Computer Science in High Schools

This year, I got an intern with a resume that did not mention my high school's CS project with a single word. Therefore, at this point, either success or failure in my high school CS career does not matter at all, so I can honestly reflect on it. I reviewed again all my computer science related records and writings to ensure the content in this article is as accurate as possible. I hope it still helps.

Critter World is Turing Complete - A Not-So-Rigorous Proof

Critter World is Cornell's CS 2112's Final Project. It is a simulated hexagon world where critters, controled by programs, can move, eat, mate, bud, attack, etc. The programming language is very primitive and not Turing complete, but it's still useful and expressive enough to cleverly control one step of a critter move. You can see the spec publicly here.

A Year of Change - Reflection on My Website's Architecture Update


I bought the domain in February 2015 and officially started my own website. Before that, I hosted my website on the free tk domain, but I decided to remove that kind of sketchiness when I received my first scholarship. The website is poorly maintained, received no update for almost a year since it's published. After I was admitted to Cornell in December 2016, I started to update my website more often, but still not as frequent as I would do right now. In a quite slow progress, the website finally got to an acceptable shape at the end of July last year.

Function Reference in SAMPL - A Design Mistake and the Fix


In most functional programming languages, a function IS a value. Therefore, it can be easily passed as a parameter for a function. For example, this is legal in OCaml:

let f (i: int): float = float_of_int i
let test (f: 'a -> 'b) (a: 'a) : 'b = f a
let ( * ) = test f 3

Even for Javascript, this can be done easily:

function f(s) {
return parseInt(s);
function test(f, a) {
return f(a);
const ignoreMe = test(f, '3');

Design Choice of SAMPL - Written After the First Alpha Release


Starting from May 21, after I finished the algo final at Cornell, I started to develop my own programming language SAMPL. I decide to design a new language for a while, because I was frustrated by the ugliness of OCaml's namespace but miss its nice functional features. The exact name of the language was not chosen with much deliberation: I just want the name to contain a substring SAM.

Project DEFCON 1: A Confidential Data Storage System


This short article is devoted to describe a data storage system that ensures data confidentiality even if you are interrogated under torture. I personally call the system Project DEFCON 1.

The system, with an option to switch on and off, lies behind the usual login feature as a second-step authenticator. Since it dramatically increased the complexity of login process, it is recommended to switch it on only when you feel imminent threat, as suggested by the name 'DEFCON 1'.

Nerd Pride

On the evening of December 8, 2016, exactly on 5:01 PM in Eastern Standard Time, the photons of Cornell Engineering acceptance letter struck my eyes. For me, it was a confirmation, a confirmation for an unexpected success of a rebellion.

Welcome to My Blog!

This is the zeroth post in my blog. Since the content of the post might change when I migrate the blog from one place to another, I choose to set the time to be 1970-01-01.

It is a Hello World post, but I will also use this post to test various features of Docusaurus.