Skip to content
This repository was archived by the owner on Oct 26, 2025. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
33 changes: 0 additions & 33 deletions .github/ISSUE_TEMPLATE/01-bug.yml

This file was deleted.

25 changes: 0 additions & 25 deletions .github/ISSUE_TEMPLATE/02-documentation.yml

This file was deleted.

27 changes: 0 additions & 27 deletions .github/ISSUE_TEMPLATE/03-feature.yml

This file was deleted.

27 changes: 0 additions & 27 deletions .github/ISSUE_TEMPLATE/04-tooling.yml

This file was deleted.

8 changes: 7 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,14 @@
# Changelog

### 2.0.0

- Redwood uses prettier 3, and prettier 3 removes the sync API. This means we now have to operate entirely async. This is a breaking change from the sdl-codegen API, as you need to await the exposed public fns.
- There is a verbose option which provides info on the timings of the codegen.
- Big watch mode improvements

### 1.1.2

Removed this because its over-reaching:
Pulled back this a lot because its over-reaching:

- When a resolver is simply a fn to a literal, narrow to that exact type in the codegen (instead of keeping the optional promise type)

Expand Down
4 changes: 2 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@sdl-codegen/node",
"version": "1.1.2",
"version": "2.0.0",
"description": "GraphQL .d.ts file generation for SDL-first projects",
"repository": {
"type": "git",
Expand All @@ -18,6 +18,7 @@
],
"scripts": {
"build": "tsc",
"build:watch": "tsc --watch",
"format": "prettier \"**/*\" --ignore-unknown",
"format:write": "pnpm format --write",
"jest": "vitest",
Expand All @@ -39,7 +40,6 @@
},
"dependencies": {
"@mrleebo/prisma-ast": "^0.12.0",
"@prettier/sync": "0.5.2",
"ts-morph": "^22.0.0"
},
"devDependencies": {
Expand Down
26 changes: 8 additions & 18 deletions src/formatDTS.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,24 +5,14 @@ try {
hasPrettierInstalled = !!require.resolve("prettier")
} catch (error) {}

import * as prettier from "@prettier/sync"

export const getPrettierConfig = (path: string): unknown => {
if (!hasPrettierInstalled) return {}

if (!prettier?.default?.resolveConfig) return {}
if (typeof prettier.default.resolveConfig !== "function") return {}

// I confirmed that this lookup hits caches in RedwoodJS
return prettier.default.resolveConfig(path) ?? {}
}

export const formatDTS = (path: string, content: string, config: unknown): string => {
export const formatDTS = async (path: string, content: string): Promise<string> => {
if (!hasPrettierInstalled) return content

if (!prettier?.default?.format) return content
if (typeof prettier.default.format !== "function") return content

// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access, @typescript-eslint/no-unsafe-call
return prettier.default.format(content, { ...(config as object), filepath: path }) as string
try {
const prettier = await import("prettier")
if (!prettier) return content
return prettier.format(content, { filepath: path })
} catch (error) {
return content
}
}
71 changes: 44 additions & 27 deletions src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,27 +10,27 @@ import { createSharedSchemaFiles } from "./sharedSchema.js"
import { CodeFacts, FieldFacts } from "./typeFacts.js"
import { RedwoodPaths } from "./types.js"

export * from "./main.js"
export * from "./types.js"

import { basename, join } from "node:path"

interface SDLCodeGenReturn {
export interface SDLCodeGenReturn {
// Optional way to start up a watcher mode for the codegen
createWatcher: () => { fileChanged: (path: string) => void }
createWatcher: () => { fileChanged: (path: string) => Promise<void> }
// Paths which were added/changed during the run
paths: string[]
}

/** The API specifically for the Redwood preset */
export function runFullCodegen(preset: "redwood", config: { paths: RedwoodPaths; verbose?: true }): SDLCodeGenReturn
export async function runFullCodegen(preset: "redwood", config: { paths: RedwoodPaths; verbose?: true }): Promise<SDLCodeGenReturn>

export function runFullCodegen(preset: string, config: unknown): SDLCodeGenReturn
export async function runFullCodegen(preset: string, config: unknown): Promise<SDLCodeGenReturn>

export function runFullCodegen(preset: string, config: unknown): SDLCodeGenReturn {
export async function runFullCodegen(preset: string, config: unknown): Promise<SDLCodeGenReturn> {
if (preset !== "redwood") throw new Error("Only Redwood codegen is supported at this time")
const verbose = (config as { verbose?: true }).verbose
const verbose = !!(config as { verbose?: true }).verbose
const startTime = Date.now()
const step = makeStep(verbose)

const paths = (config as { paths: RedwoodPaths }).paths
const sys = typescript.sys
Expand Down Expand Up @@ -62,8 +62,8 @@ export function runFullCodegen(preset: string, config: unknown): SDLCodeGenRetur
prismaSchema = prismaModeller(prismaSchemaBlocks)
}

getGraphQLSDLFromFile(pathSettings)
getPrismaSchemaFromFile(pathSettings)
await step("Read the GraphQL schema", () => getGraphQLSDLFromFile(pathSettings))
await step("Read the Prisma schema", () => getPrismaSchemaFromFile(pathSettings))

if (!gqlSchema) throw new Error("No GraphQL Schema was created during setup")

Expand All @@ -83,46 +83,51 @@ export function runFullCodegen(preset: string, config: unknown): SDLCodeGenRetur
const filepaths = [] as string[]

// Create the two shared schema files
const sharedDTSes = createSharedSchemaFiles(appContext)
filepaths.push(...sharedDTSes)
await step("Create shared schema files", async () => {
const sharedDTSes = await createSharedSchemaFiles(appContext)
filepaths.push(...sharedDTSes)
})

let knownServiceFiles: string[] = []
const createDTSFilesForAllServices = () => {
const createDTSFilesForAllServices = async () => {
// TODO: Maybe Redwood has an API for this? Its grabbing all the services
const serviceFiles = appContext.sys.readDirectory(appContext.pathSettings.apiServicesPath)
knownServiceFiles = serviceFiles.filter(isRedwoodServiceFile)
for (const path of knownServiceFiles) {
const dts = lookAtServiceFile(path, appContext)
const dts = await lookAtServiceFile(path, appContext)
if (dts) filepaths.push(dts)
}
}

// Initial run
createDTSFilesForAllServices()
await step("Create DTS files for all services", createDTSFilesForAllServices)

const endTime = Date.now()
const timeTaken = endTime - startTime

if (verbose) console.log(`[sdl-codegen]: Full run took ${timeTaken}ms`)

const createWatcher = () => {
const oldSDL = ""

return {
fileChanged: (path: string) => {
fileChanged: async (path: string) => {
if (isTypesFile(path)) return
if (path === appContext.pathSettings.graphQLSchemaPath) {
const newSDL = appContext.sys.readFile(path)
if (newSDL === oldSDL) return

if (verbose) console.log("[sdl-codegen] SDL Schema changed")
getGraphQLSDLFromFile(appContext.pathSettings)
createSharedSchemaFiles(appContext)
createDTSFilesForAllServices()
await step("GraphQL schema changed", () => getGraphQLSDLFromFile(appContext.pathSettings))
await step("Create all shared schema files", () => createSharedSchemaFiles(appContext))
await step("Create all service files", createDTSFilesForAllServices)
} else if (path === appContext.pathSettings.prismaDSLPath) {
if (verbose) console.log("[sdl-codegen] Prisma schema changed")
getPrismaSchemaFromFile(appContext.pathSettings)
createDTSFilesForAllServices()
await step("Prisma schema changed", () => getPrismaSchemaFromFile(appContext.pathSettings))
await step("Create all shared schema files", createDTSFilesForAllServices)
} else if (isRedwoodServiceFile(path)) {
if (knownServiceFiles.includes(path)) {
if (verbose) console.log("[sdl-codegen] New service file")
createDTSFilesForAllServices()
if (!knownServiceFiles.includes(path)) {
await step("Create all shared schema files", createDTSFilesForAllServices)
} else {
if (verbose) console.log("[sdl-codegen] Service file changed")
lookAtServiceFile(path, appContext)
await step("Create known service files", () => lookAtServiceFile(path, appContext))
}
}
},
Expand All @@ -135,8 +140,20 @@ export function runFullCodegen(preset: string, config: unknown): SDLCodeGenRetur
}
}

const isTypesFile = (file: string) => file.endsWith(".d.ts")

const isRedwoodServiceFile = (file: string) => {
if (!file.includes("services")) return false
if (file.endsWith(".d.ts")) return false
if (file.endsWith(".test.ts") || file.endsWith(".test.js")) return false
if (file.endsWith("scenarios.ts") || file.endsWith("scenarios.js")) return false
return file.endsWith(".ts") || file.endsWith(".tsx") || file.endsWith(".js")
}

const makeStep = (verbose: boolean) => async (msg: string, fn: () => Promise<unknown> | Promise<void> | void) => {
if (!verbose) return fn()
console.log("[sdl-codegen] " + msg)
console.time("[sdl-codegen] " + msg)
await fn()
console.timeEnd("[sdl-codegen] " + msg)
}
3 changes: 0 additions & 3 deletions src/main.ts

This file was deleted.

2 changes: 1 addition & 1 deletion src/prismaModeller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ export const prismaModeller = (schema: PrismaSchemaBlocks) => {
leadingFieldComments.push(p.text.replace("/// ", "").replace("// ", ""))
} else if (p.type === "break") {
leadingFieldComments.push("")
} else if (p.type === "attribute" || p.type === "field") {
} else {
properties.set(p.name, {
leadingComments: leadingFieldComments.join("\n"),
property: p,
Expand Down
Loading