How to Make SelectFields for Prisma enums in RedwoodJS
Demo: https://rw-office-hours-enum-select-list.netlify.app
GH Repo: [redwood-office-hours/2022-10-05-enum-select-options at main · redwoodjs/redwood-office-hours · GitHub](redwood-office-hours/2022-10-05-enum-select-options at main · redwoodjs/redwood-office-hours · GitHub}
The Problem
- Cannot get values from the enum to make a select control because Redwood generates the enum as a type -- and that means you cannot iterate and build options for each entry
- Web cannot access Prisma client types because the web side doesn't connect to the database
- Enum values don't have friendly, readable labels, e.g: "EMPIRE_STRIKES_BACK" vs "empire Strikes Back"
Current Scaffolding
Scaffolding will render enums in forms with Radio Options or Checkboxes.
- But, scaffolding won't pickup new enums .... you would have to re-scaffold and force update the web components.
- Plus, select fields take up less space in a form.
Code
Let’s make a way to return enum values and labels in a friendly way!
Prisma Schema
enum Episode {
NEW_HOPE
EMPIRE_STRIKES_BACK
RETURN_OF_THE_JEDI
ROGUE_ONE
}
model Character {
id Int @id @default(autoincrement())
name String @unique
appearsIn Episode[]
}
GraphQL Schema
Need Postgres for enums …
// 2022-10-05-enum-select-options/api/src/graphql/options.sdl.ts
export const schema = gql`
interface OptionItem {
label: String!
}
type EpisodeOption implements OptionItem {
value: Episode!
label: String!
}
type Query {
episodeOptions: [EpisodeOption!]! @skipAuth
}
`
Services
// 2022-10-05-enum-select-options/api/src/services/episodeOptions/episodeOptions.ts
import { Episode } from '@prisma/client'
import type { QueryResolvers, EpisodeOption } from 'types/graphql'
import { label } from 'src/lib/helpers'
const getEnumValues = (enumType: Record<string, string>) => {
return Object.values(enumType).map((value) => {
return {
value,
label: label(value),
}
})
}
export const episodeOptions: QueryResolvers['episodeOptions'] = () => {
return getEnumValues(Episode) as EpisodeOption[]
}
Other Approaches
- Scripts to construct enums by parsing the Prisma Schema/DMMF