Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add default value for NODE_ENV #2507

Merged
merged 3 commits into from
Feb 17, 2025
Merged

Add default value for NODE_ENV #2507

merged 3 commits into from
Feb 17, 2025

Conversation

sodic
Copy link
Contributor

@sodic sodic commented Feb 12, 2025

Fixes this:

image

@infomiho Couldn't find a better way to set a default value. Is this ok?

Copy link
Contributor Author

@sodic sodic Feb 12, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@infomiho I tried to define list of all necessary env vars and somehow ensure (in the type system) that both serverProdSchema and serverDevSchema:

  1. Define constraints for all env vars (NODE_ENV, WASP_SERVER...).
  2. Can only make the existing constraints stricter.
  3. Define no other constraints (to prevent typos).

The second point is optional The original list doesn't need to define any constraints, it can just be a list and leave all the constraining to serverProdSchema and serverDevSchema.

I was hoping Zod supports something that, but seemingly none of its methods (e.g., extend, merge) fit my use case.

I also tried to use a type definition and satisfies, but couldn't make it work. GPTs kept suggesting complicated custom generic functions, so I gave up (don't think it's worth it)

It would work something like this (I'm making up the narrow method):

// This doesn't have to be Zod, it could just be a normal type, perhaps that's even better.
// (but I couldn't make that work either).
const envRequirements = z.object({
  NODE_ENV: z.enum(['development', 'production']),
  WASP_SERVER_URL: serverUrlSchema,
  WASP_WEB_CLIENT_URL: clientUrlSchema,
  JWT_SECRET: z.string(),
});

const serverDevSchema = envRequirements.narrow({
  NODE_ENV: z.literal('development'),
  WASP_SERVER_URL: serverUrlSchema
    .default('http://localhost:3001'),
  WASP_WEB_CLIENT_URL: clientUrlSchema
    .default('http://localhost:3000/'),
  JWT_SECRET: jwtTokenSchema
    .default('DEVJWTSECRET'),
})

const serverProdSchema = envRequirements.narrow({
  NODE_ENV: z.literal('production'),
  WSP_SERVER_URL: serverUrlSchema, // error: typo
  WASP_SERVER_URL: z.string(), // error: widens constraints
  // Error for missing JWT_SECRET, no constraints defined
})

Did I miss something, can Zod do this?
If not, I'll keep it as is. A custom generic function is too much IMO.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Too bad we couldn't do it like you imagined, I see unions in Zod 4 will get some love, but it's unclear when it will go out - that might help us in the future.

The solution you implemented is good enough, I don't see anything better you could have done.

Copy link
Contributor

@infomiho infomiho left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, tested locally 👍

@sodic sodic merged commit 62ba51a into main Feb 17, 2025
6 checks passed
@sodic sodic deleted the filip-default-node-env branch February 17, 2025 11:07
@sodic sodic self-assigned this Feb 18, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants