AI 资讯
Cross-Cultural UX: Designing SaaS Interfaces for Global Users
A SaaS interface that works well for US users may confuse or alienate users in China, Germany, or Japan. Cultural differences affect everything from layout preferences to color meanings, form field expectations, and payment preferences. This guide covers the cross-cultural UX principles applied at tanstackship.com , a SaaS serving users across English, German, and Chinese markets. Cultural Dimensions and UI Impact Hofstede's Dimensions Applied to SaaS Design Dimension High vs Low UI Impact Power Distance Acceptance of hierarchy Navigation depth, permission displays Individualism vs Collectivism Personal vs group focus Social proof, testimonials Uncertainty Avoidance Tolerance for ambiguity Error messages, help text density Long-term Orientation Pragmatic vs normative Pricing display, trial periods By Market UX Element US (Low PD, High IND) DE (Low PD, High UA) CN (High PD, High COL) Navigation Flat, exploratory Structured, organized Hierarchical, guided Error handling Forgiving, "try again" Specific, detailed Authority-mediated Social proof Individual testimonials Expert reviews + data Group endorsement Pricing Monthly preferred Annual preference (trust) Discount attraction Help/Support Self-service docs Detailed documentation Chat + personal support Color meanings Green=success Green=environment Red=prosperity Color and Visual Design Color Meanings Across Cultures Color Western (US/EU) China Germany Japan Red Danger, passion Prosperity, luck Financial (deficit) Life, energy Blue Trust, technology Trust, immortality Trust, stability Trust, calm Green Success, nature Health, harmony Environment Youth, energy White Purity, clean Mourning Clean, efficiency Purity Yellow Warning, caution Imperial, power Jealousy Courage Practical Application // Adapt color scheme based on locale const colorSchemes = { en : { primary : " #2563EB " , // Blue — trust success : " #16A34A " , // Green — success danger : " #DC2626 " , // Red — danger warning : " #F59E0B " , // Yellow — warnin
AI 资讯
I shipped a support desk by deleting a dependency
I added a support desk to LaraFoundry this week. The first commit in the slice removed a package instead of adding one. LaraFoundry is a reusable SaaS core for Laravel that I'm extracting in public from an older app of mine. Auth, multi-tenancy, roles, activity log, notifications, billing seam, and now support tickets. The rule for every module is the same: lift the proven idea out of the old code, modernise it, harden it, and make it something you can composer require into a fresh Laravel app without inheriting a pile of assumptions. Tickets is where that rule got interesting, because the old code didn't own its ticket model. It leaned on a third-party ticket library. Why a ticket package is wrong for a reusable core A third-party ticket package is a perfectly reasonable choice when you're building one app. You get tables, a model, a status enum and a UI scaffold for free. It's the wrong choice for a core that other apps install. Pull it into the core and every host app inherits that package's migrations, its table names, its status vocabulary and its idea of what a ticket is. The dependency becomes load-bearing in projects that never asked for it, and the day it lags a Laravel release, every downstream app waits. So I cut it (decision D-4.2-1 in my notes) and wrote the model by hand. The model is about 180 lines. There is no magic. Two tables, a uuid, a status, a couple of scopes. The diff against "depend on the package" was less code in the core, not more, because I only kept the behaviour I actually use. Here's the top of the model, with the extraction notes I leave for future me: /** * A support ticket: the channel between a host user and the platform operator. * * Extracted from the donor App\Models\Ticket, which sat on a third-party * ticket package. That dependency is cut: this is a self-contained model. * Categories and labels are JSON slug arrays driven by config, not pivot * tables. The dead assigned_to column and the donor's invalid-operator * query are
AI 资讯
How I Built a Free SEO Audit Tool with Next.js, Supabase, and Stripe in 1 Week
Last weekend I started building SiteGrade — a free instant SEO audit tool that gives any website an A–F letter grade and the top fixes ranked by impact. I just launched it. This post is the build log: the architecture decisions that worked, the ones that didn't, and the gotchas you'd save time knowing about. If you're considering building a similar audit/scanner tool, or just want to see what a 2026 Next.js + Supabase + Stripe stack looks like in practice, this should be useful. Why I built it I got tired of family and friends asking me "how's the SEO on my website?" and not having a good answer to send back. Every existing tool I tried either cost $99+/month (Ahrefs, Semrush) or threw 200 metrics at people who just wanted to know if their site was OK. The wedge I built around: one letter grade, three top fixes, plain English, no signup. The paid tier ($29/mo) re-audits weekly and emails the report so non-technical users can track improvements as their developer makes them. The stack Nothing exotic. Everything is the obvious choice for a 2026 indie SaaS, which is the whole point — boring stack means I spent zero time fighting infrastructure and 100% of my time on the actual audit logic. Next.js 14 App Router — frontend + API routes in one repo Supabase — Postgres + auth + RLS + file storage, EU-hosted for GDPR Stripe — subscriptions + Billing Portal + webhooks Resend — transactional email (audit reports, weekly reports, Supabase auth via Custom SMTP) Vercel — hosting + cron jobs for the weekly re-audit cheerio — HTML parsing for the audit checks Google PageSpeed Insights API — Core Web Vitals + mobile performance Total monthly infrastructure cost at zero traffic: ~$0 (everyone on free tiers). At 100 paying customers it'd still be under $30/mo. The audit logic — what 15 checks look like in code Each audit runs 15 checks and produces a score from 0-100, then maps that to a letter grade (A: 90+, B: 75+, C: 60+, D: 45+, F: below 45). The checks are structured as pure fu
AI 资讯
The Letter VCs Are Quietly Deleting from ARR
The Letter VCs Are Quietly Deleting from ARR Startups are reporting revenue they haven't earned yet. VCs know it. Investors are cheering anyway. We've seen this movie. You're evaluating an AI startup. The pitch deck shows $100 million in ARR. The growth curve is parabolic. The deck says they signed $100 million. What it doesn't say is that $70 million of that is "committed ARR": contracts signed but not yet invoiced, customers who haven't deployed yet, pilots that count toward the number if they convert. Subtract the gap and you've got $30 million in actual recognized revenue hiding under a $100 million headline. This is the ARR inflation playbook, and it's running at full speed right now. The Trick Has a Name "CARR" stands for Contracted or Committed ARR. It's a legitimate concept. In industries where revenue accrues slowly after contract signing (healthcare AI deployments, energy optimization platforms, multi-year enterprise integrations), the gap between signature and recognition can legitimately take months or years to close. Reporting CARR alongside ARR, properly labeled, is defensible. That's not what's happening. What's happening is simpler: founders strip the "C" and just call it ARR. One VC told TechCrunch the gap between CARR and actual ARR can run as high as 70% [1]. In some confirmed cases the spread is 3-5x. Another investor said flatly: "For sure they are reporting CARR as ARR" [1]. The article indicates that the investor community is not only aware, but many are actively complicit. The logic follows its own warped rationality. When one startup in a category inflates, the others have to follow to stay competitive for talent and headlines. "When one startup does it in a category, it is hard not to do it yourself just to keep up," as one investor put it [1]. Spellbook CEO Scott Stevenson, one of the few willing to call this in public, described the practice as a "huge scam," adding that major VC funds are not just watching it happen but actively supporti
AI 资讯
I Built MCP Servers for 9 SaaS APIs — Here's What I Learned About the Pattern
I Built MCP Servers for 9 SaaS APIs — Here's What I Learned About the Pattern I've spent the last few weeks building MCP (Model Context Protocol) servers for various APIs — CoinGecko, Stripe, Jira, PostHog, Plausible, Etherscan, DeFiLlama, Jobber, and Resend. Nine servers, 68 tools, all published to npm and indexed on Glama. Along the way, I noticed the same architecture keeps working. If you're building an MCP server for your own API — or thinking about hiring someone to do it — here's the pattern. The Three-Layer Architecture Every MCP server I build has three layers: 1. Tool Definitions (the contract) Each API endpoint becomes an MCP tool with a typed input schema. I use Zod for validation — it catches bad inputs before they hit your API. { name : " send_email " , description : " Send a single email via Resend " , inputSchema : { from : z . string (). email (), to : z . union ([ z . string (). email (), z . array ( z . string (). email ())]), subject : z . string (). min ( 1 ), html : z . string (). optional (), text : z . string (). optional (), }, } The description matters more than you think. LLMs read these descriptions to decide which tool to call. A vague description like "send email" wastes tokens. A specific one like "Send a single transactional email via Resend API. Supports HTML and plain text. Returns message ID and delivery status." gets used correctly. 2. API Client (the plumbing) This layer handles auth, rate limiting, and error transformation. The key insight: don't leak HTTP errors to the LLM. Transform them into structured, actionable messages. // Bad: "Error: 429" // Good: "Rate limited by Resend API. Retry after 30 seconds. You've sent 100 emails in the last hour." 3. Output Formatter (the presentation) Raw JSON dumps are terrible for LLM consumption. Format responses as markdown tables, bullet points, or structured text. The LLM reads this output to decide what to do next — make it scannable. ## Email Sent Successfully - **Message ID:** abc123
AI 资讯
I turn a spreadsheet into hundreds of static SEO pages — so I built PageForge (free beta)
I run a couple of small niche sites — a pet-health tool and a travel-info site. The thing that actually moves the needle for both isn't clever copywriting. It's having a lot of pages that each answer one specific, low-competition question. "Puppy vaccine schedule by breed." "Is [neighborhood] worth visiting." That kind of thing. This approach has a name: programmatic SEO . You take a data set (one row = one page), pour it into a template, and generate pages at scale. Done well, it's how directories, comparison sites, and tool sites quietly rank for thousands of long-tail terms. Done badly, it's a spam farm that Google buries. More on that later, because it matters. The problem: the tooling is either expensive or a Rube Goldberg machine When I went looking for a way to do this without hand-coding every page, I found two camps: Agency-grade SaaS — powerful, but priced at $99–$299/month . That's a lot of money to spit out HTML when you're a solo operator running sites that make beer money. No-code stacks — wire a spreadsheet to a CMS to a static-site generator with a couple of automation tools in between. It works, but now you maintain a fragile chain of four services, and your pages live inside someone else's platform. Neither felt right. I just wanted: spreadsheet in, clean HTML out, files I own. What I actually built (for myself, first) So I wrote a generator for my own sites. Every morning it reads a CSV, applies a template, and produces a folder of static HTML pages — each with valid JSON-LD, proper meta tags, an internal-link hub, and a sitemap. I deploy the folder. Done. After running it daily for months on my own properties, I cleaned it up and turned it into a product: PageForge . The core idea is deliberately boring: CSV + template → a ZIP of clean static HTML pages you own. No dashboard you have to log into forever. No lock-in. The output is just files. If you stop using PageForge tomorrow, your pages keep working because they're plain HTML sitting in your r
AI 资讯
5 micro-SaaS ideas devs are asking for on Reddit
I have a side habit. When I run out of ideas for what to build next, I do not open Twitter or Product Hunt. I open Reddit. There are about thirty subs where the same complaint comes up every week. Someone describes a workflow they hate, asks if a tool exists, and a commenter says "I wish, please tell me if you find one." That second comment is the cofounder you do not need to pay. Here are 5 I pulled from threads in the last few months. Each one has a real Reddit post behind it, real search volume on the keyword someone would type into Google, and a wedge small enough to build over a weekend. None of these are billion-dollar ideas. All of them could be a $2k MRR side project if you actually shipped. 1. Invoice reminders for trade contractors "i know the title sounds made up. invoice reminders for plumbers. $14K a month. but that's exactly why it works. nobody is competing for this." r/passive_income, 3,653 upvotes Search demand: 7,200 monthly searches for "invoice reminder software" and adjacent terms. Why it works: plumbers, electricians, and HVAC techs send invoices and then forget about them. Their customers also forget. Nobody wants to be the awkward one chasing money. A scheduled email or SMS sequence converts ghosted invoices into paid ones. The buyer is one tradesperson, the value is measured in actual dollars recovered, and the competition is QuickBooks (terrible at this) or nothing. Wedge: a single Stripe-or-QBO connector that sends a polite nudge at day 7, a firmer one at day 14, and a "final notice" template at day 30. Charge $19 a month. 2. Field service software for solo tradespeople "Is there field service management software that doesn't assume you have a team? I run residential HVAC solo, sometimes one helper when it gets busy. Everything I've tried is built for dispatching crews." r/EntrepreneurRideAlong Search demand: 8,800 monthly searches for "field service management software" with solo and small-business modifiers. Why it works: Jobber, Houseca
AI 资讯
10 prompt patterns I use every single day
10 Prompt Patterns I Use Every Single Day Last Tuesday I spent 40 minutes arguing with Claude about a database schema before I realized I had never told it what I already tried. I described the problem, it gave me the same three suggestions I had already ruled out, I pushed back, it apologized and gave me variations of the same three suggestions. The entire session was garbage because I started from zero instead of from where I actually was. I closed the tab, rewrote my first message, and had a working solution in six minutes. That gap — between how most people prompt and how it actually works when you treat the model like a collaborator who needs real context — is what this post is about. Pattern 1 & 2: Lead With What You Already Tried, and State the Constraint That Binds You These two patterns are almost always used together, so I won't pretend they're separate. When you describe a problem without the history of your attempts, you are forcing the model to rediscover your dead ends. Every developer knows this frustration: you explain a bug, get back a solution you tried on Monday, explain you tried that, get a variation, explain that too — it's a recursive waste. The fix is brutal honesty upfront: "I need X. I already tried A and B. A failed because [specific reason]. B is off the table because [constraint]. Don't suggest either." The constraint layer is the other half. Models are optimists by default. They will give you the architecturally clean, perfectly testable solution that requires three new dependencies and a refactor of your auth layer. Unless you tell them you are shipping in two days, can't add dependencies, and the code needs to be readable by someone who last touched Python in 2019. Constraints aren't limitations on the answer — they are the answer. Front-load them or you will spend the session rejecting suggestions that are technically correct but situationally useless. Pattern 3 & 4: Output First, Reasoning After — and Diff Only, Not Rewrites Two sid
AI 资讯
How We Built Cryptographic Invoice Signatures for a SaaS Invoicing Platform
How Reinvoice Uses HMAC Signatures to Detect Invoice Tampering Every invoice sent through Reinvoice includes a cryptographic integrity signature. It is not a PDF stamp, a visual badge, or a checkbox. It is an HMAC-SHA256 hash generated from the invoice payload and a server-side signing secret. If signed invoice data changes after creation, Reinvoice can recompute the hash, compare it to the stored signature, and flag the invoice as potentially tampered with. Here is why we built it, how it works, and what we learned. Why Integrity Checks Matter for Invoicing Invoices are high-value documents. A single altered field could change a payment amount, tax calculation, client record, or audit trail. Most invoicing systems treat invoices as ordinary database records. That works for normal CRUD workflows, but it does not automatically prove that the invoice data being viewed today is the same data that was created and sent. Reinvoice adds an integrity layer. When an invoice is created, we sign the fields that define the invoice. Later, when someone verifies the invoice, we recompute the signature from the current data and compare it against the original stored signature. If the values do not match, the invoice is flagged. The Implementation The signature is stored in two places: on the invoice record in the database, and behind a public verification endpoint. import { createHmac , timingSafeEqual } from ' node:crypto ' ; const SIGNATURE_FIELDS = [ ' invoiceNumber ' , ' issuerName ' , ' clientName ' , ' totalAmount ' , ' currency ' , ' taxAmount ' , ' issuedAt ' , ' dueDate ' , ' lineItems ' , ' notes ' , ' subtotal ' , ' discountAmount ' , ' shippingAmount ' , ] as const ; export function generateInvoiceHash ( invoice : InvoiceData ): string { const payload = SIGNATURE_FIELDS . map (( field ) => { const value = invoice [ field as keyof InvoiceData ]; return ` ${ field } = ${ JSON . stringify ( value )} ` ; }). join ( ' | ' ); return createHmac ( ' sha256 ' , SIGNING_SECRET )
AI 资讯
How to build a credit system for a Next.js AI app (Stripe + Supabase)
If you're building an AI app (image generation, transcription, an agent, anything that calls a model) you've probably realized a flat "$10/month" doesn't work. Every action costs you real money in GPU/API spend, so a single power user can torch your margins. The answer is usage credits : users buy a balance, each action spends some. Credits sound trivial. They are not. I've shipped about 10 small AI/SaaS apps, and the credit layer is where I got burned every single time. It took three patterns to fix it for good. Here they are, with copy-pasteable code for Next.js + Supabase + Stripe. Get these right and your billing won't oversell, double-charge, or strand a user's money. The three things everyone gets wrong Overdrawing. Two requests arrive at once, both read "balance = 1," both spend. Now the balance is negative and you gave away work for free. Double-granting. Stripe retries webhooks (it will ), and if you grant credits on every delivery, a $9 purchase becomes $18 of credits. Forgetting the refund. The AI job fails after you've already charged the credits. The user paid for nothing and emails you angry. Let's kill all three. Part 1. The atomic spend (overdraw becomes impossible) The mistake is doing the check in your app code: // DON'T: read-then-write has a race condition const { balance } = await getBalance ( userId ); if ( balance < cost ) throw new Error ( " insufficient " ); await setBalance ( userId , balance - cost ); // two concurrent requests both pass the check Do it in the database, in one statement, with the guard in the WHERE clause: -- balances: one row per user create table credit_balances ( user_id uuid primary key references auth . users ( id ) on delete cascade , balance integer not null default 0 check ( balance >= 0 ), updated_at timestamptz not null default now () ); -- append-only ledger = audit log + idempotency guard (see Part 2) create table credit_ledger ( id bigint generated always as identity primary key , user_id uuid not null referen
AI 资讯
Building a SaaS engine in public: shipping the billing seam, not billing
I tagged v0.9.0 of LaraFoundry this week: billing. Except the honest headline is that I shipped the billing seam , not billing. The free core now has the whole shape of a subscription system, a payment-gateway contract, a driver manager, a real access gate over subscription columns, and it cannot take a single cent. That is on purpose, and the reason is the most interesting part of the phase. LaraFoundry is a SaaS core I'm extracting in public from a live CRM, one module at a time. The deal I made with myself early on: the core is free and stays free for everything except money. Auth, multi-tenancy, RBAC, the admin console, the activity log, i18n, files: all free. The day a business wants to charge its customers , that is the paid part. So billing could not just be "another module." It had to split cleanly down a line, with the free side carrying real, useful structure and the paid side carrying the parts that actually move money. The donor habit I would not carry Here is what the original CRM did when a company "paid" for its subscription: // TODO: real payment gateway integration // TEMPORARY: every payment is successful, for testing $paymentStatus = 'success' ; That success was hardcoded. There was no Stripe, no Paddle, no gateway at all. "Paying" wrote a row into a company_payments table and flipped the subscription date forward. For a CRM I run myself, with one real user, that was fine: I never needed the real thing, so the placeholder sat there indefinitely. The moment this becomes a reusable core, that placeholder is poison. A success that is always true is worse than no gateway, because it looks like billing works. So the rule for this phase was simple: the fake gateway does not get extracted. Whatever stands in its place has to be honest about the fact that it takes no money. What the seam actually is The free core ships a PaymentGatewayInterface : subscribe, cancel, refund, status, and verify a webhook. It describes only the mechanics of moving money. It d
开发者
Database Indexing Mistakes That Kill SaaS Performance at Scale
Your API is fast. Your code is clean. Your architecture looks solid on paper. Then you hit 500,000 records and everything slows down. Queries that ran in 12ms now take 4 seconds. Your dashboards lag. Users start filing support tickets. Your on-call engineer is staring at a query plan at midnight wondering what went wrong. Nine times out of ten, the answer is indexing. Not missing indexes — wrong indexes. Indexes that exist but don't help. Indexes that actively hurt write performance without meaningfully improving reads. This is a breakdown of the most damaging database indexing mistakes in production SaaS systems — and how to fix them before they become incidents. Mistake 1: Indexing Everything "Just in Case" The most common mistake isn't under-indexing. It's over-indexing out of anxiety. New engineers especially fall into this pattern — add an index on every column that appears in a WHERE clause, just to be safe. Seems responsible. It isn't. Every index you add is a write tax. On every INSERT, UPDATE, and DELETE, PostgreSQL (or MySQL) has to update every index on that table. On a table with 8 indexes, every write touches 8 data structures. At low volume, this is invisible. At 10,000 writes per minute, it becomes your bottleneck. The fix: Audit your indexes regularly. In PostgreSQL: SELECT schemaname , tablename , indexname , idx_scan , idx_tup_read , idx_tup_fetch FROM pg_stat_user_indexes ORDER BY idx_scan ASC ; Any index with idx_scan = 0 or near zero hasn't been used since your last stats reset. That's a candidate for removal — not immediately, but after investigation. Mistake 2: Not Understanding Index Selectivity An index on a boolean column ( is_active , is_deleted ) is almost always useless. Here's why: selectivity measures how many distinct values exist relative to total rows. A boolean column has two values. If 95% of your rows have is_active = true , an index on that column tells the query planner almost nothing useful. It will often skip the index entire
AI 资讯
Why Your SaaS Integration Layer Needs AI (And What 'AI-Native' Actually Means)
Integrations kill product velocity. Every SaaS team knows this. You ship a killer feature, customers love it, then they ask: "Can it sync with Salesforce? What about HubSpot? Zendesk?" Suddenly your roadmap is hostage to building connector after connector. Each one takes 2-3 weeks. Your engineers hate it. Your customers wait. Competitors who solve this faster win deals. The standard response has been iPaaS platforms. They help, but they don't fundamentally change the game. You still need engineers to map fields, handle edge cases, and maintain brittle connections. The real breakthrough isn't just automation , it's making integrations LLM-native from the ground up . What Actually Makes an Integration Layer "AI-Native"? Let's cut through the marketing speak. Every B2B tool now claims to be "AI-powered." Most just added a ChatGPT wrapper to their UI. Real AI-native architecture means three things: 1. LLM-Ready Connectivity via MCP Servers Model Context Protocol (MCP) is Anthropic's standard for connecting LLMs to external data sources. If your integration layer doesn't support MCP servers natively, your AI features will always be bolted on, not built in. MCP servers expose your SaaS data to language models in a structured way. Instead of engineers writing custom API wrappers for every LLM interaction, you get a standardized interface. Claude, GPT-4, and future models can query your integration layer directly. Example: A customer support tool with native MCP integration lets an AI agent pull ticket history from Zendesk, check Stripe subscription status, and update Salesforce records in one conversation flow. No custom code. No brittle middleware. 2. AI-Mapped Data Migration Data migration is where most SaaS deals die. Customer says "we'll switch from ServiceNow to your ITSM if you migrate our 50,000 tickets." Your team estimates 6 weeks. Deal stalls. Traditional migration means: Manual field mapping spreadsheets Custom scripts for data transformation Downtime windows Hi
AI 资讯
I built a detention-pay calculator for truckers in a day — unglamourous niches beat another AI wrapper
Every "what should I build" thread on here is full of AI wrappers fighting over the same five SaaS founders. Meanwhile there's a guy sitting at a loading dock right now, doing arithmetic in his head, who is about to undercharge his broker by a few hundred bucks because nobody built him a 30-second tool. I built that tool. It's a free detention-pay calculator for truck drivers. This is the build log — the niche-selection, the single-file stack, and two decisions (an SVG gauge and a no-mail-service auth scheme) that were more interesting than the app deserves. I'm not a trucker. I build small free web tools for industries other may find unglamourous or not enticing enough. That honesty matters later. The problem (worth $2–6k/yr to one user) Truckers get a "free time" window at a dock — usually 2 hours. Past that, the broker owes detention pay (~$50–100/hr). Drivers leave an estimated $2,000–6,000/year of it unclaimed, mostly because the math + the paperwork is annoying enough to skip. So the spec wrote itself: In/out times + free hours + rate → dollars owed. Export a dispute-ready PDF they can email the broker. Work on a phone, no login, instant. Validating before writing a line The mistake I almost made: assume the niche is empty because I'd never heard of it. I checked. It is not empty — DockClaim ($49/mo, GPS tracking), Detention Buddy, a couple of $9.99/mo App Store apps, even a free email-gated web calculator or two. That killed my first instinct ("be the only one") but clarified the real wedge: everything is a paid app download or email-gated. The opening was a genuinely free, no-signup, instant web version that also generates the claim PDF. Not "the only detention tool" — the one with the least friction. I'll say more on why I'm careful about that claim at the end. Lesson: validate to find your angle , not just a go/no-go. "Crowded but all friction-heavy" is a fine market. The stack: one HTML file No framework. The whole app is a single self-contained .html — m
AI 资讯
Why my single Next.js app runs 4 different domains (and how the proxy.ts decides who sees what)
> TL;DR — I run four different domains off one Next.js codebase: a marketing site at pagestrike.com , an authenticated app at app.pagestrike.com, a public publishing domain at pagestrike.app, and customer-owned domains. The trick isn't deploying four apps — it's a single proxy.ts that reads the host and rewrites/redirects/passes-through per-request. This post walks through why I chose this shape, the parts I got wrong, and the cookie-domain trick that makes it all stick. Stack: Next.js 16 App Router , Supabase , Vercel , one proxy.ts file (~370 lines). This is the second post in my build-in-public series on PageStrike . Last week I wrote about the 6-CTA architecture — modeling conversion intent as a discriminated union so one launch could be a checkout, a COD form, or a calendar booking. This post is about a different primitive: modeling host as routing context so one codebase can serve four very different audiences. Why four domains, not one Most SaaS apps live at one domain — say myapp.com with /dashboard under it. That works until you grow into edge cases that don't fit: Marketing pages get spammed by your own dashboard headers. Your marketing nav says "Sign in / Pricing / Blog". Your dashboard nav says "Launches / Contacts / Settings". You either A/B them with conditional logic everywhere or you live with the noise. Public user-generated pages share your domain reputation. When a customer publishes a landing page at myapp.com/p/[slug] , every spammy LP from a free-tier user drags down myapp.com 's sender reputation, search trust, and ad-account standing. Google and Meta penalize the host, not the path. Custom domains don't route cleanly. A customer who buys acmewidgets.com and points it at your app expects their LP at acmewidgets.com/ — not myapp.com/p/acme-widgets . You need a rewrite that's transparent to the visitor, doesn't 404 on _next/static/* , and survives RSC prefetches. I split PageStrike — a free AI landing page builder — across four hosts to solve al
AI 资讯
AI Coding Tools Compared: Copilot vs Cursor vs Claude Code vs Gemini CLI
AI coding tools are no longer just autocomplete. In 2026, they are becoming coding assistants, terminal agents, code reviewers, and sometimes full workflow helpers. But the real question is: Which AI coding tool should developers actually use? Here is a short, practical comparison. Quick comparison Tool Best for Main strength Watch out for GitHub Copilot Daily coding inside IDE Fast autocomplete and GitHub workflow support Can feel limited for deep architecture work Cursor Full AI-first coding experience Great for editing across files and working inside a project You may rely on it too much without reviewing code Claude Code Terminal-based agentic coding Strong reasoning, repo understanding, and command execution Needs careful review before running changes Gemini CLI Open-source terminal AI agent Good for terminal workflows, debugging, and automation Output quality depends heavily on task clarity 1. GitHub Copilot GitHub Copilot is the safest default choice for most developers. It works well inside common IDEs and is useful for: Autocomplete Small functions Unit tests Refactoring Explaining code GitHub-based workflows GitHub also has Copilot coding agent support, which can work on assigned tasks, make code changes, and open pull requests from GitHub workflows. :contentReference[oaicite:0]{index=0} Use Copilot if: You want AI help without changing your full coding workflow. Best for: Junior to senior developers Teams already using GitHub Everyday coding productivity 2. Cursor Cursor is best when you want an AI-first editor experience. Instead of only helping with one line or one function, Cursor is useful when you want to ask questions about your whole project and make multi-file changes. Use Cursor if: You want your editor to feel like an AI coding workspace. Best for: Building features quickly Editing multiple files Understanding unfamiliar codebases Indie hackers and startup builders My honest take: Cursor is very productive, but developers should avoid blindly ac
AI 资讯
I Built a Side Project Selling Pine Script Strategies for Prop Traders
Started propfirmpinescripts.com a while back selling pine script strategies for futures prop firm traders. Figured I would share some of what worked and what has not. The problem I was solving I was actually trading on Apex myself and kept running into the same thing. Every pine script strategy I found online was not built for prop firm rules. Daily loss limits not enforced in code. No end of day flatten. Blew an evaluation partly because of it. Figured other traders had the same problem. Coded the rules myself, then decided to sell the scripts. What I built Pre-built pine scripts for 4 instruments: GC (gold futures), MES (micro S&P), MNQ (micro Nasdaq), CL (crude oil). Each one has daily loss lock, EOD flatten, win lock coded in. You can configure the limits for different firms without touching the core logic. Priced at $50 for a single script or $150 for all 4. What actually moved conversions Adding real payout screenshots. Like actual Apex payout certificates from traders who passed using the strategies. Before I did that — traffic but weak conversions. After — noticeably better. Prop firm traders do not trust backtest results at all anymore. Too many people have gamed them. A real funded account payout is the only thing that actually means something to them. Where things are at Still early. Revenue is real but small. Building more SEO content, getting into prop firm communities, and eventually a subscription tier for updates when firms change their rules. If you are a dev with trading knowledge this space is underbuilt.
AI 资讯
How I Protected My Inbox from Spam Bots While Building Landing Pages
As developers, indie hackers, and solo founders, we launch numerous static sites, minimal landing pages, and open-source project documentation blocks. Every single one of these deployments shares a universal prerequisite: a reliable path to gather raw incoming user feedback, inbound sales leads, or bug reports. The traditional path of least resistance has long been to embed a hardcoded HTML <form> inside our page, or worse, expose a standard mailto: link. However, we all know what happens next. Within hours of your app hitting public hosting servers or GitHub, automated asynchronous spam bots find your raw source code, harvest your personal email address, and turn your inbox into a living nightmare. I used to spend hours configuring captchas, writing honey-pot filters, or spinning up custom Serverless Lambda routines just to secure a simple contact form. Eventually, I realized I was fighting the wrong battle. The best way to protect your inbox isn't to build a better shield around your frontend form; it's to remove the form from your code entirely. That is why I built FormCrab.com . 🦀 The Problem: Why Client-Side Forms are a Risk When you embed a custom form or mailto link into your landing page, you are effectively publishing your communication architecture to the world. Spam bots don't even need to render your page anymore; they use basic regex scrapers to crawl through millions of raw static HTML repositories looking for keywords like type="email" or action="..." . Once your endpoint or raw email identity is captured, it is added to bulk programmatic marketing lists. The Trade-Off We All Hate: Option A: Spin Up a Custom Backend. Configuring an Express or Spring Boot API routing layer solely to act as an authenticated SMTP relay. This adds infrastructural complexity and database burdens to what should be a 15-minute frontend project. Option B: Use Form Backends. Even if you use a standard form endpoint handler, you still have to code the frontend UI, handle valida
AI 资讯
Best AI Tools for Conversion Rate Optimization in 2026: Stop Running A/B Tests, Start Building a Conversion System
The best AI tools for conversion rate optimization (CRO) in 2026 are the platforms that continuously...
开发者
How Smart Growth Teams Automate Their Marketing Stack in 2026 (Without Hiring More People)
Your growth targets went up. Your team size didn’t. Maybe it even went down. Meanwhile, the...