npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2025 – Pkg Stats / Ryan Hefner

@gobuildlabs/saas-starter-kit

v0.1.0

Published

SaaS Starter Kit - Reusable utilities for building SaaS applications (Stripe helpers, Supabase auth, SEO utilities and Database, Utils)

Downloads

38

Readme

SaaS Starter Kit

Reusable utilities and helpers for building SaaS applications with Stripe, Supabase, Next.js, and Prisma.

Overview

This package contains extracted, framework-agnostic utilities from the LaunchKit SaaS boilerplate. It uses dependency injection to eliminate hard-coded configuration imports, making it suitable for distribution as an npm package.

Installation

# As workspace package (current setup)
pnpm add @gobuildlabs/saas-starter-kit@workspace:*

# Future: As published npm package
npm install @gobuildlabs/saas-starter-kit

Modules

🔐 Authentication (Supabase)

Create Supabase clients and authentication helpers.

import { createSupabaseAuth, createAuthHelpers } from '@gobuildlabs/saas-starter-kit/auth';

// Server-side authentication
const supabaseAuth = createSupabaseAuth({
  url: process.env.NEXT_PUBLIC_SUPABASE_URL!,
  anonKey: process.env.NEXT_PUBLIC_SUPABASE_ANON_KEY!,
  serviceRoleKey: process.env.SUPABASE_SERVICE_ROLE_KEY,
});

export async function createServerClient() {
  const cookieStore = await cookies();
  return supabaseAuth.createServerClient(cookieStore);
}

export const supabaseAdmin = supabaseAuth.getAdminClient();

// Auth helpers
const authHelpers = createAuthHelpers({
  defaultRedirect: '/dashboard',
  appUrl: process.env.NEXT_PUBLIC_APP_URL!,
});

const callbackUrl = authHelpers.getValidCallbackUrl('/pricing');
const user = await authHelpers.getUser(supabase);
const isAuth = await authHelpers.isAuthenticated(supabase);

Available Functions:

  • createSupabaseAuth(config) - Create server-side Supabase client factory
  • createSupabaseClientFactory(config) - Create client-side Supabase singleton
  • createAuthHelpers(config) - Create auth helper functions
    • getValidCallbackUrl(url) - Validate callback URLs (prevent open redirects)
    • getUser(supabase) - Get current authenticated user
    • getSession(supabase) - Get current session
    • isAuthenticated(supabase) - Check if user is authenticated

💳 Stripe Integration

Stripe pricing and subscription management utilities.

import { createStripeHelpers } from '@gobuildlabs/saas-starter-kit/stripe';
import { saasConfig } from './config/saas.config';

const stripe = createStripeHelpers(saasConfig);

// Get plan details
const plan = stripe.getPlan('pro');
const paidPlans = stripe.getPaidPlans();
const hasFeature = stripe.hasPlanFeature('pro', 'hdDownloads');

// Trial management
const trialDays = stripe.getTrialDays('pro');
const trialText = stripe.formatTrialPeriod('pro'); // "14-day free trial"
const isInTrial = stripe.isInTrial(subscription);
const daysRemaining = stripe.getTrialDaysRemaining(subscription);

// Customer portal
const portalUrl = await stripe.createCustomerPortalSession(customerId, returnUrl);

// Webhook helpers
const planType = stripe.getPlanTypeByPriceId(priceId);

Available Functions:

  • getPlan(planType) - Get plan details
  • getPaidPlans() - Get all paid plans
  • getAllPlans() - Get all plans including free
  • hasPlanFeature(planType, feature) - Check if plan has feature
  • getPlanLimit(planType, limitKey) - Get feature limit value
  • hasTrial(planType) - Check if plan has trial
  • getTrialDays(planType) - Get trial days
  • formatTrialPeriod(planType) - Format trial for display
  • isInTrial(subscription) - Check if subscription in trial
  • getTrialDaysRemaining(subscription) - Get remaining trial days
  • createCustomerPortalSession(customerId, returnUrl) - Create Stripe portal session
  • getPlanTypeByPriceId(priceId) - Get plan type from price ID (for webhooks)

🔍 SEO & Metadata

Next.js metadata and structured data helpers.

import { createSEOHelpers } from '@gobuildlabs/saas-starter-kit/seo';
import { saasConfig } from './config/saas.config';

const seo = createSEOHelpers(saasConfig);

// Generate page metadata
export const metadata = seo.getSEOTags({
  title: "Pricing",
  description: "Simple, transparent pricing",
  canonicalUrlRelative: "/pricing",
  keywords: ["SaaS", "pricing"],
  twitterCreator: "@yourhandle",
});

// Generate structured data
const orgSchema = seo.getOrganizationSchema();
const websiteSchema = seo.getWebsiteSchema();
const productSchema = seo.getProductSchema({
  name: "Pro Plan",
  description: "Full features",
  price: 19,
  currency: "USD",
});

// Render JSON-LD
const jsonLd = seo.renderStructuredData(orgSchema);

Available Functions:

  • getSEOTags(params) - Generate Next.js metadata
  • getOrganizationSchema() - Generate organization JSON-LD
  • getWebsiteSchema() - Generate website JSON-LD
  • getProductSchema(product) - Generate product JSON-LD
  • renderStructuredData(data) - Convert schema to JSON string

🗄️ Database (Prisma)

Prisma client with singleton pattern.

import { createPrismaClient } from '@gobuildlabs/saas-starter-kit/db';

export const prisma = createPrismaClient({
  log: ['query'], // Optional: enable query logging
});

// Use as normal
const users = await prisma.user.findMany();

🎨 Utilities

General helper functions.

import { cn } from '@gobuildlabs/saas-starter-kit/utils';

// Merge Tailwind classes (uses clsx + tailwind-merge)
<div className={cn('text-red-500', isActive && 'bg-blue-500')} />

Architecture Pattern: Dependency Injection

All utilities use dependency injection instead of hard-coded imports:

Before (tightly coupled):

import { saasConfig } from '@config/saas.config'; // ❌ Hard-coded

export function getPlan(planType) {
  return saasConfig.stripe.plans[planType];
}

After (dependency injection):

export function createStripeHelpers(config: SaasConfig) {
  return {
    getPlan: (planType) => config.stripe.plans[planType],
    // ... other functions
  };
}

This allows the same code to work with any configuration.

Project Structure

packages/saas-starter-kit/
├── src/
│   ├── lib/
│   │   ├── stripe/
│   │   │   ├── config.ts           # Stripe helpers
│   │   │   └── index.ts
│   │   ├── auth/
│   │   │   ├── supabase-server.ts  # Server-side Supabase
│   │   │   ├── supabase-client.ts  # Client-side Supabase
│   │   │   ├── helpers.ts          # Auth utilities
│   │   │   └── index.ts
│   │   ├── seo/
│   │   │   ├── metadata.ts         # SEO & metadata
│   │   │   └── index.ts
│   │   ├── db/
│   │   │   ├── prisma.ts           # Prisma client
│   │   │   └── index.ts
│   │   └── utils/
│   │       ├── classnames.ts       # cn() utility
│   │       └── index.ts
│   ├── types/
│   │   └── index.ts                # TypeScript types
│   └── index.ts                    # Main entry point
├── dist/                           # Compiled JavaScript + declarations
├── package.json
├── tsconfig.json
└── README.md

Development

# Build the package
pnpm build

# Watch mode (rebuild on changes)
pnpm dev

# Type check
pnpm type-check

# Clean build artifacts
pnpm clean

Migration Status

Completed Extractions:

  1. Stripe utilities - lib/stripe-config.tssrc/lib/stripe/config.ts
  2. Auth utilities - lib/supabase.ts, lib/supabase-client.ts, lib/auth-helpers.tssrc/lib/auth/
  3. SEO utilities - lib/seo.tssrc/lib/seo/metadata.ts
  4. Database utilities - lib/prisma.tssrc/lib/db/prisma.ts
  5. General utilities - lib/utils.tssrc/lib/utils/classnames.ts

🚧 Future Enhancements:

  • API route templates (webhooks, checkout)
  • Reusable React components (PricingCard, AuthForm, etc.)
  • CLI scaffolding tool (npx @gobuildlabs/saas-init)
  • Email templates
  • Analytics helpers
  • Feature flag system

Backward Compatibility

All web app files maintain backward compatibility through wrapper pattern:

// apps/web/lib/stripe-config.ts
import { createStripeHelpers } from '@gobuildlabs/saas-starter-kit/stripe';
import { saasConfig } from '@config/saas.config';

const stripeHelpers = createStripeHelpers(saasConfig);

// Re-export for backward compatibility - existing code keeps working!
export const {
  getPlan,
  getPaidPlans,
  // ... all functions
} = stripeHelpers;

Package Exports

The package provides modular exports for tree-shaking:

// Main entry
import { createStripeHelpers, createSEOHelpers } from '@gobuildlabs/saas-starter-kit';

// Subpath exports
import { createStripeHelpers } from '@gobuildlabs/saas-starter-kit/stripe';
import { createSupabaseAuth } from '@gobuildlabs/saas-starter-kit/auth';
import { createSEOHelpers } from '@gobuildlabs/saas-starter-kit/seo';
import { createPrismaClient } from '@gobuildlabs/saas-starter-kit/db';
import { cn } from '@gobuildlabs/saas-starter-kit/utils';

// Types
import type { SaasConfig, PricingPlan } from '@gobuildlabs/saas-starter-kit/types';

Type Safety

Full TypeScript support with generated declaration files:

import type {
  SaasConfig,
  PricingPlan,
  PricingPlans,
  StripeHelpers,
  SEOHelpers,
  AuthHelpers,
  SupabaseAuthHelpers,
  SupabaseClientFactory,
} from '@gobuildlabs/saas-starter-kit';

Peer Dependencies

The package lists framework dependencies as optional peers:

  • @prisma/client (optional) - Only needed if using DB utilities
  • @supabase/ssr (optional) - Only needed if using auth utilities
  • @supabase/supabase-js (optional) - Only needed if using auth utilities
  • clsx (optional) - Only needed if using cn() utility
  • tailwind-merge (optional) - Only needed if using cn() utility
  • next (optional) - Only needed if using SEO utilities

This allows consumers to only install what they need.

License

MIT

Next Steps

After completing Phase 1 (extraction), the roadmap includes:

Phase 2: CLI Tool - Create npx @gobuildlabs/saas-init command Phase 3: Template Repository - Minimal starter template Phase 4: Component Library - Extract React components Phase 5: API Route Templates - Parameterized API routes Phase 6: Publishing - Publish to npm registry

Contributing

This package is currently part of a monorepo. To add new utilities:

  1. Create new module in src/lib/[module-name]/
  2. Use dependency injection pattern (accept config as parameter)
  3. Add barrel export in module's index.ts
  4. Export from main src/index.ts
  5. Add subpath export in package.json
  6. Build and test: pnpm build && pnpm type-check
  7. Create wrapper in apps/web/lib/ for backward compatibility

Support

For issues and questions, please open an issue on GitHub.