> ## Documentation Index
> Fetch the complete documentation index at: https://docs.hiveku.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Configure Environment Variables

> Store secrets and configuration for your app

Environment variables are how your app gets API keys, feature flags, and config without hardcoding them into source files. Hiveku manages them per environment and injects them automatically.

## Where to Find Them

Go to **Settings > Environment** in your project. You'll see tabs for:

* **Production** — your live site
* **Staging** — pre-release testing
* **Development** — local dev / preview branches

Each tab has its own set of variables.

## Adding a Variable

<Steps>
  <Step title="Open the right environment">
    Click **Production** (or Staging/Development) based on where this variable should apply.
  </Step>

  <Step title="Click Add Variable">
    Enter a **Key** (like `STRIPE_SECRET_KEY`) and a **Value** (like `sk_live_...`).
  </Step>

  <Step title="Save">
    Click **Save**. The variable is encrypted at rest and injected into your runtime.
  </Step>

  <Step title="Redeploy if needed">
    Runtime vars take effect immediately. **Build-time vars (NEXT\_PUBLIC\_\*) need a redeploy** to actually propagate to the browser bundle.
  </Step>
</Steps>

## Or Ask the AI

```
Add STRIPE_SECRET_KEY=sk_live_abc123 to production
```

```
Set NEXT_PUBLIC_ANALYTICS_ID to "G-ABC123" in production and staging
```

The AI confirms what it'll add, then writes the vars. Great for batch updates.

## Build-Time vs Runtime

This distinction matters.

<Tabs>
  <Tab title="Build-time (NEXT_PUBLIC_*)">
    Variables prefixed with `NEXT_PUBLIC_` are **baked into the browser bundle at build time**.

    * Used on the client (React components, browser JS)
    * Visible to anyone who views source — never put secrets here
    * **Require a redeploy** after changing the value

    Examples: `NEXT_PUBLIC_ANALYTICS_ID`, `NEXT_PUBLIC_API_URL`, `NEXT_PUBLIC_STRIPE_PUBLISHABLE_KEY`.
  </Tab>

  <Tab title="Runtime (everything else)">
    Variables without the `NEXT_PUBLIC_` prefix live on the server.

    * Never sent to the browser
    * Safe to store secrets (API keys, DB passwords)
    * Pick up new values on the next container restart (usually instant)

    Examples: `STRIPE_SECRET_KEY`, `DATABASE_URL`, `OPENAI_API_KEY`.
  </Tab>
</Tabs>

<Warning>
  Never put a secret in a `NEXT_PUBLIC_*` variable. Those end up in the browser where anyone can read them.
</Warning>

## Auto-Injected Variables

Hiveku sets these for you automatically — you don't need to add them:

| Variable            | Meaning                                      |
| ------------------- | -------------------------------------------- |
| `NODE_ENV`          | `production`, `development`, etc             |
| `AWS_REGION`        | The region your project runs in              |
| `HIVEKU_PROJECT_ID` | Unique project identifier                    |
| `DATABASE_URL`      | Postgres connection (if a DB is provisioned) |

Your code can use these directly: `process.env.DATABASE_URL`.

## Never Hardcode Secrets

Bad:

```typescript theme={null}
const stripe = new Stripe("sk_live_abc123...");
```

Good:

```typescript theme={null}
const stripe = new Stripe(process.env.STRIPE_SECRET_KEY!);
```

If you hardcode a key into source, it ends up in git history, logs, and potentially the browser bundle — rotate it immediately if that happens.

## Per-Environment Variables

You'll often want the same key with different values per environment.

```
Production:   STRIPE_SECRET_KEY = sk_live_abc...
Staging:      STRIPE_SECRET_KEY = sk_test_def...
Development:  STRIPE_SECRET_KEY = sk_test_xyz...
```

Hiveku automatically picks the right value based on which environment your app is running in.

## Reading Variables in Code

<Tabs>
  <Tab title="Server-side (Node)">
    ```typescript theme={null}
    const apiKey = process.env.STRIPE_SECRET_KEY;
    if (!apiKey) throw new Error("Missing STRIPE_SECRET_KEY");
    ```
  </Tab>

  <Tab title="Client-side (React)">
    ```typescript theme={null}
    const analyticsId = process.env.NEXT_PUBLIC_ANALYTICS_ID;
    // Only works for NEXT_PUBLIC_* vars
    ```
  </Tab>

  <Tab title="API routes">
    ```typescript theme={null}
    export async function POST(req: Request) {
      const key = process.env.OPENAI_API_KEY!;
      // ...
    }
    ```
  </Tab>
</Tabs>

## Verifying a Variable Is Set

After adding or changing a variable:

<Steps>
  <Step title="Redeploy if it's NEXT_PUBLIC_*">
    Click **Deploy** — the new value won't reach the browser until then.
  </Step>

  <Step title="Add a test route">
    Create a quick API route like `/api/env-test`:

    ```typescript theme={null}
    export async function GET() {
      return Response.json({
        hasKey: !!process.env.MY_VAR,
      });
    }
    ```
  </Step>

  <Step title="Hit the route">
    Visit the URL. `hasKey: true` confirms the variable is injected.
  </Step>

  <Step title="Never log the value itself">
    Logging the value can leak it into your logs. Log only presence (`hasKey: true/false`).
  </Step>
</Steps>

## Troubleshooting

<AccordionGroup>
  <Accordion title="process.env.MY_VAR is undefined in the browser">
    Only `NEXT_PUBLIC_*` variables reach the browser. Rename to `NEXT_PUBLIC_MY_VAR` and redeploy. Regular env vars work server-side only.
  </Accordion>

  <Accordion title="I added a variable but my app still errors 'undefined'">
    Two common causes:

    1. You added it to Staging but your app is running Production (check the environment tab)
    2. It's a build-time var (`NEXT_PUBLIC_*`) and you haven't redeployed yet — runtime vars take effect on the next container restart, build-time vars need a full redeploy
  </Accordion>

  <Accordion title="I accidentally committed a secret to git">
    **Rotate the key immediately** at the provider (Stripe, OpenAI, etc.) — assume it's compromised. Then remove it from your source, commit the removal, and store the new value in Hiveku env vars only.
  </Accordion>

  <Accordion title="My secret is larger than 4KB">
    Most env systems have a size limit. For large blobs (like a full JSON config or a certificate), store them in AWS Secrets Manager or a similar store, and keep just the pointer / reference in env vars.
  </Accordion>

  <Accordion title="Variable shows in Hiveku but not in my container">
    Check you're reading from the right environment. `process.env.NODE_ENV` should match the tab where you set the variable. If it still fails, redeploy — occasionally runtime injection lags a previous deploy.
  </Accordion>
</AccordionGroup>

## What's Next?

<CardGroup cols={2}>
  <Card title="Deploy your site" icon="rocket" href="/how-tos/deploy-site">
    Push env changes live
  </Card>

  <Card title="Set up a database" icon="database" href="/how-tos/setup-database">
    Uses DATABASE\_URL automatically
  </Card>
</CardGroup>
