Chris Shiflett http://shiflett.org/ en-us Chris Shiflett is an entrepreneur and web developer focused on building community and bettering the open web. Building an MCP Server for My Lab http://shiflett.org/blog/2026/building-an-mcp-server http://shiflett.org/blog/2026/building-an-mcp-server I’ve had a ~/local directory full of projects for as long as I can remember. I have my own ~/local/bin of command-line tools I’ve made over the years, and individual projects live in ~/local/{project}. It’s my personal lab.

Over time, my lab started to look a little bit like a graveyard of ideas. A few were active, but most were unfinished.

Last year, I started to tidy up a bit. I archived old ideas I’m no longer interested in. I made Landice work again; I rebuilt the infrastructure for Faculty (and recently redesigned the website, too); I rebuilt my personal server; I made a proper website for Roost; I built a travel log for a local Scout troop (inspired by Landice); and I built a tool to help me stay on top of school emails called Schoolcase (sort of like TripIt for school and activities).

In my last blog post, I described my reluctance to adopt AI. It was being hyped by a lot of the same people who spent years hyping Web3. But I gave it a chance, and I’ve been pleasantly surprised. It’s gotten better, and although I do wonder if the body of work it’s learning from is getting worse, it’s useful in this moment.

When it comes to new technology, some people like to jump right in. Others take the stairs, which might look something like this:

  • Use chat as a reference. Sometimes all you need is a reminder or nudge in the right direction.
  • Use chat as a rubber duck. Sometimes you just need to talk through a problem, and the solution becomes apparent while you explain it.
  • Use chat as a collaborator. You do the typing; you both do some thinking. You talk through problems. You plan. You ask for pushback and critique.
  • At some point, you start to let chat write some code to speed up the process.

Whether you jump right in or take the stairs, once you start building with AI, you’re in the same place. This is when things change. Beyond this point, rather than describing AI as chat, I like to describe it as a robot. It’s more capable, and the way you interact with it becomes multifaceted.


Like many before me, I ran into some familiar problems.

The first problem for me was a direct result of a personal preference. I prefer Claude’s chat interface by a large margin. It uses a lovely serif font and a pleasant color palette. Plus, the responses from Claude Code are clearly geared toward execution, not thinking, making it less suitable as a collaborative partner. Good software has a lot more to do with the thinking.

When using the chat interface, I’d have a choice to make when I arrived at a solution — switch to Claude Code and ask it to help implement the solution, or stay in chat and copy and paste code snippets or full files. (A third choice would be to continue writing all of the code myself, but I wanted to work alongside my robot.) Regardless of which path I took, I was dissuaded from participating. It felt like an all-or-nothing decision, not the way I wanted to work. If I stayed in chat, the working files would diverge from the real ones the moment I did anything myself. And Claude Code — which at least has access to the same files you do — is designed to do the work for you.

My robot agrees:

The asymmetry is real: I have hands on the codebase, you’re watching the output scroll by. Even when I narrate what I’m doing, the rhythm is “I do, you approve.”

The second problem was a lack of memory. If a conversation with your robot runs long enough, you need to start a new chat, and you get a new robot that doesn’t remember anything. The forgetting isn’t a flaw; it’s statelessness — each conversation starts from nothing. There are lots of solutions to this problem. I started simply, with Markdown files. Before starting a new chat, I’d ask my robot to update a Markdown file with everything from the current session. This approach works, but it has some downsides. Because I was pasting entire files, every update risked data loss. And, as with code, I found myself dissuaded from making updates myself, leaving everything to the robot. Accuracy drifted, because I wouldn’t bother making small corrections.

The common thread is this: when your robot makes a change, it changes a copy. You paste that copy back over the real file by hand, and if you’ve edited that file yourself in the meantime, your edit is gone. The last save wins. It makes editing your own code feel risky. Every change you make becomes a debt you owe the next paste, and if you forget to pay it, your work vanishes. So you stop. You fall into directing your robot to do everything, because it feels safer to work that way, and you end up with a workflow that punishes you for participating in your own project.

There are solutions to these problems, solved by people long before I encountered them. But many of them focus on solving problems exclusively for the robot. For example, a common approach is to put your knowledge in a vector database the model can search. That works, and it’s the same general approach I’m after: fetch what’s relevant before answering (this approach is known as RAG). The difference is what the knowledge is. A vector store is something only my robot can read. I want something I can read, too. I don’t want to be left on the outside of my own project’s knowledge.

So I decided to build an MCP server for my lab.


MCP is an open standard for connecting AI apps to external systems. For developers, it’s a way to make anything you build available as a tool your robot can use.

I had used MCP in Chrome already. Giving Claude access to Chrome — a browser I don't otherwise use — seemed safer than giving it access to the browser I do use, and with developer tools it could inject things into the DOM, which turned out to be a nice way to quickly prototype ideas.

I had also recently used Directus on a client project, and it ships with an MCP server, which turned out to be a nice side benefit for the client.

I wanted to learn more about MCP, and building my own server seemed like a fun way to do so. But there was a more principled reason, too: I wanted the boundaries on what my robot can touch to be decided by code I wrote, not inherited from whichever app I happen to be using.

The path of least resistance was Python. The most-traveled way to build an MCP server is to use a Python library called FastMCP, and every tutorial assumes it. I chose PHP instead — and not out of nostalgia.

I know Python, but I've been building with PHP for a long time, and it fits how I work — rarely in pure designer or developer mode, but usually a blend of the two. PHP’s roots as a templating language make it a perfect fit: you build logic in the same place you build the UI. This is why PHP and I still get along.

Plus, David Soria Parra — a former release manager for PHP and longtime PHP community member — is one of MCP’s co-creators. PHP isn’t an outsider choice in this ecosystem; it’s in the bloodline. There’s also an official PHP SDK for MCP, built in collaboration with the PHP Foundation and Symfony, and that’s what I built on.

The easiest way to get started is with Composer:

composer require mcp/sdk

Once you have the SDK, the server itself is simple — just a couple of includes and some tools mapped to methods (note the placeholders below):

use Mcp\Server;
use Mcp\Server\Transport\StdioTransport;

$server = Server::builder()
    ->setServerInfo('Your Server', '1.0.0')
    ->addTool([LibraryTools::class, 'methodName'], 'tool_name')
    ->addTool([LibraryTools::class, 'anotherMethod'], 'another_tool')
    ->build();

$server->run(new StdioTransport());

This maps a tool called tool_name to a method called methodName (and a tool called another_tool to anotherMethod). They’re often the same name, but they don’t have to be.

The next step is to configure your MCP server in a file called claude_desktop_config.json. (MCP is supported by ChatGPT and others, too, and this is the only step that differs.) The easiest way to find the file is via the Edit Config button in Settings → Developer in the desktop app. If there isn’t one yet, you can create it with that button and then populate it with the following (adjust paths as needed):

{
  "mcpServers": {
    "lab": {
      "command": "/path/to/php",
      "args": [
        "/path/to/server.php"
      ]
    }
  }
}

The last step is to restart Claude desktop. Claude will run your server, and the tools you added with addTool() will be available to your robot. If you want to test your server first, just run it from the command line — but note that no output is what success looks like.

What I’ve built here is a local MCP server. It runs on my machine and talks to Claude over stdio. The SDK also ships an HTTP transport, so you could put a server on the internet instead. The tool code wouldn’t change — just the transport. Hosting it is a different exercise than a normal PHP site, though. A normal site handles a request and exits, but an MCP server needs to stay running, so you'd run it as a process behind a web server like nginx rather than as a typical PHP app.

That's the whole MCP picture. Local or remote, the server is a set of tools and a transport. If that’s what you came for, you’re all set; the rest of this post is about the particular lab I built on top of it.


I wanted my library to be as accessible to me as it is to my robot. Markdown files are the obvious choice, but I wanted to think through how they would be organized.

I decided to lean into the library metaphor. My library is comprised of three concepts:

  • A shelf is a directory in the library
  • A book is a Markdown file
  • A chapter is a section (##) in a Markdown file

Reading from this library is pretty straightforward. AI loves Markdown, so file_get_contents() is just about all you need:

public function read(?string $project = null, ?string $book = null): string {
    $path = $this->resolveBook($project, $book);
    return file_get_contents($path);
}

Updating is a little different. I wanted to give my robot the ability to create or update a book, but I decided that if a book has chapters (i.e., if it’s long enough to warrant sections), the robot should only be able to update one chapter at a time. For shorter books (without chapters), it’s allowed to replace the entire book. This addresses one of the problems with pasting entire files: when my robot is updating everything, information can easily get lost.

In the end, I built standard CRUD tools, but I decided to leave out the D (delete). Removing something from the library requires human intervention, because that’s the kind of friction I want. Creating knowledge should be easy; destroying it shouldn’t be.


The library is half of the lab. The other half is the workshop. I wanted to give Claude’s chat interface the same ability to edit code as Claude Code has, with similar boundaries. If you use Claude Code from the command line, it’s bound by where you are. That’s good, but I wanted something more specific to how I work, and I want Claude to only have access to what I’m currently working on through interfaces I scope.

Claude Code’s main editing tool is a string replacement — find an exact block of code, swap it for another — and that’s what I wanted in chat. So the lab has an edit tool that does the same thing: it’s a str_replace with an additional check. If the string is missing or appears more than once, it refuses with an error message that lets Claude know why. It’s the same spirit as updating a single chapter instead of rewriting a whole book taken one step further, and because it patches the file in place rather than pasting a fresh copy over it, an edit I made myself can’t silently disappear.

I start a working session by saying, in plain words, that I want to work on a project. The server records the project and today’s date. While the session is open, the tools can read and write within that project’s root.

The boundary doesn’t rely on a single check. It’s defense in depth. The first layer of defense is filter input. Project, book, and chapter names must match a strict pattern — lowercase letters, numbers, and hyphens only. A name that matches cannot contain a slash or .., so directory traversal is impossible before a path is even assembled. The second layer is to use realpath to confirm the path is inside the project root. That catches anything the first layer might miss, like a symlink pointing somewhere it shouldn’t.

None of this is new. It’s the same stuff we’ve been doing for years applied to a new kind of tool.

There are two other properties I enforce. First, one project at a time, declared in a file I can read. Second, the session expires at the end of the day it was started. This is as much for me as it is for security. Working past midnight requires a deliberate request to reopen the project. That small bit of friction arrives exactly when I might need it most, when it’s time to close the laptop and go to bed.


Once my MCP server was ready, I put it to the test. I opened a new chat — a robot with no memory of any of this — and I said I wanted to work on the lab.

It read the overview. It read the brief, chapter by chapter: what was done, what was in progress, what was next. It read the books. And then it gave me an accurate, prioritized summary of where the project stood, and asked me what I wanted to focus on. A fresh robot, up to speed and ready to work, in seconds.

That was the forgetting solved. And when Claude and I are both working from the same files, editing stops being a risk. I noticed it the first time I fixed something small. My initial instinct was to tell my robot to do it, because that’s how I had learned to keep the working copy updated, but then I remembered I could just fix it myself. There’s no working copy to reconcile, because there’s no copy. I’m a participant again, not a director afraid to touch anything.

The later versions of the server were built using the server itself. The lab is now being built in the lab.

For some people, participation is inefficiency. For me, it’s what I love to do. I make things.


As weekend projects go, this was a pretty good one, and now that I’ve used it on some real work, I can honestly say it’s a better way for me to work with my robot.

My lab used to be a graveyard of ideas. It still has quite a few unfinished projects, but now there’s a library that remembers them (useful with or without a robot) and a workshop with boundaries I built myself.

It isn't finished, but if you're a PHP developer who'd like to try it, let me know.

]]>
Wed, 27 May 2026 00:00:00 -0600
Just You Wait http://shiflett.org/blog/2026/just-you-wait http://shiflett.org/blog/2026/just-you-wait I turn 50 today.

I feel incredibly lucky to have experienced these particular 50 years.

I was born in 1976 — when Steve Jobs and Steve Wozniak founded Apple, the year after Bill Gates dropped out of Harvard to start Microsoft. But I grew up largely without technology. To me, technology came in waves, and it was always exciting and new.

I remember the Atari 2600, and later the Nintendo. The Commodore 64. The acoustic coupler in War Games. My first PC. The turbo button that made it fast (50 MHz). The sound of dial-up. I remember BBSes and MUDs. Archie, Gopher, Veronica, and the World Wide Web. I was there for all of it.

1994 was a big year for me. I graduated high school in the spring, and started college in the fall. Swamp Ophelia came out that year, and I’ve been an Indigo Girls fan ever since. (I just saw them on Tuesday.) It was a huge year for technology, too. Linux 1.0 was released, the World Wide Web went mainstream, and the W3C was founded. Netscape was released. Amazon was founded. Yahoo! came online. Rasmus created PHP. Even the QR code was invented in 1994.

I loved technology. I ended up switching my major to computer science, because it had the word computer in the name. I learned everything I could and exhausted the curriculum. The department chair told me I should learn HTML, because my C programs could output HTML, and that was the way to build the UIs of the future. I just had to print a couple of extra lines (HTTP headers, but I didn’t know that yet), and voila! I was a web developer. Perl made some things easier, and PHP made them easier still.

When I graduated, I got a job at the USPS in Memphis, and within a couple of years, I was leading one of the most important teams in the organization.

It didn’t start that way. Academia had given me a lot, but the job demanded more. I stopped by Borders every night on my way home to read books and decide which one I was going to buy. A lot of the good ones had animals on the front. (I would later write one of those.) My second bedroom had a dozen servers and half a dozen workstations, most of which were bought on eBay, some of which I built myself. I ran every OS imaginable — multiple flavors of Linux, BeOS, and even Windows. I was building with ColdFusion and Solaris during the day, PHP and Linux at night. I learned all about networking and routing tables. I built my own device drivers. I built Quake to run in ASCII, because Quake was open source. I wrote shell scripts (and had an especially fun time with Expect) and made web apps. I built APIs.

For a few years, I was learning faster than at any other time in my life. I don’t know exactly when it happened, but I went from feeling like I was in over my head to feeling incredibly competent.

I could do anything.

My team built a solution for providing every US citizen with a personal digital certificate. We also built a universal registration system for all USPS services. It was called eServices Registration. I was in a lot of meetings about it, including one with Microsoft, who wanted us to integrate Microsoft Passport. I asked some questions in that meeting, particularly regarding their use of cookies and a recent cookie vulnerability in Internet Explorer. I left that meeting having disclosed a security vulnerability to Microsoft that I discovered just by talking to them, and it led to my first article, published in 2600 Magazine.

This began a deep interest in HTTP and security. You couldn’t view source to see HTTP in the same way you could see HTML, so I made a proxy called Protoscope that would add HTTP request and response details to the HTML. This was years before Firebug. Protoscope taught me HTTP, and I knew it better than any spec, because I got to see how things were actually working. (For many years, the best reference for cookies was a spec published by Netscape, not the RFC.) I ended up writing one of the first books on HTTP.


We lived in Manhattan when we first moved to NYC, above the famous B&H Photo on 34th Street. I worked on 14th Street building eDonkey, which became the world’s largest P2P network. I handled everything server-side and called myself a webmaster. Being the largest P2P network in the world during the height of file sharing meant we were in the news almost daily. I bought server hardware (including two Cisco LocalDirectors) on eBay and learned a lot about networking security and scalability. It was estimated at one point that eDonkey traffic accounted for 40% of all internet traffic worldwide.

My RSS feed dates back to 2003, which is when I started calling my website a blog. I wrote about CSRF that year, and my now-canonical article was published in 2004. I didn’t fully appreciate my luck at the time, but my curiosity had led me to security during the most influential moment possible. The security standards we still use today were mostly established in those years, and I happened to be the one making a lot of them.

There was a moment when someone named Marc and someone else named Mark wanted to hire me. One was famous (Netscape), and the other was working on something called TheFacebook, which seemed like a silly name.

In 2009, I went to Iceland with my friends Andrei and Helgi. During the trip, we built a map journal called Landice. The sunset in Stykkishólmur was a turning point. I came back home with a desire to create scalability problems instead of solve them.

This began a new period. I moved into a shared studio in Dumbo that would become Studiomates. I met Tina, Jessica, and Cameron. I immersed myself in design and product.

I started Brooklyn Beta, perhaps the thing I’m most proud of to this day. Ira Glass interviewed Tavi Gevinson (when she was still in high school) and made a balloon animal for my daughter Tegan; Tony Fadell spoke about the iPod a week before he announced Nest; and Cory Booker dropped by on his way to campaign with Obama. John Maeda and Aimee Mann were in the audience, as were the founders of Kickstarter, Pinterest, Shopify, and Airbnb. Letterboxd was introduced there. It started small — about 100 people the first year — and grew to about 1,500 people for the final two years.


I don’t know exactly when it happened, but at some point I lost my spark. Technology was no longer inspiring. Developer experience became a thing — it’s sort of like trickle-down economics for technology. The web was rebuilt with JavaScript, and nothing worked anymore. Experimentation was replaced with extraction. Tech giants built walls. Google’s browser became dominant, and they started flexing that power.

Then came the blockchain, cryptocurrency, and Web3. The people building it were young and didn’t know the web we lost. All they knew was what remained, which made anything new seem like an improvement. I tried to get into it, honestly. I invented a card-trading game for the 2018 World Cup that was one of the first NFT projects on OpenSea. I backed Peacefall and won some tournaments. I bought Bitcoin and Ethereum. I gave it a chance. But nothing felt new and exciting.

Technology had a dark side, too. Cambridge Analytica. Myanmar. Brexit and Trump. Surveillance as a business model. Ethan put it succinctly: “the web I grew up in looks very, very different from the web today.” I wasn’t the only one feeling uninspired. Some of the people I trusted and admired the most got quieter. Maybe you did, too.

And on top of it all, we had a pandemic to contend with.

I pursued meaning in my work. After meeting a neuroscientist who had developed an algorithm to measure happiness, I founded a neuroscience company with him that aimed to help people live longer, healthier, happier lives. His idea was to have people rate events in their calendar to gauge how they were doing. My idea was to use photos instead. We built a good product and made meaningful progress in the science of mental health. But it didn’t give me my spark back.

Faculty remained through it all, doing good work, but in my absence its reputation had waned. In some ways, I suppose I had, too.


Some people had been talking about AI for a long time, but now it was everyone. The people hyping it were mostly the same people who were hyping blockchain and Web3. The people with a lot of experience and perspective weren’t. It was easy to dismiss.

But I’ve never been good at dismissing things. I’d given Web3 a chance, and I wasn’t going to pretend I was above giving AI one, too. When everyone started fawning over ChatGPT, my curiosity got the best of me.

AI had plenty of problems. It was wrong a lot. It certainly wasn’t being fueled by generosity. Instead of Sir Tim Berners-Lee, we had uninspiring billionaires. The money being burned was hard to fathom — companies like OpenAI were losing more, faster, than any company in history. The knowledge it possessed was taken without consideration for who owned it. It felt like a continuation of technology’s downward trend. To some of you reading this, that’s still all it is.

I started using it the way I used to use YouTube — to learn things. I even used it to diagnose a commercial furnace at Roost that wasn’t heating anymore. Everyday things.

Somewhere along the way, something changed. I stopped using AI to learn things I didn’t know and started using it to rediscover things I did. I rebuilt infrastructure I had neglected for years. I revived old projects. I made Landice work again. I started making things again.

Something else happened, too. I stopped thinking of myself as washed up. For years, I had described myself as a former whatever. I only ever allowed myself to be one version of myself at a time.

But depth doesn’t expire.

Building with AI has also helped me realize that my security expertise might matter again. I asked AI about CSRF, and it answered with my own explanations from decades ago. I thought that might bother me, but it didn’t. I never wrote those articles to accumulate status. I wrote them because I wanted to share what I had learned. I gave that work to the open web. I never imagined my words would be recited back to me by a robot. But maybe that's the tradition working as intended: people share what they know, so someone else can build on it.

For the first time in years, I see possibility. Not utopia. AI’s problems aren’t being exaggerated. Like every technology before it, it will reflect the people building it. But possibility is the right word for what I’m feeling, and I haven’t felt it in a while. Not just for young people who haven’t lost their enthusiasm. For people who have been here long enough to remember when the web was open, generous, optimistic, and built by people who simply wanted to make things and share them with the world. That sharing was an expression of our gratitude, and that gratitude is still there.

I think experience matters now more than ever. I think curiosity matters. And I think a lot of people who may have quietly counted themselves out have something important to contribute.

So here’s my birthday wish, for me and for you: let’s be curious and generous. I plan to spend a lot of my time making things again. I’d love some company.

I’m 50 today, and I’m just getting started.

Just you wait.

]]>
Thu, 21 May 2026 08:37:10 -0600
Good products begin with good decisions http://shiflett.org/blog/2026/good-products http://shiflett.org/blog/2026/good-products Faculty has been a product studio for ten years. This week, we’re launching something new: a productized engagement called the Faculty Sprint.

Ten years ago, building products was slower and more expensive. Clients spent real money to refine an idea before committing to it, because the risk of taking the wrong path was enormous. We called this part of the process discovery, and we were very good at it. What people want is someone who can see the shape of an idea and distill its essence, so what gets built is something users comprehend and love. After that, building is the easy part.

A lot has changed since then. Building is faster, cheaper, and more accessible than it’s ever been. Some people think decisions matter less, because if you get it wrong, you can rebuild quickly. In practice, the opposite is true. When execution is cheap, the allure of progress carries teams forward, justifying their bad decisions instead of pausing to fix them. It doesn’t just enable bad decisions. It normalizes them. Good judgment is the differentiator now in a way it wasn’t ten years ago.

Sometimes the most important decisions are smaller than they sound. I’ve watched products reach clarity the moment the URLs got settled. URLs are the clearest expression of information architecture, and once they’re right, everything downstream gets easier. Small, early decisions tend to work like this. They look unimportant in isolation, but they compound and clarify.

This is what the Faculty Sprint is for: getting the small early decisions right.

We focus on the shape of the idea. Sometimes the decision is what not to build. Sometimes it’s how to position the product so people understand it. Sometimes it’s the details of the UI. We spend the first part of the engagement on the decisions, and the rest of it making those decisions real.

May is taken. July and September are open. Apply at faculty.com/sprint or reach out to learn more.

]]>
Mon, 11 May 2026 11:22:02 -0600
2025 Recap http://shiflett.org/blog/2026/2025-recap http://shiflett.org/blog/2026/2025-recap Per tradition, my first blog post of the year is a recap of the prior year. Here’s what I remember from 2025.

I’ve been writing these recaps for many years now, and I’ve also been reading everyone else’s. It’s clear that 2025 was a challenging year for a lot of people. Let’s look out for each other, support each other, and hope that 2026 can be a little better.

In last year’s recap, I made this commitment:

Optimism is the antidote to despair. For my part, I’m doubling down on building community, strengthening relationships, supporting people, and trying to make a difference.

I’m going to give myself credit for this one, even though I’ll admit it hasn’t always been easy to stay optimistic.

Much of my year revolved around my three labors of love: Faculty, Studioworks, and Roost.

Faculty

Faculty has built a reputation for doing good work over the years, and it continued to be both a source of pride and a source of uncertainty for me.

For the last few years, I’ve been anticipating a pendulum swing that has yet to materialize. When Andy Bell wrote about how hard last year was, it made me realize that we weren’t alone. Despite our struggles, I think those who aren’t participating in the race to the bottom might be poised for success in spite of it all.

It’s estimated that 90% of startups fail, so if that is your expectation, it makes some sense that fail fast is such a popular concept. The problem, of course, is that this leads to widespread mediocrity, and a lot of good ideas aren’t given a chance to succeed.

If you have a good idea and want to give it the best chance of success, consider hiring Faculty. (To get started, you can email me personally.)

Studioworks

Studioworks officially launched in October, after months of hard work. We aim to be a complete solution for creatives and freelancers who want a simpler way to run their business, so they can spend more time doing the work they love.

We started with invoicing, partly because we noticed a widespread trend among all of our competitors to skim a little off the top of every payment processed through their platforms. Our business model is simple and honest: we charge $39 per month, and that’s our only revenue. We win when our customers win.

Studioworks is opinionated in quiet ways. We focus on the parts of running a creative business that affect trust, clarity, and how seriously you’re taken by clients. Here are some examples:

  • Professionalism - Studioworks is designed to make you look professional without making you look generic. All invoices and client pages are hosted on your own subdomain, presented in colors and type that you choose, and free of a lot of the third-party branding noise that makes free platforms feel so cheap.
  • Customizations - We spend an unusual amount of time on color and typography. Not for novelty, but because these details signal care and craft.
  • Security - Because you’re on your own subdomain and we know what we’re doing, we don’t have to take a paranoid approach to security and do things like log you out all the time or require silly password rules. This affects your clients, too. The result is small conveniences that add up, and you look more polished and competent.
  • Reminders - We want to respect the fact that you own the client relationship, not us. We never email your clients without letting you know first. No more embarrassing reminders for invoices already paid.
  • Line items - Your work doesn’t always fit neatly into “hours × rate” so we don’t force it to. Fixed fees are presented simply, and we offer more flexibility when you do need to charge in multiples. For example, charging “3 × $500 per item” makes it clear that you’re not charging an hourly rate that might invite scrutiny from finance and delay payment.

In short, Studioworks is designed to help creatives and freelancers look professional and streamline running their business.

I’m excited about all that 2026 has in store for our customers. Proposals, time tracking, file sharing, and a client hub that facilitates everything from contracts to approvals are just a few examples of what we have on the roadmap.

Roost

Running a coworking studio in a world where more people than ever are working from home has its challenges, but I still love getting to work at Roost every day.

I started Roost after realizing that “coworking” had slowly been co-opted by companies chasing scale and margins. What I wanted instead was something smaller, more intentional, and more human — a place for people who genuinely like working around other people (you know, coworking).

Roost is a true coworking studio. There are no private offices. We do have meeting rooms you can book for calls or meetings, but the expectation is that it’s fine to be visible, take calls at your desk, and make a little noise. It’s a space for people who feed off of the energy of other people working.

We’re community-first, but we don’t force it. We don’t offer day passes or short-term memberships, which means the people you see every day are the people you’ll keep seeing. Over time, that creates a familiar, neighborhood-like feeling. It’s worth getting to know people because they’re not just passing through.

We’re also flexible in ways other coworking spaces can’t be. We don’t police meeting room hours or enforce rules we don’t need. Instead, we rely on mutual respect and a shared sense of responsibility for the space and the culture.

Roost isn’t for everyone, and that’s by design. But for the right people, it’s a calm, welcoming place to do good work. I’m proud of what it continues to be, even as the world around it keeps changing.

The rest of the year unfolded in smaller moments — family milestones, injuries (unfortunately), recoveries, trips, concerts, and other small moments that matter (to me). Here are a few things that stood out, month by month.

January

  • Tegan tried scuba diving and loved it.
  • Jessica and I hosted a few Studioworks AMAs.
  • Jessica and Nick visited Boulder, and we held a special Studioworks event at Roost.
  • I started strength training in an attempt to regain my lost athleticism.

February

  • I started playing pickup soccer again.
  • I got recertified in CPR and Wilderness First Aid.
  • I attended Klondike with Killian and Troop 78.

March

  • Snowshoe hike in RMNP.
  • We went skiing in Breckenridge, one of our favorite places.
  • Tegan and Killian both won an award for their work with the Library Teen Advisory Board.

April

  • Soccer season started. Strength training paid off, and I was back to scoring goals and loving it.
  • Then I got injured.

May

  • Tegan graduated from middle school.
  • Tegan and Christina went to NYC to celebrate.

June

  • I had knee surgery for the second time.
  • We began onboarding Studioworks customers with 1:1 sessions.
  • On June 30, we rolled Studioworks out to all Founding Members.

July

  • Indigo Girls at Red Rocks. I didn’t get to meet them this time, but it was still awesome.

August

  • I bought the Switch 2 with Mario Kart World. Fun for the whole family.
  • Killian went on a backpacking trip with Scouts I was meant to lead, but I had to miss it due to my injury.
  • Creative Mornings Boulder!

September

October

November

  • Tegan had her wisdom teeth removed.
  • Joy Oladokun at Boulder Theater.
  • Christina got to accompany Killian on a Troop 78 trip to the Great Sand Dunes.
  • My dad visited Boulder while on a multi-day road trip. It was great to see him.

December

December was very full. Or maybe I just remember it better, since it just happened.

Early in the month, Jessica and I were on a couple of podcasts:

  • Design Better, hosted by Eli and Aarron, explores the intersection of design, technology, and the creative process.
  • ShopTalk, hosted by Chris and Dave, is a weekly podcast about building websites and the people who make them.

My mom visited Boulder and got to experience the early Christmas season, including seeing Tegan in the Christmas parade.

We hosted a very special event at Roost featuring Kelli Anderson, Erica Heinz, and surprise guest Rosston Meyer from Poposition Press. Right before they arrived, the power went out. Here’s what I wrote the next day:

Last night didn’t go as planned. Somehow it was even better.

The power went out just before Kelli Anderson and Erica Heinz arrived. Candles came out. String lights ran on batteries. We poured mulled wine and spiced tea, set up the battery-powered projector, and gathered closer.

Kelli and Erica were incredible, and we had a surprise guest: Poposition Press! The room was warm, attentive, and fully present. It felt intimate, human, and quietly magical.

Grateful for everyone who rolled with it and made the night what it was, and thanks to Dylan Zsigray for taking some photos.

I’m already planning more events in 2026 and cannot wait. Dan suggested we take the blackout vibe (candles, intimacy) to future events, even when we have power. I like it.

I took 6 kids to see Zootopia 2 (Tegan, Killian, and Riley each brought a friend). I love the cinema and thought Zootopia 2 was very cute.

2025 was hard in ways that don’t always show up cleanly on a timeline, but I’m still here, still building, and still grateful for my family, friends, and the people I get to work with.

]]>
Tue, 06 Jan 2026 15:27:09 -0700
Studioworks http://shiflett.org/blog/2025/studioworks http://shiflett.org/blog/2025/studioworks

Studioworks is live!

I can honestly say Studioworks is the best invoicing platform out there, with the lowest fees, best design (and most design customizations), and simplest UI.

But that’s not all we’re about. We’re building a company that honors and serves creatives, because we think creatives can help us imagine a better future. We’re building a company with a simple, honest business model, because we want to prove that it’s possible. We’re building a company with strong values, because we think values matter.

We don’t offer free trials, but to celebrate our launch, we’re offering a free month to anyone who signs up with a referral link. If you’re curious to try it out and support a small team doing things a little differently, here’s mine:

https://studioworks.app/join/chris

Our new marketing site has some fun interactions, too, including some of the design customizations we use in the product:

https://studioworks.app/

Thanks to everyone who has given us your support, enthusiasm, and feedback along the way. We're very grateful.

]]>
Wed, 08 Oct 2025 17:00:00 -0600