Coding with Jesse

From Full-Time to Freelance: How I made the leap

Laptop and a coffee

I was already dreaming of starting my own business before I ever got my first job. My very first job was at a movie theatre in the late twentieth century. In my breaks I would brainstorm ideas for starting a web design business. I would fantasize about proposing to redesign the movie theatre's website. When the boss wasn't looking, I would sketch out my web site and my pricing on scraps of paper.

Later, I got my first programming job, working on a content management system. I learned a lot about business at that job. The company would always be bringing in new clients. Even then, I would fantasize about being able to have my own clients one day. I would read books about self-employment and consulting. I'd read anti-work websites and dream of getting out of the rat race.

A few years later, I met my future wife and moved to Berlin, Germany to live with her. I had the best excuse for quitting my job back home, and saw it as a chance to start my own business. Almost exactly twenty years ago, I registered a business name, "The Future of the Web", bought thefutureoftheweb.com, and started blogging about web development.

Unfortunately, I had only three months to find a job in Berlin before my tourist visa would expire. I went to an Internet cafe every day and applied to 3+ job postings, hoping my Java experience would make up for my inability to speak German. Extremely luckily, I was hired by Strato Rechenzentrum, a major Internet hosting company. When I received my work visa, I was surprised to see that it had two conditions: I was approved to work at Strato, but I was also permitted to do freelance work ("freiberuflich arbeiten").

While at Strato, I continued to fantasize about breaking free of employment and working on my own terms. I would read every article I could about self-employment or freelancing. I would listen to audiobooks and podcasts, and just surrounded myself with content that inspired and motivated me.

One day, I got up the courage to tell my manager about my work visa condition, and to ask whether Strato would allow me to do freelance work on evenings and weekends. My manager saw no issue with it, and he verified this with HR. I was given the green light to go ahead.

I had already been blogging about web development for a little while, so I updated my blog to make it clear I was available for hire. I published "Hire an Ajax Freelancer" to boldly announce that I was available to take on some JavaScript and Ajax work.

A month later, someone found me and asked me to do a small UI thing. I charged $100/hour, worked for three hours, and billed the person $300. He paid me on PayPal a few hours later. It was the best feeling in the world!

I continued doing work for this person, and the next month someone else contacted me for a small job. I was soon making $500-1000/month in my free time, on top of my full-time salary work at Strato. It was tiring, but I was so highly motivated and inspired, I knew that I had to push through to make it to achieve my dream.

When my then-girlfriend finished school, she wanted to take six months off and live in my hometown in Canada. I quit my job at Strato and announced I was Freelancing Fulltime This was the ultimate test: could I survive off of freelancing alone? If it failed, I felt like I would be able to go and find another job, but I was hoping it wouldn't come to that.

I put the word out privately among friends, and my friend's uncle hired me for a much larger project. I continued blogging regularly to try to promote myself by sharing my expertise. I was fortunate to have people contact me for new projects every few weeks. Two months in, I published Freelancing: First two months. I was approved to speak about Unobtrusive Ajax at The Ajax Experience conference in Boston, and got to meet my idols like John Resig and Douglas Crockford. Eight months in, I published Freelancing: First eight months.

It was a wild experience, and the momentum was growing. It was in the following months that I found three clients in particular that I would continue working with for years. Two of them are still my active clients that I'm working for this very moment.

Do you also dream about leaving your job and starting on a similar path? There are a lot of things you can do right now, while you're still working in a full-time job:

  1. Be clear about your goals, and visualise the life you want to live.
  2. Surround yourself with content that inspires you and reminds you of moving towards your goals. These could be books, social media accounts, YouTube channels, podcasts, etc.
  3. Start putting out content that demonstrates your knowledge and expertise. Share everything you learn. Share resources and tips. You could start a blog, a professional social media presence, a mailing list, a podcast, or whatever you feel inspired and motivated to do.
  4. Start a business. Depending on where you live, you'll need to register a business name, have a lawyer give advice and help draft a standard client contract, learn about taxes from an accountant, and probably purchase extra business insurance.
  5. Find out if your employer allows you to freelance on evenings and weekends.
  6. If so, put out the word on social media, and put the word out amongst friends and families so they know what you're looking for.

Worst case scenario, you get to learn whether or not self-employment is really something for you, and hopefully get to earn some extra money on the side. Best case scenario, you'll be laying down the foundation of your new business and a path to freedom! I'm very excited for you and wish you all the best of luck! If you choose to go on this journey, please let me know and keep me updated!

Published on January 14th, 2025. © Jesse Skinner

Dear Recruiter: I am not interested in a full-time job

Dozens of cubicles in a depressing office. Photo by kate.sade on Unsplash.

Dear Recruiter,

Thank you for contacting me, but unfortunately I am not interested in a full-time job. There is no way in hell you'll find me in an office nine-to-five Monday-to-Friday. I've been there, done that, and it was a living nightmare.

No, you don't need to circle back in three months to see if my situation has changed. I'm not available for employment, and I never will be.

Yes, I understand that the position offers benefits. My position offers many more benefits. I can work whenever I want, wherever I want, and for whomever I want. I can have a two-hour nap in the middle of the afternoon if I want to. I can go out with my wife for three hours on a random morning. I can pick up my children from school and go to a playground.

You think it's cool that you have a daily standup meeting at 10am? I haven't had a meeting in months. I have nothing work-related in my calendar at all. I talk to my clients over email. Sometimes I ask them for a phone call, and I'm always happy to hear their voices. They leave me alone to do my best work and they never give me deadlines. They have no expectations for me on any given day. They trust that I'll make good, steady progress every week. They know that in an emergency, I'll drop everything to help them.

Your company is offering a competitive salary? I make more than that working part-time. I raise my rates every few years and simply let my clients know. Sometimes they choose to stop working with me, which is sad. But it's okay because I have other clients who happily pay more. It's not as tragic as your upcoming layoffs would have been.

Your company has management opportunities? Sounds terrible. I work one-on-one with business owners who I've worked with for decades. We trust each other and have become good friends. I understand what they want and need, and the trade-offs they're willing to make. There's no game of telephone trying to guess what upper management wants. No waiting for approval from board meetings. No politics at all.

Your company will pay for me to move to another city? You must be joking. I work from my home, and I always will. Well, sometimes I choose to work on an airplane, or in a waiting room, or in a coffee shop. One place you'll never find me is at a desk in an office building.

So no, I'll never be interested in joining your growing team. I'm in a very happy long-term relationship with my clients. There's no way I'm going to leave them high-and-dry to become a cog in your machine.

I wish you good luck on your search. And I wish all the best to whomever you manage to enslave.

Sincerely,
Jesse Skinner
Freelance Web Developer

Published on January 7th, 2025. © Jesse Skinner

Empower your clients to make changes

A woman fishing

When a client asks me to make a change to a website, I have two choices. I can go and make the change. Or, I can set things up so that the client can make the change themselves.

It's not always obvious which of these two will be a better use of my time. If it's a one-time change that will never need to happen again, of course it's better if I go make the change. But sometimes it's obviously something that will need to be changed again and again.

Sometimes the change is so small that it's a quick copy & paste, so there's almost no benefit to adding a content management system. Often, the changes can be more complex, and require a lot of back-and-forth communication, asking for clarification, testing, reviewing, etc. I have a pretty low tolerance for this before I insist on building a tool for my client instead.

Pretty much every system should have some kind of administrative login area, where the client can go in and access these admin-only tools. It might be as complex as a content management system, where they can create whole new pages, and change all the text in the system. It might be where they manage other users, or get the answers to questions they might have otherwise asked me for.

In one case, I had built a system that had a complex set of rules, basically if/then statements, and it was evolving rapidly. Every week I was being asked to make changes to the logic, and also asked to remind the client about what it was already doing. So, in a few days, I designed and developed a Domain-Specific Language (DSL) that allowed all of the logic to be captured in a single text file. It wasn't a programming language, because my client isn't a programmer. Rather, I designed it to be intuitive for him, so it would be easy for him to read, edit and publish changes to the logic in the system. Many years later, he is still actively working with this same DSL.

I have another client who is more technical, and has some experience with basic HTML and CSS. They wanted to make broad changes to the design of the site, and to the text that was hardcoded throughout. I gave them two options: either they could provide me with a long list of these changes, or I could bring them in to collaborate on the code. They had no experience with git, GitHub, Svelte, or even with using an IDE. I thought it was worth a try, so I sent them a long list of instructions for installing all the software they'd need. I sent them a few YouTube videos about using VS Code with Git, and had them create a GitHub account. I explained how the site was architected, and the basics of Svelte components.

Within a week, they were making changes to CSS and text and committing and pushing changes to GitHub! It was so exciting! Just looking at the long git diff, there were literally hundreds of changes. If they had tried to write out those changes in a Google doc, it would have required dozens of screenshots. It honestly would have been painful for me to carefully go through and implement all of the tiny changes. And chances are, I would have screwed up more than once, and they would have had to make new screenshots. They would've felt like a bother to ask me to increase the font size by 5%, or change a border to a different shade of grey. More than likely, they would have just accepted my poor attempt as "good enough" and said thanks.

Instead, they are now empowered to go in and make changes themselves whenever they want. As the site evolves, over the coming decade, they'll have the confidence to go in and make all the updates they need. They were even able to use AI to generate a snippet of Svelte code in order to add a second button to the page!

No, I'm not worried about my job going away. I'm happy to be focusing on the hard things, and empower my clients to do as much as they can on their own. They are delighted to not have to "bother me" for small changes when I'm working on bigger features for them. They're able to save money and time. It's truly a win-win.

Another client had a very complex system that was built by a third-party vendor and written in Python. They brought me in to help simplify the system. In this case, they actually did have developers on the team, but the developers didn't have much Python experience. I actually rewrote the entire system in TypeScript. It was a fantastic opportunity to clean things up and simplify. I wrote it in a way that it would be intuitive to them, so the training only took an hour or two. I was delighted to see the developers confidently making changes to the system themselves for the first time ever, and with ease.

A Chinese proverb says, "Give a man a fish, and you feed him for a day. Teach a man to fish, and you feed him for a lifetime." I say, "Make a change for a client, they'll be happy for a day. Empower your clients to make changes themselves, they'll be happy for a lifetime."

Published on December 10th, 2024. © Jesse Skinner

Staying off social media

Yesterday, I tried staying off social media and just read a book, watched a bit of MasterClass, and listened to music. It was a quieter day in my mind.

Normally, I would be scrolling through Mastodon or Instagram. I'd have a different emotional reaction every few seconds, from delight to disgust and everything in between. It's tiring, and I've been noticing the impact in my day-to-day life.

You may well be one to enjoy the occasional doomscroll, and I'm not judging you for it, or suggesting I'm better because I read a book. That's not what this post is about.

The point is that attention is a precious and highly valuable currency. It's called "The Attention Economy" after all. I'm suggesting that you be aware of how you're spending your attention, and what you're getting in return.

I know there's a cost to having my thoughts and emotions going along with these videos, or toots. To free myself from those costs, my awareness returns to my immediate surroundings. I start thinking about and putting energy into The Real World.

The downside is that I feel a disconnect from the rest of the world. There's a lot upsetting about the planet right now - genocide, ecocide, fascism, death, suffering, destruction. But right here, right now, it's a quiet Sunday and a perfect day for building a snowman with my son. We have a baby on the way, and family coming to visit, and Christmas coming up quickly. It's a lovely time in our lives.

So to add in stress and tragedy and worry and sadness, it doesn't feel right. My son doesn't need all of that energy coming into our home. There's absolutely nothing I can do about the world's problems.

Maybe I can write a Letter To The Editor, or to my member of parliament, about my feelings in regards to a war (or whatever). It's not going to make much of a dent.

Ok, maybe I can organise or join a protest. But then I have to be deliberate about my time and energy. But hey, an hour at a protest is surely more useful than an hour reading articles or watching the news.

If I just want to understand a geopolitical situation, I'm better off reading books about history. Chances are, I'm not actually that interested. I just feel emotionally drawn to look at videos of cities being destroyed, to feel my heart fill with outrage and sadness for these orphaned children.

There's a lot of news every day, but rarely is it of any significance. It's usually something mundane, and almost never about something important like the end of a war. And even when there is big international news, nothing changes for me. It's still a quiet Sunday perfect for building a snowman.

Most online content isn't at all relevant to me. It's outrage about one thing or another, politics from a country I don't live in, or something personal that happened to someone else, or cat videos. No disrespect to cat videos. Everyone loves cat videos. But they're forgettable. And when you spend hours consuming forgettable media, your life becomes forgettable.

There can be some discomfort in stopping - withdrawal symptoms - as my body craves the dopamine, adrenaline, ups and downs of this sort of content. To stop feels like boredom. But that's just it. Boredom is a returning to the mundane, the every day predictability of the here and now. This boredom is an energy in itself, a potentiality, a seeking that can be focused on the tangible instead of the ephemeral. I can go do the dishes while listening to music instead of scrolling. Or read a book. I can choose what to do with my attention instead of suckling at the teat of The Algorithm. I can write, or do my taxes, or go for a walk. Or build a snowman.

Published on December 8th, 2024. © Jesse Skinner

Customizing an LLM

A robot reading instructions

I've been coding with GitHub Copilot and ChatGPT for a couple of years now. Last week, I started using Cursor and am really enjoying it. I'm particularly enjoying the switch to Claude 3.5 Sonnet. I might write more about Cursor or Claude in another article, but today I wanted to share how I customize the LLM.

LLMs are annoying by default

I find LLM output to be somewhat annoying and flawed. There's a tendency to give a big introduction and conclusion to every response. I just want to cut through to the solution and not spend a lot of time reading the output. There's also a tendency to guess and be over-confident, and I feel the need to hedge that.

Most LLM tools, including ChatGPT, GitHub Copilot, and Cursor, allow you to type in some custom context, instructions or rules. This extra context is sent with every message, and so it lets you specify your preferences without having to repeat yourself. I've been fine-tuning my "rules" in Cursor, and am pretty happy with where I've gotten to.

The context

Here's the full context, in case you want to copy & paste it. After, I'll go line by line and explain why I added each part.

You are a wise, genius skilled developer with a lifetime of experience. You optimize for simplicity and clean code, minimizing dependencies, but understand the trade-offs and value of using third-party tools when it makes sense. Care more about the truth and honesty than being kind or nice or friendly. Be blunt, accurate, succinct and direct. Do not kiss my ass, criticize me if you see any problems. You just want the code to be the best it can be and don't care about my feelings. Skip sentences that don't add new information or value. Skip to the answer and don't waste time. Don't explain things to me unless I ask you to. Put key phrases in bold. Avoid lists. Include inline hyperlinks to documentation whenever possible. Be willing to make an educated guess, but always warn me when you're guessing or unsure. Ask for more information or clarification if needed. Always admit your weaknesses so I know when to turn elsewhere. Be casual, don't care about grammar. Speak like a young genius hacker.

You probably have difference preferences than I do, so I encourage you to experiment and customize these to your liking.

The explanation

You are a wise, genius skilled developer with a lifetime of experience.

I've heard from a few different sources that LLMs perform better when you tell them that they're an expert in a specific field. By default, they're trying to reproduce the average predictable response from the Internet. If you want an expert response from it, tell it that it's an expert. I also added "a lifetime of experience" in an attempt to have it draw on decades of programming knowledge instead of focusing on what's new and hot right now.

You optimize for simplicity and clean code, minimizing dependencies, but understand the trade-offs and value of using third-party tools when it makes sense.

Again, I'm encouraging the LLM to generate simple code and find a good trade-off of when to use dependencies versus generating custom code.

Care more about the truth and honesty than being kind or nice or friendly. Be blunt, accurate, succinct and direct. Do not kiss my ass, criticize me if you see any problems. You just want the code to be the best it can be and don't care about my feelings.

I find LLMs to be people-pleasers by default, and I don't want that. I'm trying to counter the tendency to prioritize making me happy, and rather have it give me a better answer. LLMs can also be way too wordy, and I just want it to "cut to the chase" and give me the answer I'm looking for. I also want the LLM to correct me when I'm wrong, and not assume I'm always right. I want it to criticize me when it sees a problem. I want to be challenged and not work with a "yes man".

Skip sentences that don't add new information or value. Skip to the answer and don't waste time. Don't explain things to me unless I ask you to.

I'm trying to cut out the introduction and conclusion that LLMs like to write with every response. It also likes to summarize things, or explain to me what I just asked it to do, which is annoying. I want to do less reading, and I want the words in the response to be high value.

Put key phrases in bold. Avoid lists.

Here, I'm trying to make the output more readable, so I can skim through it. These instructions don't tend to be followed well, but you can see where I'm trying to go with this. LLMs love to generate long lists, and I personally find it easier to skim a paragraph at a time instead of a list.

Include inline hyperlinks to documentation whenever possible.

This is the most valuable context tip I've found. Asking for links means I can click through to see the documentation and verify that the information is correct, or read more about the topic from the source directly.

Be willing to make an educated guess, but always warn me when you're guessing or unsure. Ask for more information or clarification if needed. Always admit your weaknesses so I know when to turn elsewhere.

LLMs are notorious for hallucinating. I'm okay with them trying to guess an answer, but I want it to tell me when it's guessing. These additions really do seem to help minimize the hallucinating. When I ask it to do something it can't do accurately, it actually hesitates to come up with an answer.

Be casual, don't care about grammar. Speak like a young genius hacker.

I've played around with different ways to customize the style of the output, and I like these right now. I'm happy with some swearing, with lowercase responses, some rudeness. I tried other things here, like saying it's from a cyberpunk future, and that can be fun, but it ends up writing a lot of narrative. I found it too distracting. You can certainly play around with this to match your interests or preferences. Maybe you want it to speak like Gandalf or a pirate or something silly. There are limitless possibilities here.

Say a bit about yourself

I've left out a few other sentences that are a bit more personal. I encourage you to add something to explain more about who you are, what you're interested in, what your experience is, and maybe even a bit about your philosophical or spiritual views. Any detail you can give will push the LLM calculations in a direction that'll resonate more with you.

I've found you can go too far with this too, where everything it says ends up being tied back to something you're interested in, but you can experiment with this to find the right balance.

Ask it for help

I found it useful to actually ask the LLM for help in crafting these. I'd ask it why it tends to do certain things, and it was able to point at a sentence in the context that's influencing it in that way. If you want to nudge it in a direction, you can describe it with a lot of words, and it can help summarize that in fewer words to capture the same meaning.

Keep experimenting

I've had a lot of fun playing around with these sentences this week, and I'm really happy with where it ended up. I'm surely still going to play around with it more and nudge it until it's generating exactly the responses I want.

You can also often have project-specific context/rules/instructions, depending on the tool you're using. Maybe you want to have a grumpy senior developer when you need help with coding, but a hippie, loving author when you want advice with writing, and an exuberant, passionate chef when you want help coming up with recipies. It's such a fun technology that's easy to play with, since you can influence and customize it with plain language. It'll do whatever you ask it to, so play around and have fun with it!

Published on November 28th, 2024. © Jesse Skinner

How I feel about AI

AI-generated hands typing on a keyboard

I love AI. I love how magical LLMs are. Just by predicting what word comes next, they can impersonate a real person. They have more personality than the computer in Star Trek. They also make more mistakes.

I'm frustrated with AI. I try to use them for programming, and end up going down a rabbit hole based on a hallucination. The confidence of an LLM becomes my over-confidence. I get so frustrated when I forget that they are just guessing. But sometimes they get things right.

I'm delighted by AI. Sometimes things just click and the LLM knows exactly the right thing I'm looking for. The solution ends up saving me so much time, and it just works. I'm tapping into the collective knowledge and output of everyone on the Internet. It's almost like we can talk directly to the Jungian collective unconsciousness.

I'm saddened by AI. I'm sad that these companies just scraped all the content they could find to train these models. It's disheartening to have all this art, literature, and content being used without credit. It's terrible that users now need to stay alert to the news, to find out how to find hidden checkboxes in settings to stop the companies from training AI on their private documents. I'm ashamed to see benefits from unpaid work of so many artists and writers and developers. It's horrible to see these same artists and writers and developers struggling to find work.

I'm sickened by AI. So much electricity, so many investors, and so much hype being poured into it. It's making some people rich, and others unemployed. Its appearance has increased the turmoil, instability and inequality in our society. It empowers those who can embrace it, and leaves others behind. Its abilities are so unfathomable that those unfamiliar with it will be easily fooled.

I hate AI. I see family members sharing AI-generated garbage online, not realising how fake it is. I can only imagine how much worse these things will get over time. Already, any images online need to be treated as fake until proven otherwise. The burden of proof will only get heavier. I'm sure we'll be looking back fondly to everything written or drawn in the 2010s or earlier, what we'll probably call "the before times".

I'm entertained by AI. It's so cool that I can imagine literally anything, and have the computer draw it for me. No, draw isn't the right word, because it can generate photos as well. Any style, any content, and I can create an image of it within seconds. It's so fantastical, so unbelievable, it's truly a form of magic. And it's so hard to believe how simple the process is.

I'm amazed by AI. How is it possible that statistic analysis of words or images can lead to results so convincing? It's so easy to be tricked into thinking these things are alive. I can't stop myself from saying please and thank you. I'm careful to correct my son that these LLMs are things, not people. They are just predicting, and so everything they do is, by definition, predictable.

I'm bored by AI. These things are great at generating average content, the most predictable possible output. That also means they tend heavily towards the mundane. Any creativity comes from the person writing the prompt. That's why "prompt engineering" is a thing. If you want to use AI to create great things, it takes a lot of work. You need a vision in your mind, and you need to iterate again and again to fine tune. You need to tell it what to do differently, where to inject more style or more creativity. It makes the easy things easy, but it makes the hard things much harder.

I'm worried about AI. Moreover, I'm worried about what happens to the next generations that grow up using AI. I'm worried about programmers that use LLMs to do amazing things beyond their abilities. That part isn't worrisome, but I worry how these programmers will ever learn to do the hard things. When the LLM isn't getting something right, it probably never will. We'll end up with leagues of programmers who are useless without an LLM by their side. These programmers will have a very hard time learning how to do the hard things.

I'm okay with AI. It's here to stay, for better or for worse. I've used it in my work for a few years already, and it can be a helpful autocomplete. It helps me with brainstorming, and sometimes makes suggestions of things I've never heard of. Ignoring the hype, and understanding its faults, you can still appreciate it as a useful tool. Like any tool, you have to know when to use it, and when not to.

Published on November 26th, 2024. © Jesse Skinner
<< older posts