Repository navigation
refactor(sdk): bundle graphql types and make graphql a dev dependency #2816
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
Changes from all commits
aca6f28
1789148
b460618
bb8d271
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,5 @@ | ||
| --- | ||
| "@tailor-platform/sdk": patch | ||
| --- | ||
|
|
||
| The SDK no longer installs `graphql`, `@urql/core`, or `wonka` as dependencies. The `DocumentNode` type that HTTP adapter `input` handlers and the executor `query` option accept is now included in the SDK's type declarations, so a project without `graphql` still gets `query` type-checked, and documents typed with `graphql` 16 or 17, including `TypedDocumentNode`, keep type-checking. If your project imports `graphql`, `@urql/core`, or `wonka` without declaring it, which only works when your package manager hoists it, add it to your own dependencies. If you use `graphql` 15 with `skipLibCheck: true`, passing a `parse()` result to the executor `query` option is now a type error, as it already was for HTTP adapters. |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,8 +1,9 @@ | ||
| import { cpSync } from "node:fs"; | ||
| import { cpSync, mkdirSync, readFileSync, readdirSync, writeFileSync } from "node:fs"; | ||
| import path from "node:path"; | ||
| import Sonda from "sonda/rolldown"; | ||
| import { defineConfig } from "tsdown"; | ||
| import { entry } from "./scripts/build-entries.mjs"; | ||
| import type { OutputOptions, PreRenderedChunk } from "rolldown"; | ||
|
|
||
| function copyToOutDir(outDir: string, source: string, dest: string): void { | ||
| cpSync(path.resolve(source), path.join(outDir, dest)); | ||
|
|
@@ -17,6 +18,24 @@ const jsPlugins = [ | |
| }), | ||
| ]; | ||
|
|
||
| const GRAPHQL_DIR = "node_modules/graphql/"; | ||
| const VENDOR_GRAPHQL_DIR = "vendor/graphql"; | ||
| const UP_TO_PACKAGES_DIR = /^(?:.*\/)?packages\//; | ||
|
|
||
| function stableChunkName(name: string): string { | ||
| const graphqlAt = name.indexOf(GRAPHQL_DIR); | ||
| if (graphqlAt !== -1) | ||
| return `${VENDOR_GRAPHQL_DIR}/${name.slice(graphqlAt + GRAPHQL_DIR.length)}`; | ||
| return name.replace(UP_TO_PACKAGES_DIR, ""); | ||
| } | ||
|
|
||
| function renameChunk(template: OutputOptions["entryFileNames"]) { | ||
| return (chunk: PreRenderedChunk): string => { | ||
| const resolved = typeof template === "function" ? template(chunk) : (template ?? "[name].js"); | ||
| return resolved.replace("[name]", stableChunkName(chunk.name.replace(/\.d$/, ""))); | ||
| }; | ||
| } | ||
|
|
||
| const externalDeps = ["vite", "vitest", /^@tailor-platform\/sdk$/]; | ||
|
|
||
| const sharedOptions = { | ||
|
|
@@ -62,6 +81,28 @@ export default defineConfig([ | |
| }, | ||
| unbundle: true, | ||
| root: "src", | ||
| deps: { neverBundle: externalDeps }, | ||
| deps: { neverBundle: externalDeps, dts: { alwaysBundle: [/^graphql(\/|$)/] } }, | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The inlined types under declare const doc: HttpAdapterTypedDocumentNode<{ user: { id: string } }, { id: string }>;
export const definitions = doc.definitions;With
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. b460618 adds |
||
| outputOptions: (options) => ({ | ||
| ...options, | ||
| entryFileNames: renameChunk(options.entryFileNames), | ||
| chunkFileNames: renameChunk(options.chunkFileNames), | ||
| }), | ||
| onSuccess: (config) => { | ||
| const vendorDir = path.join(config.outDir, VENDOR_GRAPHQL_DIR); | ||
| mkdirSync(vendorDir, { recursive: true }); | ||
| copyToOutDir(config.outDir, `${GRAPHQL_DIR}LICENSE`, `${VENDOR_GRAPHQL_DIR}/LICENSE`); | ||
| for (const file of readdirSync(vendorDir, { recursive: true, encoding: "utf8" })) { | ||
| if (!file.endsWith(".d.mts")) continue; | ||
| const target = path.join(vendorDir, file); | ||
| writeFileSync( | ||
| target, | ||
| readFileSync(target, "utf8").replace(/^\/\/#region (.*)$/gm, (line, region: string) => { | ||
| const graphqlAt = region.indexOf(GRAPHQL_DIR); | ||
| if (graphqlAt === -1) return line; | ||
| return `//#region graphql/${region.slice(graphqlAt + GRAPHQL_DIR.length)}`; | ||
| }), | ||
| ); | ||
| } | ||
| }, | ||
| }, | ||
| ]); | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Without
graphqlinstalled, the executor'soperation.query(kind: "graphql") is no longer type-checked. Its type comes from@urql/core, whose document types rely on@0no-co/graphql.web's/*@ts-ignore*/ import * as GraphQL from 'graphql'; oncegraphqlcan't be resolved they accept any value. Until now the SDK's owngraphqlresolved that import.In an npm or pnpm project that installs the packed SDK without
graphql,tsc --strictrejects this on the base (Type 'number' is not assignable to type 'DocumentInput<unknown, AnyVariables>') and accepts it on this PR. Typingquerywith the inlinedDocumentNode, as the HTTP adapter does, would avoid relying ongraphqlbeing resolvable.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Addressed by b460618:
queryis now typedstring | DocumentNodewith the bundled types, and@urql/coreis removed.With the packed SDK installed without
graphql, yourquery: 1example now failstsc --strictwith TS2769 (Type 'number' is not assignable to type 'string | DocumentNode').A string
querycompiles cleanly, and the published.d.mtsfiles have no references tographqlor@urql.