A Terminal as a Portfolio
I rebuilt mg.design as an interactive terminal. You type commands, it answers. Here's why a hard constraint like "it's a terminal" made the design easier, not harder, and what it takes to make a fake shell feel real in the browser.
5 min read
This week I rebuilt mg.design as a terminal. When the page loads, a prompt boots up and types out who I am. From there, you type commands. experience prints a career timeline. portfolio lists selected builds. contact gives you the links. help shows everything else.
It went from first commit to working site in a few days. And the most interesting part wasn't the code. It was what the constraint did to the design.
Why a terminal#
A portfolio has a strange job. It has to show taste and skill, quickly, to people who are skimming. Most portfolio sites solve that the same way: a big headline, a grid of project cards, an about section. They blur together.
A terminal is an opinion. It says, before you read a word, that this person builds things and is comfortable in the tools. For the audience I care about, mostly engineers, founders and people hiring for technical leadership, that's the right first signal.
It's also honest about how I work. A lot of my day is in a terminal, increasingly with agents in it. The site looks like the place the work happens.
The constraint does the design work#
The best thing about "it's a terminal" is how many decisions it makes for you:
- Typography: one monospaced font. That's it. I used Geist Mono.
- Layout: a single column of text that scrolls. No grid, no breakpoints to agonise over.
- Colour: a dark background, a light foreground and one or two accents for prompts and links.
- Navigation: commands. There's no menu to design.
- Content: short. Terminal output that runs for pages feels wrong, so everything gets edited down.
That last one is underrated. Writing for a terminal forces tighter copy. When the format punishes long paragraphs, you stop writing them.
The commands are the information architecture#
On a normal site, the information architecture is the nav bar. Here, it's the command list:
whoami who I am, typed out on load
experience career timeline
portfolio selected builds, as clickable chips
proof evidence of senior-level work
systems architecture and tech stack
resume a short principal-architect summary
ideology operating principles
contact links
message compose a note from the terminal
neofetch a system summary, for fun
clear clear the screen
Choosing those names was the real design work. Each one had to be a word someone might guess, short enough to type and specific enough to mean one thing. ideology is a little playful. proof is blunt on purpose: it's the command for people who want evidence, not adjectives.
Making a fake shell feel real#
A terminal in the browser only works if it behaves like one. People who live in terminals notice immediately when it doesn't. The details that matter:
- Tab completion. Type
exp, press Tab, getexperience. This is the one people try first. - History. Up and down arrows walk back through what you typed.
- A blinking cursor and a real prompt. Small, but it sells the illusion.
- Typed output for the intro. The
whoamitext types itself out on load, so the page feels alive before you touch it. clearworks. Of course it does.
Under the hood it's a simple loop:
on enter:
add the input to history
look up the command
if found: render its output block
else: print "command not found", suggest help
scroll to the bottom
focus the prompt again
Each command returns a block of rendered output. Most are text. Some are richer: the portfolio command prints project names as clickable chips, so it's still a terminal, but you don't have to type a URL to open something.
Don't trap people in the gimmick#
A terminal portfolio can easily become a puzzle. Not everyone visiting knows what a command line is, and nobody should need to.
A few things keep it friendly:
- It starts talking first. The intro types itself out, and it ends by suggesting
help. You're never facing an empty prompt with no idea what to do. - Links are clickable. Output isn't just text to read. Project chips and contact links work with a mouse or a tap.
- Mobile has to work. On a phone, typing commands is awkward, so the clickable parts carry more of the load.
messagekeeps contact in the flow. You can write a note without leaving the terminal.
The gimmick should be the frame, not the gate. If someone can't get to the content, the design has failed, no matter how clever it looks.
Why not a normal site with a terminal easter egg#
The obvious compromise is a regular portfolio with a hidden terminal you can open with a keystroke. Plenty of sites do this, and it's fun.
But an easter egg is something most people never find. It says "I can build a terminal", which isn't very interesting. Making the terminal the whole site says something different: this is how I want you to meet me.
It also keeps the work honest. With a hidden terminal, the real site still needs all the usual decisions, and the terminal is extra. With the terminal as the site, there's one experience to get right. Every hour goes into making that one thing good.
There's a cost, of course. Some visitors will bounce because it isn't what they expected. For a personal site aimed at technical people, that's a trade I'm comfortable making. For a product's marketing site, it probably wouldn't be.
The stack#
The stack is intentionally plain: Next.js 16 with the App Router and Turbopack, Tailwind CSS v4, TypeScript and Geist Mono. It deploys anywhere that runs Next.js.
The plainness is the point. All the effort went into the experience: the commands, the copy and the small behaviours that make it feel like a real shell. None of it needed an unusual tool.
The repo also carries instructions for coding agents, which suits the format. A terminal is mostly copy and behaviour. Both are easy to describe precisely, and precise descriptions are what agents work best from.
What I'd tell someone trying this#
- Pick a constraint that says something about you. A terminal works for me because it's true to how I work. It might not be your thing.
- Let the constraint make decisions. Fewer fonts, fewer colours, fewer layouts. Enjoy it.
- Treat command names as navigation. Spend real time on them.
- Get the small behaviours right. Tab completion and history are what make it feel real.
- Always give a way out. Clickable links and a helpful first screen mean nobody gets stuck.
The takeaway#
Rebuilding my portfolio as a terminal made the design simpler, not harder. One font, one column and a list of commands replaced most of the usual decisions, and the format forces tighter writing. The trick is to make the shell feel real for people who know terminals, and friendly for people who don't.
Related
- Leadership
The Tech Job Exodus Isn't New: When Opening the File Stopped Being Enough
Around 2012 and 2013, knowing how to operate the tools stopped being enough to hold a job on the web. You had to be able to build. The AI shift feels like that again, only faster. What I saw then, what's different now, and what I'd do about it.
Careers · AI · Front-end · Leadership6 min read
- Engineering
Don't Install Yesterday's Release
Most malicious package releases are caught within hours. A one-day waiting period before installing anything new costs almost nothing and sidesteps a whole class of supply-chain attacks. Here's how I set it up, and where the exceptions go.
Security · Infrastructure · Next.js6 min read
- Product
Shipping a Real Product in 24 Hours
Why I still build products against a one-day clock, and the habits that make it work: cutting scope hard, using the same stack every time, letting agents do the heavy lifting, leaning on a design system, and agreeing on what 'done' means before I start.
Product · Prototyping · Agents · Design systems8 min read