Technology · Software & Engineering

Software engineering, infrastructure and applied AI.

Websites, online stores and custom software for Canadian businesses — designed as well as built. Senior engineers scope it and build it, and your team is left with a system it can run without us.

TNAADO’s founder, in a black and red I’M EVERYWHERE cap, showing a client work in progress on a MacBook. The client stands in the foreground watching the screen, in a bright room with a vertical timber slat wall behind them.
TNAADO’s founder walking a client through a build in progress

We walk clients through the build while it is still being built.

By the time it is handed over, the people who have to run it have already watched it work. Every build ends with a written runbook and a named engineer to call.

D.01 · Expertise

What we build

Five areas we are asked for most often. Open one and the panel runs the actual mechanic — real policy syntax, real Stripe statuses, real migration filenames — rather than a diagram of it.

  1. Live table invoices · policy invoices_read

    create policy "invoices_read" on public.invoices for select
      using (user_id = auth.uid() or public.is_admin());

    no rows — the policy matched nothing for this caller

    inv_4f1a8f2c…paid2,400.00
    inv_51c94a91…open860.00
    inv_60028f2c…open1,150.00
    inv_63d7c7e0…void0.00
    inv_71884a91…paid3,900.00
    inv_7a45b104…draft540.00

     

    Policy taken from a live TNAADO table. The six rows are sample data.

    • Postgres RLS on Supabase
    • policy per table, per operation
    • SECURITY DEFINER helper functions
    • service_role kept server-side only
    • grants audited separately from policies

    We design the policies with the schema rather than after it, and audit them as a separate pass: every table checked for RLS enabled, every policy read against the grants that sit underneath it, and every anon-role privilege removed unless there is a reason for it.

    • shoot.tnaado.ca sign-in requiredProduction crew system. A crew member is returned only the shoots they are assigned to; a producer is returned the whole schedule. The rule producing that split is a policy of exactly the shape above, applied by Postgres before a row ever reaches the app.
    • site.tnaado.ca sign-in requiredRole-gated newsroom CMS. Editing, analytics and billing are separate roles, and which one you hold is checked in the database rather than in the interface.

    The service_role key that bypasses all of this never reaches a browser. It exists only inside server-side functions, which is the whole reason the rules can live in the database.

  2. Live object PaymentIntent · CAD 2,400.00

    created
    requires_
    confirmation
    requires_
    action
    processing
    succeeded
    ↓ card_declined · retry with a new payment method
    webhook
    payment_intent.created
    created

    Statuses and event names are Stripe’s own. Handlers are idempotent: the same event id delivered twice does not charge twice.

    • Stripe Payment Intents & Checkout
    • Connect marketplace payouts
    • webhook signature check + idempotency
    • Apple receipt verification server-side
    • subscriptions, refunds, disputes

    The failure branches are the part that takes the time: declines, 3-D Secure challenges the customer abandons, webhooks delivered twice, and payouts that need a hold. We build the handler for each of those before the happy path is called done.

    • shoot.tnaado.ca sign-in requiredStripe Connect payouts to production crew: a payout is computed from the shoot record, queued, held until it is approved, then released to the crew member’s connected account.
    • The Dispatch iOS · v1.0.8An Apple in-app subscription, with the receipt verified server-side against Apple instead of trusted from the device.

    Live functions doing this work: billing-webhook, connect-webhook, process-payout-queue, release-payout, stripe-balance.

  3. Live build The Dispatch · iOS

    1. Written briefScreens, data model and the one thing it must do well, agreed before any code.
    2. Wireframe and schemaLayout and the Postgres tables behind it, built together.
    3. Build and TestFlightSwiftUI against the real backend, on devices, every build numbered.
    4. App Store submissionScreenshots generated in the simulator at every required size, listing copy, review.

    Screenshots are generated in the iOS simulator at each size Apple requires, so they are reproducible for the next release.

    • Swift and SwiftUI, native
    • Supabase backend, Postgres + RLS
    • StoreKit purchases, verified server-side
    • TestFlight, then App Store Connect API
    • simulator-generated screenshots

    Two apps built this way are on the Canadian App Store now, and you can open either one before you talk to us:

    Both checked against the App Store on 13 August 2026. Further iOS builds are finished and going through release; they are deliberately not listed here, because you cannot open them yet.

  4. Live repo supabase/migrations

    filename0 / 7 applied
    1. 20260731045025_live_events_freshness_and_reaper.sqlapplied
    2. 20260801223741_anon_default_privileges_no_dml.sqlapplied
    3. 20260801224732_restrict_rollup_analytics_daily_to_service_role.sqlapplied
    4. 20260803025500_app_registry_add_socials.sqlapplied
    5. 20260803202753_portfolio_items_gallery_videos.sqlapplied
    6. 20260803232609_ingest_state_record_and_lock_grants.sqlapplied
    7. 20260806141701_drop_dead_anon_invoice_policies.sqlapplied

    Seven consecutive migrations from TNAADO Inc’s own admin database, in the order they were applied.

    • timestamped, forward-only files
    • one migration written, then pushed
    • verified with supabase migration list
    • no edits to an already-applied file
    • destructive changes state their rollback

    The filename carries the date and what it did, so anyone reading the database six months later can find the change that caused what they are looking at without us in the room.

    A migration that has been applied is never edited. A correction is a new file, so the history stays true to what the database actually did.

  5. Live window 24h · edge functions

    stripe-balance
    process-payout-queue
    connect-webhook
    send-reminders
    billing-webhook

     

    Five functions from one production database. Scheduled runs are fixed times; webhook lanes fire when the provider sends an event.

    • Supabase Edge Functions, Deno
    • pg_cron for scheduled runs
    • retry with backoff, then a dead letter
    • provider webhooks: Stripe, Apple, Google
    • failures alert rather than fail quietly

    Most of what keeps a system honest runs when nobody is watching: payouts released, invoices sent, stale records reaped, provider events reconciled against what the database already believes.

    • tnaado.ca/live-map open, no sign-inA scheduled job pulls road, transit, weather and incident feeds every five minutes and writes them into one table; a second job clears records once they go stale. The map only reads that table, so it stays fast however slow the sources are.

    Each of these is a Deno function deployed next to the database and invoked by the scheduler or by the provider, never by a browser.

D.02 · Websites & design

We design the website, not only the software.

Most of what a business needs is not a platform. It is a website — a brochure site for a clinic, a storefront for a shop, a landing page for a campaign, an editorial site for a realtor. We design it as well as build it: layout, type, colour, and how your brand is applied across every page. It is priced by the page and by the integration, like everything else here.

sluekie.com
The Sluekie storefront home page: a silk bedding brand, with a navy hero, the headline “Transform Your Nights Forever” and a product room photograph beside it. The Buuiteks storefront home page, an oral care brand. The Sam Pakdel Realty home page: a black editorial layout with the headline “Toronto Real Estate” and a portrait of the agent. The Deen’s Group home page, a commercial real estate and events brand. The Apex Marketing landing page, a lead-generation page for an advertising agency.
01 Sketch 02 Design 03 Live

Five client sites — pick one

Storefront · Home & textiles

Luxurious silk bedding and textiles engineered for better sleep and elevated beauty.

Storefront · Personal care

Premium oral care solutions for smokers. Professional teeth whitening and long-lasting breath control designed for people who refuse to compromise.

Brochure site and CMS · Real estate

An editorial real-estate brand with a full self-service CMS and a secure client document portal — built so Sam runs everything himself.

Next.js · React · TypeScript · Tailwind CSS · Framer Motion · Supabase · Resend

Brochure site · Commercial real estate

Curated access to exclusive investment opportunities and private experiences for those who value alignment and discretion.

Next.js · React · TypeScript · Tailwind CSS · Framer Motion

Landing page · Marketing

Modern lead-generation landing page for a social media and advertising agency.

Next.js · React · TypeScript · Tailwind CSS · Framer Motion

Worked example

A custom store, priced in the open

  • 6 pages × $325$1,950
  • 2 integrations × $525$1,050
Custom Shopify build, starting at $3,000

The same three units price everything: $325 a page, $525 an API integration, $900 a special feature such as a custom checkout, a booking system or a customer portal. Four build tiers run from Presence — a brochure site or a landing page — through Store and Platform to Application. After launch, hosting is $44.99 a month and full management $349.99.

The full price list →
Phase 01

Sketch

Every page is drawn before a line of code: what sits where, what a visitor sees first, and what a phone gets instead. The structure is settled while it is still cheap to change.

Phase 02

Design

We design it. Typefaces, colour, spacing, and how your logo and brand are applied across every page.

You are not asked to arrive with a Figma file, and you are not handed a template with your name dropped into it.

Phase 03

Build

Hand-built, responsive down to phone size, your content wired in, and each integration connected and tested end to end. It runs on its own preview URL first, so you watch it work before anyone else can.

D.03 · How we build

Yes, we use AI to write code. Here is who is responsible for it.

We use Claude Code and similar tooling on every build in this practice, and it is the reason the timelines on this page are short. We would rather say so than have you find out. What matters is not whether a tool drafted something — it is what has to happen before that draft reaches your production database.

  1. Scoped by a person

    A senior engineer sets the architecture and the boundaries before any tool runs. The tool does not choose how your system is shaped.

  2. Read line by line

    Every generated change is read before it merges. Nothing merges because a model produced it. Auth, payments and schema changes get a second engineer regardless of who wrote them.

  3. Named, and on the phone

    One engineer, by name, answers if it breaks in production after handoff. That does not change because the first draft was machine-written.

What the tool drafts

  • Scaffolding and boilerplate
  • First-pass SQL migrations
  • Test fixtures
  • Routine implementation

Work that used to take most of a day takes minutes. That is where the speed comes from.

What it never does

  • Choose the architecture
  • Approve its own diff
  • Decide what is safe to deploy
  • Touch auth or payments unreviewed

These move at human speed by design, and we do not pretend otherwise.

Some people call this vibe coding. Fair enough — the tool really is doing a lot of the typing. The question worth asking any firm that uses these tools is who reads the output before it ships, and who answers the phone when it breaks.

The staircase at TNAADO’s Toronto office: deep red treads rising between white walls toward a lit glass doorway at the top.
The staircase at TNAADO HQ, King Street West

The path up

From a first call to a system you run.

  1. 01 First call

    What you are building, the constraints, and what shipped looks like.

  2. 02 Scoped

    A senior engineer sets the architecture and the boundaries before any tool runs.

  3. 03 Built in the open

    You are walked through it while it is still being built, on its own preview URL.

  4. 04 Read line by line

    Every change is read before it merges. Auth, payments and schema get a second engineer.

  5. 05 Handed over

    A written runbook, and one named engineer to call if it breaks in production.

This page is what we can build. Who we are and why us — the Toronto office, how the firm is staffed, the portfolio and the origin — is the technology practice page.

The firm →

Client builds on the record, each with its stack and what it does.

Case studies →

D.04 · Let’s talk

Got something to build?

It starts with a quick call. Tell us what you’re building, the constraints and what shipped looks like.

Start a conversation
Listening…