Is your feature request related to a problem? Please describe.
Generating files that are checked into source control is suboptimal when working on a team where these files constantly change鈥攅specially when there's only a single file (ref #1292).
Describe the solution you'd like
It would be awesome if there was a webpack loader that transformed .graphql files into JavaScript modules that export client code. For example:
# getViewer.graphql
query getViewer {
viewer {
id
}
}
Once the webpack loader is added to the configuration, you could import from that .graphql file the client code, for example when using the urql or react-apollo plugins:
import { useGetViewer, GetViewerComponent } from '../getViewer.graphql';
// Now you can use useGetViewer and GetViewerComponent!
Note how there's no intermediary files generated that are checked into source control, everything happens inside of webpack and is opaque to the user.
This would also require a change to the generated TypeScript declarations to make sure TypeScript understands what is exported from all those .graphql files.
I think by combining some of the types generated by typescript-operations and the TypeScript modules generated by typescript-graphql-files-modules could work.
We just need to note that some parts of the typescript-operations are not declarative (for example, enum should be generated as type and not as enum, and there is a flag for that), because d.ts files can only contain TypeScript declarations and not code.
Then, we can create a very simple Webpack plugin that will build the HOC/Hooks/Components in runtime and export it (and then just match it to the declared one in the d.ts file).
Having a webpack loader for the runtime parts is a nice idea that's marred slightly by the fact that the types would still need to be generated to the filesystem for typechecking to work, but there's no real way around that. A webpack loader would also lend itself naturally to solving issues like #1570 and #1797 (incremental and selective builds).
Edit: #1846 seems to be a large step towards enabling this.
Here's an example of a webpack loader that emits typings for CSS modules.
Funnily enough we already use that exact webpack loader in our project. If the @graphql-codegen/webpack-loader worked that exact way I would be _very_ happy!
One downside to generating just declarations is that a user would have to take extra steps to test the queries and mutations (at least when using react-apollo). For jest you would have to configure jest to run with webpack I guess, which has some difficulties. Maybe a better alternative would be a babel macro? Since this also has wider support for different bundlers.
I think this is already done with graphql-tag/loader - https://github.com/apollographql/graphql-tag#webpack-preprocessing-with-graphql-tagloader
When you use the typescript-graphql-files-modules (https://graphql-code-generator.com/docs/plugins/typescript-graphql-files-modules) you can generate .d.ts file with declarations for all your graphql client side files that declares what operations are exported from it.
In our project we do not commit the files generated by graphql-code-generator into source control. We generate them when we build / run the application.
For jest runs (and other nodejs processes during development) you can use graphql-tag-loader-register to process graphql files on the .
You can use https://www.npmjs.com/package/graphql2js to convert graphql files to javascript in advance as part of building for production (e.g. when you are running babel, webpack, etc.)
Let's continue the discussion here: https://github.com/dotansimha/graphql-code-generator/issues/3494
Thank you :)
Most helpful comment
I think by combining some of the types generated by
typescript-operationsand the TypeScript modules generated bytypescript-graphql-files-modulescould work.We just need to note that some parts of the
typescript-operationsare not declarative (for example,enumshould be generated astypeand not asenum, and there is a flag for that), becaused.tsfiles can only contain TypeScript declarations and not code.Then, we can create a very simple Webpack plugin that will build the HOC/Hooks/Components in runtime and export it (and then just match it to the declared one in the
d.tsfile).