✨ Become an Affiliate (50%)!

Envin - type-safe environment variable validation tool with live previews

·10 min read

Say goodbye to runtime environment variable errors. Envin provides framework-agnostic, type-safe validation with real-time previews and an interactive CLI that works with Next.js, Vite, Astro, and any JavaScript framework.

Environment variables are the silent killers of JavaScript applications. One missing DATABASE_URL, an incorrect API_ENDPOINT, or a mistyped boolean value can bring your entire production deployment to its knees. We've all been there - spending hours debugging why your app works locally but fails in production, only to discover a single environment variable wasn't properly configured.

That's why we're excited to introduce Envin - our new open-source library that brings type-safe environment variable validation to any JavaScript framework. Whether you're building with Next.js, React Native, browser extensions, or any other framework, Envin ensures your environment variables are validated, typed, and accessible with full TypeScript support.

Envin invalid access error

What is Envin?

Envin is a framework-agnostic, type-safe tool designed to validate and preview your environment variables using your favorite schema validator. Built with developers in mind, it provides:

  • Type-safe validation - Define your schema once and get full TypeScript support
  • Framework-agnostic design - Works with Next.js, Vite, Astro, React Native, and any JavaScript framework
  • Client/server separation - Strict protection of server-side variables from client access
  • Interactive CLI - Real-time previews and validation during development
  • Extensible presets - Pre-configured setups for popular platforms
  • Standard Schema support - Works with Zod, Yup, Joi, and other popular validators

Being open-source means complete transparency and community-driven development - you can inspect the code, contribute features, and ensure your project's foundation is secure from day one.

Why environment variable validation matters for startups?

In the fast-paced startup environment, configuration errors can be costly. Consider these common scenarios:

  • Production deployments fail because a required environment variable is missing
  • API integrations break due to incorrect endpoint URLs
  • Security vulnerabilities emerge from exposed sensitive variables
  • Team onboarding takes longer because environment setup is complex
  • Cross-environment bugs waste precious development time

Envin addresses these challenges by providing a robust, type-safe foundation for environment variable management that scales with your startup's growth.

Environment variables should be boring. When they're properly validated and typed, you can focus on building features instead of debugging configuration issues.

Getting started with Envin

Getting started with Envin is incredibly straightforward, making it accessible for projects of any size.

Installation

Install the core package alongside your preferred schema validator:

# Using npm
npm install envin zod

# Using yarn
yarn add envin zod

# Using pnpm
pnpm add envin zod

💡 Pro tip: Envin supports any Standard Schema validator, so you can use Zod, Yup, Joi, or any other validator you prefer!

Basic configuration

Create an env.config.ts file in your project root:

import { defineEnv } from "envin";
import { z } from "zod";

const env = defineEnv({
  shared: {
    NODE_ENV: z.enum(["development", "production"]),
  },
  server: {
    DATABASE_URL: z.string().url(),
    JWT_SECRET: z.string().min(32),
  },
  client: {
    NEXT_PUBLIC_API_URL: z.string().url(),
    NEXT_PUBLIC_APP_URL: z.string().url(),
  },
  clientPrefix: "NEXT_PUBLIC_",
});

export default env;

Using validated environment variables

Once configured, access your environment variables with full TypeScript support:

import env from "./env.config";

// ✅ Fully typed and validated
const databaseUrl = env.DATABASE_URL; // string
const apiUrl = env.NEXT_PUBLIC_API_URL; // string
const nodeEnv = env.NODE_ENV; // "development" | "production"

// ❌ TypeScript error - server variable on client
const secret = env.JWT_SECRET; // Error: Cannot access server variable on client

Key features that set Envin apart

Framework-agnostic design

Unlike other environment validation tools that are tied to specific frameworks, Envin works seamlessly across the JavaScript ecosystem:

FrameworkSupportClient PrefixBuilt-in Presets
Next.jsNEXT_PUBLIC_
ViteVITE_
AstroPUBLIC_
React NativeCustom
Node.jsN/A
Any FrameworkConfigurable

Strict client/server separation

Envin provides built-in protection against accidentally exposing server-side environment variables to the client:

// Client-side component
"use client";

import env from "../../env.config";

export const ClientComponent = () => {
  // ❌ This will throw a clear error message
  return <div>{env.DATABASE_URL}</div>;

  // ✅ This works perfectly
  return <div>{env.NEXT_PUBLIC_API_URL}</div>;
};

This protection helps prevent security vulnerabilities and makes it impossible to accidentally expose sensitive information like database URLs or API keys to the client.

Interactive CLI with live previews

The Envin CLI provides an interactive development experience with real-time validation:

# Preview your environment variables
npx @envin/cli@latest dev

The CLI generates a beautiful web interface that:

  • Displays all your environment variables with their current values
  • Shows validation status for each variable
  • Highlights missing or invalid configurations
  • Provides helpful error messages and suggestions
  • Updates in real-time as you modify your .env files

This is particularly valuable for:

  • Debugging configuration issues during development
  • Onboarding new team members with clear visual feedback
  • Validating production environments before deployment

Integrating Envin with modern development workflows

Monorepo compatibility

Envin works beautifully in monorepo environments, especially when combined with Turborepo:

// packages/env/env.config.ts
export const createEnv = (clientPrefix: string) =>
  defineEnv({
    shared: {
      NODE_ENV: z.enum(["development", "production"]),
    },
    server: {
      DATABASE_URL: z.string().url(),
    },
    client: {
      [`${clientPrefix}API_URL`]: z.string().url(),
    },
    clientPrefix,
  });

// apps/web/env.config.ts
import { createEnv } from "@acme/env";
export default createEnv("NEXT_PUBLIC_");

// apps/mobile/env.config.ts
import { createEnv } from "@acme/env";
export default createEnv("EXPO_PUBLIC_");

TypeScript integration

Envin leverages TypeScript's power to provide compile-time safety:

// Type inference works automatically
const config = {
  apiUrl: env.NEXT_PUBLIC_API_URL, // Inferred as string
  retries: parseInt(env.RETRY_COUNT), // You handle type conversion
  features: {
    auth: env.NODE_ENV === "production", // Type-safe comparisons
  },
};

For additional TypeScript improvements, explore our guide on making your TypeScript smarter with one line of code.

Advanced Envin techniques

Custom validation logic

Envin supports complex validation scenarios:

const env = defineEnv({
  server: {
    DATABASE_URL: z
      .string()
      .url()
      .refine(
        (url) => url.startsWith("postgresql://"),
        "Database URL must be a PostgreSQL connection string",
      ),
    REDIS_URL: z.string().url().optional(),
    PORT: z.coerce.number().min(1000).max(65535).default(3000),
  },
  client: {
    NEXT_PUBLIC_APP_URL: z
      .string()
      .url()
      .refine(
        (url) => !url.endsWith("/"),
        "App URL should not end with a trailing slash",
      ),
  },
  clientPrefix: "NEXT_PUBLIC_",
});

Environment-specific configurations

Handle different environments elegantly:

const env = defineEnv({
  shared: {
    NODE_ENV: z.enum(["development", "staging", "production"]),
  },
  server: {
    DATABASE_URL: z.string().url(),
    LOG_LEVEL: z
      .enum(["debug", "info", "warn", "error"])
      .default(process.env.NODE_ENV === "development" ? "debug" : "info"),
  },
  clientPrefix: "NEXT_PUBLIC_",
});

Integration with existing tools

Envin plays well with other development tools:

// Works with dotenv
import "dotenv/config";
import env from "./env.config";

// Integrates with config libraries
export const config = {
  database: {
    url: env.DATABASE_URL,
    ssl: env.NODE_ENV === "production",
  },
  api: {
    baseUrl: env.NEXT_PUBLIC_API_URL,
    timeout: parseInt(env.API_TIMEOUT || "5000"),
  },
};

Envin vs. existing solutions

FeatureEnvint3-envdotenv-safeenvsafe
Framework SupportAnyNext.js focusedAnyAny
TypeScript Support✅ Full✅ Full❌ Limited✅ Full
Client/Server Separation✅ Built-in✅ Built-in❌ Manual❌ Manual
Interactive CLI✅ Live Preview❌ None❌ None❌ None
Schema ValidatorAny Standard SchemaZod onlyCustomCustom
Runtime Validation
Development Experience✅ Excellent✅ Good❌ Basic❌ Basic

Real-world use cases

E-commerce platforms

For e-commerce applications built with TurboStarter, Envin ensures:

const env = defineEnv({
  server: {
    STRIPE_SECRET_KEY: z.string().startsWith("sk_"),
    DATABASE_URL: z.string().url(),
    WEBHOOK_SECRET: z.string().min(20),
  },
  client: {
    NEXT_PUBLIC_STRIPE_PUBLISHABLE_KEY: z.string().startsWith("pk_"),
    NEXT_PUBLIC_APP_URL: z.string().url(),
  },
  clientPrefix: "NEXT_PUBLIC_",
});

SaaS applications

For SaaS products with complex integrations:

const env = defineEnv({
  server: {
    DATABASE_URL: z.string().url(),
    REDIS_URL: z.string().url(),
    EMAIL_SERVICE_API_KEY: z.string().min(10),
    ANALYTICS_API_KEY: z.string().min(10),
    PAYMENT_WEBHOOK_SECRET: z.string().min(20),
  },
  client: {
    NEXT_PUBLIC_APP_URL: z.string().url(),
    NEXT_PUBLIC_ANALYTICS_ID: z.string().min(5),
  },
  clientPrefix: "NEXT_PUBLIC_",
});

Mobile applications

For React Native apps using Expo:

const env = defineEnv({
  shared: {
    NODE_ENV: z.enum(["development", "production"]),
  },
  client: {
    EXPO_PUBLIC_API_URL: z.string().url(),
    EXPO_PUBLIC_APP_SCHEME: z.string().min(3),
  },
  clientPrefix: "EXPO_PUBLIC_",
});

The future of Envin

We're committed to continuously improving Envin with exciting features on our roadmap:

FeatureDescriptionStatus
Visual Schema BuilderGUI for creating environment schemasIn Development
Team CollaborationShared environment templatesPlanned
Cloud ValidationRemote environment validation servicePlanned
IDE ExtensionsVS Code and other editor integrationsPlanned
Auto-migrationAutomatic schema updatesResearching

Getting involved with the community

Envin is open-source and community-driven. Here's how you can get involved:

Contributing

We welcome contributions of all kinds:

  1. 🐛 Report bugs on GitHub Issues
  2. 💡 Suggest features through GitHub Discussions
  3. 📝 Improve documentation with pull requests
  4. 🔧 Submit code following our contribution guidelines
  5. Star the repository to show your support

Community support

Join our vibrant developer community:

🌟 Join our Discord community to connect with other developers using Envin and get help with your environment variable challenges!

Integration with TurboStarter

While Envin is completely free and open-source, it integrates seamlessly with TurboStarter kits for an even better development experience. TurboStarter customers get:

  • Pre-configured Envin setups for web, mobile, and extension projects
  • Advanced environment templates for common use cases
  • Priority support for Envin-related questions
  • Early access to new Envin features and integrations

Start building with confidence today

Environment variable management doesn't have to be a source of stress and bugs. With Envin's type-safe validation, framework-agnostic design, and interactive development tools, you can ensure your applications are properly configured from development to production.

Whether you're building a simple side project or scaling a complex enterprise application, Envin provides the foundation you need to manage environment variables with confidence.

# Get started in seconds
npm install envin zod

# Try the interactive CLI
npx @envin/cli dev

Ready to eliminate environment variable bugs forever?

Start using Envin today and join the developers who are building more reliable applications with type-safe environment variable validation.

For comprehensive documentation and advanced usage examples, visit the Envin documentation.

For those looking to accelerate their development even further, check out our TurboStarter kits which come with Envin pre-configured alongside authentication, database connections, and deployment setups.

If you're working with modern development workflows, explore our guides on Turborepo CLI techniques and Cursor AI best practices to maximize your productivity.


Open source and free forever. Support the project by starring our GitHub repository and sharing it with your fellow developers. Together, let's make environment variable bugs a thing of the past! 🚀

Have you tried Envin in your projects? We'd love to hear your feedback and use cases! Share your experience on GitHub Discussions or join our Discord community to connect with other developers.

world map
Community

Connect with like-minded people

Join our community to get feedback, support, and grow together with 100+ builders on board, let's ship it!

Join us

Ship your startup everywhere. In minutes.

Don't spend time on complex setups. TurboStarter simplifies everything.