<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0">
<channel>
<title>Coder Legion - Recent posts tagged dev-tools</title>
<link>https://coderlegion.com/tag/dev-tools</link>
<description>Powered by Question2Answer</description>
<item>
<title>Multi-tenant SaaS, explained with a football academy</title>
<link>https://coderlegion.com/32528/multi-tenant-saas-explained-with-a-football-academy</link>
<description>&lt;p&gt;&quot;Multi-tenant&quot; is one of those words that sounds harder than it is.&lt;br&gt;
I put it on my CV.&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt; is multi-tenant and role-based.&lt;br&gt;
Real academies run on it.&lt;/p&gt;
&lt;p&gt;So here's what that actually means, for beginners.&lt;br&gt;
No cloud diagrams.&lt;br&gt;
Just a football academy, a building, and some locked doors.&lt;/p&gt;
&lt;p&gt;One note before we start.&lt;br&gt;
This is about the general idea and the textbook patterns.&lt;br&gt;
It is not a tour of how Track My Academy is wired inside.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/multi-tenant-saas-explained-with-a-football-academy/cover.jpg&quot; alt=&quot;Three footballs lined up on artificial grass while a squad in black kit warms up on the pitch behind them&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@leo_visions_&quot;&gt;Leo_Visions&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/soccer-balls-lined-up-on-field-with-players-training-SfCiU3xdap0&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h3 id=&quot;the-building-what-a-tenant-is&quot;&gt;The building: what a tenant is&lt;/h3&gt;
&lt;p&gt;Picture one big sports building.&lt;br&gt;
Lots of academies rent space in it.&lt;br&gt;
Each one has its own players, coaches, fees and attendance.&lt;/p&gt;
&lt;p&gt;Every academy is a &lt;strong&gt;tenant&lt;/strong&gt;.&lt;br&gt;
The building is your software.&lt;/p&gt;
&lt;p&gt;Microsoft's &lt;a rel=&quot;nofollow&quot; href=&quot;https://learn.microsoft.com/en-us/azure/architecture/guide/multitenant/considerations/tenancy-models&quot;&gt;guide to tenancy models&lt;/a&gt; says that if your customers are other organisations, you usually map each tenant to one customer.&lt;br&gt;
It also says a single tenant typically has many users.&lt;br&gt;
One academy, many people.&lt;/p&gt;
&lt;p&gt;That's the whole trick of SaaS.&lt;br&gt;
You build the building once.&lt;br&gt;
Everyone rents.&lt;/p&gt;
&lt;h3 id=&quot;the-rooms-roles&quot;&gt;The rooms: roles&lt;/h3&gt;
&lt;p&gt;Inside one academy, not everyone gets the same keys.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;The &lt;strong&gt;owner&lt;/strong&gt; sees everything: fees, invoices, every batch.&lt;/li&gt;
&lt;li&gt;A &lt;strong&gt;coach&lt;/strong&gt; sees their batches and marks attendance.&lt;/li&gt;
&lt;li&gt;A &lt;strong&gt;parent&lt;/strong&gt; sees their own child, their invoices, their messages.&lt;/li&gt;
&lt;li&gt;A &lt;strong&gt;player&lt;/strong&gt; sees their own reports.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;That is role-based access control, or RBAC.&lt;br&gt;
NIST, who &lt;a rel=&quot;nofollow&quot; href=&quot;https://csrc.nist.gov/projects/role-based-access-control&quot;&gt;formalised the model&lt;/a&gt; back in 1992, says it has become the predominant model for advanced access control because it reduces the cost of managing access.&lt;br&gt;
Users get roles. Roles get permissions.&lt;br&gt;
You don't hand out keys one person at a time.&lt;br&gt;
You hand out &quot;coach keys&quot;.&lt;/p&gt;
&lt;p&gt;The model was later adopted as a standard, ANSI/INCITS 359, &lt;a rel=&quot;nofollow&quot; href=&quot;https://csrc.nist.gov/projects/role-based-access-control&quot;&gt;first in 2004&lt;/a&gt;.&lt;br&gt;
Not a new idea. Just a very useful one.&lt;/p&gt;
&lt;p&gt;Here's the bit people mix up.&lt;br&gt;
Roles decide which rooms you can enter &lt;em&gt;inside&lt;/em&gt; your academy.&lt;br&gt;
Tenancy decides which academy's rooms you can see &lt;em&gt;at all&lt;/em&gt;.&lt;br&gt;
A coach at Academy A should never see Academy B's attendance, even with full coach keys.&lt;br&gt;
Microsoft's guide puts it as needing to consider &lt;a rel=&quot;nofollow&quot; href=&quot;https://learn.microsoft.com/en-us/azure/architecture/guide/multitenant/considerations/tenancy-models&quot;&gt;both tenant and user identity&lt;/a&gt; when you authorise anything.&lt;/p&gt;
&lt;h3 id=&quot;three-ways-to-share-a-building&quot;&gt;Three ways to share a building&lt;/h3&gt;
&lt;p&gt;AWS's SaaS Lens names &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.aws.amazon.com/wellarchitected/latest/saas-lens/silo-pool-and-bridge-models.html&quot;&gt;three patterns: silo, pool and bridge&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Silo.&lt;/strong&gt; Every academy gets its own building.&lt;br&gt;
In software terms, dedicated resources per tenant: its own stack, or at least its own database.&lt;br&gt;
AWS notes that even a silo still shares one identity, onboarding and operations setup.&lt;br&gt;
Otherwise you're running a managed service, not SaaS.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Pool.&lt;/strong&gt; Everyone shares one building.&lt;br&gt;
Same servers, same database, same tables.&lt;br&gt;
AWS calls it &quot;the more classic notion of multi-tenancy&quot;.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Bridge.&lt;/strong&gt; A mix.&lt;br&gt;
Some parts siloed, some pooled.&lt;br&gt;
AWS says this acknowledges that &quot;SaaS businesses aren't always exclusively silo or pool.&quot;&lt;/p&gt;
&lt;p&gt;Microsoft describes the same spectrum, from &lt;a rel=&quot;nofollow&quot; href=&quot;https://learn.microsoft.com/en-us/azure/architecture/guide/multitenant/considerations/tenancy-models&quot;&gt;fully isolated to fully shared&lt;/a&gt;, and says to treat isolation as a spectrum, not a switch.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/multi-tenant-saas-explained-with-a-football-academy/training-lanes-cones.jpg&quot; alt=&quot;Training lanes marked with white lines on a black surface, with white hurdles and yellow cones in separate lanes&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@redaska&quot;&gt;Steve Pancrate&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/football-field-with-white-lines-numbers-hurdles-and-yellow-cones-FzAyjb2_Hys&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;Same surface, separate lanes. That's roughly the picture.&lt;br&gt;
In the database, it usually looks like one of these:&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;&lt;th&gt;Model &lt;/th&gt;&lt;th&gt;Academy analogy &lt;/th&gt;&lt;th&gt;Trade-off&lt;/th&gt;&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;&lt;td&gt;Database per tenant &lt;/td&gt;&lt;td&gt;Each academy has its own building &lt;/td&gt;&lt;td&gt;Strong isolation, costs grow with every new tenant&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td&gt;Schema or collection per tenant &lt;/td&gt;&lt;td&gt;Own floor, shared building &lt;/td&gt;&lt;td&gt;In between, and more things to manage&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td&gt;Shared tables with a &lt;code&gt;tenant_id&lt;/code&gt; &lt;/td&gt;&lt;td&gt;Shared rooms, every item labelled with the academy's name &lt;/td&gt;&lt;td&gt;Cheapest, but every query must filter correctly&lt;/td&gt;&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;MongoDB's own &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.mongodb.com/docs/atlas/build-multi-tenant-arch/&quot;&gt;multi-tenant guidance&lt;/a&gt; is blunt about the middle option.&lt;br&gt;
It says to &quot;avoid putting all tenants with their own collections into a single database.&quot;&lt;br&gt;
It suggests a database per tenant for a small, stable number of tenants with strict access needs.&lt;br&gt;
And shared collections when tenant numbers keep growing.&lt;/p&gt;
&lt;p&gt;With shared collections, MongoDB says: &quot;Every document must have a &lt;code&gt;tenantId&lt;/code&gt; field, and every database query must filter by that field.&quot;&lt;br&gt;
That sentence is the whole risk of the pool model.&lt;/p&gt;
&lt;h3 id=&quot;the-noisy-neighbour&quot;&gt;The noisy neighbour&lt;/h3&gt;
&lt;p&gt;Shared buildings have one classic problem.&lt;br&gt;
One academy throws a party and the whole building shakes.&lt;/p&gt;
&lt;p&gt;Microsoft calls it the &lt;a rel=&quot;nofollow&quot; href=&quot;https://learn.microsoft.com/en-us/azure/architecture/antipatterns/noisy-neighbor/noisy-neighbor&quot;&gt;noisy neighbour antipattern&lt;/a&gt;.&lt;br&gt;
It happens &quot;when one tenant's performance is degraded because of the activities of another tenant.&quot;&lt;br&gt;
Say one academy runs a giant report while another is marking attendance at the gate.&lt;br&gt;
The second one waits.&lt;/p&gt;
&lt;p&gt;The fixes on that page are sensible.&lt;br&gt;
Monitor usage per tenant, not just overall.&lt;br&gt;
Apply quotas, throttling or rate limits.&lt;br&gt;
Run heavy, non-urgent jobs at off-peak times.&lt;br&gt;
Cap expensive queries.&lt;/p&gt;
&lt;p&gt;The silo model mostly avoids this.&lt;br&gt;
Microsoft's tenancy guide says dedicated deployments make tenants &lt;a rel=&quot;nofollow&quot; href=&quot;https://learn.microsoft.com/en-us/azure/architecture/guide/multitenant/considerations/tenancy-models&quot;&gt;unlikely to affect each other's performance&lt;/a&gt;.&lt;br&gt;
But if one tenant costs X, it says, 100 tenants probably cost 100 times that.&lt;/p&gt;
&lt;h3 id=&quot;the-scary-one-data-leaks&quot;&gt;The scary one: data leaks&lt;/h3&gt;
&lt;p&gt;Noisy neighbours are annoying.&lt;br&gt;
Leaks are a different category.&lt;/p&gt;
&lt;p&gt;AWS's whitepaper on &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.aws.amazon.com/whitepapers/latest/saas-tenant-isolation-strategies/saas-tenant-isolation-strategies.html&quot;&gt;tenant isolation strategies&lt;/a&gt; says crossing that boundary &quot;would represent a significant and potentially un-recoverable event for a SaaS business.&quot;&lt;br&gt;
Imagine a parent opening the app and seeing another academy's fee list.&lt;br&gt;
That's not a bug report. That's a trust problem.&lt;/p&gt;
&lt;p&gt;In a shared database, one forgotten filter is enough.&lt;br&gt;
So I think the safest habit is to not rely on remembering.&lt;br&gt;
Make the database refuse.&lt;/p&gt;
&lt;p&gt;PostgreSQL has &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.postgresql.org/docs/current/ddl-rowsecurity.html&quot;&gt;row-level security&lt;/a&gt; for exactly this.&lt;br&gt;
Once it's on and no policy exists, it uses default-deny: no rows are visible or can be modified.&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://supabase.com/docs/guides/database/postgres/row-level-security&quot;&gt;Supabase's RLS guide&lt;/a&gt; builds on the same feature and points out it still protects data when it's reached through third-party tools.&lt;/p&gt;
&lt;p&gt;Here's a small &lt;strong&gt;illustrative example&lt;/strong&gt;.&lt;br&gt;
It is not Track My Academy's code, just the pattern:&lt;/p&gt;
&lt;pre&gt;&lt;code class=&quot;language-sql&quot;&gt;-- Example only: a shared attendance table, labelled by academy.
ALTER TABLE attendance ENABLE ROW LEVEL SECURITY;

CREATE POLICY academy_isolation ON attendance
  USING (academy_id = current_setting('app.current_academy')::uuid);
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;The app sets &lt;code&gt;app.current_academy&lt;/code&gt; for each request.&lt;br&gt;
Postgres then filters every query on that table to that academy, even one where someone forgot the &lt;code&gt;WHERE&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;Two catches from the Postgres docs.&lt;br&gt;
Superusers and roles with &lt;code&gt;BYPASSRLS&lt;/code&gt; always skip these policies.&lt;br&gt;
Table owners do too, unless you use &lt;code&gt;FORCE ROW LEVEL SECURITY&lt;/code&gt;.&lt;br&gt;
So the app shouldn't connect as the owner.&lt;/p&gt;
&lt;h3 id=&quot;how-i-d-think-about-it&quot;&gt;How I'd think about it&lt;/h3&gt;
&lt;p&gt;My opinion, for a small team:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Decide what a tenant is on day one.&lt;/strong&gt; For academy software it's obvious. For other products it often isn't.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Put the tenant ID on everything.&lt;/strong&gt; Retrofitting it later is miserable.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Let the database enforce isolation where it can.&lt;/strong&gt; Code reviews miss things. Default-deny doesn't get tired.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Keep roles and tenancy separate in your head.&lt;/strong&gt; Different questions, different checks.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Watch per-tenant usage.&lt;/strong&gt; You can't fix a noisy neighbour you can't see.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Test for leaks on purpose.&lt;/strong&gt; Microsoft's guide says to &lt;a rel=&quot;nofollow&quot; href=&quot;https://learn.microsoft.com/en-us/azure/architecture/guide/multitenant/considerations/tenancy-models&quot;&gt;verify one tenant's data isn't leaked&lt;/a&gt; to another, whatever model you pick.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;For context, the very first Track My Academy prototype had no database at all.&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/a-coach-complained-so-i-started-a-company&quot;&gt;The Excel sheet was the database&lt;/a&gt;.&lt;br&gt;
A long way from tenancy models.&lt;/p&gt;
&lt;h3 id=&quot;faq&quot;&gt;FAQ&lt;/h3&gt;
&lt;h4 id=&quot;what-is-a-tenant-in-saas-&quot;&gt;What is a tenant in SaaS?&lt;/h4&gt;
&lt;p&gt;A customer, usually an organisation, whose data and users are kept separate from every other customer's, even though they all use the same software.&lt;/p&gt;
&lt;h4 id=&quot;is-a-shared-database-with-a-tenant-id-safe-&quot;&gt;Is a shared database with a tenant ID safe?&lt;/h4&gt;
&lt;p&gt;It can be, if every query is filtered by tenant and you add a database-level guard like row-level security. The risk is a single missed filter.&lt;/p&gt;
&lt;h4 id=&quot;what-s-the-difference-between-multi-tenancy-and-rbac-&quot;&gt;What's the difference between multi-tenancy and RBAC?&lt;/h4&gt;
&lt;p&gt;Tenancy keeps organisations apart. RBAC decides what each person can do inside their own organisation.&lt;/p&gt;
&lt;h3 id=&quot;sources&quot;&gt;Sources&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.aws.amazon.com/wellarchitected/latest/saas-lens/silo-pool-and-bridge-models.html&quot;&gt;AWS Well-Architected SaaS Lens: Silo, pool, and bridge models&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.aws.amazon.com/whitepapers/latest/saas-tenant-isolation-strategies/saas-tenant-isolation-strategies.html&quot;&gt;AWS whitepaper: SaaS Tenant Isolation Strategies&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://learn.microsoft.com/en-us/azure/architecture/guide/multitenant/considerations/tenancy-models&quot;&gt;Microsoft Azure Architecture Center: Tenancy models for a multitenant solution&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://learn.microsoft.com/en-us/azure/architecture/antipatterns/noisy-neighbor/noisy-neighbor&quot;&gt;Microsoft Azure Architecture Center: Noisy neighbor antipattern&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.mongodb.com/docs/atlas/build-multi-tenant-arch/&quot;&gt;MongoDB Atlas: Build a multi-tenant architecture&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.postgresql.org/docs/current/ddl-rowsecurity.html&quot;&gt;PostgreSQL docs: Row security policies&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://supabase.com/docs/guides/database/postgres/row-level-security&quot;&gt;Supabase docs: Row Level Security&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://csrc.nist.gov/projects/role-based-access-control&quot;&gt;NIST CSRC: Role-based access control&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&quot;what-next&quot;&gt;What next&lt;/h3&gt;
&lt;p&gt;How it started, Excel sheet and all: &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/a-coach-complained-so-i-started-a-company&quot;&gt;a coach complained, so I started a company&lt;/a&gt;.&lt;br&gt;
And what happens when the shared building goes dark: &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-night-i-broke-production&quot;&gt;the night I broke production&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Running an academy? &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt; handles attendance, fees, player reports and parent messages, and there's a free plan.&lt;/p&gt;
</description>
<category>Articles</category>
<guid isPermaLink="true">https://coderlegion.com/32528/multi-tenant-saas-explained-with-a-football-academy</guid>
<pubDate>Sat, 31 Oct 2026 12:30:00 +0000</pubDate>
</item>
<item>
<title>Shipping Android and iOS solo (iOS: coming soon)</title>
<link>https://coderlegion.com/32524/shipping-android-and-ios-solo-ios-coming-soon</link>
<description>&lt;p&gt;I built the Track My Academy mobile apps myself.&lt;br&gt;
Both of them. Android and iOS.&lt;/p&gt;
&lt;p&gt;The Android app is live in production.&lt;br&gt;
The iOS app is coming soon.&lt;/p&gt;
&lt;p&gt;That second line is the honest one.&lt;br&gt;
It's also the one every solo founder ends up writing at some point.&lt;/p&gt;
&lt;p&gt;So this post isn't a victory lap.&lt;br&gt;
It's a look at what actually stands between one person and two app stores.&lt;br&gt;
Fees, rules, testers, reviewers.&lt;br&gt;
And why, for a product like ours, I think Android first is the sensible order.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/shipping-android-and-ios-solo/cover.jpg&quot; alt=&quot;A smartphone showing the word android next to a small green Android robot figure&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@redaquamedia&quot;&gt;Denny Müller&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/green-frog-iphone-case-beside-black-samsung-android-smartphone-HfWA-Axq6Ek&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h3 id=&quot;building-it-is-the-part-you-expect&quot;&gt;Building it is the part you expect&lt;/h3&gt;
&lt;p&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt; started as a web app, and the web app is live.&lt;br&gt;
Real academies run on it.&lt;br&gt;
The first version came together with AI tools, mostly vibe coding, in about three months.&lt;br&gt;
That story, and the agency build that came before it, is in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-app-that-arrived-from-2006&quot;&gt;the app that arrived from 2006&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;The stack behind it is React, FastAPI, MongoDB, Supabase, Firebase and a few friends.&lt;/p&gt;
&lt;p&gt;Here's the thing nobody tells you when you're writing code at night.&lt;br&gt;
Writing the app is the part you can control.&lt;br&gt;
Getting it into a store is a different job, with somebody else's rules.&lt;/p&gt;
&lt;h3 id=&quot;the-two-doors-play-console-and-app-store-connect&quot;&gt;The two doors: Play Console and App Store Connect&lt;/h3&gt;
&lt;p&gt;Each platform has one front door.&lt;br&gt;
On Android it's the Play Console.&lt;br&gt;
On iOS it's App Store Connect, which needs a paid Apple Developer Program membership.&lt;/p&gt;
&lt;p&gt;The price of entry is the first difference.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;&lt;th&gt;&lt;/th&gt;&lt;th&gt;Google Play &lt;/th&gt;&lt;th&gt;Apple App Store&lt;/th&gt;&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;&lt;td&gt;Account cost &lt;/td&gt;&lt;td&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://support.google.com/googleplay/android-developer/answer/6112435&quot;&gt;US$25, one time&lt;/a&gt; &lt;/td&gt;&lt;td&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/programs/&quot;&gt;$99 a year&lt;/a&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td&gt;Identity checks &lt;/td&gt;&lt;td&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://support.google.com/googleplay/android-developer/answer/6112435&quot;&gt;Government ID and a card in your legal name may be asked for&lt;/a&gt; &lt;/td&gt;&lt;td&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/programs/enroll/&quot;&gt;Legal name for individuals; a D-U-N-S Number for organisations&lt;/a&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;tr&gt;&lt;td&gt;Beta testing &lt;/td&gt;&lt;td&gt;Closed testing tracks &lt;/td&gt;&lt;td&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/programs/&quot;&gt;TestFlight, up to 10,000 external testers&lt;/a&gt;&lt;/td&gt;&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;For a bootstrapped team, one fee is a rounding error and the other is a yearly subscription.&lt;br&gt;
Neither is the real obstacle.&lt;br&gt;
But it does tell you something about how each store thinks.&lt;/p&gt;
&lt;p&gt;Apple's organisation route has its own homework.&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/programs/enroll/&quot;&gt;Apple's enrolment page&lt;/a&gt; says an organisation must be a legal entity that can sign contracts, needs a D-U-N-S Number, and needs a public, working website on its own domain.&lt;br&gt;
The organisation's name then shows as the seller name on the App Store.&lt;br&gt;
None of that is hard.&lt;br&gt;
All of it takes time you didn't plan for.&lt;/p&gt;
&lt;h3 id=&quot;google-s-12-testers-and-14-days&quot;&gt;Google's 12 testers and 14 days&lt;/h3&gt;
&lt;p&gt;Android is not a free pass either.&lt;/p&gt;
&lt;p&gt;If you open a personal Play developer account today, you can't just upload and publish.&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://support.google.com/googleplay/android-developer/answer/14151465&quot;&gt;Google's rules&lt;/a&gt; for personal accounts created after 13 November 2023 say at least 12 testers must be opted in to a closed test when you apply for production access.&lt;br&gt;
And they must have stayed opted in for the preceding 14 days, continuously.&lt;/p&gt;
&lt;p&gt;For a big company, 12 testers is a Slack message.&lt;br&gt;
For a solo developer, it's a favour you ask of friends, family and anyone who owes you one.&lt;br&gt;
Then you wait two weeks and hope nobody uninstalls.&lt;/p&gt;
&lt;p&gt;My opinion: it's annoying, and it's also fair.&lt;br&gt;
Two weeks with real people on real phones finds bugs you won't find alone.&lt;/p&gt;
&lt;h3 id=&quot;apple-s-reviewers-read-the-guidelines-so-you-have-to&quot;&gt;Apple's reviewers read the guidelines so you have to&lt;/h3&gt;
&lt;p&gt;On iOS the gate is a human review.&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/distribute/app-review/&quot;&gt;Apple says&lt;/a&gt; it typically reviews at least 50% of submissions in under 24 hours and 90% in under 48 hours.&lt;br&gt;
That's quick.&lt;br&gt;
Passing is the slower bit.&lt;/p&gt;
&lt;p&gt;The same page says that, on average, over 40% of unresolved issues relate to guideline 2.1, App Completeness.&lt;br&gt;
The &lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/app-store/review/guidelines/&quot;&gt;App Store Review Guidelines&lt;/a&gt; put it plainly: submissions &quot;should be final versions with all necessary metadata and fully functional URLs included&quot;.&lt;br&gt;
Placeholder text and temporary content have to go.&lt;/p&gt;
&lt;p&gt;There's also a line I like for its honesty.&lt;br&gt;
If your app has a login, include demo account details &quot;(and turn on your back-end service!)&quot;.&lt;br&gt;
Someone clearly learned that the hard way.&lt;/p&gt;
&lt;p&gt;A product like ours is almost entirely behind a login.&lt;br&gt;
It's role-based, so different people see different things.&lt;br&gt;
So a reviewer needs a working account and enough data to see the app do its job.&lt;/p&gt;
&lt;p&gt;Then there's guideline 4.2, Minimum Functionality.&lt;br&gt;
Your app &quot;should include features, content, and UI that elevate it beyond a repackaged website.&quot;&lt;br&gt;
If you already have a good web app, this is the trap.&lt;br&gt;
Wrapping it and shipping it is the fastest route, and the one most likely to bounce.&lt;/p&gt;
&lt;p&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/distribute/app-review/&quot;&gt;Apple's list of common problems&lt;/a&gt; also includes broken links, a missing privacy policy, inaccurate screenshots and unclear data-access prompts.&lt;br&gt;
Boring things.&lt;br&gt;
The boring things are always the ones that get you.&lt;/p&gt;
&lt;h3 id=&quot;why-android-first-for-us&quot;&gt;Why Android first, for us&lt;/h3&gt;
&lt;p&gt;Here's where I'll be opinionated.&lt;/p&gt;
&lt;p&gt;In India, Android isn't the bigger platform.&lt;br&gt;
It's nearly the only one.&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://gs.statcounter.com/os-market-share/mobile/india&quot;&gt;StatCounter's figures for September 2026&lt;/a&gt; put Android at 93.89% of mobile OS share in India and iOS at 6.05%.&lt;/p&gt;
&lt;p&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt; is for sports academies.&lt;br&gt;
Attendance, fees, player reports, messages to parents.&lt;br&gt;
The coach who started all this ran everything from his phone.&lt;br&gt;
His story is in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/a-coach-complained-so-i-started-a-company&quot;&gt;how a coach's complaint turned into a company&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;If you're building for that person in India, the odds say their phone runs Android.&lt;br&gt;
So for an Indian sports-academy product, I think Android first is simply the order the market hands you.&lt;br&gt;
Add a one-time fee and a review flow you can test yourself, and the choice makes itself.&lt;/p&gt;
&lt;p&gt;That doesn't make iOS optional.&lt;br&gt;
Some parents and owners will be on iPhones.&lt;br&gt;
And the web app covers anyone in between while the iOS app is still on its way.&lt;/p&gt;
&lt;h3 id=&quot;what-i-d-tell-another-solo-dev&quot;&gt;What I'd tell another solo dev&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Budget for the store, not just the code.&lt;/strong&gt; Fees, verification, screenshots, privacy policy, demo accounts.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Line up your testers early.&lt;/strong&gt; On Play, 14 days only starts once they're in.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Read guidelines 2.1 and 4.2 before you build, not after.&lt;/strong&gt; It's cheaper to design for them.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Ship where your users are first.&lt;/strong&gt; For us, that's Android.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Say &quot;coming soon&quot; out loud.&lt;/strong&gt; It's fine. It beats pretending.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The iOS app is coming soon.&lt;br&gt;
When it's out, you'll hear about it here.&lt;br&gt;
Probably with too many exclamation marks.&lt;/p&gt;
&lt;h3 id=&quot;faq-1&quot;&gt;FAQ&lt;/h3&gt;
&lt;h4 id=&quot;is-the-track-my-academy-ios-app-out-&quot;&gt;Is the Track My Academy iOS app out?&lt;/h4&gt;
&lt;p&gt;Not yet. The Android app and the web app are live. The iOS app is coming soon.&lt;/p&gt;
&lt;h4 id=&quot;do-new-google-play-developers-need-testers-before-going-live-&quot;&gt;Do new Google Play developers need testers before going live?&lt;/h4&gt;
&lt;p&gt;Personal accounts created after 13 November 2023 need at least 12 testers opted in to a closed test for 14 days in a row before applying for production access.&lt;/p&gt;
&lt;h4 id=&quot;how-much-does-it-cost-to-publish-on-both-stores-&quot;&gt;How much does it cost to publish on both stores?&lt;/h4&gt;
&lt;p&gt;Google Play charges a US$25 one-time fee. The Apple Developer Program costs $99 a year.&lt;/p&gt;
&lt;h3 id=&quot;sources-1&quot;&gt;Sources&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/programs/&quot;&gt;Apple Developer Program&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/programs/enroll/&quot;&gt;Apple: Enrolment requirements&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/app-store/review/guidelines/&quot;&gt;Apple: App Store Review Guidelines&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.apple.com/distribute/app-review/&quot;&gt;Apple: App Review&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://support.google.com/googleplay/android-developer/answer/14151465&quot;&gt;Google Play Console Help: Testing requirements for new personal developer accounts&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://support.google.com/googleplay/android-developer/answer/6112435&quot;&gt;Google Play Console Help: Registering a developer account&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://gs.statcounter.com/os-market-share/mobile/india&quot;&gt;StatCounter: Mobile operating system market share, India&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&quot;what-next-1&quot;&gt;What next&lt;/h3&gt;
&lt;p&gt;How the product got built in the first place: &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-app-that-arrived-from-2006&quot;&gt;the app that arrived from 2006&lt;/a&gt;.&lt;br&gt;
And what happens after you ship: &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-night-i-broke-production&quot;&gt;we blamed our code, it was SSL&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Running an academy? &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt; handles attendance, fees, player reports and parent messages.&lt;/p&gt;
</description>
<category>Articles</category>
<guid isPermaLink="true">https://coderlegion.com/32524/shipping-android-and-ios-solo-ios-coming-soon</guid>
<pubDate>Fri, 30 Oct 2026 08:30:00 +0000</pubDate>
</item>
<item>
<title>I tried to build my own offline Claude Code</title>
<link>https://coderlegion.com/32523/i-tried-to-build-my-own-offline-claude-code</link>
<description>&lt;p&gt;&lt;em&gt;Cover photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@afgprogrammer&quot;&gt;Mohammad Rahmani&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/laptop-displaying-code-and-steaming-mug-LrxSl4ZxoRs&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;Claude Code and Bolt made coding agents look easy.&lt;br&gt;
You type a sentence, and a model reads your files, edits them and runs things.&lt;/p&gt;
&lt;p&gt;So naturally I wanted my own.&lt;br&gt;
Offline. On my machine. No account, no trial, no meter running.&lt;/p&gt;
&lt;p&gt;I built a personal coding-agent experiment to explore one specific thing: contextual memory limits.&lt;br&gt;
How much can a local model actually keep in its head while it works on your code?&lt;/p&gt;
&lt;p&gt;This isn't a results post.&lt;br&gt;
It's about the stack, and about the wall the experiment was built to poke at.&lt;br&gt;
Because anyone who tries this will hit the same wall.&lt;/p&gt;
&lt;h3 id=&quot;the-stack&quot;&gt;The stack&lt;/h3&gt;
&lt;p&gt;Four pieces, all of them free.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.electronjs.org/docs/latest/&quot;&gt;Electron&lt;/a&gt;&lt;/strong&gt; for the desktop app. In its own words: &quot;By embedding Chromium and Node.js into its binary, Electron allows you to maintain one JavaScript codebase.&quot;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;React&lt;/strong&gt; for the interface.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://github.com/microsoft/monaco-editor&quot;&gt;Monaco&lt;/a&gt;&lt;/strong&gt; for the editor. Its README calls it &quot;the fully featured code editor from VS Code&quot;. You get a real editor without building one.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.ollama.com/faq&quot;&gt;Ollama&lt;/a&gt;&lt;/strong&gt; to run the model locally. Its FAQ is plain about it: &quot;Ollama runs locally. We don't see your prompts or data when you run locally.&quot;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Why offline?&lt;br&gt;
Partly the obvious reasons: your code stays on your machine, and it works without internet.&lt;/p&gt;
&lt;p&gt;Partly me.&lt;br&gt;
Early on, we chased every free AI trial going, with &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/dozens-of-email-accounts-and-zero-shame&quot;&gt;dozens of email accounts&lt;/a&gt;, because we didn't yet know how to use Claude or Codex.&lt;br&gt;
A model that runs on your own laptop never asks for a new email address.&lt;br&gt;
If you can get it for free, why spend money on it?&lt;/p&gt;
&lt;h3 id=&quot;the-real-constraint-the-context-window&quot;&gt;The real constraint: the context window&lt;/h3&gt;
&lt;p&gt;A model doesn't remember your project.&lt;br&gt;
It only sees what's in its context window: the prompt, the files you paste in, the chat so far.&lt;br&gt;
Everything outside that window doesn't exist for it.&lt;/p&gt;
&lt;p&gt;A coding agent eats context fast.&lt;br&gt;
File contents, tool output, error logs, its own previous answers.&lt;br&gt;
It all piles up.&lt;/p&gt;
&lt;p&gt;Local models start with a small window.&lt;br&gt;
The &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.ollama.com/faq&quot;&gt;Ollama FAQ&lt;/a&gt; says &quot;By default, Ollama uses a context window size of 4096 tokens.&quot;&lt;br&gt;
Its &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.ollama.com/context-length&quot;&gt;context length page&lt;/a&gt; says the default now depends on your VRAM: 4k under 24 GiB, 32k between 24 and 48 GiB, and 256k at 48 GiB or more.&lt;br&gt;
The &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.ollama.com/modelfile&quot;&gt;Modelfile reference&lt;/a&gt; still lists &lt;code&gt;num_ctx&lt;/code&gt; with &quot;Default: 2048&quot;.&lt;/p&gt;
&lt;p&gt;So even the docs don't agree with each other.&lt;br&gt;
Which is a lesson in itself: check what you're actually running.&lt;br&gt;
The context length page suggests running &lt;code&gt;ollama ps&lt;/code&gt; and looking at the CONTEXT column.&lt;/p&gt;
&lt;p&gt;The same page recommends at least 64,000 tokens for &quot;web search, agents, and coding tools&quot;.&lt;br&gt;
You raise it with the &lt;code&gt;OLLAMA_CONTEXT_LENGTH&lt;/code&gt; environment variable, or per request with &lt;code&gt;num_ctx&lt;/code&gt; inside &lt;code&gt;options&lt;/code&gt;, &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.ollama.com/faq&quot;&gt;per the FAQ&lt;/a&gt;.&lt;/p&gt;
&lt;h3 id=&quot;why-you-can-t-just-turn-the-number-up&quot;&gt;Why you can't just turn the number up&lt;/h3&gt;
&lt;p&gt;Because memory isn't free.&lt;br&gt;
Ollama's &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.ollama.com/context-length&quot;&gt;context length page&lt;/a&gt; says it directly: a larger context uses more memory.&lt;/p&gt;
&lt;p&gt;The reason is the KV cache.&lt;br&gt;
While a model generates, it stores keys and values for every token it has seen, so it doesn't recompute them.&lt;br&gt;
NVIDIA's &lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.nvidia.com/blog/mastering-llm-techniques-inference-optimization/&quot;&gt;guide to LLM inference optimisation&lt;/a&gt; gives the formula:&lt;br&gt;
batch size × sequence length × 2 × layers × hidden size × bytes per value.&lt;/p&gt;
&lt;p&gt;Their worked example is Llama 2 7B in 16-bit precision.&lt;br&gt;
At 4,096 tokens, the KV cache alone comes to about 2 GB.&lt;br&gt;
That's on top of the model weights.&lt;/p&gt;
&lt;p&gt;And it grows linearly.&lt;br&gt;
Double the context, roughly double the cache.&lt;br&gt;
On a laptop, that's the whole game.&lt;br&gt;
Every extra token of memory competes with the model itself for the same RAM.&lt;/p&gt;
&lt;h3 id=&quot;bigger-isn-t-the-same-as-better&quot;&gt;Bigger isn't the same as better&lt;/h3&gt;
&lt;p&gt;Say you find the memory.&lt;br&gt;
You still have a problem.&lt;/p&gt;
&lt;p&gt;The 2023 paper &lt;a rel=&quot;nofollow&quot; href=&quot;https://arxiv.org/abs/2307.03172&quot;&gt;Lost in the Middle&lt;/a&gt;, by Nelson F. Liu and colleagues, tested models on finding information in long inputs.&lt;br&gt;
Performance was usually best when the relevant bit was at the start or the end.&lt;br&gt;
It dropped when the information sat in the middle, even for models built for long contexts.&lt;/p&gt;
&lt;p&gt;Their conclusion: &quot;current language models do not robustly make use of information in long input contexts.&quot;&lt;/p&gt;
&lt;p&gt;For a coding agent, that's uncomfortable.&lt;br&gt;
The file you read twenty minutes ago is now somewhere in the middle.&lt;br&gt;
It's technically in context. It may as well not be.&lt;/p&gt;
&lt;h3 id=&quot;how-claude-code-deals-with-it&quot;&gt;How Claude Code deals with it&lt;/h3&gt;
&lt;p&gt;The tool that inspired the experiment doesn't pretend the problem away.&lt;br&gt;
It manages it.&lt;/p&gt;
&lt;p&gt;Anthropic's &lt;a rel=&quot;nofollow&quot; href=&quot;https://code.claude.com/docs/en/memory&quot;&gt;memory docs&lt;/a&gt; start with: &quot;Each Claude Code session begins with a fresh context window.&quot;&lt;br&gt;
Knowledge carries across sessions in two ways: CLAUDE.md files you write, and auto memory that Claude writes itself.&lt;br&gt;
Both are loaded at the start of every conversation.&lt;/p&gt;
&lt;p&gt;The docs also say to keep each CLAUDE.md under 200 lines.&lt;br&gt;
&quot;Longer files consume more context and reduce adherence.&quot;&lt;br&gt;
Even the memory has a memory budget.&lt;/p&gt;
&lt;p&gt;Then there's compaction.&lt;br&gt;
The &lt;a rel=&quot;nofollow&quot; href=&quot;https://code.claude.com/docs/en/context-window&quot;&gt;context window docs&lt;/a&gt; say Claude Code &quot;compacts automatically as you approach the limit&quot;.&lt;br&gt;
Running &lt;code&gt;/compact&lt;/code&gt; &quot;replaces the conversation with a structured summary&quot;.&lt;br&gt;
Afterwards it re-reads up to five of the files it read or edited most recently.&lt;br&gt;
The project-root CLAUDE.md is re-read from disk and survives.&lt;/p&gt;
&lt;p&gt;So the trick isn't a bigger window.&lt;br&gt;
It's deciding what deserves to be in the window at all.&lt;/p&gt;
&lt;h3 id=&quot;what-anyone-trying-this-will-hit&quot;&gt;What anyone trying this will hit&lt;/h3&gt;
&lt;p&gt;My opinion, from the research above, for anyone building their own local agent:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;The default window is smaller than you think.&lt;/strong&gt; If the agent seems to forget your file instantly, check the context length before blaming the model.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Memory is the budget.&lt;/strong&gt; Context costs RAM through the KV cache. On a laptop, you're trading model size against how much it can see.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Order matters.&lt;/strong&gt; Put instructions and the most important code at the start or the end, not buried in the middle.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Write memory to disk.&lt;/strong&gt; A short notes file that loads every session beats hoping the model remembers turn three.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Summarise on purpose.&lt;/strong&gt; Long chats need compacting. Doing it deliberately beats letting the window quietly overflow.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;None of this makes a local agent as good as the hosted ones.&lt;br&gt;
It does make it clear why they're built the way they are.&lt;/p&gt;
&lt;h3 id=&quot;faq-2&quot;&gt;FAQ&lt;/h3&gt;
&lt;h4 id=&quot;what-is-the-default-context-length-in-ollama-&quot;&gt;What is the default context length in Ollama?&lt;/h4&gt;
&lt;p&gt;It depends on which page you read and how much VRAM you have.&lt;br&gt;
The FAQ says 4096 tokens. The context length page says 4k, 32k or 256k depending on VRAM.&lt;br&gt;
Run &lt;code&gt;ollama ps&lt;/code&gt; to see what you actually got.&lt;/p&gt;
&lt;h4 id=&quot;why-does-a-bigger-context-window-need-more-memory-&quot;&gt;Why does a bigger context window need more memory?&lt;/h4&gt;
&lt;p&gt;The model keeps a KV cache entry for every token in context.&lt;br&gt;
That cache grows linearly with context length, so doubling the window roughly doubles its memory.&lt;/p&gt;
&lt;h4 id=&quot;how-does-claude-code-remember-things-between-sessions-&quot;&gt;How does Claude Code remember things between sessions?&lt;/h4&gt;
&lt;p&gt;Through CLAUDE.md files you write and auto memory notes it writes itself.&lt;br&gt;
Both load at the start of each session. Long sessions get compacted into a summary.&lt;/p&gt;
&lt;h3 id=&quot;sources-2&quot;&gt;Sources&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.ollama.com/context-length&quot;&gt;Ollama: Context length&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.ollama.com/faq&quot;&gt;Ollama: FAQ&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.ollama.com/modelfile&quot;&gt;Ollama: Modelfile reference&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://developer.nvidia.com/blog/mastering-llm-techniques-inference-optimization/&quot;&gt;NVIDIA: Mastering LLM techniques, inference optimisation&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://arxiv.org/abs/2307.03172&quot;&gt;Liu et al., Lost in the Middle: How Language Models Use Long Contexts (arXiv 2307.03172)&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://code.claude.com/docs/en/memory&quot;&gt;Claude Code docs: How Claude remembers your project&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://code.claude.com/docs/en/context-window&quot;&gt;Claude Code docs: Explore the context window&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.electronjs.org/docs/latest/&quot;&gt;Electron documentation&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://github.com/microsoft/monaco-editor&quot;&gt;Monaco Editor on GitHub&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&quot;what-next-2&quot;&gt;What next&lt;/h3&gt;
&lt;p&gt;How I learned these tools in the first place: &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/dozens-of-email-accounts-and-zero-shame&quot;&gt;dozens of email accounts and zero shame&lt;/a&gt;.&lt;br&gt;
And what happens when an AI coding agent does its job and the humans don't: &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-night-i-broke-production&quot;&gt;the night I broke production&lt;/a&gt;.&lt;/p&gt;
</description>
<category>Articles</category>
<guid isPermaLink="true">https://coderlegion.com/32523/i-tried-to-build-my-own-offline-claude-code</guid>
<pubDate>Thu, 29 Oct 2026 12:30:00 +0000</pubDate>
</item>
<item>
<title>I built a pager for my own developers</title>
<link>https://coderlegion.com/32522/i-built-a-pager-for-my-own-developers</link>
<description>&lt;p&gt;An earlier post ended with a promise.&lt;br&gt;
Sort of.&lt;/p&gt;
&lt;p&gt;In &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-night-i-broke-production&quot;&gt;the night I broke production&lt;/a&gt;, an expired SSL certificate on our backend domain failed silently.&lt;br&gt;
It took us about four hours to find it.&lt;br&gt;
I stayed in the office all night.&lt;/p&gt;
&lt;p&gt;At the end I mentioned, almost in passing, that I later built a &quot;Pager System&quot; for Track My Academy developers.&lt;br&gt;
An internal, real-time error and notification system.&lt;br&gt;
The idea: problems should find developers, not wait to be found.&lt;/p&gt;
&lt;p&gt;This post is about that idea.&lt;br&gt;
Why a tiny team needs a pager at all.&lt;br&gt;
And what I think a good one should and shouldn't do.&lt;/p&gt;
&lt;h3 id=&quot;a-very-old-idea&quot;&gt;A very old idea&lt;/h3&gt;
&lt;p&gt;Pagers were not invented for developers.&lt;br&gt;
They were invented for doctors.&lt;/p&gt;
&lt;p&gt;According to &lt;a rel=&quot;nofollow&quot; href=&quot;https://en.wikipedia.org/wiki/Pager&quot;&gt;Wikipedia's history of the pager&lt;/a&gt;, Al Gross patented the first telephone pager system in 1949, intended for physicians.&lt;br&gt;
The physicians, apparently, did not love the idea of being permanently on call.&lt;br&gt;
I relate.&lt;/p&gt;
&lt;p&gt;A year later, a paging service for doctors launched around New York City.&lt;br&gt;
Doctors paid US$12 a month for a pager that worked within about 40 km of one transmitter.&lt;/p&gt;
&lt;p&gt;And pagers never quite died.&lt;br&gt;
Wikipedia notes that in 2017 the UK's NHS was thought to use over 10% of the world's remaining pagers.&lt;br&gt;
Volunteer firefighters and rural first responders still carry them.&lt;/p&gt;
&lt;p&gt;The point of a pager has never changed.&lt;br&gt;
Something important is happening.&lt;br&gt;
The right person needs to know.&lt;br&gt;
Now, not when they next check.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/pager-system-for-my-own-developers/pager-circuit-board.jpg&quot; alt=&quot;A small circuit board with a Motorola chip in the middle, held between two fingers&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@winstonchen&quot;&gt;Winston Chen&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/a-close-up-of-a-person-holding-a-small-electronic-device-8Hrs6AIM6R4&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h3 id=&quot;why-a-small-team-needs-one&quot;&gt;Why a small team needs one&lt;/h3&gt;
&lt;p&gt;Big companies have on-call rotations, incident commanders and very serious dashboards.&lt;br&gt;
Small teams have a group chat and hope.&lt;/p&gt;
&lt;p&gt;Hope is not a monitoring strategy.&lt;br&gt;
I found that out the hard way, overnight.&lt;/p&gt;
&lt;p&gt;Track My Academy runs on React, FastAPI, MongoDB, Supabase, AWS EC2, Vercel, Razorpay, Firebase and Redis.&lt;br&gt;
That's a lot of moving parts for a small team.&lt;br&gt;
Any one of them can have a bad day.&lt;br&gt;
And real academies run on it, so their bad day becomes our bad day.&lt;/p&gt;
&lt;p&gt;The awkward truth is that a small team can't afford to watch everything.&lt;br&gt;
Nobody is sitting in front of a dashboard all day.&lt;br&gt;
We're shipping features, fixing bugs and, in my case, occasionally attending class.&lt;/p&gt;
&lt;p&gt;So the system has to do the watching.&lt;br&gt;
And when something breaks, it has to come and find a human.&lt;/p&gt;
&lt;h3 id=&quot;the-rules-i-d-steal-from-google&quot;&gt;The rules I'd steal from Google&lt;/h3&gt;
&lt;p&gt;Google's SRE book has a chapter on &lt;a rel=&quot;nofollow&quot; href=&quot;https://sre.google/sre-book/monitoring-distributed-systems/&quot;&gt;monitoring distributed systems&lt;/a&gt;.&lt;br&gt;
I keep going back to it.&lt;/p&gt;
&lt;p&gt;Three lines from it should be on every developer's wall:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&quot;Every page should be actionable.&quot;&lt;/li&gt;
&lt;li&gt;&quot;Every page response should require intelligence.&quot;&lt;/li&gt;
&lt;li&gt;&quot;Pages should be about a novel problem or an event that hasn't been seen before.&quot;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;If a human gets woken up and the fix is a script, automate the script.&lt;br&gt;
If the alert is something they'll ignore, delete the alert.&lt;/p&gt;
&lt;p&gt;The same chapter splits monitoring into two questions: &quot;what's broken, and why?&quot;&lt;br&gt;
What's broken is the symptom.&lt;br&gt;
Why is the cause.&lt;/p&gt;
&lt;p&gt;That distinction would have saved us hours.&lt;br&gt;
We had a symptom: everything was down.&lt;br&gt;
We jumped straight to a cause we'd picked ourselves: our new code.&lt;br&gt;
The real cause was a certificate nobody was watching.&lt;/p&gt;
&lt;p&gt;It also lists four golden signals: latency, traffic, errors and saturation.&lt;br&gt;
If you can only measure four things, the book says, measure those.&lt;/p&gt;
&lt;h3 id=&quot;the-danger-a-pager-that-cries-wolf&quot;&gt;The danger: a pager that cries wolf&lt;/h3&gt;
&lt;p&gt;There's a catch with alerting.&lt;br&gt;
Too much of it is almost as bad as none.&lt;/p&gt;
&lt;p&gt;The SRE book says that &quot;when pages occur too frequently, employees second-guess, skim, or even ignore incoming alerts&quot;.&lt;br&gt;
And one line I really like: &quot;I can only react with a sense of urgency a few times a day before I become fatigued.&quot;&lt;/p&gt;
&lt;p&gt;Hospitals know this problem well.&lt;br&gt;
The US agency AHRQ has a primer on &lt;a rel=&quot;nofollow&quot; href=&quot;https://psnet.ahrq.gov/primer/alert-fatigue&quot;&gt;alert fatigue&lt;/a&gt;.&lt;br&gt;
It describes one study where ICU monitors generated &quot;more than 2 million alerts in one month&quot;, or &quot;187 warnings per patient per day&quot;.&lt;br&gt;
It also says clinicians &quot;override the vast majority&quot; of computerised ordering warnings.&lt;/p&gt;
&lt;p&gt;Doctors are not careless.&lt;br&gt;
They're human, and humans tune out noise.&lt;br&gt;
Developers are the same, only with worse posture.&lt;/p&gt;
&lt;h3 id=&quot;what-i-think-a-good-internal-pager-should-do&quot;&gt;What I think a good internal pager should do&lt;/h3&gt;
&lt;p&gt;This is opinion, not a spec.&lt;br&gt;
But if you're a small team building your own, here's what I'd aim for.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Page on symptoms users feel.&lt;/strong&gt; Errors, slow responses, failed payments. Not every log line.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Say what's broken in one sentence.&lt;/strong&gt; The person reading it may have just woken up.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Go to the right person.&lt;/strong&gt; Not the whole team. One owner per alert.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Stay quiet when things are fine.&lt;/strong&gt; Every alert that isn't urgent teaches people to ignore the urgent ones.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Watch the boring stuff.&lt;/strong&gt; Certificates, domains, disk space, expiring keys.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Get pruned regularly.&lt;/strong&gt; If an alert fired and nobody acted, change it or remove it.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;You don't have to build it from scratch either.&lt;br&gt;
Tools like &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.sentry.io/product/alerts/&quot;&gt;Sentry&lt;/a&gt; let you send notifications or create tickets when issues match rules you set.&lt;br&gt;
Its docs say the goal is alerts that are &quot;valuable and not too noisy&quot;.&lt;br&gt;
They suggest using filters so you only hear about issues your team needs to know about.&lt;/p&gt;
&lt;h3 id=&quot;about-those-certificates&quot;&gt;About those certificates&lt;/h3&gt;
&lt;p&gt;The boring stuff deserves its own section, because it got us.&lt;/p&gt;
&lt;p&gt;Certificates are about to expire a lot more often.&lt;br&gt;
In 2025 the CA/Browser Forum &lt;a rel=&quot;nofollow&quot; href=&quot;https://cabforum.org/2025/04/11/ballot-sc081v3-introduce-schedule-of-reducing-validity-and-data-reuse-periods/&quot;&gt;passed a ballot&lt;/a&gt; to cut the maximum TLS certificate lifetime from 398 days to 47 days.&lt;br&gt;
The reductions start in March 2026 and finish in March 2029.&lt;/p&gt;
&lt;p&gt;Meanwhile, Let's Encrypt &lt;a rel=&quot;nofollow&quot; href=&quot;https://letsencrypt.org/2025/01/22/ending-expiration-emails/&quot;&gt;stopped sending expiry reminder emails&lt;/a&gt; on 4 June 2025.&lt;br&gt;
Its reasons included that more people now have reliable renewal automation.&lt;br&gt;
It pointed people to third-party monitoring instead.&lt;/p&gt;
&lt;p&gt;So: shorter lifetimes, fewer reminders.&lt;br&gt;
If your renewal automation ever quietly fails, nobody is going to email you about it.&lt;br&gt;
Your users will tell you instead.&lt;/p&gt;
&lt;p&gt;Automate renewals.&lt;br&gt;
Then monitor the automation anyway.&lt;/p&gt;
&lt;h3 id=&quot;the-point&quot;&gt;The point&lt;/h3&gt;
&lt;p&gt;A pager isn't about being available all the time.&lt;br&gt;
Honestly, I'd like to sleep more, not less.&lt;/p&gt;
&lt;p&gt;It's about not spending four hours blaming the wrong thing.&lt;br&gt;
The problem should arrive with a name attached.&lt;br&gt;
Then the human can do the part that needs a human.&lt;/p&gt;
&lt;h3 id=&quot;faq-3&quot;&gt;FAQ&lt;/h3&gt;
&lt;h4 id=&quot;does-a-small-team-really-need-alerting-&quot;&gt;Does a small team really need alerting?&lt;/h4&gt;
&lt;p&gt;I think so. Small teams have fewer people watching, so the system has to do the watching for them.&lt;/p&gt;
&lt;h4 id=&quot;what-should-trigger-a-page-&quot;&gt;What should trigger a page?&lt;/h4&gt;
&lt;p&gt;Something urgent, actionable and user-facing. If nobody needs to act right now, it's a ticket or a report, not a page.&lt;/p&gt;
&lt;h4 id=&quot;how-do-i-avoid-alert-fatigue-&quot;&gt;How do I avoid alert fatigue?&lt;/h4&gt;
&lt;p&gt;Fewer, better alerts. Review the ones that fired, and delete or fix any that nobody acted on.&lt;/p&gt;
&lt;h3 id=&quot;sources-3&quot;&gt;Sources&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://en.wikipedia.org/wiki/Pager&quot;&gt;Wikipedia: Pager&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://sre.google/sre-book/monitoring-distributed-systems/&quot;&gt;Google SRE book: Monitoring distributed systems&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://psnet.ahrq.gov/primer/alert-fatigue&quot;&gt;AHRQ PSNet: Alert fatigue&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.sentry.io/product/alerts/&quot;&gt;Sentry docs: Alerts&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://cabforum.org/2025/04/11/ballot-sc081v3-introduce-schedule-of-reducing-validity-and-data-reuse-periods/&quot;&gt;CA/Browser Forum: Ballot SC-081v3&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://letsencrypt.org/2025/01/22/ending-expiration-emails/&quot;&gt;Let's Encrypt: Ending support for expiration notification emails&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&quot;what-next-3&quot;&gt;What next&lt;/h3&gt;
&lt;p&gt;The full outage story is in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-night-i-broke-production&quot;&gt;the night I broke production&lt;/a&gt;.&lt;br&gt;
For where the late nights happen, see &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/three-monitors-one-monster-can&quot;&gt;three monitors, one Monster can&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Running an academy? &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt; handles attendance, fees, player reports and parent messages.&lt;/p&gt;
</description>
<category>Articles</category>
<guid isPermaLink="true">https://coderlegion.com/32522/i-built-a-pager-for-my-own-developers</guid>
<pubDate>Thu, 29 Oct 2026 08:30:00 +0000</pubDate>
</item>
<item>
<title>Dozens of email accounts: learning AI coding tools as a student</title>
<link>https://coderlegion.com/32505/dozens-of-email-accounts-learning-ai-coding-tools-as-a-student</link>
<description>&lt;p&gt;Let me confess something.&lt;br&gt;
Early on, we had dozens of email accounts.&lt;br&gt;
Not for spam. Not for anything shady.&lt;br&gt;
For free AI trials.&lt;/p&gt;
&lt;p&gt;This post is about learning AI coding tools as a student.&lt;br&gt;
No budget. No clue. Lots of inboxes.&lt;br&gt;
It's also about what that chaos actually taught me.&lt;br&gt;
Spoiler: the lesson is not &quot;make fifty email accounts&quot;.&lt;/p&gt;
&lt;h3 id=&quot;the-great-free-trial-hunt&quot;&gt;The great free trial hunt&lt;/h3&gt;
&lt;p&gt;Here's what our learning strategy looked like.&lt;/p&gt;
&lt;p&gt;Find an AI tool.&lt;br&gt;
Sign up for the free trial.&lt;br&gt;
Use it until the trial ends.&lt;br&gt;
Make a new email.&lt;br&gt;
Repeat.&lt;/p&gt;
&lt;p&gt;When we ran out of our own accounts, a few friends lent us theirs.&lt;/p&gt;
&lt;p&gt;My friends were very generous.&lt;br&gt;
Possibly too generous.&lt;/p&gt;
&lt;p&gt;It was less elegant than it sounds.&lt;br&gt;
It worked.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/dozens-of-email-accounts-and-zero-shame/student-coding-at-night.jpg&quot; alt=&quot;A student coding on a laptop late at night while learning AI coding tools&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@rc820&quot;&gt;Chirayu Trivedi&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/a-person-is-coding-on-a-laptop-at-night-M1yPeeHZ08w&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h3 id=&quot;why-we-did-it&quot;&gt;Why we did it&lt;/h3&gt;
&lt;p&gt;The honest reason is simple.&lt;/p&gt;
&lt;p&gt;We didn't know how to use Claude or Codex yet.&lt;br&gt;
We didn't know which tool was good at what.&lt;br&gt;
We definitely didn't have money for every subscription.&lt;br&gt;
And even if we had, I wouldn't have spent it. More on that later.&lt;/p&gt;
&lt;p&gt;So we tested everything.&lt;/p&gt;
&lt;p&gt;Some tools were brilliant.&lt;br&gt;
Some were brilliant at sounding brilliant.&lt;br&gt;
A few were just autocomplete with a marketing budget.&lt;/p&gt;
&lt;p&gt;You only learn the difference by using them.&lt;/p&gt;
&lt;p&gt;We were hardly the only curious ones.&lt;br&gt;
The &lt;a rel=&quot;nofollow&quot; href=&quot;https://survey.stackoverflow.co/2025/ai&quot;&gt;Stack Overflow 2025 Developer Survey&lt;/a&gt; asked developers about AI.&lt;br&gt;
84% said they use or plan to use AI tools.&lt;br&gt;
Only 33% said they trust the accuracy of those tools.&lt;br&gt;
46% said they actively distrust it.&lt;/p&gt;
&lt;p&gt;So nearly everyone uses them, and plenty don't trust them.&lt;br&gt;
That gap is the whole story of learning these tools.&lt;/p&gt;
&lt;h3 id=&quot;i-learn-by-touching-things&quot;&gt;I learn by touching things&lt;/h3&gt;
&lt;p&gt;This is how my brain works.&lt;/p&gt;
&lt;p&gt;I don't read the manual first.&lt;br&gt;
I touch the thing until it makes sense.&lt;br&gt;
I do it badly first, on purpose or otherwise.&lt;/p&gt;
&lt;p&gt;Sometimes the thing breaks.&lt;br&gt;
Sometimes I break.&lt;br&gt;
Usually, by the end, I understand it.&lt;/p&gt;
&lt;p&gt;Nothing about my path was planned, by the way.&lt;br&gt;
I was a bio-maths student in class 12, then &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/bio-maths-to-computer-science&quot;&gt;ended up in computer science&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Free trials suited a brain like mine.&lt;br&gt;
Low cost. High chaos. Fast learning.&lt;/p&gt;
&lt;p&gt;The first night of building &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt; had the same energy.&lt;br&gt;
A MacBook Air, a second-hand iPhone, ChatGPT and VS Code.&lt;br&gt;
Mostly research, then a landing page I actually liked.&lt;/p&gt;
&lt;p&gt;Why I was building it myself at all is its own saga.&lt;br&gt;
That's in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-app-that-arrived-from-2006&quot;&gt;the app that arrived from 2006&lt;/a&gt;.&lt;/p&gt;
&lt;h3 id=&quot;how-to-evaluate-ai-coding-assistants-without-fifty-inboxes&quot;&gt;How to evaluate AI coding assistants without fifty inboxes&lt;/h3&gt;
&lt;p&gt;Here's the version I'd hand to a student today.&lt;/p&gt;
&lt;p&gt;Give every tool the same small, real task.&lt;br&gt;
Not &quot;build me Instagram&quot;.&lt;br&gt;
Something like a form, a bug fix, or one API route.&lt;/p&gt;
&lt;p&gt;Then check these things:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Does it read your code?&lt;/strong&gt; Some tools guess. Guessing is expensive.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Does it explain itself?&lt;/strong&gt; If you can't follow the change, you can't own it.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Does it admit doubt?&lt;/strong&gt; Confident nonsense is the worst kind of nonsense.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;What happens when it's wrong?&lt;/strong&gt; Paste the error back and watch how it recovers.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;What does it cost after the trial?&lt;/strong&gt; The free tier is the trailer, not the film.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The same survey has a lovely detail here.&lt;br&gt;
The top frustration, for 66%, was answers &quot;almost right, but not quite&quot;.&lt;/p&gt;
&lt;p&gt;Almost right is the danger zone.&lt;br&gt;
It's where a student copies, pastes, ships and cries.&lt;br&gt;
Fully wrong is easy to spot.&lt;br&gt;
Almost right walks straight into production wearing a fake moustache.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/dozens-of-email-accounts-and-zero-shame/students-comparing-ai-tools-on-laptop.jpg&quot; alt=&quot;Students gathered around a laptop, comparing AI coding assistants on a shared task&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@silverkblack&quot;&gt;Vitaly Gariev&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/diverse-group-of-students-gathered-around-a-laptop-8gAbl776pc0&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h3 id=&quot;prompting-is-just-clear-thinking&quot;&gt;Prompting is just clear thinking&lt;/h3&gt;
&lt;p&gt;After enough trials, patterns start to show.&lt;/p&gt;
&lt;p&gt;The biggest one: good prompts are just clear thinking.&lt;br&gt;
If I can't explain what I want, the AI can't either.&lt;br&gt;
Turns out, that's also true for humans.&lt;/p&gt;
&lt;p&gt;Anthropic's own &lt;a rel=&quot;nofollow&quot; href=&quot;https://platform.claude.com/docs/en/build-with-claude/prompt-engineering/claude-prompting-best-practices&quot;&gt;prompting best practices&lt;/a&gt; say roughly the same.&lt;br&gt;
They suggest treating Claude like a brilliant but new employee.&lt;br&gt;
Brilliant, yes. But missing all your context.&lt;br&gt;
Their golden rule: show your prompt to a colleague with minimal context.&lt;br&gt;
If the colleague would be confused, the model will be too.&lt;/p&gt;
&lt;p&gt;That's not some secret AI trick.&lt;br&gt;
That's just writing a decent ticket.&lt;/p&gt;
&lt;p&gt;Here's a simple prompt shape I'd suggest to any student:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;What you're building, in one sentence.&lt;/li&gt;
&lt;li&gt;What already exists: files, stack, the exact error.&lt;/li&gt;
&lt;li&gt;What &quot;done&quot; looks like.&lt;/li&gt;
&lt;li&gt;What it must not touch.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;The last one saves more pain than the other three combined.&lt;br&gt;
AI tools love &quot;helpfully&quot; rewriting files you never mentioned.&lt;/p&gt;
&lt;h3 id=&quot;what-all-those-trials-taught-me&quot;&gt;What all those trials taught me&lt;/h3&gt;
&lt;p&gt;&lt;strong&gt;AI is a tool, not a teammate.&lt;/strong&gt;&lt;br&gt;
It doesn't know your product.&lt;br&gt;
It doesn't care about your deadline.&lt;br&gt;
You still have to think.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Every tool has a personality.&lt;/strong&gt;&lt;br&gt;
Some write great code and terrible explanations.&lt;br&gt;
Some explain beautifully and then write broken code.&lt;br&gt;
Knowing which is which saves hours.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;The tool matters less than the person using it.&lt;/strong&gt;&lt;br&gt;
A good developer with a basic tool beats a confused one with every tool.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Curiosity compounds.&lt;/strong&gt;&lt;br&gt;
Later, I built a personal offline coding-agent experiment.&lt;br&gt;
Electron, React, Ollama and the Monaco editor.&lt;br&gt;
It was inspired by Claude Code and Bolt.&lt;br&gt;
The point was to explore the limits of contextual memory.&lt;br&gt;
You don't build that unless you've poked a lot of tools first.&lt;/p&gt;
&lt;p&gt;If you're curious what the battle station looks like, see &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/three-monitors-one-monster-can&quot;&gt;three monitors, one Monster can&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/dozens-of-email-accounts-and-zero-shame/code-on-developer-monitor.jpg&quot; alt=&quot;Colourful code on a developer's monitor, the daily view when using AI coding assistants&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@jakubzerdzicki&quot;&gt;Jakub Żerdzicki&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/code-displayed-on-computer-screens-v-jFS1AsHXo&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h3 id=&quot;free-and-student-plans-for-ai-tools-the-legit-route&quot;&gt;Free and student plans for AI tools: the legit route&lt;/h3&gt;
&lt;p&gt;Please don't take the email thing as a tutorial.&lt;/p&gt;
&lt;p&gt;Read the terms of service of whatever you sign up for.&lt;br&gt;
If the terms say one trial per person, that means one.&lt;br&gt;
Respect them. Breaking the rules is not a growth hack.&lt;/p&gt;
&lt;p&gt;The good news: students have proper options now.&lt;/p&gt;
&lt;p&gt;GitHub's &lt;a rel=&quot;nofollow&quot; href=&quot;https://education.github.com/pack&quot;&gt;Student Developer Pack&lt;/a&gt; bundles tools and offers for students.&lt;br&gt;
Some offers are free while you're a student.&lt;br&gt;
Others are credits, discounts or time-limited trials.&lt;/p&gt;
&lt;p&gt;GitHub's docs also say &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.github.com/en/copilot/how-tos/copilot-on-github/set-up-copilot/enable-copilot/set-up-for-students&quot;&gt;verified students get free access to Copilot's features&lt;/a&gt;.&lt;br&gt;
GitHub rechecks that eligibility every month.&lt;br&gt;
The &lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.github.com/en/copilot/get-started/plans&quot;&gt;Copilot plans page&lt;/a&gt; lists what each plan includes.&lt;/p&gt;
&lt;p&gt;Offers change, though.&lt;br&gt;
Read the official page, not a random thread from two years ago.&lt;/p&gt;
&lt;p&gt;My free advice, which is worth exactly what you paid:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Start with official student programmes.&lt;/li&gt;
&lt;li&gt;Use free tiers honestly: one account per human.&lt;/li&gt;
&lt;li&gt;Ask your college whether it already has licences.&lt;/li&gt;
&lt;li&gt;Pay for one tool once it saves you real hours.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;And please, don't pay for &quot;training&quot; dressed up as an internship.&lt;br&gt;
I've already &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/i-paid-for-an-internship&quot;&gt;made that mistake for you&lt;/a&gt;.&lt;/p&gt;
&lt;h3 id=&quot;learning-by-building-beats-learning-by-watching&quot;&gt;Learning by building beats learning by watching&lt;/h3&gt;
&lt;p&gt;Don't wait until you can afford the perfect setup.&lt;br&gt;
Start with whatever you can get your hands on.&lt;br&gt;
Learn by doing it badly first.&lt;/p&gt;
&lt;p&gt;Pick one tiny project.&lt;br&gt;
Ship it to one real person.&lt;br&gt;
Let the AI help, but read every line it writes.&lt;/p&gt;
&lt;p&gt;When it breaks, and it will, you'll learn more than any course.&lt;br&gt;
I wrote about the most expensive version of that in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-night-i-broke-production&quot;&gt;the night I broke production&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;I did it badly for a long time.&lt;br&gt;
Now I do it slightly less badly.&lt;br&gt;
That's called progress.&lt;/p&gt;
&lt;h3 id=&quot;the-real-reason-jugaad-over-spending&quot;&gt;The real reason: jugaad over spending&lt;/h3&gt;
&lt;p&gt;Here's the deeper truth.&lt;br&gt;
It wasn't only about money we didn't have.&lt;br&gt;
It's how I'm wired.&lt;/p&gt;
&lt;p&gt;I value money a lot.&lt;br&gt;
I hate mindless spending.&lt;br&gt;
I save wherever I can.&lt;/p&gt;
&lt;p&gt;If a service is available for free, I won't pay for it.&lt;br&gt;
Coupons, discounts, free trials, student offers.&lt;br&gt;
I look for all of them.&lt;/p&gt;
&lt;p&gt;My rule is simple.&lt;br&gt;
If you can get it for free, why spend money on it?&lt;/p&gt;
&lt;p&gt;In Hindi, we call this &lt;a rel=&quot;nofollow&quot; href=&quot;https://en.wikipedia.org/wiki/Jugaad&quot;&gt;jugaad&lt;/a&gt;.&lt;br&gt;
Making scarce resources go further with creative improvisation.&lt;br&gt;
Jugaad takes time.&lt;br&gt;
But you always learn something while doing it.&lt;/p&gt;
&lt;p&gt;For me, spending money felt more wrong than spending time.&lt;br&gt;
Time spent figuring things out turned into skills.&lt;br&gt;
Money spent on shortcuts would just have turned into receipts.&lt;/p&gt;
&lt;p&gt;That's the real story behind dozens of email accounts.&lt;br&gt;
Not desperation.&lt;br&gt;
A habit of refusing to pay for what I could figure out myself.&lt;/p&gt;
&lt;h3 id=&quot;faq-4&quot;&gt;FAQ&lt;/h3&gt;
&lt;h4 id=&quot;what-s-the-best-way-of-learning-ai-coding-tools-as-a-student-&quot;&gt;What's the best way of learning AI coding tools as a student?&lt;/h4&gt;
&lt;p&gt;Build one small, real project with one tool.&lt;br&gt;
Read every line it produces.&lt;br&gt;
Then give a second tool the same task and compare.&lt;/p&gt;
&lt;h4 id=&quot;are-there-free-ai-coding-tools-for-students-&quot;&gt;Are there free AI coding tools for students?&lt;/h4&gt;
&lt;p&gt;Some, yes.&lt;br&gt;
GitHub's docs say verified students get free access to Copilot's features.&lt;br&gt;
Check the official pages, because student offers change.&lt;/p&gt;
&lt;h4 id=&quot;should-i-make-multiple-email-accounts-for-free-trials-&quot;&gt;Should I make multiple email accounts for free trials?&lt;/h4&gt;
&lt;p&gt;No.&lt;br&gt;
Read the terms of service and respect them.&lt;br&gt;
Our trial hunt is a confession, not a strategy.&lt;/p&gt;
&lt;h3 id=&quot;sources-4&quot;&gt;Sources&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://survey.stackoverflow.co/2025/ai&quot;&gt;Stack Overflow 2025 Developer Survey: AI&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://platform.claude.com/docs/en/build-with-claude/prompt-engineering/claude-prompting-best-practices&quot;&gt;Claude prompting best practices&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://education.github.com/pack&quot;&gt;GitHub Student Developer Pack&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.github.com/en/copilot/how-tos/copilot-on-github/set-up-copilot/enable-copilot/set-up-for-students&quot;&gt;GitHub Docs: Copilot for students&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.github.com/en/copilot/get-started/plans&quot;&gt;GitHub Docs: Copilot plans&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&quot;what-next-4&quot;&gt;What next&lt;/h3&gt;
&lt;p&gt;Want the origin story? Read &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/a-coach-complained-so-i-started-a-company&quot;&gt;how a coach's complaint became a company&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Run a sports academy? Have a look at &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt;.&lt;br&gt;
It's published by &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmytech.in&quot;&gt;TrackMy Tech&lt;/a&gt;, where I'm Executive Director.&lt;/p&gt;
&lt;p&gt;Student founder who wants to talk tools? &lt;a rel=&quot;nofollow&quot; href=&quot;https://calendar.rahuldk.in&quot;&gt;Book a call&lt;/a&gt;.&lt;/p&gt;
</description>
<category>Articles</category>
<guid isPermaLink="true">https://coderlegion.com/32505/dozens-of-email-accounts-learning-ai-coding-tools-as-a-student</guid>
<pubDate>Wed, 28 Oct 2026 04:30:00 +0000</pubDate>
</item>
<item>
<title>Outsourcing vs building it yourself: our app arrived from 2006</title>
<link>https://coderlegion.com/32517/outsourcing-vs-building-it-yourself-our-app-arrived-from-2006</link>
<description>&lt;p&gt;Every founder has a moment where they say, &quot;Fine. I'll do it myself.&quot;&lt;br&gt;
Mine came with a very specific smell.&lt;br&gt;
The smell of PHP and a design from another decade.&lt;/p&gt;
&lt;p&gt;This post is about outsourcing app development vs building it yourself.&lt;br&gt;
I've done the first one badly and the second one stubbornly.&lt;br&gt;
So I have opinions.&lt;br&gt;
Lots of them.&lt;/p&gt;
&lt;h3 id=&quot;the-idea-was-simple&quot;&gt;The idea was simple&lt;/h3&gt;
&lt;p&gt;It started with a coach complaining.&lt;br&gt;
His students' fee payments just wouldn't tally.&lt;/p&gt;
&lt;p&gt;Small problem.&lt;br&gt;
Annoying problem.&lt;br&gt;
The kind that sticks in your head.&lt;/p&gt;
&lt;p&gt;That problem became &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt;.&lt;br&gt;
The full origin story is in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/a-coach-complained-so-i-started-a-company&quot;&gt;how a coach's complaint turned into a company&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;At that point, I had basically zero real coding experience.&lt;br&gt;
I'd made small, chota-chota apps.&lt;br&gt;
But I had no idea how an app actually works in production.&lt;br&gt;
Domains, servers, deployment: all a mystery.&lt;/p&gt;
&lt;p&gt;What I did have was a business mindset.&lt;br&gt;
How the product should look.&lt;br&gt;
How we'd get customers.&lt;br&gt;
How we'd get paid.&lt;br&gt;
That's it.&lt;/p&gt;
&lt;p&gt;So we did what sensible people do.&lt;br&gt;
We looked for freelancers and found an agency.&lt;br&gt;
The plan was to pay them for a white-label solution.&lt;/p&gt;
&lt;p&gt;On paper, that's textbook &lt;a rel=&quot;nofollow&quot; href=&quot;https://en.wikipedia.org/wiki/Outsourcing&quot;&gt;outsourcing&lt;/a&gt;.&lt;br&gt;
You pay an external provider to do work you'd otherwise do in-house.&lt;br&gt;
Except we didn't really have an &quot;in-house&quot;.&lt;br&gt;
We had enthusiasm.&lt;br&gt;
Enthusiasm is not a department.&lt;/p&gt;
&lt;h3 id=&quot;then-the-build-arrived&quot;&gt;Then the build arrived&lt;/h3&gt;
&lt;p&gt;I opened it.&lt;br&gt;
I looked at it.&lt;br&gt;
It looked back at me from 2006.&lt;br&gt;
It looked like it had jumped straight out of a template from that year.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/the-app-that-arrived-from-2006/old-crt-computer-monitor.jpg&quot; alt=&quot;An old CRT computer monitor on a desk, the kind of screen our first outsourced app seemed designed for&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@siri_louis&quot;&gt;Siri louis&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/silver-crt-computer-monitor-on-brown-wooden-desk-KdMgF5Q9EP4&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;PHP.&lt;br&gt;
A design that belonged in a museum.&lt;br&gt;
The kind of interface that makes you check your calendar.&lt;/p&gt;
&lt;p&gt;To be fair, PHP isn't the villain here.&lt;br&gt;
Plenty of good software runs on it.&lt;br&gt;
The design was the villain.&lt;br&gt;
And, probably, so was our brief.&lt;/p&gt;
&lt;p&gt;Not a single screen looked decent.&lt;br&gt;
The thing technically worked.&lt;br&gt;
But it looked so bad that nobody wanted to touch it.&lt;br&gt;
I was ashamed to show it even to my friends.&lt;br&gt;
That's how bad it was.&lt;/p&gt;
&lt;p&gt;So we scrapped the whole thing.&lt;/p&gt;
&lt;p&gt;I sat there and thought one clear thought.&lt;br&gt;
&quot;Damn. I'll do this myself.&quot;&lt;br&gt;
I'd build it with AI tools, the way people now call &lt;a rel=&quot;nofollow&quot; href=&quot;https://en.wikipedia.org/wiki/Vibe_coding&quot;&gt;vibe coding&lt;/a&gt;.&lt;/p&gt;
&lt;h3 id=&quot;the-stupidest-50-000-i-ve-ever-spent&quot;&gt;The stupidest ₹50,000 I've ever spent&lt;/h3&gt;
&lt;p&gt;Let me be honest about the price.&lt;br&gt;
We paid that agency ₹50,000.&lt;br&gt;
It's the stupidest way to spend 50k I can think of.&lt;/p&gt;
&lt;p&gt;And it wasn't even my money.&lt;br&gt;
It was my co-founder's.&lt;br&gt;
He didn't take it too hard.&lt;br&gt;
But I was responsible for that decision.&lt;br&gt;
I still feel bad about it, honestly.&lt;/p&gt;
&lt;h3 id=&quot;outsourcing-app-development-vs-building-it-yourself&quot;&gt;Outsourcing app development vs building it yourself&lt;/h3&gt;
&lt;p&gt;Here's my honest comparison, after one very educational PHP build.&lt;br&gt;
These are opinions, not laws of physics.&lt;/p&gt;
&lt;p&gt;Outsourcing makes sense when:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;You know exactly what you want, down to the screens.&lt;/li&gt;
&lt;li&gt;The app supports your business but isn't the business.&lt;/li&gt;
&lt;li&gt;Someone on your side can review the code and the design.&lt;/li&gt;
&lt;li&gt;You have budget for a second round. There's always a second round.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Building it yourself makes sense when:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;The product &lt;em&gt;is&lt;/em&gt; the business.&lt;/li&gt;
&lt;li&gt;You'll be changing it every week for years.&lt;/li&gt;
&lt;li&gt;You're willing to be bad at it for a while.&lt;/li&gt;
&lt;li&gt;You'd rather understand every bug than pay someone to explain it.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Track My Academy was clearly the second list.&lt;br&gt;
It's the company, not a side tool.&lt;/p&gt;
&lt;p&gt;There's also a third option people forget.&lt;br&gt;
Build the first version yourself.&lt;br&gt;
Then bring in people who already understand what you're making.&lt;br&gt;
For most student founders, that's where I'd point them.&lt;/p&gt;
&lt;h3 id=&quot;how-to-write-a-product-brief-that-doesn-t-come-back-from-2006&quot;&gt;How to write a product brief that doesn't come back from 2006&lt;/h3&gt;
&lt;p&gt;Here's the thing nobody tells you.&lt;/p&gt;
&lt;p&gt;If you can't describe what good looks like, you won't get good.&lt;br&gt;
You'll get whatever the builder thinks &quot;done&quot; means.&lt;/p&gt;
&lt;p&gt;And their &quot;done&quot; might be from 2006.&lt;/p&gt;
&lt;p&gt;Bigger companies write a &lt;a rel=&quot;nofollow&quot; href=&quot;https://en.wikipedia.org/wiki/Product_requirements_document&quot;&gt;product requirements document&lt;/a&gt;.&lt;br&gt;
It says what the product should do, not how to build it.&lt;br&gt;
You don't need forty pages.&lt;br&gt;
You need one honest page.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/the-app-that-arrived-from-2006/website-wireframe-sketch.jpg&quot; alt=&quot;A hand-drawn website wireframe sketched on paper with an orange pen, the start of a clear product brief&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@sigmund&quot;&gt;Compagnons&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/website-wireframe-sketch-on-paper-4UGmm3WRUoQ&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;My checklist for a one-page product brief:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Who it's for.&lt;/strong&gt; &quot;A coach with one batch&quot; beats &quot;sports organisations&quot;.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;The one painful job.&lt;/strong&gt; For us, that was attendance and payments.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Three apps you like the look of.&lt;/strong&gt; Screenshots, not adjectives.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;What &quot;done&quot; means.&lt;/strong&gt; Which screens, which actions, which devices.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;What you won't build yet.&lt;/strong&gt; This list saves more money than any discount.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Who checks the work.&lt;/strong&gt; If nobody can read code, say so upfront.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Point three is the one I'd underline twice.&lt;br&gt;
&quot;Modern and clean&quot; means nothing.&lt;br&gt;
Every design was modern and clean once.&lt;br&gt;
Even in 2006.&lt;/p&gt;
&lt;p&gt;The aim is a &lt;a rel=&quot;nofollow&quot; href=&quot;https://en.wikipedia.org/wiki/Minimum_viable_product&quot;&gt;minimum viable product&lt;/a&gt;.&lt;br&gt;
That means just enough features for early users to actually use it.&lt;br&gt;
Then their feedback tells you what to build next.&lt;br&gt;
Not your imagination at 2 a.m.&lt;/p&gt;
&lt;h3 id=&quot;the-first-night-of-building-a-saas-mvp-myself&quot;&gt;The first night of building a SaaS MVP myself&lt;/h3&gt;
&lt;p&gt;My setup was not exactly a startup lab.&lt;/p&gt;
&lt;p&gt;A MacBook Air.&lt;br&gt;
A second-hand iPhone my cofounder got me.&lt;br&gt;
ChatGPT.&lt;br&gt;
VS Code.&lt;/p&gt;
&lt;p&gt;That was the entire tech stack of my ambition.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/the-app-that-arrived-from-2006/first-workspace.jpg&quot; alt=&quot;Rahul at his first workspace with a MacBook and an iPhone, the Track My Academy goals poster behind him&quot;&gt;&lt;/p&gt;
&lt;p&gt;Did I start coding immediately?&lt;br&gt;
No.&lt;br&gt;
Mostly, I researched.&lt;/p&gt;
&lt;p&gt;How do real products look?&lt;br&gt;
How do people structure an app like this?&lt;br&gt;
Why does everything I write look worse than everything I see?&lt;/p&gt;
&lt;p&gt;By the end of it, I'd built a landing page.&lt;br&gt;
A landing page I actually liked.&lt;br&gt;
That was the night I stopped waiting for someone else.&lt;/p&gt;
&lt;p&gt;Building it properly took about three months.&lt;br&gt;
The first working version alone took more than a month and a half.&lt;br&gt;
Changes, then more changes, then changes to the changes.&lt;/p&gt;
&lt;p&gt;When I look at that first version now, I'm honestly embarrassed.&lt;br&gt;
It might be the worst thing that ever happened to a piece of software.&lt;br&gt;
The version we have today? I'm really proud of it.&lt;/p&gt;
&lt;p&gt;I learn by touching the thing until it makes sense.&lt;br&gt;
That means doing it badly first, then slightly less badly.&lt;br&gt;
The AI help came from wherever we could find it.&lt;br&gt;
That story is in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/dozens-of-email-accounts-and-zero-shame&quot;&gt;dozens of email accounts and zero shame&lt;/a&gt;.&lt;/p&gt;
&lt;h3 id=&quot;the-modern-stack-i-ended-up-with&quot;&gt;The modern stack I ended up with&lt;/h3&gt;
&lt;p&gt;No PHP this time.&lt;br&gt;
Again, nothing against PHP.&lt;br&gt;
I just needed a fresh start and a clean conscience.&lt;/p&gt;
&lt;p&gt;Here's what Track My Academy runs on:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;React&lt;/strong&gt; for the web front end.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://fastapi.tiangolo.com/&quot;&gt;FastAPI&lt;/a&gt;&lt;/strong&gt;, a Python framework for building APIs with type hints.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;MongoDB&lt;/strong&gt;, a document database.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://supabase.com/docs&quot;&gt;Supabase&lt;/a&gt;&lt;/strong&gt;, which bundles Postgres, auth, storage and realtime features.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;AWS EC2&lt;/strong&gt; and &lt;strong&gt;Vercel&lt;/strong&gt;, where things actually run.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Razorpay&lt;/strong&gt;, the payments gateway.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Firebase&lt;/strong&gt; and &lt;strong&gt;Redis&lt;/strong&gt;, quietly doing their jobs in the background.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;None of this is exotic.&lt;br&gt;
It's just current.&lt;br&gt;
And I can explain why every piece is there.&lt;/p&gt;
&lt;p&gt;That's my real advice for anyone outsourcing.&lt;br&gt;
Ask the builder, &quot;Which stack, and why?&quot;&lt;br&gt;
If the answer is &quot;it's what we always use&quot;, that's information.&lt;br&gt;
Treat it like a yellow card.&lt;/p&gt;
&lt;p&gt;Knowing the stack also means knowing exactly how to break it.&lt;br&gt;
I proved that when &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-night-i-broke-production&quot;&gt;I took production down for hours&lt;/a&gt;.&lt;br&gt;
Ownership cuts both ways.&lt;/p&gt;
&lt;h3 id=&quot;then-i-built-the-android-and-ios-apps-too&quot;&gt;Then I built the Android and iOS apps too&lt;/h3&gt;
&lt;p&gt;The web app wasn't the end.&lt;br&gt;
Coaches aren't sitting at desks.&lt;br&gt;
They're on a pitch, holding a phone and a whistle.&lt;/p&gt;
&lt;p&gt;So I built the Android and iOS apps for Track My Academy.&lt;br&gt;
The Android app is live in production.&lt;br&gt;
The iOS app is coming soon.&lt;br&gt;
Apple reviews things slowly. So do I, to be fair.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/the-app-that-arrived-from-2006/android-and-iphone-apps.jpg&quot; alt=&quot;Two smartphones held up against a city skyline, one Android and one iPhone&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@rmrdnl&quot;&gt;Daniel Romero&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/two-smartphones-held-up-against-city-skyline-txROtUzmo_c&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;This is where building it yourself pays off.&lt;br&gt;
I'd built the backend, so I knew it inside out.&lt;br&gt;
The apps were new screens, not new mysteries.&lt;/p&gt;
&lt;p&gt;If I'd outsourced the web app, the mobile apps would've started from zero.&lt;br&gt;
Or from 2006 again.&lt;br&gt;
I'm not sure which is worse.&lt;/p&gt;
&lt;p&gt;Today &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt; covers attendance, fees, player analytics and parent communication.&lt;br&gt;
Real academies run on it.&lt;br&gt;
It's multi-tenant and role-based, which is a fancy way of saying &quot;complicated&quot;.&lt;br&gt;
It works on the web and Android, with iOS coming soon.&lt;br&gt;
It's published by &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmytech.in&quot;&gt;TrackMy Tech&lt;/a&gt;, our bootstrapped sports-tech company.&lt;/p&gt;
&lt;h3 id=&quot;what-i-learned-from-the-2006-build&quot;&gt;What I learned from the 2006 build&lt;/h3&gt;
&lt;p&gt;I'm not angry at the agency that built it.&lt;br&gt;
Okay, a little.&lt;br&gt;
Mostly at myself.&lt;/p&gt;
&lt;p&gt;Outsourcing works when you know what you want.&lt;br&gt;
It doesn't work when you're hoping someone reads your mind.&lt;/p&gt;
&lt;p&gt;Building it myself meant I understood every piece.&lt;br&gt;
When something breaks, I know where to look.&lt;br&gt;
When a coach wants a feature, I know what it costs.&lt;/p&gt;
&lt;p&gt;None of that exists if I'd accepted the museum piece.&lt;/p&gt;
&lt;p&gt;So, should you build it yourself?&lt;br&gt;
Not always.&lt;br&gt;
But if what comes back makes you wince, listen to the wince.&lt;/p&gt;
&lt;p&gt;Your irritation is data.&lt;/p&gt;
&lt;p&gt;Mine turned into a company.&lt;br&gt;
Yours might turn into something too.&lt;br&gt;
Or at least into a better landing page.&lt;/p&gt;
&lt;p&gt;I'll take either.&lt;/p&gt;
&lt;h3 id=&quot;faq-5&quot;&gt;FAQ&lt;/h3&gt;
&lt;h4 id=&quot;is-it-cheaper-to-outsource-app-development-or-build-it-yourself-&quot;&gt;Is it cheaper to outsource app development or build it yourself?&lt;/h4&gt;
&lt;p&gt;Outsourcing usually looks cheaper on day one.&lt;br&gt;
Building yourself costs time instead of money.&lt;br&gt;
Outsourcing costs money, then often time anyway, in revisions.&lt;br&gt;
If the product is your business, I'd rather pay with time.&lt;/p&gt;
&lt;h4 id=&quot;what-should-a-product-brief-for-a-developer-include-&quot;&gt;What should a product brief for a developer include?&lt;/h4&gt;
&lt;p&gt;Who it's for and the one painful job it solves.&lt;br&gt;
Three reference apps, with screenshots.&lt;br&gt;
A clear definition of done, and a list of what's out of scope.&lt;br&gt;
And who will review the work before you pay for it.&lt;/p&gt;
&lt;h4 id=&quot;can-a-non-technical-founder-build-a-saas-mvp-&quot;&gt;Can a non-technical founder build a SaaS MVP?&lt;/h4&gt;
&lt;p&gt;I was a bio-maths student in class 12.&lt;br&gt;
That story is in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/bio-maths-to-computer-science&quot;&gt;how I ended up in computer science&lt;/a&gt;.&lt;br&gt;
So yes, eventually.&lt;br&gt;
Expect to be bad at it first.&lt;br&gt;
That's the tuition fee.&lt;/p&gt;
&lt;h3 id=&quot;your-turn&quot;&gt;Your turn&lt;/h3&gt;
&lt;p&gt;Run a sports academy and tired of spreadsheets?&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Try Track My Academy&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Stuck deciding between outsourcing and building it yourself?&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://calendar.rahuldk.in&quot;&gt;Book a call with me&lt;/a&gt; and we can argue about it.&lt;/p&gt;
&lt;p&gt;Or see where all this happens now, in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/three-monitors-one-monster-can&quot;&gt;my three-monitor desk setup&lt;/a&gt;.&lt;/p&gt;
</description>
<category>Articles</category>
<guid isPermaLink="true">https://coderlegion.com/32517/outsourcing-vs-building-it-yourself-our-app-arrived-from-2006</guid>
<pubDate>Tue, 27 Oct 2026 08:30:00 +0000</pubDate>
</item>
<item>
<title>Production outage lessons: we blamed our code. It was SSL.</title>
<link>https://coderlegion.com/32504/production-outage-lessons-we-blamed-our-code-it-was-ssl</link>
<description>&lt;p&gt;Building a product is one job.&lt;br&gt;
Keeping it alive is a completely different job.&lt;/p&gt;
&lt;p&gt;Nobody warns you about the second one.&lt;br&gt;
Or they do, and you don't listen.&lt;br&gt;
I didn't listen.&lt;/p&gt;
&lt;p&gt;This post is my production outage lessons, learnt the expensive way.&lt;br&gt;
One backend split, one expired SSL certificate, four hours of blaming the wrong thing.&lt;br&gt;
And what I'd do differently: checklists, rollbacks, monitoring and postmortems.&lt;/p&gt;
&lt;h3 id=&quot;the-clever-idea-splitting-the-backend&quot;&gt;The clever idea: splitting the backend&lt;/h3&gt;
&lt;p&gt;This happened in 2026, not long after we incorporated TrackMy Tech.&lt;br&gt;
We'd just become a private limited company.&lt;br&gt;
And we had a nagging feeling we weren't doing things professionally enough.&lt;br&gt;
We wanted to fix that.&lt;/p&gt;
&lt;p&gt;We also had real problems.&lt;br&gt;
Lots of payment-related issues.&lt;br&gt;
A steady stream of API errors.&lt;br&gt;
And the load wasn't balancing well.&lt;/p&gt;
&lt;p&gt;Then an Instagram reel showed up.&lt;br&gt;
I shared it with the team.&lt;br&gt;
&quot;This model is so capable. We can try some serious stuff with it.&quot;&lt;br&gt;
That one reel kicked off the whole cycle.&lt;/p&gt;
&lt;p&gt;The plan: split the backend into separate pieces.&lt;br&gt;
We used an AI coding agent to do the heavy lifting.&lt;br&gt;
To be fair to the agent, it did its job.&lt;br&gt;
It was us who got things wrong.&lt;/p&gt;
&lt;p&gt;On paper, splitting load sounds smart.&lt;br&gt;
Spread the work. Feel like a real engineering team.&lt;br&gt;
Put &quot;distributed&quot; in your head and feel tall.&lt;/p&gt;
&lt;h3 id=&quot;then-everything-went-down&quot;&gt;Then everything went down&lt;/h3&gt;
&lt;p&gt;Not slowly. Not politely.&lt;br&gt;
Everything went down.&lt;br&gt;
For hours.&lt;/p&gt;
&lt;p&gt;If you've never broken production, let me describe the feeling.&lt;br&gt;
Your stomach drops to somewhere near your shoes.&lt;br&gt;
Every message notification sounds like an accusation.&lt;/p&gt;
&lt;p&gt;Real academies use &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt;.&lt;br&gt;
Real coaches. Real parents. Real attendance.&lt;/p&gt;
&lt;p&gt;None of them care about our clever architecture.&lt;br&gt;
They care that the app works.&lt;/p&gt;
&lt;p&gt;And it did not work.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/the-night-i-broke-production/server-room-network-cabinets.jpg&quot; alt=&quot;A server room with rows of network cabinets under blue cables&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@tvick&quot;&gt;Taylor Vick&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/server-room-with-network-cabinets-aWslrFhs1w4&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h3 id=&quot;the-real-culprit-an-expired-ssl-certificate&quot;&gt;The real culprit: an expired SSL certificate&lt;/h3&gt;
&lt;p&gt;We were sure we'd broken the code.&lt;br&gt;
So we did what any panicking team does.&lt;br&gt;
We checked the split.&lt;br&gt;
We checked the code.&lt;br&gt;
Then we checked it all again.&lt;/p&gt;
&lt;p&gt;About four hours later, we found it.&lt;br&gt;
It wasn't the code at all.&lt;br&gt;
The SSL certificate on our backend domain had expired.&lt;br&gt;
Right in the middle of the transition.&lt;/p&gt;
&lt;p&gt;It was failing silently.&lt;br&gt;
And we were busy blaming our own clever architecture.&lt;/p&gt;
&lt;p&gt;When we finally saw it, we just stared at the screen.&lt;br&gt;
Oh God.&lt;br&gt;
This is why debugging is hard.&lt;/p&gt;
&lt;p&gt;Here's why it's so sneaky.&lt;br&gt;
A &lt;a rel=&quot;nofollow&quot; href=&quot;https://en.wikipedia.org/wiki/Public_key_certificate&quot;&gt;TLS certificate&lt;/a&gt; proves a server is who it claims to be.&lt;br&gt;
Every certificate has a &quot;Not After&quot; date.&lt;br&gt;
After that date, it's simply no longer valid.&lt;br&gt;
Apps and browsers stop trusting the server, and requests fail.&lt;/p&gt;
&lt;p&gt;Short certificate lifetimes are normal now.&lt;br&gt;
&lt;a rel=&quot;nofollow&quot; href=&quot;https://letsencrypt.org/docs/faq/&quot;&gt;Let's Encrypt says&lt;/a&gt; its default certificates are valid for 90 days.&lt;br&gt;
It recommends renewing them every 60 days.&lt;br&gt;
Miss a renewal and the clock just quietly runs out.&lt;/p&gt;
&lt;p&gt;The timing is what fooled us.&lt;br&gt;
Two things changed at once: our backend, and the certificate's validity.&lt;br&gt;
So naturally we blamed the change we'd made ourselves.&lt;/p&gt;
&lt;p&gt;Google's &lt;a rel=&quot;nofollow&quot; href=&quot;https://sre.google/sre-book/introduction/&quot;&gt;SRE book&lt;/a&gt; says roughly 70% of outages come from changes to a live system.&lt;br&gt;
We were the change.&lt;br&gt;
We just weren't the cause.&lt;/p&gt;
&lt;h3 id=&quot;the-longest-night-in-the-office&quot;&gt;The longest night in the office&lt;/h3&gt;
&lt;p&gt;I stayed in the office all night.&lt;/p&gt;
&lt;p&gt;Not because it looks dedicated on LinkedIn.&lt;br&gt;
Because it was my mess, and I wanted it fixed.&lt;/p&gt;
&lt;p&gt;There's a special kind of quiet in an office at 3 a.m.&lt;br&gt;
It's just you, the monitors, and your mistakes.&lt;/p&gt;
&lt;p&gt;The Monster cans on the wall were not decoration that night.&lt;br&gt;
They were fuel.&lt;br&gt;
(The full tour of that desk is in &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/three-monitors-one-monster-can&quot;&gt;three monitors, one Monster can&lt;/a&gt;.)&lt;/p&gt;
&lt;p&gt;Office nights are not rare for me, sadly.&lt;br&gt;
That's a whole other post: &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/exams-the-office-and-a-1am-gate&quot;&gt;exams, the office and a 1 a.m. gate&lt;/a&gt;.&lt;/p&gt;
&lt;h3 id=&quot;when-i-m-stuck-badly-enough-i-call-arun&quot;&gt;When I'm stuck badly enough, I call Arun&lt;/h3&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/the-night-i-broke-production/arun.jpg&quot; alt=&quot;Arun, our CTO, smiling at the camera&quot;&gt;&lt;/p&gt;
&lt;p&gt;Every founder needs one person who picks up at any hour.&lt;br&gt;
For me, that's Arun. Our CTO.&lt;/p&gt;
&lt;p&gt;No questions asked. He just picks up.&lt;br&gt;
At any hour. Which is frankly suspicious.&lt;/p&gt;
&lt;p&gt;If you want to know who he is, here's &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.arunvignesh.my/&quot;&gt;his portfolio&lt;/a&gt;.&lt;br&gt;
He's the reason &quot;stuck&quot; never becomes &quot;stuck forever&quot;.&lt;/p&gt;
&lt;p&gt;The lesson here isn't technical.&lt;br&gt;
Know who you'll call before the crisis, not during it.&lt;/p&gt;
&lt;h3 id=&quot;a-deployment-checklist-i-d-hand-my-past-self&quot;&gt;A deployment checklist I'd hand my past self&lt;/h3&gt;
&lt;p&gt;I'm not going to pretend I have a grand theory.&lt;br&gt;
But here's the checklist that night burned into my brain.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Check the boring stuff first.&lt;/strong&gt; SSL certificates, DNS, environment variables. Then blame the code.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Know when every certificate expires.&lt;/strong&gt; Write the dates down before you touch anything.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Change one big thing at a time.&lt;/strong&gt; Two changes, one failure, endless guessing.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Deploy when people are awake.&lt;/strong&gt; Ideally the people who can fix it.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Know your way back.&lt;/strong&gt; Before you ship, not after.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Watch it after you ship.&lt;/strong&gt; &quot;Deployed&quot; is not the same as &quot;working&quot;.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Google's SRE book lists three practices for safer changes.&lt;br&gt;
Progressive rollouts.&lt;br&gt;
Quickly and accurately detecting problems.&lt;br&gt;
Rolling back safely when problems arise.&lt;/p&gt;
&lt;p&gt;That's basically my checklist, written by people with far more sleep.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/the-night-i-broke-production/deployment-checklist-notebook.jpg&quot; alt=&quot;A hand ticking items off a deployment checklist in a notebook&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@jakubzerdzicki&quot;&gt;Jakub Żerdzicki&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/hand-checking-off-items-on-a-to-do-list-fXlL5I0IvK0&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h3 id=&quot;rollbacks-have-a-way-back&quot;&gt;Rollbacks: have a way back&lt;/h3&gt;
&lt;p&gt;If you can't undo a change quickly, you're not deploying.&lt;br&gt;
You're gambling.&lt;/p&gt;
&lt;p&gt;One classic pattern is &lt;a rel=&quot;nofollow&quot; href=&quot;https://martinfowler.com/bliki/BlueGreenDeployment.html&quot;&gt;blue-green deployment&lt;/a&gt;, as Martin Fowler describes it.&lt;br&gt;
You keep two nearly identical production environments.&lt;br&gt;
One is live. The other gets the new version.&lt;br&gt;
You test the idle one, then switch the router over.&lt;/p&gt;
&lt;p&gt;If it breaks, you switch the router back.&lt;br&gt;
Fowler calls it &quot;a rapid way to rollback&quot;.&lt;/p&gt;
&lt;p&gt;You don't need a fancy setup to steal the idea.&lt;br&gt;
Keep the old config. Keep the old build.&lt;br&gt;
Know the exact command that puts things back.&lt;br&gt;
Practise it once on a calm day.&lt;/p&gt;
&lt;h3 id=&quot;monitoring-and-alerting-find-out-before-your-users-do&quot;&gt;Monitoring and alerting: find out before your users do&lt;/h3&gt;
&lt;p&gt;The worst way to discover an outage is from a user.&lt;br&gt;
The second worst is from a friend asking &quot;is your app down?&quot;&lt;/p&gt;
&lt;p&gt;The Google SRE chapter on &lt;a rel=&quot;nofollow&quot; href=&quot;https://sre.google/sre-book/monitoring-distributed-systems/&quot;&gt;monitoring distributed systems&lt;/a&gt; is a good start.&lt;br&gt;
It names four golden signals: latency, traffic, errors and saturation.&lt;br&gt;
Measure those and page a human when they look wrong.&lt;br&gt;
I'd add one more for small teams: certificate expiry dates.&lt;br&gt;
That gets you decently covered, according to the book.&lt;/p&gt;
&lt;p&gt;It also says something I love: &quot;Every page should be actionable.&quot;&lt;br&gt;
An alert you ignore is just a very expensive ringtone.&lt;/p&gt;
&lt;p&gt;Later, I built a &quot;Pager System&quot; for Track My Academy developers.&lt;br&gt;
It's an internal real-time error and notification system.&lt;br&gt;
The idea is simple: problems should find developers, not wait to be found.&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://www.rahuldk.in/posts/the-night-i-broke-production/monitoring-dashboard-graphs.jpg&quot; alt=&quot;A laptop showing monitoring dashboard graphs for latency and traffic&quot;&gt;&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Photo: &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/@lukechesser&quot;&gt;Luke Chesser&lt;/a&gt; on &lt;a rel=&quot;nofollow&quot; href=&quot;https://unsplash.com/photos/graphs-of-performance-analytics-on-a-laptop-screen-JKUTrJ4vK00&quot;&gt;Unsplash&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;h3 id=&quot;write-the-postmortem-and-keep-it-blameless&quot;&gt;Write the postmortem, and keep it blameless&lt;/h3&gt;
&lt;p&gt;After the fix, the temptation is to sleep and never speak of it again.&lt;br&gt;
Don't.&lt;/p&gt;
&lt;p&gt;Write an incident postmortem.&lt;br&gt;
Google's chapter on &lt;a rel=&quot;nofollow&quot; href=&quot;https://sre.google/sre-book/postmortem-culture/&quot;&gt;postmortem culture&lt;/a&gt; puts it nicely.&lt;br&gt;
&quot;Writing a postmortem is not punishment.&quot;&lt;br&gt;
It's a learning opportunity for the whole company.&lt;/p&gt;
&lt;p&gt;Their triggers include user-visible downtime and an engineer having to roll back.&lt;br&gt;
A multi-hour outage ticks both boxes with enthusiasm.&lt;/p&gt;
&lt;p&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.atlassian.com/incident-management/postmortem&quot;&gt;Atlassian's guide to incident postmortems&lt;/a&gt; is very practical.&lt;br&gt;
It covers a timeline, root cause, impact, metrics and action items.&lt;br&gt;
It suggests a review meeting within 24 to 48 hours of resolution.&lt;br&gt;
Then draft the write-up straight after.&lt;br&gt;
Wait longer and the details evaporate.&lt;/p&gt;
&lt;p&gt;Blameless doesn't mean nobody made a mistake.&lt;br&gt;
It means you fix the system so the next person can't make it.&lt;br&gt;
Even if the next person is, once again, me.&lt;/p&gt;
&lt;h3 id=&quot;was-it-worth-it-&quot;&gt;Was it worth it?&lt;/h3&gt;
&lt;p&gt;Honestly? Yes.&lt;br&gt;
Not the outage. The outage was terrible.&lt;br&gt;
But I learned more in that one night than in a month of tutorials.&lt;/p&gt;
&lt;p&gt;Mistakes are expensive teachers.&lt;br&gt;
They're also very, very memorable.&lt;/p&gt;
&lt;p&gt;I'd still prefer the tutorials, though.&lt;/p&gt;
&lt;h3 id=&quot;faq-6&quot;&gt;FAQ&lt;/h3&gt;
&lt;h4 id=&quot;what-are-the-most-important-production-outage-lessons-for-a-small-team-&quot;&gt;What are the most important production outage lessons for a small team?&lt;/h4&gt;
&lt;p&gt;Change one thing at a time.&lt;br&gt;
Always have a tested way back.&lt;br&gt;
Monitor the basics so you hear about problems before users do.&lt;/p&gt;
&lt;h4 id=&quot;can-an-expired-ssl-certificate-take-down-a-backend-&quot;&gt;Can an expired SSL certificate take down a backend?&lt;/h4&gt;
&lt;p&gt;Yes, and quietly.&lt;br&gt;
Once a certificate passes its expiry date, clients stop trusting the server.&lt;br&gt;
Requests fail, and it can look exactly like a code bug.&lt;/p&gt;
&lt;h4 id=&quot;what-should-go-in-an-incident-postmortem-&quot;&gt;What should go in an incident postmortem?&lt;/h4&gt;
&lt;p&gt;A timeline, the impact, the root cause and clear action items.&lt;br&gt;
Keep it blameless.&lt;br&gt;
Fix the system, not the person.&lt;/p&gt;
&lt;h3 id=&quot;sources-5&quot;&gt;Sources&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://sre.google/sre-book/introduction/&quot;&gt;Google SRE book: Introduction&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://sre.google/sre-book/monitoring-distributed-systems/&quot;&gt;Google SRE book: Monitoring distributed systems&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://sre.google/sre-book/postmortem-culture/&quot;&gt;Google SRE book: Postmortem culture&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://www.atlassian.com/incident-management/postmortem&quot;&gt;Atlassian: Incident postmortems&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://martinfowler.com/bliki/BlueGreenDeployment.html&quot;&gt;Martin Fowler: Blue-green deployment&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://en.wikipedia.org/wiki/Public_key_certificate&quot;&gt;Wikipedia: Public key certificate&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://letsencrypt.org/docs/faq/&quot;&gt;Let's Encrypt FAQ&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&quot;what-next-5&quot;&gt;What next&lt;/h3&gt;
&lt;p&gt;Curious how the product got built in the first place? Read &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/the-app-that-arrived-from-2006&quot;&gt;the app that arrived from 2006&lt;/a&gt;.&lt;br&gt;
Or how I learned the tools: &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.rahuldk.in/blog/dozens-of-email-accounts-and-zero-shame&quot;&gt;dozens of email accounts and zero shame&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Running an academy? &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmyacademy.com&quot;&gt;Track My Academy&lt;/a&gt; handles attendance, fees, player analytics and parent communication.&lt;br&gt;
It's built by &lt;a rel=&quot;nofollow&quot; href=&quot;https://www.trackmytech.in&quot;&gt;TrackMy Tech&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Want to talk shipping, breaking and fixing things? &lt;a rel=&quot;nofollow&quot; href=&quot;https://calendar.rahuldk.in&quot;&gt;Book a call&lt;/a&gt;.&lt;/p&gt;
</description>
<category>Articles</category>
<guid isPermaLink="true">https://coderlegion.com/32504/production-outage-lessons-we-blamed-our-code-it-was-ssl</guid>
<pubDate>Mon, 26 Oct 2026 12:01:40 +0000</pubDate>
</item>
<item>
<title>I Built a Set of Free Web Tools While Working on Client Projects — Here They Are</title>
<link>https://coderlegion.com/27226/i-built-a-set-of-free-web-tools-while-working-on-client-projects-here-they-are</link>
<description>&lt;p&gt;As a designer/developer working across branding, TYPO3 builds, and client campaigns, I kept running into the same small, annoying tasks — checking contrast ratios, generating favicons in five formats, minifying a stylesheet before deploy. So over time I built myself a little toolbox to handle them. Sharing it here in case it saves someone else the same repeated Googling.&lt;/p&gt;
&lt;p&gt;Most of these came out of solving a problem once for a client and thinking &quot;I'll need this again.&quot; If you build Websites or juggle design + dev like I do, they're free to use: &lt;strong&gt;stefan-andres.at/tools.&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Design &amp;amp; Marketing&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Palette &amp;amp; Contrast Checker&lt;/strong&gt; — Upload a logo, extract the brand colors, check WCAG contrast, and export ready-to-use CSS variables.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Icon &amp;amp; Favicon Generator&lt;/strong&gt; — One upload, every format you need: favicon, iOS &amp;amp; Android app icons, social profile pictures.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Web Image Optimizer&lt;/strong&gt; — Compress images, convert to WebP/AVIF, and resize for web performance in one pass.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;SEO Check&lt;/strong&gt; — Drop in a page URL and get an instant on-page SEO check: title, meta description, headings, and alt texts.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;For Developers&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;CSS Minifier&lt;/strong&gt; — Paste or upload a stylesheet, strip whitespace and redundancy, download the compressed file.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;JS Minifier&lt;/strong&gt; — Paste or upload a script, compress and mangle it safely, download the smaller file.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;SVG Optimizer&lt;/strong&gt; — Paste or upload an SVG, strip unnecessary code, download the smaller file.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;CSS Clamp() Calculator&lt;/strong&gt; — Enter a min and max size, get a ready-to-use clamp() formula for fluid typography.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;JSON Formatter &amp;amp; Validator&lt;/strong&gt; — Paste or upload JSON, catch syntax errors down to the exact line and column, copy it cleanly formatted.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;TYPO3 Fluid ViewHelper Generator&lt;/strong&gt; — Generate custom ViewHelpers, TCA fields &amp;amp; FlexForms, and test Fluid templates live.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;For Clients / Agency Work&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Client Briefing &amp;amp; Scope Generator&lt;/strong&gt; — Capture background, target audience and scope, then auto-generate a brief, sign-off email and quote block, exportable as PDF.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Curious what small tools others here have built for their own workflow — always looking to add more to the pile.&lt;/p&gt;
</description>
<category>Articles</category>
<guid isPermaLink="true">https://coderlegion.com/27226/i-built-a-set-of-free-web-tools-while-working-on-client-projects-here-they-are</guid>
<pubDate>Tue, 15 Sep 2026 07:20:18 +0000</pubDate>
</item>
<item>
<title>Thinking Differently</title>
<link>https://coderlegion.com/19693/thinking-differently</link>
<description>&lt;p&gt;Hey everyone!  I'm Krrish Savlani founder of High Vision Labs.&lt;/p&gt;
&lt;p&gt;I’ve always been obsessed with high-standard processes and creating the best possible developer experience, which led me to my current focus.&lt;/p&gt;
&lt;p&gt;For the last few months, under High Vision Labs, I've been quietly building our core product: Thinking Differently.&lt;/p&gt;
&lt;p&gt;I’m going to be completely honest: I don’t have infinite scale, flawless metrics, or a bulletproof system to promise you today. &lt;/p&gt;
&lt;p&gt;The platform is early, and it’s a beta in the truest sense of the word.&lt;/p&gt;
&lt;p&gt;But I have a specific obsession.&lt;/p&gt;
&lt;p&gt;Most developer platforms optimize for the developer's initial setup.&lt;/p&gt;
&lt;p&gt; I want to build something that optimizes for what happens after the code is written.&lt;/p&gt;
&lt;p&gt;Because your customers will never see your databases, your APIs, or your backend architecture. But they will judge your product by them every single day.&lt;/p&gt;
&lt;p&gt;To a developer, a slow query is just a latency metric. To a customer, it’s a frustrating experience.&lt;/p&gt;
&lt;p&gt;To a developer, a dropped connection is a server error. To a customer, it’s a broken promise.&lt;/p&gt;
&lt;p&gt;Every backend decision we make eventually becomes a judgment from the customer.&lt;/p&gt;
&lt;p&gt;That’s why I’m building Thinking Differently.&lt;/p&gt;
&lt;p&gt;The goal isn't just to give you another tool; it’s to help you build products that users can actually trust, by aligning backend decisions with real-world user outcomes.&lt;/p&gt;
&lt;p&gt;We are nowhere near perfect yet. &lt;/p&gt;
&lt;p&gt;But the North Star is clear:&lt;/p&gt;
&lt;p&gt; Technology is never the destination. The success of your product is.&lt;/p&gt;
&lt;p&gt;The first beta will be opening soon.&lt;/p&gt;
&lt;p&gt;I'm looking for a small handful of developers who want early access, aren't afraid of a few bugs, and want to help me shape this vision from the ground up.&lt;/p&gt;
&lt;p&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://docs.google.com/forms/d/e/1FAIpQLSenXYnC9scSGY4_8YAoH6wB3KhzmgrqW8EHrextuPqPL8Fhrw/viewform&quot;&gt;https://docs.google.com/forms/d/e/1FAIpQLSenXYnC9scSGY4_8YAoH6wB3KhzmgrqW8EHrextuPqPL8Fhrw/viewform&lt;/a&gt;&lt;/p&gt;
</description>
<category>Launches</category>
<guid isPermaLink="true">https://coderlegion.com/19693/thinking-differently</guid>
<pubDate>Thu, 04 Jun 2026 21:03:12 +0000</pubDate>
</item>
</channel>
</rss>