Compare commits
158 Commits
0.20.0-nex
...
main
| Author | SHA1 | Date |
|---|---|---|
|
|
9e5c27c509 | |
|
|
601c2f03f4 | |
|
|
4e085dc7b2 | |
|
|
1e6b9212d3 | |
|
|
4d8e37177b | |
|
|
eec4b91091 | |
|
|
8e65081539 | |
|
|
7ee48c4f2c | |
|
|
e9dc7e0c4a | |
|
|
9875e90dae | |
|
|
9a1050792b | |
|
|
df9cb700a9 | |
|
|
123dc61fac | |
|
|
251af9461b | |
|
|
b906288c58 | |
|
|
11d028277e | |
|
|
509c246e88 | |
|
|
aaa45204b6 | |
|
|
7349e3633c | |
|
|
892af670a4 | |
|
|
bc12ca0f8e | |
|
|
0f37c3e9d4 | |
|
|
6c1530a3d5 | |
|
|
92f20dc9e9 | |
|
|
bbc969a5b0 | |
|
|
0d06f26b12 | |
|
|
e901bebd51 | |
|
|
87a82a28b1 | |
|
|
3de7f399c6 | |
|
|
45b9d5a926 | |
|
|
b92545fe4f | |
|
|
4d035019a4 | |
|
|
9ec3442539 | |
|
|
c0e55b53b4 | |
|
|
a7c26ba587 | |
|
|
703d5595da | |
|
|
02015ede84 | |
|
|
2934d6d38c | |
|
|
5e3b837ec0 | |
|
|
b24d132d38 | |
|
|
e5658cadba | |
|
|
333dfb8757 | |
|
|
02a73b5d74 | |
|
|
7e744aa0d3 | |
|
|
e65b5a7952 | |
|
|
d4c6260774 | |
|
|
6de1cb6917 | |
|
|
555ae79ded | |
|
|
a003ff074f | |
|
|
855a482c54 | |
|
|
266f1a82ce | |
|
|
380ed9d4ca | |
|
|
5984ee122e | |
|
|
a914cc33d1 | |
|
|
03b5ffd24a | |
|
|
4531519e6c | |
|
|
8e0ce1b4a1 | |
|
|
df7d1370f9 | |
|
|
ebcdb29a3e | |
|
|
81ec5c0f08 | |
|
|
2b0708d675 | |
|
|
2759c551c7 | |
|
|
10ea65f6f1 | |
|
|
690abb7299 | |
|
|
2e1c32b794 | |
|
|
3a92760058 | |
|
|
031c77257a | |
|
|
31a6137f90 | |
|
|
571fa4d124 | |
|
|
145f664914 | |
|
|
189a5becb7 | |
|
|
70eda57c61 | |
|
|
7ff557b6e7 | |
|
|
5844b7fa74 | |
|
|
cfff794306 | |
|
|
d2e586bd3f | |
|
|
7b84cd63db | |
|
|
3c18d6c1e3 | |
|
|
3f05c1d0ea | |
|
|
16ac615f9b | |
|
|
9a3915e11c | |
|
|
ce1bd8c594 | |
|
|
74c93e2ce4 | |
|
|
a59273de88 | |
|
|
5056129b40 | |
|
|
c89c72bda2 | |
|
|
3050c3bb42 | |
|
|
7f16b8b750 | |
|
|
291e86a669 | |
|
|
4625a13b52 | |
|
|
8827f28ead | |
|
|
d220d3195d | |
|
|
27e35e51ee | |
|
|
3f78131abb | |
|
|
06cd0a02e6 | |
|
|
5d23123cc0 | |
|
|
e3b414ddde | |
|
|
43f1da24e7 | |
|
|
46ad529954 | |
|
|
0f5f14526c | |
|
|
c79d3cb9a9 | |
|
|
d1634b2a58 | |
|
|
29f03a03e7 | |
|
|
0b28c77678 | |
|
|
0ce49b91b7 | |
|
|
7f0dd11a8b | |
|
|
aa283addcf | |
|
|
1f5b025837 | |
|
|
218bf11f18 | |
|
|
fbcfba3165 | |
|
|
bb936cb95c | |
|
|
cb1e17ef56 | |
|
|
666746c1df | |
|
|
af73f669f5 | |
|
|
bfdd42095b | |
|
|
de049990df | |
|
|
025d82e767 | |
|
|
b327841a63 | |
|
|
0788e86772 | |
|
|
1c7b9b1736 | |
|
|
55bca2d8c7 | |
|
|
cb22957a84 | |
|
|
217779b7ea | |
|
|
fe1dd14317 | |
|
|
3f27f9e979 | |
|
|
91c775e48a | |
|
|
4f3cef9d38 | |
|
|
d99621210b | |
|
|
a7829443b2 | |
|
|
b69b30f5c1 | |
|
|
ea3f994c40 | |
|
|
9afc64387d | |
|
|
5116a18255 | |
|
|
2141a77167 | |
|
|
8c324a6cdf | |
|
|
bcc0cee16f | |
|
|
1a3c3c552c | |
|
|
c4b35b3035 | |
|
|
fcc66ebe98 | |
|
|
2e76a4fd0b | |
|
|
c1aa2674f7 | |
|
|
5c05a36932 | |
|
|
08556d456f | |
|
|
bef7786a7d | |
|
|
c2acf9b564 | |
|
|
2b44900b37 | |
|
|
0ed742a8a5 | |
|
|
5c4d6decdb | |
|
|
4c52f594fe | |
|
|
c9f4354aef | |
|
|
54e313e3c3 | |
|
|
bd9ea3f8c6 | |
|
|
1ebae9f2a8 | |
|
|
6b5fccebed | |
|
|
9b1f212ca4 | |
|
|
d9f743c0bc | |
|
|
78b8b08dc3 | |
|
|
80ad53135c |
|
|
@ -1,35 +1,36 @@
|
|||
name: pr
|
||||
|
||||
on: [pull_request]
|
||||
on:
|
||||
- pull_request
|
||||
|
||||
jobs:
|
||||
graphql-14:
|
||||
graphql-15:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-node@v1
|
||||
with:
|
||||
node-version: 12.x
|
||||
node-version: 14.x
|
||||
- name: Install Dependencies
|
||||
run: yarn --frozen-lockfile && yarn format:ci
|
||||
- name: Install GraphQL@14.x
|
||||
run: yarn add graphql@^14.5.8
|
||||
- name: Install GraphQL@15.x
|
||||
run: yarn add graphql@^15
|
||||
- name: Test
|
||||
run: yarn -s test:ci --testPathIgnorePatterns v15
|
||||
run: yarn -s test:ci
|
||||
|
||||
test:
|
||||
strategy:
|
||||
matrix:
|
||||
node-version: [10.x, 12.x]
|
||||
node-version: [14.x, 16.x]
|
||||
os: [macos-latest, ubuntu-latest, windows-latest]
|
||||
runs-on: ${{ matrix.os }}
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-node@v1
|
||||
- uses: actions/setup-node@v2
|
||||
with:
|
||||
node-version: ${{ matrix.node-version }}
|
||||
- name: Install Dependencies
|
||||
run: yarn --frozen-lockfile
|
||||
run: yarn --frozen-lockfile || yarn --frozen-lockfile
|
||||
- name: Check Prettier
|
||||
if: matrix.os != 'windows-latest'
|
||||
run: yarn format:ci
|
||||
|
|
@ -37,7 +38,7 @@ jobs:
|
|||
run: yarn -s test:ci
|
||||
- name: Upload coverage to Codecov
|
||||
uses: codecov/codecov-action@v1
|
||||
if: matrix.os == 'ubuntu-latest' && matrix.node-version == '10.x'
|
||||
if: matrix.os == 'ubuntu-latest' && matrix.node-version == '14.x'
|
||||
with:
|
||||
directory: ./coverage
|
||||
|
||||
|
|
@ -55,22 +56,24 @@ jobs:
|
|||
# rm examples/star-wars/star-wars-schema.graphql
|
||||
# node examples/star-wars/dist/schema.js
|
||||
# git diff --exit-code
|
||||
node-version: [10.x]
|
||||
node-version: [14.x]
|
||||
os: [macos-latest]
|
||||
runs-on: ${{ matrix.os }}
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-node@v1
|
||||
- uses: actions/setup-node@v2
|
||||
with:
|
||||
node-version: ${{ matrix.node-version }}
|
||||
- name: Install Dependencies
|
||||
run: yarn --frozen-lockfile && yarn format:ci
|
||||
run: yarn --frozen-lockfile || yarn --frozen-lockfile
|
||||
- name: Check Formatting
|
||||
run: yarn format:ci
|
||||
- name: Link
|
||||
run: yarn link
|
||||
- name: Example Install
|
||||
run: yarn --cwd=examples/${{ matrix.example }} --frozen-lockfile
|
||||
- name: Example Use Link
|
||||
run: yarn --cwd=examples/${{ matrix.example }} link @nexus/schema
|
||||
run: yarn --cwd=examples/${{ matrix.example }} link nexus
|
||||
- name: Example Typecheck
|
||||
run: yarn --cwd=examples/${{ matrix.example }} tsc
|
||||
|
||||
|
|
@ -80,8 +83,8 @@ jobs:
|
|||
- uses: actions/checkout@v2
|
||||
with:
|
||||
fetch-depth: 0
|
||||
- uses: actions/setup-node@v1
|
||||
- uses: actions/setup-node@v2
|
||||
- name: Install Dependencies
|
||||
run: yarn --frozen-lockfile
|
||||
run: yarn --frozen-lockfile || yarn --frozen-lockfile
|
||||
- name: Prettier
|
||||
run: yarn format:ci
|
||||
|
|
|
|||
|
|
@ -2,43 +2,43 @@ name: trunk
|
|||
|
||||
on:
|
||||
push:
|
||||
branches: [develop]
|
||||
branches: [main]
|
||||
|
||||
jobs:
|
||||
graphql-14:
|
||||
graphql-15:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-node@v1
|
||||
- uses: actions/setup-node@v2
|
||||
with:
|
||||
node-version: 12.x
|
||||
node-version: 14.x
|
||||
- name: Install Dependencies
|
||||
run: yarn --frozen-lockfile
|
||||
- name: Install GraphQL@14.x
|
||||
run: yarn add graphql@^14.5.8
|
||||
run: yarn --frozen-lockfile && yarn format:ci
|
||||
- name: Install GraphQL@15.x
|
||||
run: yarn add graphql@^15
|
||||
- name: Test
|
||||
run: yarn -s test:ci --testPathIgnorePatterns v15
|
||||
run: yarn -s test:ci
|
||||
|
||||
test:
|
||||
strategy:
|
||||
matrix:
|
||||
node-version: [10.x, 12.x]
|
||||
node-version: [14.x, 16.x]
|
||||
os: [macos-latest, ubuntu-latest, windows-latest]
|
||||
runs-on: ${{ matrix.os }}
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-node@v1
|
||||
- uses: actions/setup-node@v2
|
||||
with:
|
||||
node-version: ${{ matrix.node-version }}
|
||||
- name: Install Dependencies
|
||||
run: yarn --frozen-lockfile
|
||||
run: yarn --frozen-lockfile || yarn --frozen-lockfile
|
||||
- name: Check Prettier
|
||||
if: matrix.os != 'windows-latest'
|
||||
run: yarn format:ci
|
||||
- name: Test
|
||||
run: yarn -s test:ci
|
||||
- name: Upload coverage to Codecov
|
||||
if: matrix.os == 'ubuntu-latest' && matrix.node-version == '10.x'
|
||||
if: matrix.os == 'ubuntu-latest' && matrix.node-version == '14.x'
|
||||
uses: codecov/codecov-action@v1
|
||||
with:
|
||||
directory: ./coverage
|
||||
|
|
@ -57,22 +57,24 @@ jobs:
|
|||
# rm examples/star-wars/star-wars-schema.graphql
|
||||
# node examples/star-wars/dist/schema.js
|
||||
# git diff --exit-code
|
||||
node-version: [10.x]
|
||||
node-version: [14.x]
|
||||
os: [macos-latest]
|
||||
runs-on: ${{ matrix.os }}
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-node@v1
|
||||
- uses: actions/setup-node@v2
|
||||
with:
|
||||
node-version: ${{ matrix.node-version }}
|
||||
- name: Install Dependencies
|
||||
run: yarn --frozen-lockfile && yarn format:ci
|
||||
run: yarn --frozen-lockfile || yarn --frozen-lockfile
|
||||
- name: Check Formatting
|
||||
run: yarn format:ci
|
||||
- name: Link
|
||||
run: yarn link
|
||||
- name: Example Install
|
||||
run: yarn --cwd=examples/${{ matrix.example }} --frozen-lockfile
|
||||
- name: Example Use Link
|
||||
run: yarn --cwd=examples/${{ matrix.example }} link @nexus/schema
|
||||
run: yarn --cwd=examples/${{ matrix.example }} link nexus
|
||||
- name: Example Typecheck
|
||||
run: yarn --cwd=examples/${{ matrix.example }} tsc
|
||||
|
||||
|
|
@ -83,9 +85,9 @@ jobs:
|
|||
- uses: actions/checkout@v2
|
||||
with:
|
||||
fetch-depth: 0
|
||||
- uses: actions/setup-node@v1
|
||||
- uses: actions/setup-node@v2
|
||||
- name: Install Dependencies
|
||||
run: yarn --frozen-lockfile
|
||||
run: yarn --frozen-lockfile || yarn --frozen-lockfile
|
||||
- name: Release Canary
|
||||
env:
|
||||
NPM_TOKEN: ${{secrets.NPM_TOKEN}}
|
||||
|
|
|
|||
|
|
@ -5,3 +5,4 @@ examples/*/dist
|
|||
website/static/playground-dist
|
||||
yarn-error.log
|
||||
coverage/*
|
||||
tests/esm/out/
|
||||
|
|
@ -1,4 +1,4 @@
|
|||
(c) 2018-2019 Tim Griesser
|
||||
(c) 2018-2022 Tim Griesser
|
||||
|
||||
Permission is hereby granted, free of charge, to any person
|
||||
obtaining a copy of this software and associated documentation
|
||||
|
|
|
|||
16
README.md
16
README.md
|
|
@ -1,17 +1,17 @@
|
|||
# Nexus Schema
|
||||
# Nexus
|
||||
|
||||

|
||||
[](https://badge.fury.io/js/%40nexus%2Fschema)
|
||||
[](https://github.com/graphql-nexus/nexus/actions/workflows/trunk.yml)
|
||||
[](https://badge.fury.io/js/nexus)
|
||||
|
||||
Declarative, code-first and strongly typed GraphQL schema construction for TypeScript & JavaScript.
|
||||
|
||||
## Installation
|
||||
|
||||
```
|
||||
npm install @nexus/schema graphql
|
||||
npm install nexus graphql
|
||||
```
|
||||
|
||||
Note you must also add `graphql`. Nexus Schema pins to it as a [peer dependency](https://nodejs.org/en/blog/npm/peer-dependencies/).
|
||||
Note you must also add `graphql`. Nexus pins to it as a [peer dependency](https://nodejs.org/en/blog/npm/peer-dependencies/).
|
||||
|
||||
## Features
|
||||
|
||||
|
|
@ -33,7 +33,7 @@ Note you must also add `graphql`. Nexus Schema pins to it as a [peer dependency]
|
|||
## Example
|
||||
|
||||
```ts
|
||||
import { queryType, stringArg, makeSchema } from '@nexus/schema'
|
||||
import { queryType, stringArg, makeSchema } from 'nexus'
|
||||
import { GraphQLServer } from 'graphql-yoga'
|
||||
|
||||
const Query = queryType({
|
||||
|
|
@ -70,8 +70,8 @@ More examples can be found in the [`/examples`](./examples) directory:
|
|||
|
||||
## Documentation
|
||||
|
||||
You can find the docs for Nexus Schema [here](http://nexusjs.org/).
|
||||
You can find the docs for Nexus [here](http://nexusjs.org/).
|
||||
|
||||
## Migrate from SDL
|
||||
|
||||
If you've been following an [SDL-first](https://www.prisma.io/blog/the-problems-of-schema-first-graphql-development-x1mn4cb0tyl3/) approach to build your GraphQL server and want to see what your code looks like when written with GraphQL Nexus, you can use the [**SDL converter**](https://nexus.js.org/converter).
|
||||
If you've been following an [SDL-first](https://www.prisma.io/blog/the-problems-of-schema-first-graphql-development-x1mn4cb0tyl3/) approach to build your GraphQL server and want to see what your code looks like when written with GraphQL Nexus, you can use the [**SDL converter**](https://nexusjs.org/converter).
|
||||
|
|
|
|||
|
|
@ -1,8 +1,8 @@
|
|||
# Nexus Schema Documentation
|
||||
# Nexus Documentation
|
||||
|
||||
[](https://app.netlify.com/sites/graphql-nexus-schema/deploys)
|
||||
|
||||
This repository contains the [source code](./src) and the [content](./content) for the [Nexus Schema documentation](/).
|
||||
This repository contains the [source code](./src) and the [content](./content) for the [Nexus documentation](/).
|
||||
|
||||
## Run locally
|
||||
|
||||
|
|
@ -13,7 +13,7 @@ yarn
|
|||
yarn dev
|
||||
```
|
||||
|
||||
To prettify or format the code, run:
|
||||
To prettify or format the code, run:
|
||||
|
||||
```
|
||||
yarn prettify
|
||||
|
|
@ -21,7 +21,7 @@ yarn prettify
|
|||
|
||||
Visit `http://localhost:8000/` to view the app.
|
||||
|
||||
## MDX blocks
|
||||
## MDX blocks
|
||||
|
||||
View the example MDX blocks on `http://localhost:8000/getting-started/example` and the usage in [example.mdx](./content/01-getting-started/04-example.mdx)
|
||||
|
||||
|
|
@ -31,8 +31,6 @@ Write MDX files in `content` folder.
|
|||
|
||||
Open [`config.js`](./config.js) for available config options for `gatsby`, `header`, `footer`, `feedback` and `siteMetadata`
|
||||
|
||||
|
||||
|
||||
## Inserting, moving and deleting files
|
||||
|
||||
All files/folders in the context are prefixed with a _position_ which indicates the order in which they appear in the sidenav on the docs website. This makes it cumbersome to insert, move and delete files because the positions of a number of other files (if not all) in the same folder might need to be adjusted. Thanks to [Luca Steeb](https://github.com/steebchen/), you can perform these operations with a dedicated CLI called [`mdtool`](https://gist.githubusercontent.com/steebchen/bd085ebde1fcf4242e3fdd0df4d202a6/raw/c04e3d262eb6a302a9fab98f6428fec9329681e2/mdtool).
|
||||
|
|
@ -51,7 +49,7 @@ chmod +x /usr/local/bin/mdtool
|
|||
```
|
||||
mdtool insert 3
|
||||
mdtool swap A B
|
||||
mdtool move A B
|
||||
mdtool move A B
|
||||
mdtool remove 4
|
||||
```
|
||||
|
||||
|
|
@ -63,7 +61,7 @@ Make place for a new file at given index and increment all numbers by one after
|
|||
$ mdtool insert INDEX
|
||||
|
||||
# e.g.:
|
||||
$ mdtool insert 2
|
||||
$ mdtool insert 2
|
||||
|
||||
# Result: for files 01-a, 02-b, 03-c, and 04-d; 03-c is renamed to 04-c and 04-d is renamed to 05-d so you can create a new file at index 2
|
||||
```
|
||||
|
|
@ -76,7 +74,7 @@ Swap two files; specify both filenames (prefix numbers get automatically adjuste
|
|||
$ mdtool swap FILENAME1 FILENAME2
|
||||
|
||||
# e.g.:
|
||||
$ mdtool swap 03-file1.mdx 07-file2.mdx
|
||||
$ mdtool swap 03-file1.mdx 07-file2.mdx
|
||||
|
||||
# Result: Files are now named: 03-file2.mdx 07-file1.mdx
|
||||
```
|
||||
|
|
@ -89,12 +87,11 @@ Move a given file to another given index
|
|||
$ mdtool move FILENAME INDEX
|
||||
|
||||
# e.g.:
|
||||
$ mdtool move 05-file.mdx 2
|
||||
$ mdtool move 05-file.mdx 2
|
||||
|
||||
# Result: 05-file.mdx is move to 02-file.mdx, plus previous files 02-*, 03-*, 04-* are incremented
|
||||
```
|
||||
|
||||
|
||||
#### `mdtool swap`
|
||||
|
||||
Shift all other items by -1 at a given index:
|
||||
|
|
@ -103,7 +100,7 @@ Shift all other items by -1 at a given index:
|
|||
$ mdtool remove INDEX
|
||||
|
||||
# e.g.:
|
||||
$ mdtool remove 2
|
||||
$ mdtool remove 2
|
||||
|
||||
# Result: 01-a, 02-b, 03-c, 04-d becomes 01-a, 02-b, 02-c, 03-d; 02-b is supposed to be manually deleted
|
||||
```
|
||||
|
|
|
|||
|
|
@ -38,7 +38,7 @@ const config = {
|
|||
title: 'Nexus - title',
|
||||
description: 'Nexus - desc',
|
||||
keywords: 'Docs, nexus, 1.0',
|
||||
docsLocation: 'https://github.com/graphql-nexus/schema/tree/develop/docs/content',
|
||||
docsLocation: 'https://github.com/graphql-nexus/nexus/tree/main/docs/content',
|
||||
twitter: {
|
||||
site: '@nexusgql',
|
||||
creator: '@nexusgql',
|
||||
|
|
|
|||
|
|
@ -8,14 +8,11 @@ metaDescription: 'An introduction to the Nexus tutorial.'
|
|||
|
||||
Welcome to _the_ Nexus tutorial! If you're new to Nexus and want a guided learning journey, this is the place! Through a handful of chapters we're going to be building just enough of a blog to give you an overview of Nexus; what it is and what it can do.
|
||||
|
||||
This tutorial is still under construction. Some chapters will continue to be refined and more added. If you're looking for our old tutorial content, it can still be found [here](/getting-started/tutorial).
|
||||
|
||||
## Assumed tools
|
||||
|
||||
Throughout this journey, we'll be making a few minor assumptions about your toolchain to keep the content flowing:
|
||||
|
||||
- Using `npm` as the package manager.
|
||||
- Using a \*nix OS
|
||||
- Using VSCode
|
||||
|
||||
If you're using another set of tools, like Yarn on Windows with Sublime Text, that's totally fine and welcome! Just know that at you'll occasionally need to adapt minor instructions to your situation.
|
||||
|
|
|
|||
|
|
@ -4,34 +4,34 @@ title: 1. Setup and first query
|
|||
|
||||
## Overview
|
||||
|
||||
In this first chapter we're just going to get the bare minimum of a Nexus Schema project setup. You'll learn about:
|
||||
In this first chapter we're just going to get the bare minimum of a Nexus project setup. You'll learn about:
|
||||
|
||||
- The `@nexus/schema` package
|
||||
- The `nexus` package
|
||||
- The `ts-node-dev` package to run your app
|
||||
- Laying out and running a Nexus Schema project
|
||||
- Laying out and running a Nexus project
|
||||
- GraphQL Playground
|
||||
|
||||
## CLI
|
||||
|
||||
Start by creating your project directory, initializing your `package.json`, and adding the needed runtime dependencies.
|
||||
|
||||
```bash-symbol
|
||||
```bash-symbol copy
|
||||
mkdir nexus-tutorial && cd nexus-tutorial
|
||||
npm init -y
|
||||
npm add @nexus/schema graphql apollo-server
|
||||
npm install nexus graphql apollo-server
|
||||
```
|
||||
|
||||
> Note: `@nexus/schema` works with any GraphQL compliant server. We'll use `apollo-server` in this tutorial, but you're free to use whichever fits your use-case best.
|
||||
> Note: `nexus` works with any GraphQL compliant server. We'll use `apollo-server` in this tutorial, but you're free to use whichever fits your use-case best.
|
||||
|
||||
We'll also need `typescript` and `ts-node-dev` as dev dependencies. `ts-node-dev` will enable you to transpile your TS files on the fly and restart your API on changes.
|
||||
|
||||
```bash-symbol
|
||||
npm add --save-dev typescript ts-node-dev
|
||||
```bash-symbol copy
|
||||
npm install --save-dev typescript ts-node-dev
|
||||
```
|
||||
|
||||
To properly get full advantage of TypeScript, we'll need a `tsconfig.json` file. Create one at the root of your project and copy paste the following
|
||||
|
||||
```json
|
||||
```json file=tsconfig.json copy
|
||||
{
|
||||
"compilerOptions": {
|
||||
"target": "ES2018",
|
||||
|
|
@ -48,26 +48,47 @@ To properly get full advantage of TypeScript, we'll need a `tsconfig.json` file.
|
|||
|
||||
Let's finally add some npm scripts to simplify our future workflows
|
||||
|
||||
```json
|
||||
<TabbedContent tabs={['Diff', 'Code']}>
|
||||
|
||||
<tab>
|
||||
|
||||
```json file=package.json
|
||||
"scripts": {
|
||||
"dev": "ts-node-dev --transpile-only --no-notify api/app.ts",
|
||||
"build": "tsc"
|
||||
"test": "echo \"Error: no test specified\" && exit 1",
|
||||
+ "dev": "ts-node-dev --transpile-only --no-notify api/index.ts",
|
||||
+ "build": "tsc"
|
||||
}
|
||||
```
|
||||
|
||||
</tab>
|
||||
|
||||
<tab>
|
||||
|
||||
```json copy
|
||||
"scripts": {
|
||||
"test": "echo \"Error: no test specified\" && exit 1",
|
||||
"dev": "ts-node-dev --transpile-only --no-notify api/index.ts",
|
||||
"build": "tsc"
|
||||
},
|
||||
```
|
||||
|
||||
</tab>
|
||||
|
||||
</TabbedContent>
|
||||
|
||||
## Creating our app layout
|
||||
|
||||
We'll now create our first module at `api/schema.ts`:
|
||||
|
||||
```bash-symbol
|
||||
```bash-symbol copy
|
||||
mkdir api && touch api/schema.ts
|
||||
```
|
||||
|
||||
We'll then setup `@nexus/schema` to create an empty schema
|
||||
We'll then setup `nexus` to create an empty schema
|
||||
|
||||
```ts
|
||||
```ts copy
|
||||
// api/schema.ts
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { join } from 'path'
|
||||
|
||||
export const schema = makeSchema({
|
||||
|
|
@ -80,14 +101,14 @@ export const schema = makeSchema({
|
|||
```
|
||||
|
||||
1. GraphQL types that will be used to construct your GraphQL schema. It's voluntarily empty for now.
|
||||
1. Output path to where `@nexus/schema` should write the generated TypeScript definition types derived from your schema. This is **mandatory** to benefit from Nexus' type-safety. We call this system "reflection". More on it later.
|
||||
1. Output path to where `@nexus/schema` should write the SDL version of your GraphQL schema. More on it later as well.
|
||||
1. Output path to where `nexus` should write the generated TypeScript definition types derived from your schema. This is **mandatory** to benefit from Nexus' type-safety. We call this system "reflection". More on it later.
|
||||
1. Output path to where `nexus` should write the SDL version of your GraphQL schema. More on it later as well.
|
||||
|
||||
Finally, we'll setup the GraphQL server. We'll intentionally separate the server instantiation from the server listening to make testing easier later.
|
||||
|
||||
Create an `api/server.ts` file and add the following code to instantiate your GraphQL server
|
||||
Create `api/server.ts` and `api/index.ts` files and add the following code to instantiate your GraphQL server:
|
||||
|
||||
```ts
|
||||
```ts copy
|
||||
// api/server.ts
|
||||
import { ApolloServer } from 'apollo-server'
|
||||
import { schema } from './schema'
|
||||
|
|
@ -95,10 +116,8 @@ import { schema } from './schema'
|
|||
export const server = new ApolloServer({ schema })
|
||||
```
|
||||
|
||||
Then create an `api/app.ts` file and add the following to make the server listening
|
||||
|
||||
```ts
|
||||
// api/app.ts
|
||||
```ts copy
|
||||
// api/index.ts
|
||||
import { server } from './server'
|
||||
|
||||
server.listen().then(({ url }) => {
|
||||
|
|
@ -110,7 +129,7 @@ server.listen().then(({ url }) => {
|
|||
|
||||
Ok, with our entrypoint setup, let's boot up dev mode and see what happens.
|
||||
|
||||
```bash-symbol
|
||||
```bash-symbol copy
|
||||
npm run dev
|
||||
```
|
||||
|
||||
|
|
|
|||
|
|
@ -20,14 +20,12 @@ Before we get going we need a moment to introduce an important part of the Nexus
|
|||
|
||||
This partly explains why Nexus has a declarative API. It needs a way to run your app reliably at build time. Declarative APIs give Nexus a higher degree of control to do this. Declarative APIs also encode enough semantic value for Nexus to do the things it needs to.
|
||||
|
||||
It also explains the need for the `--transpile-only` flag passed to `ts-node-dev`. If you don't know what it is about, **it basically tells TypeScript not to typecheck your app**. Since `@nexus/schema` needs to be run in order to generate TypeScript types, we need to ensure that `@nexus/schema` won't ever be prevented from generating these types because of.. a type error.
|
||||
It also explains the need for the `--transpile-only` flag passed to `ts-node-dev`. If you don't know what it is about, **it basically tells TypeScript not to typecheck your app**. Since `nexus` needs to be run in order to generate TypeScript types, we need to ensure that `nexus` won't ever be prevented from generating these types because of a type error.
|
||||
|
||||
You might be (rightfully) wondering: "Wait, how am I supposed to benefit from Nexus' type-safety if I disable it in `ts-node-dev`... ?". For now, the answer to that is to use your IDE's type-checker. If your IDE/terminal don't have one, then manually run an additional `tsc` process.
|
||||
You might be (rightfully) wondering: "Wait, how am I supposed to benefit from Nexus' type-safety if I disable it in `ts-node-dev`... ?". For now, the answer to that is to use your IDE's type-checker. If your IDE/terminal doesn't have one, then manually run an additional `tsc` process.
|
||||
|
||||
Just remember the following though. You should _always_ have your `npm run dev` script running when you're working on your project _even_ when you're not intending to use your server (e.g. access the GraphQL Playground). If you forget to run `npm run dev` then you will not, for example, get the static typing experience that you expect in your resolvers.
|
||||
|
||||
> There are plans to run Nexus Reflection as a separate process integrated into your IDE. You can learn more about and track the feature here ([#949](https://github.com/graphql-nexus/nexus/issues/949)) *TODO CHANGE LINK TO A NEXUS SCHEMA ISSUE?*
|
||||
|
||||
## Model the domain
|
||||
|
||||
Let's get started with our blog schema by modeling some key entities in the domain. We'll begin with the concept of a `Post`. A post will represent a page in your blog. When not published, we'll call it a _draft_.
|
||||
|
|
@ -38,17 +36,17 @@ Your modeling work is going to start on the API layer as opposed to the database
|
|||
|
||||
Create a new module for your Post object at `api/graphql/Post.ts`. We _could_ write our whole schema within say `api/schema.ts` or `api/graphql.ts`, but modularizing your GraphQL type definitions can help scale your codebase. Neither approach is inherently wrong though, so do as you see you fit. For this tutorial we'll use the modular style.
|
||||
|
||||
```bash-symbol
|
||||
```bash-symbol copy
|
||||
mkdir api/graphql && touch api/graphql/Post.ts
|
||||
```
|
||||
|
||||
To create the `Post` object we'll import the `objectType` function from the `@nexus/schema` package. This will help you building a [GraphQL Object Types](https://graphql.org/graphql-js/object-types/).
|
||||
To create the `Post` object we'll import the `objectType` function from the `nexus` package. This will help you building a [GraphQL Object Types](https://graphql.org/graphql-js/object-types/).
|
||||
|
||||
<!-- prettier-ignore -->
|
||||
```ts
|
||||
// api/graphql/Post.ts
|
||||
|
||||
import { objectType } from '@nexus/schema'
|
||||
import { objectType } from 'nexus'
|
||||
|
||||
export const Post = objectType({
|
||||
name: 'Post', // <- Name of your type
|
||||
|
|
@ -77,7 +75,7 @@ Finally, we'll import this file and pass it down to `makeSchema`
|
|||
|
||||
```ts
|
||||
// api/schema.ts
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { join } from 'path'
|
||||
+ import * as types from './graphql'
|
||||
|
||||
|
|
@ -97,7 +95,7 @@ const schema = makeSchema({
|
|||
|
||||
```ts
|
||||
// api/schema.ts
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { join } from 'path'
|
||||
import * as types from './graphql'
|
||||
|
||||
|
|
@ -146,6 +144,8 @@ Your `Post` object is in place now but there's still no way for clients to read
|
|||
|
||||
We'll start by letting API clients read the drafts of your blog.
|
||||
|
||||
> NOTE: This should cause a static type error when you save the file. Don't worry, we'll fix it in a second!
|
||||
|
||||
<ParallelBlocks>
|
||||
|
||||
<block>
|
||||
|
|
@ -153,7 +153,7 @@ We'll start by letting API clients read the drafts of your blog.
|
|||
```ts
|
||||
// api/graphql/Post.ts // 1
|
||||
|
||||
import { extendType } from '@nexus/schema'
|
||||
import { extendType } from 'nexus'
|
||||
|
||||
export const PostQuery = extendType({
|
||||
type: 'Query', // 2
|
||||
|
|
@ -182,7 +182,7 @@ type Query {
|
|||
1. The Query object is a central place in your schema where many other types will appear. Like before with the modular GraphQL types decision we again can decide to be modular here. We could either create a new `api/graphql/Query.ts` module (not modular), or we could _collocate_ the exposure of Post object with its definition in `api/graphql/Post.ts` (modular). Staying consistent with before, we'll take the modular way.
|
||||
1. To achieve collocation in Nexus we'll use `schema.extendType`. Its API is _very_ similar to `schema.objectType` with the difference that the defined fields are merged into the _targeted_ type.
|
||||
1. `.nonNull` specifies that clients will always get a value for this field. By default, in Nexus, all "output types" (types returned by fields) are nullable. This is for [best practice reasons](https://graphql.org/learn/best-practices/#nullability). In this case though we indeed want to guarantee that a list will always be returned, never `null`.
|
||||
If you're ever dissatisfied with Nexus' defaults, not to worry, [you can change them](https://www.nexusjs.org/#/api/modules/main/exports/settings?id=schemanullableinputs).
|
||||
If you're ever dissatisfied with Nexus' defaults, not to worry, [you can change them](https://nexusjs.org/docs/api/make-schema#nonnulldefaults).
|
||||
1. `.list` augments the field's type spec, making it wrapped by a List type. Here, a `[Post]`.
|
||||
1. The first parameter specifies the field's name, here `drafts`
|
||||
1. `type: 'Post'` specifies what the field's type should be. Here, a `Post`
|
||||
|
|
@ -218,7 +218,7 @@ You'll see some feedback from your IDE that you're missing a `resolve` property.
|
|||
|
||||
```ts
|
||||
// api/graphql/Post.ts
|
||||
import { extendType } from '@nexus/schema'
|
||||
import { extendType } from 'nexus'
|
||||
// ...
|
||||
|
||||
export const PostQuery = extendType({
|
||||
|
|
@ -240,7 +240,7 @@ export const PostQuery = extendType({
|
|||
|
||||
```ts
|
||||
// api/graphql/Post.ts
|
||||
import { extendType } from '@nexus/schema'
|
||||
import { extendType } from 'nexus'
|
||||
// ...
|
||||
|
||||
export const PostQuery = extendType({
|
||||
|
|
@ -268,7 +268,7 @@ You can now open up your GraphQL playground and try the following query (left);
|
|||
|
||||
<block>
|
||||
|
||||
```graphql
|
||||
```graphql copy
|
||||
{
|
||||
drafts {
|
||||
id
|
||||
|
|
@ -286,7 +286,7 @@ You can now open up your GraphQL playground and try the following query (left);
|
|||
```json
|
||||
{
|
||||
"data": {
|
||||
"posts": [
|
||||
"drafts": [
|
||||
{
|
||||
"id": 1,
|
||||
"title": "Nexus",
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
---
|
||||
title: 3. Adding mutations to Your API
|
||||
title: 3. Adding mutations to your API
|
||||
---
|
||||
|
||||
## Overview
|
||||
|
|
@ -21,7 +21,7 @@ The GraphQL Context is a plain JavaScript object shared across all resolvers. Yo
|
|||
|
||||
So go ahead and create the database with its type definition.
|
||||
|
||||
```bash-symbol
|
||||
```bash-symbol copy
|
||||
touch api/db.ts
|
||||
```
|
||||
|
||||
|
|
@ -51,7 +51,7 @@ Now to expose it in our GraphQL context there is two things we need to do:
|
|||
|
||||
We'll begin by creating a new module to hold out the context and its type.
|
||||
|
||||
```bash-symbol
|
||||
```bash-symbol copy
|
||||
touch api/context.ts
|
||||
```
|
||||
|
||||
|
|
@ -110,7 +110,7 @@ The context passed to Apollo Server can either be a function or a plain JavaScri
|
|||
|
||||
For example, if a user is logged in to your application, it would be useful to have the information regarding the user available to all the resolvers and this information would have to be retrieved from your database or an external service. The code responsible for that database or service call would be placed in the function which is passed to Apollo Server as the context.
|
||||
|
||||
Finally, let's configure Nexus to know the type of our GraphQL context by adjusting the configuration of the `makeSchema` in our `api/app.ts`.
|
||||
Finally, let's configure Nexus to know the type of our GraphQL context by adjusting the configuration of the `makeSchema` in our `api/schema.ts`.
|
||||
|
||||
<TabbedContent tabs={['Diff', 'Code']}>
|
||||
|
||||
|
|
@ -118,7 +118,7 @@ Finally, let's configure Nexus to know the type of our GraphQL context by adjust
|
|||
|
||||
```ts
|
||||
// api/schema.ts
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { join } from 'path'
|
||||
import * as types from './graphql'
|
||||
|
||||
|
|
@ -130,7 +130,7 @@ export const schema = makeSchema({
|
|||
},
|
||||
+ contextType: { // 1
|
||||
+ module: join(__dirname, "./context.ts"), // 2
|
||||
+ alias: "ContextModule", // 3
|
||||
+ export: "Context", // 3
|
||||
+ },
|
||||
})
|
||||
```
|
||||
|
|
@ -141,7 +141,7 @@ export const schema = makeSchema({
|
|||
|
||||
```ts
|
||||
// api/schema.ts
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { join } from 'path'
|
||||
import * as types from './graphql'
|
||||
|
||||
|
|
@ -153,7 +153,7 @@ export const schema = makeSchema({
|
|||
},
|
||||
contextType: { // 1
|
||||
module: join(__dirname, "./context.ts"), // 2
|
||||
alias: "ContextModule", // 3
|
||||
export: "Context", // 3
|
||||
},
|
||||
})
|
||||
```
|
||||
|
|
@ -237,7 +237,6 @@ As before we will take the collocation approach.
|
|||
<!-- prettier-ignore -->
|
||||
```ts
|
||||
// api/graphql/Post.ts
|
||||
// ...
|
||||
|
||||
export const PostMutation = extendType({
|
||||
type: 'Mutation',
|
||||
|
|
@ -271,14 +270,14 @@ We need to get the client's input data to complete our resolver. This brings us
|
|||
|
||||
Let's revise our implementation with GraphQL arguments.
|
||||
|
||||
<TabbedContent tabs={['Diff', 'Code']}>
|
||||
<TabbedContent tabs={['Diff', 'Code', 'SDL']}>
|
||||
|
||||
<tab>
|
||||
|
||||
|
||||
```ts
|
||||
import { objectType, extendType, stringArg } from '@nexus/schema'
|
||||
+import { objectType, extendType, stringArg, nonNull } from '@nexus/schema'
|
||||
import { objectType, extendType } from 'nexus'
|
||||
+import { objectType, extendType, stringArg, nonNull } from 'nexus'
|
||||
|
||||
export const PostMutation = extendType({
|
||||
type: 'Mutation',
|
||||
|
|
@ -310,9 +309,8 @@ export const PostMutation = extendType({
|
|||
|
||||
<tab>
|
||||
|
||||
|
||||
```ts
|
||||
import { objectType, extendType, stringArg, nonNull } from '@nexus/schema'
|
||||
import { objectType, extendType, stringArg, nonNull } from 'nexus'
|
||||
|
||||
export const PostMutation = extendType({
|
||||
type: 'Mutation',
|
||||
|
|
@ -340,7 +338,7 @@ export const PostMutation = extendType({
|
|||
|
||||
</tab>
|
||||
|
||||
</TabbedContent>
|
||||
<tab>
|
||||
|
||||
```ts
|
||||
Mutation {
|
||||
|
|
@ -349,6 +347,10 @@ Mutation {
|
|||
}
|
||||
```
|
||||
|
||||
</tab>
|
||||
|
||||
</TabbedContent>
|
||||
|
||||
1. Add an `args` property to the field definition to define its args. Keys are arg names and values are type specifications.
|
||||
2. Use the Nexus helpers for defining an arg type. There is one such helper for every GraphQL scalar such as `intArg` and `booleanArg`. If you want to reference a type like some InputObject then use `arg({ type: "..." })`. You can use the helpers `nonNull` and `nullable` to adjust the nullability type of the arg. You can use the functional helper `list` to turn the arg into a list type too.
|
||||
3. In our resolver, access the args we specified above and pass them through to our custom logic. If you hover over the `args` parameter you'll see that Nexus has properly typed them including the fact that they cannot be undefined.
|
||||
|
|
@ -363,8 +365,8 @@ Before we wrap this chapter let's flush out our schema a bit more. We'll add a `
|
|||
|
||||
```ts
|
||||
// api/graphql/Post.ts
|
||||
-import { objectType, extendType, stringArg, nonNull } from '@nexus/schema'
|
||||
+import { objectType, extendType, stringArg, nonNull, intArg } from '@nexus/schema'
|
||||
-import { objectType, extendType, stringArg, nonNull } from 'nexus'
|
||||
+import { objectType, extendType, stringArg, nonNull, intArg } from 'nexus'
|
||||
|
||||
export const PostMutation = extendType({
|
||||
type: 'Mutation',
|
||||
|
|
@ -397,7 +399,7 @@ export const PostMutation = extendType({
|
|||
|
||||
```ts
|
||||
// api/graphql/Post.ts
|
||||
import { objectType, extendType, stringArg, nonNull, intArg } from '@nexus/schema'
|
||||
import { objectType, extendType, stringArg, nonNull, intArg } from 'nexus'
|
||||
|
||||
export const PostMutation = extendType({
|
||||
type: 'Mutation',
|
||||
|
|
@ -447,7 +449,7 @@ Then, we'll let API clients read these published posts.
|
|||
|
||||
```ts
|
||||
// api/graphql/Post.ts
|
||||
import { extendType } from '@nexus/schema'
|
||||
import { extendType } from 'nexus'
|
||||
|
||||
export const PostQuery = extendType({
|
||||
type: 'Query',
|
||||
|
|
@ -471,7 +473,7 @@ export const PostQuery = extendType({
|
|||
|
||||
```ts
|
||||
// api/graphql/Post.ts
|
||||
import { extendType } from '@nexus/schema'
|
||||
import { extendType } from 'nexus'
|
||||
|
||||
export const PostQuery = extendType({
|
||||
type: 'Query',
|
||||
|
|
@ -512,7 +514,7 @@ Great, now head on over to the GraphQL Playground and run this query (left). If
|
|||
|
||||
<block>
|
||||
|
||||
```graphql
|
||||
```graphql copy
|
||||
mutation {
|
||||
publish(draftId: 1) {
|
||||
id
|
||||
|
|
@ -551,7 +553,7 @@ Now, that published draft should be visible via the `posts` Query. Run this quer
|
|||
|
||||
<block>
|
||||
|
||||
```graphql
|
||||
```graphql copy
|
||||
query {
|
||||
posts {
|
||||
id
|
||||
|
|
|
|||
|
|
@ -4,11 +4,7 @@ title: 4. Testing your API
|
|||
|
||||
## Overview
|
||||
|
||||
So far you've been validating your work by manual interacting with the Playground. That might be reasonable at first (depending on your relationship to TDD) but it will not scale. At some point you are going to want automated testing. So in this chapter you're going to add some automated tests to your e-commerce project. You'll learn about:
|
||||
|
||||
- Nexus' approach to testing
|
||||
- Setting up a test environment
|
||||
- The `nexus/testing` module
|
||||
So far you've been validating your work by manual interacting with the Playground. That might be reasonable at first (depending on your relationship to TDD) but it will not scale. At some point you are going to want automated testing. So in this chapter you're going to add some automated tests to your e-commerce project.
|
||||
|
||||
## It's at the system level
|
||||
|
||||
|
|
@ -28,8 +24,8 @@ During this tutorial, you'll use the [Jest testing framework](https://jestjs.io/
|
|||
|
||||
First, install `jest` and accompanying tools.
|
||||
|
||||
```bash-symbol
|
||||
npm add --save-dev jest @types/jest ts-jest graphql-request get-port
|
||||
```bash-symbol copy
|
||||
npm install --save-dev jest @types/jest ts-jest graphql-request get-port@5.1.1
|
||||
```
|
||||
|
||||
Then, configure jest and npm scripts in your `package.json`
|
||||
|
|
@ -40,7 +36,7 @@ Then, configure jest and npm scripts in your `package.json`
|
|||
|
||||
```json
|
||||
"scripts": {
|
||||
"dev": "ts-node-dev --transpile-only --no-notify api/app",
|
||||
"dev": "ts-node-dev --transpile-only --no-notify api/index.ts",
|
||||
"build": "tsc",
|
||||
+ "generate": "ts-node --transpile-only api/schema",
|
||||
+ "test": "npm run generate && jest"
|
||||
|
|
@ -62,7 +58,7 @@ Then, configure jest and npm scripts in your `package.json`
|
|||
|
||||
```json
|
||||
"scripts": {
|
||||
"dev": "ts-node-dev --transpile-only --no-notify api/app",
|
||||
"dev": "ts-node-dev --transpile-only --no-notify api/index.ts",
|
||||
"build": "tsc",
|
||||
"generate": "ts-node --transpile-only api/schema",
|
||||
"test": "npm run generate && jest"
|
||||
|
|
@ -75,7 +71,7 @@ Then, configure jest and npm scripts in your `package.json`
|
|||
}
|
||||
},
|
||||
"testEnvironment": "node"
|
||||
}
|
||||
},
|
||||
```
|
||||
|
||||
</tab>
|
||||
|
|
@ -84,7 +80,7 @@ Then, configure jest and npm scripts in your `package.json`
|
|||
|
||||
Finally, create a `tests` folder at the root of your project and a `Post.test.ts` file inside it
|
||||
|
||||
```bash-symbol
|
||||
```bash-symbol copy
|
||||
mkdir tests && touch tests/Post.test.ts
|
||||
```
|
||||
|
||||
|
|
@ -92,11 +88,11 @@ mkdir tests && touch tests/Post.test.ts
|
|||
|
||||
To ease testing, we'll create a small utility that we'll call `createTestContext`, which is designed for running integration tests.
|
||||
|
||||
When run, it will boot your app in the same process as the test suite and expose an interface for your tests to interact with it. Jest runs each test suite in its own process, so if you have have say eight test suites running in parallel that means you'll have eight app processes running too.
|
||||
When run, it will boot your app in the same process as the test suite and expose an interface for your tests to interact with it. Jest runs each test suite in its own process, so if you have say eight test suites running in parallel that means you'll have eight app processes running too.
|
||||
|
||||
Create a `tests/__helpers.ts` module with the following contents.
|
||||
|
||||
```bash-symbol
|
||||
```bash-symbol copy
|
||||
touch tests/__helpers.ts
|
||||
```
|
||||
|
||||
|
|
@ -256,13 +252,13 @@ it('ensures that a draft can be created and published', async () => {
|
|||
|
||||
1. The test context exposes a GraphQL client at `ctx.client.request` that will help us run operations against our API. Here We're using it to send a publish mutation.
|
||||
2. This is the mutation from the end of last chapter.
|
||||
3. The result will be snapshoted inline allowing us to see the input and output collocated!
|
||||
3. The result will be snapshotted inline allowing us to see the input and output collocated!
|
||||
|
||||
## Try it out
|
||||
|
||||
Now run your tests and let's see the snapshots come to life! It should look similar to this:
|
||||
|
||||
```bash-symbol
|
||||
```bash-symbol copy
|
||||
npm run test
|
||||
```
|
||||
|
||||
|
|
@ -285,7 +281,7 @@ expect(result).toMatchInlineSnapshot(`
|
|||
Published draft snapshot
|
||||
|
||||
```ts
|
||||
// Snapshot that draft and expect `published` to be false
|
||||
// Snapshot that draft and expect `published` to be true
|
||||
expect(result).toMatchInlineSnapshot(`
|
||||
+ Object {
|
||||
+ "publish": Object {
|
||||
|
|
|
|||
|
|
@ -4,14 +4,10 @@ title: 5. Persisting data (via Prisma)
|
|||
|
||||
## Overview
|
||||
|
||||
So far we have been working with in-memory data while we learn about other parts of Nexus in a focused manner, but in this chapter we're going to put the focus squarely on data and show how Nexus can be used with a database. This marks an important step toward your blog app becoming more real. You'll learn about:
|
||||
So far we have been working with in-memory data while we learn about other parts of Nexus in a focused manner, but in this chapter we're going to put the focus squarely on data and show how Nexus can be used with a database. This marks an important step toward your blog app becoming more real.
|
||||
|
||||
- Prisma
|
||||
- Setting up a Postgres database locally
|
||||
|
||||
We're going to be using a database called Postgres and a tool called Prisma to interact with it.
|
||||
|
||||
Postgres is a well known open-source relational database. Prisma is a new way of working with databases that we'll learn more about in a moment.
|
||||
In this section, you'll learn how to add Prisma to your GraphQL API.
|
||||
Prisma is a new way of working with databases that we'll learn more about in a moment.
|
||||
|
||||
Its important to understand that Nexus does not _require_ these technology choices and _could_ actually be used with any database and abstractions over them (raw SQL, query builder, ORM..). However, Nexus is built by a team at Prisma (the company) and unsurprisingly there is great integration between its tools and Nexus.
|
||||
|
||||
|
|
@ -20,69 +16,51 @@ Its important to understand that Nexus does not _require_ these technology choic
|
|||
So, what _is_ Prisma? It is an open source database toolkit that consists of the following parts:
|
||||
|
||||
- **Prisma Client**: Auto-generated and type-safe query builder for Node.js & TypeScript
|
||||
- **Prisma Migrate** (experimental): Declarative data modeling & migration system
|
||||
- **Prisma Migrate** (Preview): Declarative data modeling & migration system
|
||||
- **Prisma Studio**: GUI to view and edit data in your database
|
||||
|
||||
At the heart of Prisma is the _Prisma Schema,_ a file usually called `schema.prisma`, that you will see later in this tutorial. It is a declarative file wherein using a domain specific language you encode your database schema, connection to the database, and more.
|
||||
Prisma currently supports 4 relational databases: MySQL, PostgreSQL, SQL Server and SQLite.
|
||||
|
||||
Prisma has great [docs](https://www.prisma.io/docs/understand-prisma/introduction) so definitely check them out at some point. For now you can stay in the flow of this tutorial if you want though. We're going to focus on Prisma Client.
|
||||
|
||||
## Connect to your database
|
||||
## Set up Prisma
|
||||
|
||||
Now that you know a bit about Prisma, let's get going! Do the following:
|
||||
|
||||
- Install the Prisma Client & the Prisma CLI
|
||||
- Install the Prisma client and CLI
|
||||
- Use it in your `api/schema.ts` module
|
||||
- Create your Prisma Schema
|
||||
- Create a `.env` file to store your database credentials
|
||||
- Connect to your database
|
||||
|
||||
like so:
|
||||
|
||||
```bash-symbol
|
||||
npm add @prisma/client && npm add --save-dev @prisma/cli
|
||||
```bash-symbol copy
|
||||
npm install @prisma/client
|
||||
npm install --save-dev prisma
|
||||
```
|
||||
|
||||
```bash-symbol
|
||||
Next, add Prisma to your project by creating your [Prisma schema](https://www.prisma.io/docs/concepts/components/prisma-schema/) file with the following command:
|
||||
|
||||
```bash-symbol copy
|
||||
npx prisma init
|
||||
```
|
||||
|
||||
Almost done, but we still need to setup a Postgres database for our app to connect to. There are a ton of ways to do this so we're just going to show the most straight forward cross-platform way we know how. First, make sure you have [docker installed](https://docs.docker.com/get-docker/). Then, simply run this command:
|
||||
The command creates a new directory called `prisma` which will contain a `schema.prisma` file and add a `.env` file at the root of your project.
|
||||
|
||||
```bash-symbol
|
||||
docker run --detach --publish 5432:5432 -e POSTGRES_PASSWORD=postgres --name nexus-tutorial-postgres postgres:10
|
||||
```
|
||||
For ease of set up, this guide will use SQLite. If you wish to use your preferred database, you can make the switch by simply changing the `provider` and `url` in your `schema.prisma` file.
|
||||
|
||||
That's it. You now have a Postgres server running.
|
||||
|
||||
If you prefer setting up your local Postgres another way go for it. If our suggest approach doesn't work for you, then checkout a few other approaches listed on the [Nexus recipes page](https://www.nexusjs.org/#/references/recipes?id=setting-up-postgresql).
|
||||
|
||||
Finally, in the `prisma/.env` file you've created before, replace `<postgres_connection_url>` with your actual database URL.
|
||||
|
||||
<TabbedContent tabs={['Diff', 'Code']}>
|
||||
<tab>
|
||||
|
||||
```diff
|
||||
-DATABASE_URL="postgresql://johndoe:randompassword@localhost:5432/mydb?schema=public"
|
||||
+DATABASE_URL="postgresql://postgres:postgres@localhost:5432/myapp"
|
||||
```
|
||||
|
||||
</tab>
|
||||
<tab>
|
||||
To connect to your database, you'll need to set the `url` field in the `datasource` block in your Prisma schema.
|
||||
Since the `url` is set via an environment variable, you will define it in `.env`.
|
||||
|
||||
```diff
|
||||
DATABASE_URL="postgresql://postgres:postgres@localhost:5432/myapp"
|
||||
```
|
||||
|
||||
|
||||
</tab>
|
||||
</TabbedContent>
|
||||
|
||||
<!-- **TODO: find a way to make sure their connection url is working**
|
||||
Confirm things are setup correctly by ...
|
||||
-->
|
||||
|
||||
## Create your database schema
|
||||
## Create your first database model
|
||||
|
||||
It is now time to replace our in-memory data with actual tables in our database. To do this we'll write models in our Prisma Schema.
|
||||
|
||||
|
|
@ -91,12 +69,12 @@ In chapters 2 and 3 we already began to model our blog domain with the GraphQL t
|
|||
<TabbedContent tabs={['Diff', 'Code']}>
|
||||
<tab>
|
||||
|
||||
```groovy diff
|
||||
```prisma diff
|
||||
// prisma/schema.prisma
|
||||
|
||||
datasource db {
|
||||
provider = "postgresql"
|
||||
url = env("DATABASE_URL")
|
||||
+ provider = "sqlite"
|
||||
+ url = "file:./dev.db"
|
||||
}
|
||||
|
||||
generator client {
|
||||
|
|
@ -114,12 +92,12 @@ generator client {
|
|||
</tab>
|
||||
<tab>
|
||||
|
||||
```groovy
|
||||
```prisma
|
||||
// prisma/schema.prisma
|
||||
|
||||
datasource db {
|
||||
provider = "postgresql"
|
||||
url = env("DATABASE_URL")
|
||||
provider = "sqlite"
|
||||
url = "file:./dev.db"
|
||||
}
|
||||
|
||||
generator client {
|
||||
|
|
@ -139,19 +117,12 @@ model Post {
|
|||
|
||||
With our database schema specified, we're now ready to proceed to our first database migration! To do that, we'll use the Prisma CLI.
|
||||
|
||||
Generate our migration files...
|
||||
|
||||
```bash-symbold
|
||||
npx prisma migrate save --experimental
|
||||
```bash-symbol copy
|
||||
npx prisma migrate dev --name init --preview-feature
|
||||
```
|
||||
|
||||
You'll be asked to create the database (use the default) and give a name to the migration (call it "init").
|
||||
|
||||
Then, apply the migration...
|
||||
|
||||
```bash-symbol
|
||||
npx prisma migrate up --experimental
|
||||
```
|
||||
This will create a database migration called `init`. Once a migration is complete, the Prisma CLI will create `dev.db` database and apply the changes against your database.
|
||||
Once the first migration is complete, the Prisma CLI will install `@prisma/client` package. In subsequent migrations, Prisma CLI will generate the Prisma Client.
|
||||
|
||||
## Access your database
|
||||
|
||||
|
|
@ -164,7 +135,7 @@ Now let's finally ditch our in-memory data! Let's replace it with the Prisma Cli
|
|||
// api/db.ts
|
||||
+import { PrismaClient } from '@prisma/client'
|
||||
|
||||
export const db = new PrismaClient()
|
||||
+export const db = new PrismaClient()
|
||||
|
||||
-export interface Post {
|
||||
- id: number
|
||||
|
|
@ -185,7 +156,7 @@ export const db = new PrismaClient()
|
|||
</tab>
|
||||
<tab>
|
||||
|
||||
```ts
|
||||
```ts copy
|
||||
// api/db.ts
|
||||
import { PrismaClient } from '@prisma/client'
|
||||
|
||||
|
|
@ -219,7 +190,7 @@ export const context = {
|
|||
</tab>
|
||||
<tab>
|
||||
|
||||
```ts
|
||||
```ts copy
|
||||
// api/context.ts
|
||||
import { db } from "./db";
|
||||
import { PrismaClient } from "@prisma/client"
|
||||
|
|
@ -236,11 +207,6 @@ export const context = {
|
|||
</tab>
|
||||
</TabbedContent>
|
||||
|
||||
Finally, generate the PrismaClient using the Prisma CLI
|
||||
|
||||
```bash-symbol
|
||||
npx prisma generate
|
||||
```
|
||||
|
||||
Let's now replace all our previous in-memory db interactions with calls to the Prisma Client
|
||||
|
||||
|
|
@ -300,15 +266,15 @@ export const PostMutation = extendType({
|
|||
draftId: nonNull(intArg()),
|
||||
},
|
||||
resolve(_root, args, ctx) {
|
||||
- let postToPublish = ctx.db.posts.find((p) => p.id === args.draftId)
|
||||
- let draftToPublish = ctx.db.posts.find((p) => p.id === args.draftId)
|
||||
|
||||
- if (!postToPublish) {
|
||||
- if (!draftToPublish) {
|
||||
- throw new Error('Could not find draft with id ' + args.draftId)
|
||||
- }
|
||||
|
||||
- postToPublish.published = true
|
||||
- draftToPublish.published = true
|
||||
|
||||
- return postToPublish
|
||||
- return draftToPublish
|
||||
|
||||
+ return ctx.db.post.update({
|
||||
+ where: { id: args.draftId },
|
||||
|
|
@ -325,7 +291,7 @@ export const PostMutation = extendType({
|
|||
</tab>
|
||||
<tab>
|
||||
|
||||
```ts
|
||||
```ts copy
|
||||
// api/graphql/Post.ts
|
||||
// ...
|
||||
|
||||
|
|
|
|||
|
|
@ -11,11 +11,11 @@ There's a couple of things you'll have to do in order to run integration tests a
|
|||
|
||||
## How does it work?
|
||||
|
||||
To perform integration testing against a real database, here are the high level steps we will follow _for every tests_:
|
||||
To perform integration testing against a real database, here are the high level steps we will follow _for every test_:
|
||||
|
||||
- Connect to a Postgres database. Most likely your dev database.
|
||||
- Connect to a SQLite database. Most likely your dev database.
|
||||
- Migrate our database schema to a randomly generated schema of that database. This ensures that every tests runs from a clean un-seeded database
|
||||
- Make the Prisma Client connect to that Postgres schema
|
||||
- Make the Prisma Client connect to that SQLite database
|
||||
- Run your test
|
||||
- Teardown the schema entirely
|
||||
|
||||
|
|
@ -23,10 +23,10 @@ To perform integration testing against a real database, here are the high level
|
|||
|
||||
To achieve some of the steps described above, we'll tweak our test context.
|
||||
|
||||
First, install the `pg` and `nanoid` packages
|
||||
First, install the `sqlite3` and `nanoid` packages
|
||||
|
||||
```bash
|
||||
npm add --save-dev pg @types/pg nanoid
|
||||
```bash copy
|
||||
npm install --save-dev sqlite3 @types/sqlite3
|
||||
```
|
||||
|
||||
Then, head to your `tests/__helpers.ts` file to add the following imports and code
|
||||
|
|
@ -41,9 +41,9 @@ import { ServerInfo } from "apollo-server";
|
|||
+import { execSync } from "child_process";
|
||||
import getPort, { makeRange } from "get-port";
|
||||
import { GraphQLClient } from "graphql-request";
|
||||
+import { nanoid } from "nanoid";
|
||||
+import { join } from "path";
|
||||
+import { Client } from "pg";
|
||||
+import { Database } from "sqlite3";
|
||||
+import { db } from "../api/db";
|
||||
import { server } from "../api/server";
|
||||
|
||||
type TestContext = {
|
||||
|
|
@ -97,42 +97,24 @@ function graphqlTestContext() {
|
|||
|
||||
+function prismaTestContext() {
|
||||
+ const prismaBinary = join(__dirname, "..", "node_modules", ".bin", "prisma");
|
||||
+ let schema = "";
|
||||
+ let databaseUrl = "";
|
||||
+ let prismaClient: null | PrismaClient = null;
|
||||
+
|
||||
+ return {
|
||||
+ async before() {
|
||||
+ // Generate a unique schema identifier for this test context
|
||||
+ schema = `test_${nanoid()}`;
|
||||
+ // Generate the pg connection string for the test schema
|
||||
+ databaseUrl = `postgres://postgres:postgres@localhost:5432/testing?schema=${schema}`;
|
||||
+
|
||||
+ // Set the required environment variable to contain the connection string
|
||||
+ // to our database test schema
|
||||
+ process.env.DATABASE_URL = databaseUrl;
|
||||
+
|
||||
+ // Run the migrations to ensure our schema has the required structure
|
||||
+ execSync(`${prismaBinary} migrate up --create-db --experimental`, {
|
||||
+ env: {
|
||||
+ ...process.env,
|
||||
+ DATABASE_URL: databaseUrl,
|
||||
+ },
|
||||
+ });
|
||||
+ execSync(`${prismaBinary} db push --preview-feature`,);
|
||||
+
|
||||
+ // Construct a new Prisma Client connected to the generated Postgres schema
|
||||
+ // Construct a new Prisma Client connected to the generated schema
|
||||
+ prismaClient = new PrismaClient();
|
||||
+
|
||||
+ return prismaClient;
|
||||
+ },
|
||||
+ async after() {
|
||||
+ // Drop the schema after the tests have completed
|
||||
+ const client = new Client({
|
||||
+ connectionString: databaseUrl,
|
||||
+ });
|
||||
+ await client.connect();
|
||||
+ await client.query(`DROP SCHEMA IF EXISTS "${schema}" CASCADE`);
|
||||
+ await client.end();
|
||||
+ const client = new Database(':memory:');
|
||||
|
||||
+ await client.close();
|
||||
+
|
||||
+ // Release the Prisma Client connection
|
||||
+ await prismaClient?.$disconnect();
|
||||
|
|
@ -144,16 +126,15 @@ function graphqlTestContext() {
|
|||
</tab>
|
||||
<tab>
|
||||
|
||||
```ts
|
||||
```ts copy
|
||||
// tests/__helpers.ts
|
||||
import { PrismaClient } from "@prisma/client";
|
||||
import { ServerInfo } from "apollo-server";
|
||||
import { execSync } from "child_process";
|
||||
import getPort, { makeRange } from "get-port";
|
||||
import { GraphQLClient } from "graphql-request";
|
||||
import { nanoid } from "nanoid";
|
||||
import { join } from "path";
|
||||
import { Client } from "pg";
|
||||
import { Database } from "sqlite3";
|
||||
import { db } from "../api/db";
|
||||
import { server } from "../api/server";
|
||||
|
||||
|
|
@ -208,42 +189,23 @@ function graphqlTestContext() {
|
|||
|
||||
function prismaTestContext() {
|
||||
const prismaBinary = join(__dirname, "..", "node_modules", ".bin", "prisma");
|
||||
let schema = "";
|
||||
let databaseUrl = "";
|
||||
let prismaClient: null | PrismaClient = null;
|
||||
|
||||
return {
|
||||
async before() {
|
||||
// Generate a unique schema identifier for this test context
|
||||
schema = `test_${nanoid()}`;
|
||||
// Generate the pg connection string for the test schema
|
||||
databaseUrl = `postgres://postgres:postgres@localhost:5432/testing?schema=${schema}`;
|
||||
|
||||
// Set the required environment variable to contain the connection string
|
||||
// to our database test schema
|
||||
process.env.DATABASE_URL = databaseUrl;
|
||||
|
||||
// Run the migrations to ensure our schema has the required structure
|
||||
execSync(`${prismaBinary} migrate up --create-db --experimental`, {
|
||||
env: {
|
||||
...process.env,
|
||||
DATABASE_URL: databaseUrl,
|
||||
},
|
||||
});
|
||||
execSync(`${prismaBinary} db push --preview-feature`,);
|
||||
|
||||
// Construct a new Prisma Client connected to the generated Postgres schema
|
||||
// Construct a new Prisma Client connected to the generated schema
|
||||
prismaClient = new PrismaClient();
|
||||
|
||||
return prismaClient;
|
||||
},
|
||||
async after() {
|
||||
// Drop the schema after the tests have completed
|
||||
const client = new Client({
|
||||
connectionString: databaseUrl,
|
||||
});
|
||||
await client.connect();
|
||||
await client.query(`DROP SCHEMA IF EXISTS "${schema}" CASCADE`);
|
||||
await client.end();
|
||||
const client = new Database(':memory:');
|
||||
|
||||
await client.close();
|
||||
|
||||
// Release the Prisma Client connection
|
||||
await prismaClient?.$disconnect();
|
||||
|
|
@ -257,12 +219,10 @@ function prismaTestContext() {
|
|||
|
||||
The `prismaTestContext` is in charge of a couple of things:
|
||||
|
||||
1. Migrate a randomly generated schema before each of your test. This ensure that your tests can add data to an "isolated" and clean database.
|
||||
1. Flush the migrated schema after each of your test
|
||||
1. Add an instance of a Prisma Client connected to the schema migrated specifically for your test
|
||||
|
||||
Make sure that the `databaseUrl` variable has the right credentials to connect to your own database.
|
||||
Leave the `/testing?schema=...` part though. This ensures, once again, that your tests will add data to your Postgres instance in a separate database called `testing` in a schema that randomly generated.
|
||||
1. Connect to an in-memory instance of the SQLite database
|
||||
2. Pushes the Prisma Schema to the database
|
||||
3. Generates a new Prisma Client
|
||||
4. Add an instance of a Prisma Client connected to the schema specifically for the test
|
||||
|
||||
## Updating our test
|
||||
|
||||
|
|
@ -337,10 +297,4 @@ expect(persistedData).toMatchInlineSnapshot(`
|
|||
|
||||
Congrats, you've performed your first real-world integration test. The fact that integration tests are completely decoupled from the implementation of your GraphQL API makes it a lot easier to maintain your test suite as you evolve your API. What matters is only the data that it produces, which also helps you cover your app a lot more than a single unit test.
|
||||
|
||||
About our app, it's starting to take shape but it's still lacking something pretty important in any application: authentication.
|
||||
|
||||
Come onto the next chapter to get that added to your app!
|
||||
|
||||
<ButtonLink color="dark" type="primary" href="/getting-started/tutorial/chapter-authentication">
|
||||
Next →
|
||||
</ButtonLink>
|
||||
This is the end of the tutorial. Thanks for trying it out and please share any feedback you have with us!
|
||||
|
|
|
|||
|
|
@ -1,7 +0,0 @@
|
|||
---
|
||||
title: 7. Authentication
|
||||
---
|
||||
|
||||
## Overview
|
||||
|
||||
That's it folks! More tutorial content is forthcoming. If you want to keep tabs on its status subscribe to issue [#904](https://github.com/graphql-nexus/nexus/issues/904).
|
||||
|
|
@ -49,7 +49,7 @@ Writing a GraphQL server with Nexus differs starkly to the traditional schema-fi
|
|||
Refactoring the `Post` example above to Nexus would look like this:
|
||||
|
||||
```ts
|
||||
import { objectType, queryType, makeSchema } from '@nexus/schema'
|
||||
import { objectType, queryType, makeSchema } from 'nexus'
|
||||
|
||||
const Post = objectType({
|
||||
name: 'Post',
|
||||
|
|
@ -63,6 +63,7 @@ const Post = objectType({
|
|||
const Query = queryType({
|
||||
definition(t) {
|
||||
t.list.field('posts', {
|
||||
type: "Post",
|
||||
resolve: () => [
|
||||
{
|
||||
id: '1',
|
||||
|
|
@ -93,7 +94,7 @@ There are numerous benefits to taking a code-first approach with Nexus:
|
|||
|
||||
When building a schema-first GraphQL API, it is common to start out by placing all type definitions and resolvers in a single file. When both the schema and the resolvers live next to one another, it's fairly straightforward to work in both at the same time.
|
||||
|
||||
As the application grows, however, it is most often desired to move parts of the schema into their own separate modules and files. It's at this point that working on a GraphQL API becomes a bit more tedious. With this modularization comes the need to switch back and forth between the Schema Definition Language and JavaScript/TypeScript to write the resolvers. Not only does one need to constantly switch between files, they also need to do a context switch mentally to work between the two langauges.
|
||||
As the application grows, however, it is most often desired to move parts of the schema into their own separate modules and files. It's at this point that working on a GraphQL API becomes a bit more tedious. With this modularization comes the need to switch back and forth between the Schema Definition Language and JavaScript/TypeScript to write the resolvers. Not only does one need to constantly switch between files, they also need to do a context switch mentally to work between the two languages.
|
||||
|
||||
With Nexus, our schema and its resolvers are always defined together. Nexus also allows us to write everything in a common language. This allows us to side-step the co-location/context switching issue altogether and helps us to be more productive, even as our applications grow to be quite large.
|
||||
|
||||
|
|
@ -133,7 +134,7 @@ A downside of the schema-first approach is the need to repeat yourself in schema
|
|||
|
||||
### Defining enums
|
||||
|
||||
When defining an enum using the schema-first approach, the enum must first be defined in the schema definition languange:
|
||||
When defining an enum using the schema-first approach, the enum must first be defined in the schema definition language:
|
||||
|
||||
```graphql
|
||||
enum UserRole {
|
||||
|
|
@ -158,7 +159,7 @@ Keeping both of these in sync is tedious and error phrone, especially when files
|
|||
Refactoring the above to Nexus would look like this:
|
||||
|
||||
```ts
|
||||
import { enumType } from '@nexus/schema'
|
||||
import { enumType } from 'nexus'
|
||||
|
||||
export enum UserRole {
|
||||
ADMIN = 'ADMIN',
|
||||
|
|
@ -197,7 +198,7 @@ The schema definition languange requires that the `Post` type repeats all the fi
|
|||
With Nexus the repetitive work is kept to a bare minimum:
|
||||
|
||||
```ts
|
||||
import { interfaceType } from '@nexus/schema'
|
||||
import { interfaceType } from 'nexus'
|
||||
|
||||
const Node = interfaceType({
|
||||
name: 'Node',
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ tocDepth: 2
|
|||
|
||||
## Overview
|
||||
|
||||
This is the Nexus schema component guide. Here you will find concepts explained and a survey of how to use the API. If you are not familiar with Nexus this is a good document to read. If you are familiar, then API Docs may be of more use to you.
|
||||
This is the Nexus component guide. Here you will find concepts explained and a survey of how to use the API. If you are not familiar with Nexus this is a good document to read. If you are familiar, then API Docs may be of more use to you.
|
||||
|
||||
## GraphQL type builders
|
||||
|
||||
|
|
@ -134,9 +134,9 @@ objectType({
|
|||
definition(t) {
|
||||
t.id('a')
|
||||
t.list.id('b')
|
||||
t.nullable.list.id('c')
|
||||
t.list.nullable.id('d')
|
||||
t.nullable.list.nullable.id('e')
|
||||
t.nonNull.list.id('c')
|
||||
t.list.nonNull.id('d')
|
||||
t.nonNull.list.nonNull.id('e')
|
||||
},
|
||||
})
|
||||
```
|
||||
|
|
@ -144,10 +144,10 @@ objectType({
|
|||
```graphql
|
||||
type Alpha {
|
||||
a: ID
|
||||
b: [ID!]!
|
||||
c: [ID!]
|
||||
d: [ID]!
|
||||
e: [ID]
|
||||
b: [ID]
|
||||
c: [ID]!
|
||||
d: [ID!]
|
||||
e: [ID!]!
|
||||
}
|
||||
```
|
||||
|
||||
|
|
@ -283,4 +283,4 @@ However, the data that flows through your resolvers can be completely different
|
|||
|
||||
If that's the case, you will need to tell Nexus what the shape of this data is thanks to the ***Source Types***.
|
||||
|
||||
[You can read more about them here](/guides/source-types).
|
||||
[You can read more about them here](/guides/source-types).
|
||||
|
|
|
|||
|
|
@ -18,13 +18,13 @@ To understand the concept better, let's assume the following GraphQL query:
|
|||
|
||||
Here is an example of resolution for that query as it would be seen roughly from a GraphQL type _only_ point of view.
|
||||
|
||||

|
||||

|
||||
|
||||
When a field's type is an object, then the field's resolver returns a Source Type. Concretely this might for example be a plain JavaScript object containing node/row/document data from a database call. This Source Type data is in turn passed down to all the object type's own field resolvers.
|
||||
|
||||
Here is the above diagram updated to include Source Types now.
|
||||
|
||||

|
||||

|
||||
|
||||
Here is a step-by-step breakdown of what is going on:
|
||||
|
||||
|
|
@ -57,11 +57,12 @@ Hopefully you can see how the GraphQL types seen by the client are distinct from
|
|||
<summary>See code implementation</summary>
|
||||
|
||||
```ts
|
||||
import { queryType, objectType } from '@nexus/schema'
|
||||
import { queryType, objectType } from 'nexus'
|
||||
|
||||
export const Query = queryType({
|
||||
definition(t) {
|
||||
t.user({
|
||||
t.field('user', {
|
||||
type: 'User',
|
||||
args: {
|
||||
id: nonNull(idArg()),
|
||||
},
|
||||
|
|
@ -79,7 +80,7 @@ export interface UserSourceType {
|
|||
|
||||
export const User = objectType({
|
||||
name: 'User',
|
||||
rootTyping: {
|
||||
sourceType: {
|
||||
path: __filename,
|
||||
name: 'UserSourceType'
|
||||
},
|
||||
|
|
@ -207,7 +208,7 @@ export interface Comment {
|
|||
|
||||
// ./schema.ts
|
||||
|
||||
import { makeSchema, objectType, queryType } from '@nexus/schema'
|
||||
import { makeSchema, objectType, queryType } from 'nexus'
|
||||
import * as path from 'path'
|
||||
|
||||
const User = objectType({
|
||||
|
|
@ -295,7 +296,7 @@ export class CommentModel {
|
|||
}
|
||||
|
||||
// schema.ts
|
||||
import { makeSchema, objectType, queryType } from '@nexus/schema'
|
||||
import { makeSchema, objectType, queryType } from 'nexus'
|
||||
import * as path from 'path'
|
||||
|
||||
const User = objectType({
|
||||
|
|
@ -370,7 +371,7 @@ const schema = makeSchema({
|
|||
|
||||
If you happen to have Source Types names that can't be matched against your GraphQL Object type names using a RegEx, there are two solutions.
|
||||
|
||||
The first solution is especially useful when most of your types _can be matched using a RegEx_ but you only have a couple of types that can't. In that case, the `backingTypesMap` can help you.
|
||||
The first solution is especially useful when most of your types _can be matched using a RegEx_ but you only have a couple of types that can't. In that case, the `mapping` can help you.
|
||||
|
||||
When provided, it will be used for the Source Types rather than the auto-resolve mechanism of `sources`. It's also useful as an override for one-off cases or for scalar Source Types.
|
||||
|
||||
|
|
@ -384,7 +385,7 @@ export class SomeRandomName {
|
|||
}
|
||||
|
||||
// schema.ts
|
||||
import { makeSchema, objectType } from '@nexus/schema'
|
||||
import { makeSchema, objectType } from 'nexus'
|
||||
import * as path from 'path'
|
||||
|
||||
const User = objectType({
|
||||
|
|
@ -404,7 +405,7 @@ const schema = makeSchema({
|
|||
// ^----------------- Name used as alias for Nexus to import your Source Types.
|
||||
// eg: import * as <source> from <alias>
|
||||
}],
|
||||
backingTypesMap: {
|
||||
mapping: {
|
||||
User: 'db.SomeRandomName'
|
||||
// ^-----^------^---------- GraphQL type name
|
||||
// |------|---------- Alias of the source where the Source Type is defined
|
||||
|
|
@ -425,7 +426,7 @@ That being said, if you happen to have some Source Types that are not picked up
|
|||
Nexus will output debug logs, giving your detailed information about which Source Types were found, which were not, and why.
|
||||
|
||||
```ts
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
|
||||
const schema = makeSchema({
|
||||
// ...
|
||||
|
|
@ -445,10 +446,10 @@ We typically see two use-cases for using the local configuration of Source Types
|
|||
- When your Source Type names can't be matched against your GraphQL Object type names
|
||||
- When you simply prefer keeping your Source Types next to your Object type definition
|
||||
|
||||
To do so, you can use the `rootTyping` property as explained below:
|
||||
To do so, you can use the `sourceType` property as explained below:
|
||||
|
||||
```ts
|
||||
import { objectType, queryType } from '@nexus/schema'
|
||||
import { objectType, queryType } from 'nexus'
|
||||
|
||||
export interface MyDBUser {
|
||||
// | ^-------------------- Create your Source Type
|
||||
|
|
@ -460,10 +461,10 @@ export interface MyDBUser {
|
|||
|
||||
export const User = objectType({
|
||||
name: 'User',
|
||||
rootTyping: {
|
||||
path: __filename,
|
||||
sourceType: {
|
||||
module: __filename,
|
||||
// ^---------------------- Tell Nexus where the Source Type is.
|
||||
name: 'MyDBUser'
|
||||
export: 'MyDBUser'
|
||||
// ^---------------------- Tell Nexus the name of the exported Source Type.
|
||||
},
|
||||
definition(t) {
|
||||
|
|
|
|||
|
|
@ -149,7 +149,8 @@ The Centralized strategy allows you to discriminate your union member types in a
|
|||
const SearchResult = unionType({
|
||||
name: 'SearchResult',
|
||||
resolveType(data) {
|
||||
const __typename = data.album ? 'Song' : data.rating ? 'Movie' : data.width ? 'Photo' : null
|
||||
const __typename =
|
||||
'album' in data ? 'Song' : 'rating' in data ? 'Movie' : 'width' in data ? 'Photo' : null
|
||||
|
||||
if (!__typename) {
|
||||
throw new Error(`Could not resolve the type of data passed to union type "SearchResult"`)
|
||||
|
|
@ -188,13 +189,8 @@ const Query = queryType({
|
|||
},
|
||||
resolve(root, args, ctx) {
|
||||
return ctx.db.search(args.pattern).map((result) => {
|
||||
const __typename = result.album
|
||||
? 'Song'
|
||||
: result.rating
|
||||
? 'Movie'
|
||||
: result.width
|
||||
? 'Photo'
|
||||
: null
|
||||
const __typename =
|
||||
'album' in data ? 'Song' : 'rating' in data ? 'Movie' : 'width' in data ? 'Photo' : null
|
||||
|
||||
if (!__typename) {
|
||||
throw new Error(
|
||||
|
|
@ -236,13 +232,13 @@ const Query = queryType({
|
|||
})
|
||||
```
|
||||
|
||||
In a serious/large application with a model layer in the codebase its likely this kind of logic would not live in your resolvers at all.
|
||||
In a serious/large application with a model layer in the codebase it's likely this kind of logic would not live in your resolvers at all.
|
||||
|
||||
Like with the Centralized strategy Nexus leverages TypeScript to ensure your implementation is correct.
|
||||
|
||||
1. The resolver return type for fields whose type is a union will ensure all returned data includes a `__typename` field.
|
||||
2. For a given union type, if all fields that are typed as it have their resolvers returning data with `__typename` then back on the union type `resolveType` will be optional.
|
||||
3. Nexus is smart about what it needs to be satisfied by `__typename` presence. Rather than being a requirement of the model type, it is a requirement of the model type in resolver cases under the union type. For example note below how the `Photo` model type is not required to include `__typename` under the `photos` Query type field:
|
||||
3. Nexus is smart about when it needs to be satisfied by `__typename` presence. Rather than being a requirement of the model type, it is a requirement of the model type in resolver cases under the union type. For example note below how the `Photo` model type is not required to include `__typename` under the `photos` Query type field:
|
||||
|
||||
```ts
|
||||
const Query = queryType({
|
||||
|
|
@ -273,7 +269,7 @@ Like with the Centralized strategy Nexus leverages TypeScript to ensure your imp
|
|||
})
|
||||
```
|
||||
|
||||
Beware that when this strategy is enabled the `abstractTypeRuntimeChecks` feature will automatically be disabled. This is because it is not practical at runtime to find out if resolvers will return objects that include the `__typename` field. This trade-off can be acceptable since the runtime checks are a redundant safety measure over the static type checks. So as long as you are not ignoring static errors related to Nexus' abstract type type checks then you then you should still have a safe implementation.
|
||||
Beware that when this strategy is enabled the `abstractTypeRuntimeChecks` feature will automatically be disabled. This is because it is not practical at runtime to find out if resolvers will return objects that include the `__typename` field. This trade-off can be acceptable since the runtime checks are a redundant safety measure over the static type checks. So as long as you are not ignoring static errors related to Nexus' abstract type type checks then you should still have a safe implementation.
|
||||
|
||||
#### Modular Strategy (`isTypeOf`)
|
||||
|
||||
|
|
@ -332,7 +328,7 @@ Like with the Centralized and DMF strategies Nexus leverages TypeScript to ensur
|
|||
Nexus enables you to pick the strategy you want to use. By default only the Centralized strategy is enabled. You can pick your strategies in the `makeSchema` configuration.
|
||||
|
||||
```ts
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
|
||||
makeSchema({
|
||||
features: {
|
||||
|
|
@ -346,12 +342,12 @@ makeSchema({
|
|||
})
|
||||
```
|
||||
|
||||
Nexus enables enabling/disabling strategies because having them all enabled at can lead to a confusing excess of type errors when there is an invalid implementation of an abstract type. Nexus doesn't force you to pick only one strategy, however it does consider using multiple strategies sightly more advanced. Refer to the [Multiple Strategies](#multiple-strategies) section for details.
|
||||
Nexus enables enabling/disabling strategies because having them all enabled at can lead to a confusing excess of type errors when there is an invalid implementation of an abstract type. Nexus doesn't force you to pick only one strategy, however it does consider using multiple strategies slightly more advanced. Refer to the [Multiple Strategies](#multiple-strategies) section for details.
|
||||
|
||||
When you customize the strategy settings all strategies become disabled except for those that you opt into. For example in the following:
|
||||
|
||||
```ts
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
|
||||
makeSchema({
|
||||
features: {
|
||||
|
|
@ -407,7 +403,7 @@ In addition to giving typings for static type checks Nexus also performs runtime
|
|||
|
||||
Runtime checks are automatically enabled. In development they will be a warning but in production they will be a thrown error. This way your development flow will not be unduly interrupted but your e.g. deployment pipeline in CI will be halted helping ensure you ship correct code to your users.
|
||||
|
||||
If ever you need to diable this runtime check you can disable the feature like so:
|
||||
If ever you need to disable this runtime check you can disable the feature like so:
|
||||
|
||||
```ts
|
||||
makeSchema({
|
||||
|
|
@ -436,7 +432,7 @@ Here is a summary of the effects:
|
|||
| DMF & Modular | `*` `__typename` required _unless_ `isTypeOf` implemented on all member types of the abstract type. |
|
||||
| DMF & Modular & centralized | `*` `__typename` required _unless_ `isTypeOf` implemented on all member types of the abstract type _or_ `resolveType` on the abstract type. |
|
||||
|
||||
`*` Nexus cannot require `resolveType`/`isTypeOf` even though it _should_ becuase it cannot statically detect when you have implemented `__typename`.
|
||||
`*` Nexus cannot require `resolveType`/`isTypeOf` even though it _should_ because it cannot statically detect when you have implemented `__typename`.
|
||||
|
||||
Here is a code example:
|
||||
|
||||
|
|
@ -558,7 +554,7 @@ objectType({
|
|||
|
||||
> **Local Abstract Type Settings in the Future?**
|
||||
|
||||
Currently Nexus only supports global abstract type strategy settings. In the future however ([#623](https://github.com/graphql-nexus/schema/issues/623)) there may be ways to enable a particular strategy for only a subset of your schema. This way you could for example express that `__typename` is required in the returned model data of resolvers for one abstract type but require all other objects whom are members of _other_ abstract types to implement `isTypeOf`.
|
||||
Currently Nexus only supports global abstract type strategy settings. In the future however ([#623](https://github.com/graphql-nexus/nexus/issues/623)) there may be ways to enable a particular strategy for only a subset of your schema. This way you could for example express that `__typename` is required in the returned model data of resolvers for one abstract type but require all other objects whom are members of _other_ abstract types to implement `isTypeOf`.
|
||||
|
||||
##### _At Runtime_
|
||||
|
||||
|
|
@ -574,7 +570,7 @@ The default `resolveType` implementation is actually to apply the other strategi
|
|||
|
||||
### Interface Types in Theory
|
||||
|
||||
Interfaces allow you to define a set of fields that you can then use across objects in your schema to enforce that they all have the fields defined in the interface. Interfaces also act as a form of polymorphism at runtime. You can make a field's type be an interface and may thus then return any type that implements the interface. To illustrate the point we'll appropiate the schema that we used to show off union types.
|
||||
Interfaces allow you to define a set of fields that you can then use across objects in your schema to enforce that they all have the fields defined in the interface. Interfaces also act as a form of polymorphism at runtime. You can make a field's type be an interface and may thus then return any type that implements the interface. To illustrate the point we'll appropriate the schema that we used to show off union types.
|
||||
|
||||
```graphql
|
||||
interface Media {
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ export const UserConnectionTypes = connectionType('User')
|
|||
Where `connectionType` is really just a wrapper creating two `objectTypes`:
|
||||
|
||||
```ts
|
||||
import { core, objectType } from '@nexus/schema'
|
||||
import { core, objectType } from 'nexus'
|
||||
|
||||
export function connectionType(name: core.AllOutputTypes) {
|
||||
const Connection = objectType({
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@ A few tips when using Nexus to build out a schema:
|
|||
|
||||
## Configure your development server to auto-restart
|
||||
|
||||
The development experience works best when you are using a tool like [Nodemon](https://github.com/remy/nodemon) to restart your application as the schema changes. The GraphQL schema artifact will automatically regenerate when the server restarts in development mode. Check the [/examples](https://github.com/graphql-nexus/schema/tree/develop/examples) to see how they are setup to auto-restart.
|
||||
The development experience works best when you are using a tool like [Nodemon](https://github.com/remy/nodemon) to restart your application as the schema changes. The GraphQL schema artifact will automatically regenerate when the server restarts in development mode. Check the [/examples](https://github.com/graphql-nexus/nexus/tree/main/examples) to see how they are setup to auto-restart.
|
||||
|
||||
## VSCode: Configuring a keyboard shortcut for "Go to Type Definition"
|
||||
|
||||
|
|
|
|||
|
|
@ -44,6 +44,6 @@ A **field type** is the valid return value used to a field on an object type. In
|
|||
|
||||
### Configuring our types
|
||||
|
||||
The [Ghost Example](https://github.com/graphql-nexus/schema/blob/develop/examples/ghost/src/ghost-schema.ts) is the best to look at for an example of how we're able to capture the types from existing runtime objects or definitions and merge them with our schema.
|
||||
The [Ghost Example](https://github.com/graphql-nexus/nexus/blob/main/examples/ghost/src/ghost-schema.ts) is the best to look at for an example of how we're able to capture the types from existing runtime objects or definitions and merge them with our schema.
|
||||
|
||||
The [makeSchema](/api/make-schema) takes several options which helps us find the types we need to import into our generated schema, and customize where these generated types are output. Read more about the API [here](/api/make-schema).
|
||||
|
|
|
|||
|
|
@ -28,18 +28,3 @@ Each public API is documented below, feel free to open a PR with more examples/c
|
|||
- [extendType / extendInputType](/api/extend-type)
|
||||
- [mutationField](/api/mutation-field)
|
||||
- [queryField](/api/query-field)
|
||||
|
||||
## Resolving: Inline Function
|
||||
|
||||
One common idiom in GraphQL is exposing fields that mask or rename the property name on the backing object. GraphQL Nexus makes this simple by allowing a function as the second parameter to any built-in scalar resolver function.
|
||||
|
||||
```ts
|
||||
const User = objectType({
|
||||
name: 'User',
|
||||
definition(t) {
|
||||
t.id('id', o => o.user_id)
|
||||
t.string('name', o => o.user_name)
|
||||
t.string('description', o => o.user_description)
|
||||
},
|
||||
})
|
||||
```
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@ codeStyle: true
|
|||
## objectType
|
||||
|
||||
```ts
|
||||
objectType(typeName: string, fn: ObjectDefinitionBlock): NexusObjectType
|
||||
objectType(config: ObjectDefinitionBlock): NexusObjectType
|
||||
```
|
||||
|
||||
The most basic components of a GraphQL schema are object types, a type you can fetch from your schema, with fields:
|
||||
|
|
@ -17,7 +17,7 @@ const User = objectType({
|
|||
definition(t) {
|
||||
t.int('id', { description: 'Id of the user' })
|
||||
t.string('fullName', { description: 'Full name of the user' })
|
||||
t.field('status', { type: 'StatusEnum' })
|
||||
t.field('status', { type: StatusEnum })
|
||||
t.list.field('posts', {
|
||||
type: Post, // or "Post"
|
||||
resolve(root, args, ctx) {
|
||||
|
|
@ -46,4 +46,4 @@ const StatusEnum = enumType({
|
|||
|
||||
`queryType` / `mutationType` are shorthand for the root types.
|
||||
|
||||
Check the type-definitions or [the examples](https://github.com/graphql-nexus/schema/tree/develop/examples) for a full illustration of the various options of `objectType`, or feel free to open a PR on the docs to help document!
|
||||
Check the type-definitions or [the examples](https://github.com/graphql-nexus/nexus/tree/main/examples) for a full illustration of the various options of `objectType`, or feel free to open a PR on the docs to help document!
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@ import { ApolloServer } from 'apollo-server-express'
|
|||
import express from 'express'
|
||||
import * as HTTP from 'http'
|
||||
import * as path from 'path'
|
||||
import { makeSchema, subscriptionType } from '@nexus/schema'
|
||||
import { makeSchema, subscriptionType } from 'nexus'
|
||||
|
||||
const schema = makeSchema({
|
||||
shouldExitAfterGenerateArtifacts:
|
||||
|
|
|
|||
|
|
@ -20,4 +20,4 @@ const MediaType = unionType({
|
|||
})
|
||||
```
|
||||
|
||||
Check the type-definitions or [the examples](https://github.com/graphql-nexus/schema/tree/develop/examples) for a full illustration of the various options for `unionType`, or feel free to open a PR on the docs to help document!
|
||||
Check the type-definitions or [the examples](https://github.com/graphql-nexus/nexus/tree/main/examples) for a full illustration of the various options for `unionType`, or feel free to open a PR on the docs to help document!
|
||||
|
|
|
|||
|
|
@ -64,4 +64,15 @@ const SomeObject = objectType({
|
|||
})
|
||||
```
|
||||
|
||||
Check the type-definitions or [the examples](https://github.com/graphql-nexus/schema/tree/develop/examples) for a full illustration of the various options for `scalarType`, or feel free to open a PR on the docs to help document!
|
||||
Check the type-definitions or [the examples](https://github.com/graphql-nexus/nexus/tree/main/examples) for a full illustration of the various options for `scalarType`, or feel free to open a PR on the docs to help document!
|
||||
|
||||
|
||||
## Pass scalar to schema generation
|
||||
It's important to list the scalar in the `types` attribute of `makeSchema`
|
||||
|
||||
```ts
|
||||
const schema = makeSchema({
|
||||
types: [GQLDate] // Add Scalar to Array
|
||||
})
|
||||
```
|
||||
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ codeStyle: true
|
|||
|
||||
## interfaceType
|
||||
|
||||
[GraphQL Docs for Interface Types](https://graphql.org/learn/schema/#input-types)
|
||||
[GraphQL Docs for Interface Types](https://graphql.org/learn/schema/#interfaces)
|
||||
|
||||
In Nexus, you do not need to redefine the interface fields on the
|
||||
implementing object types, instead you may use `.implements(interfaceName)`
|
||||
|
|
|
|||
|
|
@ -30,4 +30,4 @@ const Episode = enumType({
|
|||
})
|
||||
```
|
||||
|
||||
Check the type-definitions or [the examples](https://github.com/graphql-nexus/schema/tree/develop/examples) for a full illustration of the various options of `enumType`, or feel free to open a PR on the docs to help document!
|
||||
Check the type-definitions or [the examples](https://github.com/graphql-nexus/nexus/tree/main/examples) for a full illustration of the various options of `enumType`, or feel free to open a PR on the docs to help document!
|
||||
|
|
|
|||
|
|
@ -10,11 +10,31 @@ codeStyle: true
|
|||
Defines a complex object which can be passed as an input value.
|
||||
|
||||
```ts
|
||||
export const InputType = inputObjectType({
|
||||
name: 'InputType',
|
||||
import { extendType, inputObjectType } from 'nexus'
|
||||
|
||||
export const CommentInputType = inputObjectType({
|
||||
name: 'CommentInputType',
|
||||
definition(t) {
|
||||
t.nonNull.string('key')
|
||||
t.int('answer')
|
||||
t.nonNull.int('userId')
|
||||
t.nonNull.string('body')
|
||||
}
|
||||
})
|
||||
|
||||
export const CommentMutation = extendType({
|
||||
type: 'Mutation',
|
||||
definition(t) {
|
||||
t.field('createComment', {
|
||||
type: 'Comment',
|
||||
args: { data: CommentInputType },
|
||||
resolve(_root, args, ctx) {
|
||||
return ctx.prisma.comment.create({
|
||||
data: {
|
||||
user_id: args.userId,
|
||||
body: args.body,
|
||||
}
|
||||
})
|
||||
}
|
||||
})
|
||||
},
|
||||
})
|
||||
```
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ codeStyle: true
|
|||
Defines an argument that can be used in any object or interface type. Args can be reused in multiple locations, and it can be convenient to create your own wrappers around arguments.
|
||||
|
||||
```ts
|
||||
import { intArg, core } from '@nexus/schema'
|
||||
import { intArg, core } from 'nexus'
|
||||
|
||||
function requiredInt(opts: core.ScalarArgConfig<number>) {
|
||||
return nonNull(intArg({ ...opts }))
|
||||
|
|
|
|||
|
|
@ -10,12 +10,12 @@ codeStyle: true
|
|||
Types (including arguments) can be passed into the `list()` function to wrap them in a list type.
|
||||
|
||||
```ts
|
||||
import { queryType, stringArg, list } from '@nexus/schema'
|
||||
import { queryType, stringArg, list } from 'nexus'
|
||||
|
||||
queryType({
|
||||
definition(t) {
|
||||
t.field('tags', {
|
||||
type: list('String') // -> [String]
|
||||
type: list('String'), // -> [String]
|
||||
args: {
|
||||
ids: list(stringArg()) // or list('String') -> [String]
|
||||
},
|
||||
|
|
@ -45,7 +45,7 @@ Below are some usage examples of `list()`:
|
|||
Types (including arguments) can be passed into the `nonNull()` function to mark them as non-null.
|
||||
|
||||
```ts
|
||||
import { queryType, stringArg, nonNull } from '@nexus/schema'
|
||||
import { queryType, stringArg, nonNull } from 'nexus'
|
||||
|
||||
queryType({
|
||||
definition(t) {
|
||||
|
|
@ -73,7 +73,7 @@ Below are some more usage examples of `nonNull`:
|
|||
| `list(nonNull('String'))` | `[String!]` | `[String!]` |
|
||||
| `nonNull(list(nonNull('String')))` | `[String!]!` | `[String!]!` |
|
||||
| `nonNull(nonNull('String'))` | `String!` | `String!` |
|
||||
| `nonNull(nullable('String'))` | `String! | `String! |
|
||||
| `nonNull(nullable('String'))` | `String!` | `String!` |
|
||||
|
||||
## nullable
|
||||
|
||||
|
|
@ -89,7 +89,7 @@ When types are non-nullable by default:
|
|||
To revert the non-nullability, we can use the `nullable()` helper to mark Types and Arguments as nullable.
|
||||
|
||||
```ts
|
||||
import { queryType, stringArg, nonNull } from '@nexus/schema'
|
||||
import { queryType, stringArg, nonNull } from 'nexus'
|
||||
|
||||
queryType({
|
||||
nonNullDefaults: {
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ The `types` property is required, and should contain all of the possible Nexus/G
|
|||
- `[typeA, typeB, typeC, typeD]`
|
||||
|
||||
```ts
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import * as types from './allNexusTypes'
|
||||
|
||||
export const schema = makeSchema({
|
||||
|
|
@ -31,7 +31,7 @@ export const schema = makeSchema({
|
|||
The `plugins` property is an array for adding "Plugins", or ways of extending/changing the runtime behavior of Nexus and GraphQL. Unlike the `types` property, this must be an array, and the order of the plugins matters because this influences the order of any resolver "middleware" the plugin may optionally provide.
|
||||
|
||||
```ts
|
||||
import { makeSchema, nullabilityGuard, fieldAuthorizePlugin } from '@nexus/schema'
|
||||
import { makeSchema, nullabilityGuard, fieldAuthorizePlugin } from 'nexus'
|
||||
import * as types from './allNexusTypes'
|
||||
|
||||
export const schema = makeSchema({
|
||||
|
|
@ -79,11 +79,6 @@ makeSchema({
|
|||
typeMatch: name => new RegExp(`(?:interface|type|class)\\s+(${name}s?)\\W`, 'g'),
|
||||
},
|
||||
],
|
||||
// Typing for the GraphQL context
|
||||
contextType: {
|
||||
module: '@packages/data-context/src/DataContext.ts',
|
||||
alias: 'ctx',
|
||||
},
|
||||
mapping: {
|
||||
Date: 'Date',
|
||||
DateTime: 'Date',
|
||||
|
|
@ -91,10 +86,15 @@ makeSchema({
|
|||
},
|
||||
debug: false,
|
||||
},
|
||||
// Typing for the GraphQL context
|
||||
contextType: {
|
||||
module: '@packages/data-context/src/DataContext.ts',
|
||||
alias: 'ctx',
|
||||
},
|
||||
})
|
||||
```
|
||||
|
||||
The [Ghost Example](https://github.com/graphql-nexus/schema/blob/develop/examples/ghost/src/ghost-schema.ts) is the best place to look for an example of how we're able to capture the types from existing runtime objects or definitions and merge them with our schema.
|
||||
The [Ghost Example](https://github.com/graphql-nexus/nexus/blob/main/examples/ghost/src/ghost-schema.ts) is the best place to look for an example of how we're able to capture the types from existing runtime objects or definitions and merge them with our schema.
|
||||
|
||||
## shouldExitAfterGenerateArtifacts
|
||||
|
||||
|
|
@ -125,15 +125,34 @@ makeSchema({
|
|||
## nonNullDefaults
|
||||
|
||||
Controls the nullability of the input / output types emitted by `nexus`. The current Nexus default is
|
||||
`{ output: true, input: false }`, though the `graphql-js` / spec default is `{ output: false, input: false }`.
|
||||
`{ output: false, input: false }` same as `graphql-js` spec.
|
||||
`output`: Whether output field (object type fields) types are non-null by default.
|
||||
`input`: Whether input field (field arguments, input object type fields) types are non-null by default.
|
||||
|
||||
You should make a decision on this and supply the option yourself, it may be changed / required in the future.
|
||||
|
||||
Read more on this in the [getting-started](../../../getting-started) guide.
|
||||
|
||||
### typegenConfig, formatTypegen
|
||||
### typegenConfig
|
||||
|
||||
Escape hatches for more advanced cases which need further control over. You typically won't need these.
|
||||
Escape hatch for more advanced cases which need further control over generated files. You typically won't need this.
|
||||
|
||||
### formatTypegen
|
||||
|
||||
Manually apply a formatter to the generated content before saving. Function exposes content and type of generated file.
|
||||
|
||||
```ts
|
||||
makeSchema({
|
||||
// ...
|
||||
formatTypegen: (content, type) => {
|
||||
if (type === 'types') {
|
||||
return `/* eslint-disable */
|
||||
\n ${content}`;
|
||||
}
|
||||
return content;
|
||||
},
|
||||
})
|
||||
```
|
||||
|
||||
### customPrintSchemaFn
|
||||
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ codeStyle: true
|
|||
Often times you want to split up query fields into different domains of your application, and like [`mutationField`](/api/mutation-field) are another one of the most common use-cases for `extendType`. `queryField` exists as a shorthand for this common case:
|
||||
|
||||
```ts
|
||||
import { stringArg } from '@nexus/schema'
|
||||
import { stringArg } from 'nexus'
|
||||
|
||||
export const usersQueryField = queryField('user', {
|
||||
type: SomeType,
|
||||
|
|
@ -24,7 +24,7 @@ export const usersQueryField = queryField('user', {
|
|||
as shorthand for:
|
||||
|
||||
```ts
|
||||
export const createUser = extendType({
|
||||
export const usersQueryField = extendType({
|
||||
type: 'Query',
|
||||
definition(t) {
|
||||
t.field('user', {
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@ Often times you want to split up subscription fields into different domains of y
|
|||
Like `queryField` and `mutationField` except that like `subscriptionType` the `subscribe` field is required on the type configuration. Refer to [`subscriptionType`](/api/subscription-type) docs for details
|
||||
|
||||
```ts
|
||||
import { subscriptionField } from '@nexus/schema'
|
||||
import { subscriptionField } from 'nexus'
|
||||
|
||||
export const SubscriptionField = subscriptionField('truths', {
|
||||
type: 'Boolean',
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@ We also ship with several plugins out of the box, and will have more in the near
|
|||
### Defining a sample plugin:
|
||||
|
||||
```ts
|
||||
import { plugin } from '@nexus/schema'
|
||||
import { plugin } from 'nexus'
|
||||
|
||||
export const myErrorGuardPlugin = plugin({
|
||||
name: 'MyErrorGuardPlugin',
|
||||
|
|
|
|||
|
|
@ -4,13 +4,13 @@ title: Relay Connection
|
|||
|
||||
## Connection Plugin
|
||||
|
||||
The connection plugin provides a new method on the object definition builder, enabling paginated associations between types, following the [Relay Connection Specification](https://facebook.github.io/relay/graphql/connections.htm#sec-Node). It provides simple ways to customize fields available on the `Connection`, `Edges`, or `PageInfo` types.
|
||||
The connection plugin provides a new method on the object definition builder, enabling paginated associations between types, following the [Relay Connection Specification](https://relay.dev/graphql/connections.htm#sec-Node). It provides simple ways to customize fields available on the `Connection`, `Edges`, or `PageInfo` types.
|
||||
|
||||
To install, add the `connectionPlugin` to the `makeSchema.plugins` array, along with any other plugins
|
||||
you'd like to include:
|
||||
|
||||
```ts
|
||||
import { makeSchema, connectionPlugin } from '@nexus/schema'
|
||||
import { makeSchema, connectionPlugin } from 'nexus'
|
||||
|
||||
const schema = makeSchema({
|
||||
// ... types, etc,
|
||||
|
|
@ -232,7 +232,7 @@ You can create multiple field connection types with varying defaults, available
|
|||
Custom Usage:
|
||||
|
||||
```ts
|
||||
import { makeSchema, connectionPlugin } from '@nexus/schema'
|
||||
import { makeSchema, connectionPlugin } from 'nexus'
|
||||
|
||||
const schema = makeSchema({
|
||||
// ... types, etc,
|
||||
|
|
@ -249,3 +249,33 @@ const schema = makeSchema({
|
|||
],
|
||||
})
|
||||
```
|
||||
|
||||
## Custom names for Connection / Edge types
|
||||
|
||||
You can provide a function to generate a custom name for connection and edge types. The function will receive the field and parent type names.
|
||||
|
||||
### Globally
|
||||
|
||||
```ts
|
||||
connectionPlugin({
|
||||
getConnectionName(fieldName, parentTypeName) {
|
||||
return `${parentTypeName}${upperFirst(fieldName)}Connection`
|
||||
},
|
||||
getEdgeName(fieldName, parentTypeName) {
|
||||
return `${parentTypeName}${upperFirst(fieldName)}Edge`
|
||||
},
|
||||
})
|
||||
```
|
||||
|
||||
### One-off / per-field
|
||||
|
||||
```ts
|
||||
t.connectionField('users', {
|
||||
getConnectionName(fieldName, parentTypeName) {
|
||||
return `${parentTypeName}${upperFirst(fieldName)}Connection`
|
||||
},
|
||||
getEdgeName(fieldName, parentTypeName) {
|
||||
return `${parentTypeName}${upperFirst(fieldName)}Edge`
|
||||
},
|
||||
})
|
||||
```
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@ on field & argument definitions.
|
|||
To install, add the `declarativeWrapping` to the `makeSchema.plugins` array, along with any other plugins you'd like to include:
|
||||
|
||||
```ts
|
||||
import { makeSchema, declarativeWrappingPlugin } from '@nexus/schema'
|
||||
import { makeSchema, declarativeWrappingPlugin } from 'nexus'
|
||||
|
||||
const schema = makeSchema({
|
||||
// ... types, etc,
|
||||
|
|
|
|||
|
|
@ -4,7 +4,21 @@ title: Field Authorize
|
|||
|
||||
## Field Authorize
|
||||
|
||||
The authorize plugin allows us to define field-level authorization to a query:
|
||||
The field Authorize Plugin plugin provides a new property on the field config called `authorize`.
|
||||
|
||||
```ts
|
||||
import { makeSchema, fieldAuthorizePlugin } from 'nexus'
|
||||
|
||||
const schema = makeSchema({
|
||||
// ... types, etc,
|
||||
plugins: [
|
||||
// ... other plugins
|
||||
fieldAuthorizePlugin(),
|
||||
],
|
||||
})
|
||||
```
|
||||
|
||||
It allows us to define field-level authorization to a query:
|
||||
|
||||
```ts
|
||||
t.field('postById', {
|
||||
|
|
@ -16,3 +30,5 @@ t.field('postById', {
|
|||
},
|
||||
})
|
||||
```
|
||||
|
||||
`authorize` is a function that provides authorization for an individual field. Returning `true` or `Promise<true>` means the field can be accessed. Returning `false` or `Promise<false>` will respond with a "Not Authorized" error for the field. Returning or throwing an error will also prevent the resolver from executing.
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ A single GraphQL query can potentially generate a huge workload for a server, li
|
|||
To install, add the `queryComplexityPlugin` to the `makeSchema.plugins` array, along with any other plugins you'd like to include:
|
||||
|
||||
```ts
|
||||
import { makeSchema, queryComplexityPlugin } from '@nexus/schema'
|
||||
import { makeSchema, queryComplexityPlugin } from 'nexus'
|
||||
|
||||
const schema = makeSchema({
|
||||
// ... types, etc,
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ This plugin helps us guard against non-null values crashing our queries in produ
|
|||
### Example
|
||||
|
||||
```ts
|
||||
import { nullabilityGuardPlugin } from '@nexus/schema'
|
||||
import { nullabilityGuardPlugin } from 'nexus'
|
||||
|
||||
const guardPlugin = nullabilityGuardPlugin({
|
||||
onGuarded({ ctx, info }) {
|
||||
|
|
|
|||
|
|
@ -4,13 +4,15 @@ title: Overview
|
|||
|
||||
## About
|
||||
|
||||
This plugin integrates [Prisma](https://www.prisma.io/) into [Nexus](https://nexusjs.org/). It gives you an API you to project fields from models defined in your Prisma schema into your GraphQL API. It also gives you an API to build GraphQL root fields that allow your API clients to query and mutate data.
|
||||
This plugin integrates [Prisma](https://www.prisma.io/) into [Nexus](https://nexusjs.org/). It gives you an API to project fields from models defined in your Prisma schema into your GraphQL API. It also gives you an API to build GraphQL root fields that allow your API clients to query and mutate data.
|
||||
|
||||
**Note**: You may also use [`nexus-prisma`](https://github.com/graphql-nexus/nexus-prisma), a newer API for integrating Nexus and Prisma.
|
||||
|
||||
## Installation
|
||||
|
||||
```bash-symbol
|
||||
npm add nexus-plugin-prisma @prisma/client
|
||||
npm add -D @prisma/cli
|
||||
npm install nexus-plugin-prisma @prisma/client
|
||||
npm install -D prisma
|
||||
```
|
||||
|
||||
## Usage
|
||||
|
|
@ -21,13 +23,13 @@ npm add -D @prisma/cli
|
|||
|
||||
> **Note**: If you're looking for CRUD capabilities, you must enable the `experimentalCRUD` option.
|
||||
|
||||
You can find runnable examples in the [repo examples folder](https://github.com/graphql-nexus/nexus-schema-plugin-prisma/tree/master/examples/schema).
|
||||
You can find runnable examples in the [repo examples folder](https://github.com/graphql-nexus/nexus-plugin-prisma/tree/main/examples).
|
||||
|
||||
**Example**
|
||||
|
||||
```ts
|
||||
import { nexusPrisma } from 'nexus-plugin-prisma'
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import * as types from './types'
|
||||
|
||||
const schema = makeSchema({
|
||||
|
|
@ -38,7 +40,7 @@ const schema = makeSchema({
|
|||
|
||||
## Configuration
|
||||
|
||||
Note that, In most cases, you should not need to configure anything.
|
||||
Note that, in most cases, you should not need to configure anything.
|
||||
|
||||
```ts
|
||||
type Options = {
|
||||
|
|
@ -78,7 +80,7 @@ type Options = {
|
|||
typegen?: string
|
||||
}
|
||||
computedInputs?: GlobalComputedInputs
|
||||
|
||||
|
||||
/**
|
||||
* GraphQL doesn't support union types. The plugin has to apply a flattening heuristic and pick by default the broadest member of the union.
|
||||
* On update and upsert, the broadest member is the atomic operation, which is not ideal in many cases.
|
||||
|
|
@ -97,69 +99,63 @@ There are two ways you can start with the Prisma plugin. Either from scratch, or
|
|||
|
||||
1. Create a `schema.prisma` file
|
||||
|
||||
```prisma
|
||||
//schema.prisma
|
||||
```prisma
|
||||
//schema.prisma
|
||||
|
||||
generator prisma_client {
|
||||
provider = "prisma-client-js"
|
||||
}
|
||||
generator prisma_client {
|
||||
provider = "prisma-client-js"
|
||||
}
|
||||
|
||||
model User {
|
||||
id Int @id @default(autoincrement())
|
||||
name String
|
||||
}
|
||||
```
|
||||
model User {
|
||||
id Int @id @default(autoincrement())
|
||||
name String
|
||||
}
|
||||
```
|
||||
|
||||
2. Add a datasource to your schema. We recommend you use Postgres but MySQL and SQLite are also supported.
|
||||
|
||||
To add your datasource, simply copy/paste one of the block below at the top of your `schema.prisma` file
|
||||
To add your datasource, simply copy/paste one of the block below at the top of your `schema.prisma` file
|
||||
|
||||
> **Note**: You can also pass the database credentials via a `.env` file. [Read more about it here](https://www.prisma.io/docs/reference/tools-and-interfaces/prisma-schema/prisma-schema-file#using-environment-variables)
|
||||
> **Note**: You can also pass the database credentials via a `.env` file. [Read more about it here](https://www.prisma.io/docs/reference/tools-and-interfaces/prisma-schema/prisma-schema-file#using-environment-variables)
|
||||
|
||||
Using PostgreSQL:
|
||||
Using PostgreSQL:
|
||||
|
||||
```prisma
|
||||
//schema.prisma
|
||||
```prisma
|
||||
//schema.prisma
|
||||
|
||||
datasource db {
|
||||
provider = "postgres"
|
||||
url = "postgresql://USER:PASSWORD@localhost:5432/DATABASE"
|
||||
}
|
||||
```
|
||||
datasource db {
|
||||
provider = "postgres"
|
||||
url = "postgresql://USER:PASSWORD@localhost:5432/DATABASE"
|
||||
}
|
||||
```
|
||||
|
||||
Using MySQL:
|
||||
Using MySQL:
|
||||
|
||||
```prisma
|
||||
//schema.prisma
|
||||
```prisma
|
||||
//schema.prisma
|
||||
|
||||
datasource db {
|
||||
provider = "mysql"
|
||||
url = "mysql://USER:PASSWORD@localhost:3306/DATABASE"
|
||||
}
|
||||
```
|
||||
datasource db {
|
||||
provider = "mysql"
|
||||
url = "mysql://USER:PASSWORD@localhost:3306/DATABASE"
|
||||
}
|
||||
```
|
||||
|
||||
Using SQLite:
|
||||
Using SQLite:
|
||||
|
||||
```prisma
|
||||
//schema.prisma
|
||||
```prisma
|
||||
//schema.prisma
|
||||
|
||||
datasource db {
|
||||
provider = "sqlite"
|
||||
url = "file:./dev.db"
|
||||
}
|
||||
```
|
||||
datasource db {
|
||||
provider = "sqlite"
|
||||
url = "file:./dev.db"
|
||||
}
|
||||
```
|
||||
|
||||
3. Create a migration file:
|
||||
3. Create a migration from changes in Prisma schema and run the migration
|
||||
|
||||
```bash-symbol
|
||||
npm run prisma migrate save --experimental
|
||||
```
|
||||
|
||||
4. Migrate your database:
|
||||
|
||||
```bash-symbol
|
||||
npm run prisma migrate up --experimental
|
||||
```
|
||||
```bash-symbol
|
||||
npx prisma migrate dev
|
||||
```
|
||||
|
||||
You're ready to start working!
|
||||
|
||||
|
|
@ -169,9 +165,9 @@ When starting from an existing database, you should use [Prisma's introspection]
|
|||
|
||||
1. Create a `schema.prisma` file.
|
||||
|
||||
Create a `schema.prisma` file and add your database credentials in it so that Prisma can introspect your database schema.
|
||||
Create a `schema.prisma` file and add your database credentials in it so that Prisma can introspect your database schema.
|
||||
|
||||
> **Note**: You can also pass the database credentials via a `.env` file. [Read more about it here](https://www.prisma.io/docs/reference/tools-and-interfaces/prisma-schema/prisma-schema-file#using-environment-variables)
|
||||
> **Note**: You can also pass the database credentials via a `.env` file. [Read more about it here](https://www.prisma.io/docs/reference/tools-and-interfaces/prisma-schema/prisma-schema-file#using-environment-variables)
|
||||
|
||||
Using PostgreSQL:
|
||||
|
||||
|
|
@ -208,19 +204,19 @@ When starting from an existing database, you should use [Prisma's introspection]
|
|||
|
||||
2. Introspect your database:
|
||||
|
||||
```bash-symbol
|
||||
npm run prisma introspect
|
||||
```
|
||||
```bash-symbol
|
||||
npx prisma db pull
|
||||
```
|
||||
|
||||
3. Generate the Prisma Client. Add the following block at the top of your `schema.prisma` file:
|
||||
|
||||
```
|
||||
generator prisma_client {
|
||||
provider = "prisma-client-js"
|
||||
}
|
||||
```
|
||||
```
|
||||
generator prisma_client {
|
||||
provider = "prisma-client-js"
|
||||
}
|
||||
```
|
||||
|
||||
The plugin will take care of generating the Prisma Client for you after that.
|
||||
The plugin will take care of generating the Prisma Client for you after that.
|
||||
|
||||
You're ready to start working!
|
||||
|
||||
|
|
@ -228,7 +224,7 @@ You're ready to start working!
|
|||
|
||||
Given a [Prisma schema](https://github.com/prisma/prisma2/blob/master/docs/prisma-schema-file.md) (left), you will be able to project these Prisma models onto your API and expose operations against them (middle) resulting in the GraphQL Schema (right).
|
||||
|
||||
> **Note**: `t.crud` is an experimental feature. You must explicitly enable it [via the plugin options](#type-definition).
|
||||
> **Note**: `t.crud` is an experimental feature. You must explicitly enable it [via the plugin options](#type-definition).
|
||||
|
||||
<div class="Row Collapsable">
|
||||
|
||||
|
|
@ -433,85 +429,6 @@ input UserWhereUniqueInput {
|
|||
|
||||
</div>
|
||||
|
||||
## Plugin settings
|
||||
|
||||
You can _optionally_ pass some settings to the plugin.
|
||||
|
||||
### Type definition
|
||||
|
||||
```ts
|
||||
export type PrismaClientOptions = {
|
||||
/**
|
||||
* Options to pass to the Prisma Client instantiated by the plugin.
|
||||
* If you want to instantiate your own Prisma Client, use `instance` instead.
|
||||
*/
|
||||
options: ClientOptions
|
||||
}
|
||||
|
||||
export type PrismaClientInstance = {
|
||||
/**
|
||||
* Instance of your own Prisma Client. You can import it from 'nexus-plugin-prisma/client'.
|
||||
* If you just want to pass some settings to the Prisma Client, use `options` instead.
|
||||
*/
|
||||
instance: PrismaClient
|
||||
}
|
||||
|
||||
export type Settings = {
|
||||
/**
|
||||
* Use this to pass some settings to the Prisma Client instantiated by the plugin or to pass your own Prisma Client
|
||||
*/
|
||||
client?: PrismaClientOptions | PrismaClientInstance
|
||||
/**
|
||||
* Enable or disable migrations run by the plugin when editing your schema.prisma file
|
||||
*
|
||||
* @default true
|
||||
*/
|
||||
migrations?: boolean
|
||||
/**
|
||||
* Features that require opting into. These are all disabled by default.
|
||||
*/
|
||||
features?: {
|
||||
/**
|
||||
* Enable **experimental** CRUD capabilities.
|
||||
* Add a `t.crud` method in your definition block to generate CRUD resolvers in your `Query` and `Mutation` GraphQL Object Type.
|
||||
*
|
||||
* @default false
|
||||
*/
|
||||
crud?: boolean
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Examples
|
||||
|
||||
#### Configuring the Prisma Client
|
||||
|
||||
```ts
|
||||
import { use } from 'nexus'
|
||||
import { prisma } from 'nexus-plugin-prisma'
|
||||
|
||||
use(
|
||||
prisma({
|
||||
client: { options: { log: ['query'] } },
|
||||
})
|
||||
)
|
||||
```
|
||||
|
||||
#### Using a custom instance of the Prisma Client
|
||||
|
||||
```ts
|
||||
import { nexusPrisma } from 'nexus-plugin-prisma'
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { PrismaClient } from 'nexus-plugin-prisma/client'
|
||||
|
||||
const schema = makeSchema({
|
||||
types,
|
||||
plugins: [nexusPrisma({
|
||||
client: { instance: new PrismaClient() }
|
||||
})],
|
||||
})
|
||||
```
|
||||
|
||||
## Recipes
|
||||
|
||||
### Projecting Prisma model fields
|
||||
|
|
|
|||
|
|
@ -3,11 +3,12 @@ title: API
|
|||
tocDepth: 2
|
||||
---
|
||||
|
||||
|
||||
## `t.model`
|
||||
|
||||
Only available within [`objectType`](/api/object-type) definitions.
|
||||
|
||||
`t.model` contains configurable _field projectors_ that you use for projecting fields of your [Prisma models](https://github.com/prisma/prisma2/blob/master/docs/data-modeling.md#models) onto your [GraphQL Objects](https://graphql.github.io/graphql-spec/June2018/#sec-Objects). The precise behaviour of field projectors vary by the Prisma type being projected. Refer to the respective sub-sections for details.
|
||||
`t.model` contains configurable _field projectors_ that you use for projecting fields of your [Prisma models](https://www.prisma.io/docs/reference/tools-and-interfaces/prisma-schema/data-model) onto your [GraphQL Objects](https://graphql.github.io/graphql-spec/June2018/#sec-Objects). The precise behaviour of field projectors vary by the Prisma type being projected. Refer to the respective sub-sections for details.
|
||||
|
||||
### Model-object mapping
|
||||
|
||||
|
|
@ -77,7 +78,7 @@ Currently Prisma enums cannot be [aliased](#alias) ([issue](https://github.com/g
|
|||
|
||||
#### Options
|
||||
|
||||
n/a
|
||||
[`description`](#description) [`deprecation`](#deprecation)
|
||||
|
||||
#### GraphQL Schema Contributions [`?`](#graphql-schema-contributions-legend 'How to read this')
|
||||
|
||||
|
|
@ -200,7 +201,7 @@ scalar S
|
|||
|
||||
#### Options
|
||||
|
||||
[`alias`](#alias) [`resolve`](#resolve)
|
||||
[`alias`](#alias) [`resolve`](#resolve) [`description`](#description) [`deprecation`](#deprecation)
|
||||
|
||||
#### Example
|
||||
|
||||
|
|
@ -259,7 +260,7 @@ Projecting relational fields only affects the current GraphQL object being defin
|
|||
|
||||
#### Options
|
||||
|
||||
[`type`](#type) [`alias`](#alias) [`resolve`](#resolve)
|
||||
[`type`](#type) [`alias`](#alias) [`resolve`](#resolve) [`description`](#description) [`deprecation`](#deprecation)
|
||||
|
||||
#### GraphQL Schema Contributions [`?`](#graphql-schema-contributions-legend 'How to read this')
|
||||
|
||||
|
|
@ -347,7 +348,7 @@ Like [relations](#relation) but also supports batch related options.
|
|||
|
||||
#### Options
|
||||
|
||||
[`type`](#type) [`alias`](#alias) [`resolve`](#resolve) [`filtering`](#filtering) [`pagination`](#pagination) [`ordering`](#ordering)
|
||||
[`type`](#type) [`alias`](#alias) [`resolve`](#resolve) [`filtering`](#filtering) [`pagination`](#pagination) [`ordering`](#ordering) [`description`](#description) [`deprecation`](#deprecation)
|
||||
|
||||
#### GraphQL Schema Contributions [`?`](#graphql-schema-contributions-legend 'How to read this')
|
||||
|
||||
|
|
@ -1585,7 +1586,7 @@ queryType({
|
|||
|
||||
type Query {
|
||||
user(where: UserWhereUniqueInput!): User
|
||||
users(orderBy: UserOrderByInput): [User!]!
|
||||
users(orderBy: [UserOrderByInput!]): [User!]!
|
||||
}
|
||||
|
||||
type Post {
|
||||
|
|
@ -1597,7 +1598,7 @@ type Post {
|
|||
type User {
|
||||
id: Int!
|
||||
name: String!
|
||||
posts(orderBy: UserPostsOrderByInput): [Post!]!
|
||||
posts(orderBy: [UserPostsOrderByInput!]): [Post!]!
|
||||
}
|
||||
|
||||
input UserOrderByInput {
|
||||
|
|
@ -1624,7 +1625,7 @@ enum OrderByArg {
|
|||
|
||||
```graphql
|
||||
query entrypointOrdering {
|
||||
users(orderBy: { name: asc }) {
|
||||
users(orderBy: [{ name: asc }]) {
|
||||
id
|
||||
name
|
||||
}
|
||||
|
|
@ -1632,7 +1633,7 @@ query entrypointOrdering {
|
|||
|
||||
query relationOrdering {
|
||||
user(where: { id: 1643 }) {
|
||||
posts(orderBy: { title: dsc }) {
|
||||
posts(orderBy: [{ title: desc }]) {
|
||||
title
|
||||
body
|
||||
}
|
||||
|
|
@ -2029,6 +2030,127 @@ query batchReadRelationFilter {
|
|||
</tab>
|
||||
</TabbedContent>
|
||||
|
||||
### `description`
|
||||
|
||||
```
|
||||
undefined | string
|
||||
```
|
||||
|
||||
**Applies to**
|
||||
|
||||
`t.model.<*>`
|
||||
|
||||
**About**
|
||||
|
||||
Sets a description to be included in the generated SDL for this field.
|
||||
|
||||
- `undefined` (default) No description will be added to the field.
|
||||
- `string` A description will be generated with the provided string.
|
||||
|
||||
#### Example
|
||||
|
||||
<TabbedContent tabs={["Prisma", "Nexus", "GraphQL"]}>
|
||||
<tab>
|
||||
|
||||
```prisma
|
||||
model User {
|
||||
id Int @id
|
||||
name String
|
||||
}
|
||||
```
|
||||
|
||||
</tab>
|
||||
<tab>
|
||||
|
||||
```ts
|
||||
objectType({
|
||||
name: 'User',
|
||||
definition: (t: any) => {
|
||||
t.model.id()
|
||||
t.model.name({ description: "The user's full name" })
|
||||
},
|
||||
})
|
||||
```
|
||||
|
||||
</tab>
|
||||
|
||||
<tab>
|
||||
|
||||
```graphql
|
||||
# Generated
|
||||
|
||||
type User {
|
||||
id: Int!
|
||||
|
||||
"""The user's full name"""
|
||||
name: String!
|
||||
}
|
||||
```
|
||||
|
||||
</tab>
|
||||
</TabbedContent>
|
||||
|
||||
|
||||
### `deprecation`
|
||||
|
||||
```
|
||||
undefined | string
|
||||
```
|
||||
|
||||
**Applies to**
|
||||
|
||||
`t.model.<*>`
|
||||
|
||||
**About**
|
||||
|
||||
Adds a `@deprecated` directive to the generated SDL for this field.
|
||||
|
||||
- `undefined` (default) No deprecation directive will be added to the field.
|
||||
- `string` Include a deprecation directive, using the provided string as a reason.
|
||||
|
||||
#### Example
|
||||
|
||||
<TabbedContent tabs={["Prisma", "Nexus", "GraphQL"]}>
|
||||
<tab>
|
||||
|
||||
```prisma
|
||||
model User {
|
||||
id Int @id
|
||||
name String
|
||||
}
|
||||
```
|
||||
|
||||
</tab>
|
||||
<tab>
|
||||
|
||||
```ts
|
||||
objectType({
|
||||
name: 'User',
|
||||
definition: (t: any) => {
|
||||
t.model.id()
|
||||
t.model.name({ deprecation: "Names of users are no longer collected" })
|
||||
},
|
||||
})
|
||||
```
|
||||
|
||||
</tab>
|
||||
|
||||
<tab>
|
||||
|
||||
```graphql
|
||||
# Generated
|
||||
|
||||
type User {
|
||||
id: Int!
|
||||
|
||||
name: String! @deprecated(reason: "Names of users are no longer collected")
|
||||
}
|
||||
```
|
||||
|
||||
</tab>
|
||||
</TabbedContent>
|
||||
|
||||
|
||||
### `computedInputs` (local)
|
||||
|
||||
```
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load Diff
|
|
@ -4,3 +4,10 @@ toc: false
|
|||
---
|
||||
|
||||
## Please Refer to the Sub-Pages
|
||||
|
||||
> **Note**: The [Prisma](https://www.prisma.io) team is currently [rewriting](https://github.com/graphql-nexus/nexus-plugin-prisma/issues/1039) the plugin to make it maintainable longterm.
|
||||
|
||||
- [Overview](/plugins/prisma/overview)
|
||||
- [API](/plugins/prisma/api)
|
||||
- [Removing `nexus-plugin-prisma`](/plugins/prisma/removing-the-nexus-plugin-prisma)
|
||||
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ This guide will show you the ways you can use Nexus with the Prisma toolkit.
|
|||
|
||||
## Vanilla integration
|
||||
|
||||
As a Prisma user you can easily integrate Prisma into Nexus yourself, take a look at the [with-prisma example](https://todo.com)
|
||||
As a Prisma user you can easily integrate Prisma into Nexus yourself, take a look at the [with-prisma example](https://github.com/graphql-nexus/nexus/tree/main/examples/with-prisma)
|
||||
|
||||
## Plugin!
|
||||
|
||||
|
|
|
|||
|
|
@ -38,7 +38,7 @@ With the Next.js project in place, we now need to install the other dependencies
|
|||
In addition to Nexus, we'll need a server to run the GraphQL API. Nexus works with a range of GraphQL servers. We'll use Apollo Server and opt for the `apollo-server-micro` variety as it is well-suited to serverless environments.
|
||||
|
||||
```bash-symbol
|
||||
npm i @nexus/schema apollo-server-micro
|
||||
npm i nexus apollo-server-micro
|
||||
```
|
||||
|
||||
## Create an API Route
|
||||
|
|
@ -62,7 +62,7 @@ Populate the `graphql.ts` file with a simple schema and server. Then, expose the
|
|||
```ts
|
||||
// pages/api/graphql.ts
|
||||
|
||||
import { makeSchema, queryType } from '@nexus/schema'
|
||||
import { makeSchema, queryType } from 'nexus'
|
||||
import { ApolloServer } from 'apollo-server-micro'
|
||||
|
||||
const Query = queryType({
|
||||
|
|
@ -125,7 +125,7 @@ Let's create and export a `Query` constant, as well as a `Framework` object type
|
|||
```ts
|
||||
// schema/Query.ts
|
||||
|
||||
import { objectType, queryType } from '@nexus/schema'
|
||||
import { objectType, queryType } from 'nexus'
|
||||
|
||||
export const Framework = objectType({
|
||||
name: 'Framework',
|
||||
|
|
@ -175,7 +175,7 @@ In the `index.ts` file, bring in `makeSchema` as well as the types we just creat
|
|||
```ts
|
||||
// schema/index.ts
|
||||
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import * as QueryTypes from './Query'
|
||||
|
||||
const schema = makeSchema({
|
||||
|
|
@ -193,7 +193,7 @@ Now in the `graphql.ts` for our API route, we can simply pull in the constructed
|
|||
|
||||
```ts diff
|
||||
// pages/api/graphql.ts
|
||||
- import { makeSchema, queryType } from '@nexus/schema'
|
||||
- import { makeSchema, queryType } from 'nexus'
|
||||
import { ApolloServer } from 'apollo-server-micro'
|
||||
+ import schema from '../../schema'
|
||||
|
||||
|
|
@ -344,7 +344,7 @@ In the `schema/index.ts` file, configure `makeSchema` to output the generated SD
|
|||
<tab>
|
||||
|
||||
```ts diff
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import * as QueryTypes from './Query'
|
||||
+import path from 'path'
|
||||
|
||||
|
|
@ -363,7 +363,7 @@ export default schema;
|
|||
<tab>
|
||||
|
||||
```ts diff
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import * as QueryTypes from './Query'
|
||||
import path from 'path'
|
||||
|
||||
|
|
@ -399,7 +399,7 @@ Finally we will setup our build script to run Nexus typegen before Next.js tries
|
|||
"start": "next start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@nexus/schema": "^0.19.2",
|
||||
"nexus": "^0.19.2",
|
||||
"apollo-server-micro": "^2.19.0",
|
||||
"graphql-request": "^3.3.0",
|
||||
"next": "10.0.3",
|
||||
|
|
@ -429,7 +429,7 @@ Finally we will setup our build script to run Nexus typegen before Next.js tries
|
|||
"start": "next start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@nexus/schema": "^0.19.2",
|
||||
"nexus": "^0.19.2",
|
||||
"apollo-server-micro": "^2.19.0",
|
||||
"graphql-request": "^3.3.0",
|
||||
"next": "10.0.3",
|
||||
|
|
|
|||
|
|
@ -4,22 +4,21 @@ title: Nexus Framework Users
|
|||
|
||||
## Hello Nexus Framework User!
|
||||
|
||||
If you are a `nexus` (Nexus Framework) user we strongly encourage you to migrate to `@nexus/schema` (Nexus Schema). For more detail about why and how this came about please see [this announcement](https://github.com/prisma-labs/graphql-framework-experiment/issues/1432). The following guide is written to help you transition from the framework back to the library.
|
||||
If you are a Nexus _framework_ user (`nexus` package from version `0.20` to `0.27`) we strongly encourage you to migrate to the the Nexus _library_ (`nexus` package `1.0` and up). For more detail about why and how this came about please see [this announcement](https://github.com/prisma-labs/graphql-framework-experiment/issues/1432). The following guide is written to help you transition from the framework back to the library.
|
||||
|
||||
Note that there is a [separate migration guide](https://nxs.li/unframework/plugin/prisma/migrate) detailing how to go from the Prisma plugin for Nexus Framework to the Prisma plugin for Nexus schema.
|
||||
Note that there is a [separate migration guide](https://nxs.li/unframework/plugin/prisma/migrate) detailing how to go from the Prisma plugin for Nexus Framework to the Prisma plugin for Nexus.
|
||||
|
||||
## Bundled Dependencies
|
||||
|
||||
You will need to install `@nexus/schema` and `graphql` yourself. While you're at it, uninstall `nexus` too.
|
||||
Start by uninstalling your current `nexus`. Then you will need to install `nexus@^1.0.0` which is now the library. You also now need to install `graphql` yourself.
|
||||
|
||||
```tsx
|
||||
npm uninstall nexus
|
||||
npm install @nexus/schema graphql
|
||||
```bash-symbol
|
||||
npm uninstall nexus && npm install nexus graphql
|
||||
```
|
||||
|
||||
## JavaScript Support
|
||||
|
||||
If you had been using TypeScript before only because Nexus Framework forced you to, then know that you can use JavaScript with `@nexus/schema` if you want. The rest of this guide will assume that you want to continue using TypeScript. Ignore or adapt instructions as needed if you are a JS user.
|
||||
If you had been using TypeScript before only because Nexus Framework forced you to, then know that you can use JavaScript with `nexus` if you want. The rest of this guide will assume that you want to continue using TypeScript. Ignore or adapt instructions as needed if you are a JS user.
|
||||
|
||||
## Managed TypeScript
|
||||
|
||||
|
|
@ -27,25 +26,25 @@ You will need to manage the TypeScript toolchain yourself.
|
|||
|
||||
1. Install `typescript`, `ts-node`, and `ts-node-dev`.
|
||||
|
||||
```tsx
|
||||
npm add -D typescript ts-node ts-node-dev
|
||||
```bash-symbol
|
||||
npm install -D typescript ts-node ts-node-dev
|
||||
```
|
||||
|
||||
2. The following applies to VSCode but something like it might apply to other editors as well. You must also make sure your editor is set to use the local version of TypeScript rather than the one the editor ships with. Summon the command pallet `command+shift+p` and then enter and select `typescript: select TypeScript Version...`. Then select `Workspace Version`.
|
||||
3. Ensure your tsconfig settings are correct.
|
||||
1. If you are outputting Nexus Schema typegen to `node_modules/@types/<something>/index.d.ts` like Nexus Framework did then you must ensure that the [`compilerOptions.typeRoots`](https://www.typescriptlang.org/tsconfig#typeRoots) and [`compilerOptions.types`](https://www.typescriptlang.org/tsconfig#types) fields are correctly set or not set at all. If `typeRoots` is set then ensure that where you output Nexus Schema's typegen is listed. If `types` is set then ensure that the parent directory where you output Nexus Schema's typegen is listed.
|
||||
1. If you are outputting Nexus typegen to `node_modules/@types/<something>/index.d.ts` like Nexus Framework did then you must ensure that the [`compilerOptions.typeRoots`](https://www.typescriptlang.org/tsconfig#typeRoots) and [`compilerOptions.types`](https://www.typescriptlang.org/tsconfig#types) fields are correctly set or not set at all. If `typeRoots` is set then ensure that where you output Nexus's typegen is listed. If `types` is set then ensure that the parent directory where you output Nexus's typegen is listed.
|
||||
2. If you are using Apollo Server then you must enable `skipLibCheck: true` in `compilerOptions`.
|
||||
3. Enable `strict` mode in `compilerOptions` to benefit most of all from Nexus Schema's typings.
|
||||
3. Enable `strict` mode in `compilerOptions` to benefit most of all from Nexus's typings.
|
||||
|
||||
## Development Mode
|
||||
|
||||
You will need to manage running and restarting your server on changes during development yourself. If you are using TypeScript then use the following two development scripts `dev` and `dev:typecheck`. Together, these attempt to smooth over the workflow with Nexus' reflection system and approximate a subset of what `nexus dev` did.
|
||||
|
||||
```tsx
|
||||
```json
|
||||
{
|
||||
"scripts": {
|
||||
"dev": "ts-node-dev --transpile-only ./your/main/module",
|
||||
"dev:typecheck": "tsc --noEmit --watch",
|
||||
"dev:typecheck": "tsc --noEmit --watch"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
|
@ -56,7 +55,7 @@ The following applies to VSCode but it might apply to other editors as well: You
|
|||
|
||||
## Nexus Module Discovery & Singleton Schema Builder
|
||||
|
||||
You will need to export Nexus Schema type definition values and import them into where you run your `makeSchema`. The exact module layout you use does not matter.
|
||||
You will need to export Nexus type definition values and import them into where you run your `makeSchema`. The exact module layout you use does not matter.
|
||||
|
||||
In framework you could do this:
|
||||
|
||||
|
|
@ -71,7 +70,7 @@ Now you will need to do something like this:
|
|||
```tsx
|
||||
// ./User.ts
|
||||
|
||||
import { objectType } from '@nexus/schema'
|
||||
import { objectType } from 'nexus'
|
||||
|
||||
export const User = objectType(...)
|
||||
```
|
||||
|
|
@ -79,7 +78,7 @@ export const User = objectType(...)
|
|||
```tsx
|
||||
// ./index.ts
|
||||
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { User } from './User'
|
||||
|
||||
const schema = makeSchema({
|
||||
|
|
@ -90,7 +89,7 @@ const schema = makeSchema({
|
|||
|
||||
## Fully Abstracted Reflection System
|
||||
|
||||
You need to run Nexus Schema reflection yourself explicitly. You need to do this before running `tsc` to build your app. Otherwise `tsc` will fail due to type errors because of the missing typings files.
|
||||
You need to run Nexus reflection yourself explicitly. You need to do this before running `tsc` to build your app. Otherwise `tsc` will fail due to type errors because of the missing typings files.
|
||||
|
||||
There are two primary ways you can go about this.
|
||||
|
||||
|
|
@ -101,11 +100,11 @@ Approach A might be simpler if your project can accommodate it. The primary requ
|
|||
|
||||
Approach A is simpler in that it reduces the surface area of your codebase where you need to think about eager code running during reflection (which in turn is run before build and tests). On the other hand you may already be thinking about this if you are trying to develop testable code. Use whichever approach works best for you.
|
||||
|
||||
Regardless of which choice you go with, you also need to ensure that `NODE_ENV=production` is set. If you forget to do this then Nexus Schema will (by default) run reflection. This would significantly slow down your application boot time, something you don't want in serverless environments, for example.
|
||||
Regardless of which choice you go with, you also need to ensure that `NODE_ENV=production` is set. If you forget to do this then Nexus will (by default) run reflection. This would significantly slow down your application boot time, something you don't want in serverless environments, for example.
|
||||
|
||||
Here is an example of approach A to managing reflection:
|
||||
|
||||
1. Layout your Nexus Schema type defs amongst modules under a parent dir such that each module contains a part of your GraphQL schema. Put shared parts of your GraphQL schema into `shared.ts`. Re-export all type defs in `index.ts`.
|
||||
1. Layout your Nexus type defs amongst modules under a parent dir such that each module contains a part of your GraphQL schema. Put shared parts of your GraphQL schema into `shared.ts`. Re-export all type defs in `index.ts`.
|
||||
|
||||
```json
|
||||
/src
|
||||
|
|
@ -129,7 +128,7 @@ Here is an example of approach A to managing reflection:
|
|||
```tsx
|
||||
// src/schema.ts
|
||||
|
||||
export { makeSchema } from '@nexus/schema'
|
||||
export { makeSchema } from 'nexus'
|
||||
import * as types from './graphql'
|
||||
|
||||
export const schema = makeSchema({
|
||||
|
|
@ -137,7 +136,7 @@ Here is an example of approach A to managing reflection:
|
|||
})
|
||||
```
|
||||
|
||||
4. Now you can run Nexus Schema reflection by running this subset of your app e.g. `ts-node --transpile-only src/schema`. You will probably want to capture this via a new npm script called e.g. `nexus:reflect`.
|
||||
4. Now you can run Nexus reflection by running this subset of your app e.g. `ts-node --transpile-only src/schema`. You will probably want to capture this via a new npm script called e.g. `nexus:reflect`.
|
||||
|
||||
Here is an example of approach B to managing reflection:
|
||||
|
||||
|
|
@ -145,20 +144,20 @@ Here is an example of approach B to managing reflection:
|
|||
2. When configuring `makeSchema` make sure to enable process exit when requested via an environment variable.
|
||||
|
||||
```tsx
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
|
||||
export const schema = makeSchema({
|
||||
shouldExitAfterGenerateArtifacts: Boolean(process.env.NEXUS_SHOULD_EXIT_AFTER_REFLECTION),
|
||||
})
|
||||
```
|
||||
|
||||
3. Now you can run Nexus Schema reflection by running your app with that environment variable set e.g. `NEXUS_SHOULD_EXIT_AFTER_REFLECTION=true ts-node src`. You will probably want to capture this via a new script called e.g. `nexus:reflect`.
|
||||
3. Now you can run Nexus reflection by running your app with that environment variable set e.g. `NEXUS_SHOULD_EXIT_AFTER_REFLECTION=true ts-node src`. You will probably want to capture this via a new script called e.g. `nexus:reflect`.
|
||||
|
||||
## Integrated Build Step With Bundling
|
||||
|
||||
You will need to handle the build yourself. This involves a few things:
|
||||
|
||||
1. Run Nexus Schema reflection yourself
|
||||
1. Run Nexus reflection yourself
|
||||
|
||||
This has been explained in the _Fully Abstracted Reflection System_ section.
|
||||
|
||||
|
|
@ -168,7 +167,7 @@ You will need to handle the build yourself. This involves a few things:
|
|||
|
||||
3. Optional: Run a bundler yourself
|
||||
|
||||
This is probably something you don't need to do. Nexus Framework took a packages-bundled approach to dependencies and this mean a large package size that bloated deployments necessitating techniques like tree-shaking (e.g. TypeScript dependency is over 50mb). This problem generally goes away when using the Nexus Schema library directly. However bundling for serverless deployments can still be desirable especially if your non-development dependencies are heavy and not fully used at runtime. If you were relying on Nexus Framework bundling here are some tools you can try out yourself:
|
||||
This is probably something you don't need to do. Nexus Framework took a packages-bundled approach to dependencies and this mean a large package size that bloated deployments necessitating techniques like tree-shaking (e.g. TypeScript dependency is over 50mb). This problem generally goes away when using the Nexus library directly. However bundling for serverless deployments can still be desirable especially if your non-development dependencies are heavy and not fully used at runtime. If you were relying on Nexus Framework bundling here are some tools you can try out yourself:
|
||||
|
||||
- [`spack`](https://swc-project.github.io/docs/usage-spack-cli)
|
||||
- [`esbuild`](https://github.com/evanw/esbuild)
|
||||
|
|
@ -206,13 +205,13 @@ Nexus framework comes bundled with Apollo Server and runs it for you. You will n
|
|||
1. Install new dependencies
|
||||
|
||||
```tsx
|
||||
npm add express apollo-server-express
|
||||
npm install express apollo-server-express
|
||||
```
|
||||
|
||||
2. If using TypeScript then Install typings for Express
|
||||
|
||||
```tsx
|
||||
npm add -D @types/express
|
||||
npm install -D @types/express
|
||||
```
|
||||
|
||||
3. If using TypeScript then you [need to](https://github.com/apollographql/apollo-server/issues/1977#issuecomment-662946590) enable `esModuleInterop` to be able to use Apollo Server
|
||||
|
|
@ -230,7 +229,7 @@ Nexus framework comes bundled with Apollo Server and runs it for you. You will n
|
|||
|
||||
```tsx
|
||||
import { ApolloServer } from 'apollo-server-express'
|
||||
import { makeSchema, objectType } from '@nexus/schema'
|
||||
import { makeSchema, objectType } from 'nexus'
|
||||
import createExpress from 'express'
|
||||
|
||||
const schema = makeSchema({
|
||||
|
|
@ -271,8 +270,8 @@ Following from example in the _HTTP Server_ section, here is an example with a s
|
|||
```tsx
|
||||
import * as Http from 'http'
|
||||
import { ApolloServer } from 'apollo-server-express'
|
||||
import { makeSchema, subscriptionType } from '@nexus/schema'
|
||||
import createExpress from 'express'
|
||||
import { makeSchema, subscriptionType } from 'nexus'
|
||||
import express from 'express'
|
||||
|
||||
/**
|
||||
* An example streaming data source.
|
||||
|
|
@ -310,13 +309,12 @@ const apollo = new ApolloServer({
|
|||
schema,
|
||||
})
|
||||
|
||||
const express = createExpress()
|
||||
|
||||
const app = express()
|
||||
const httpServer = Http.createServer(app)
|
||||
|
||||
apollo.installSubscriptionHandlers(httpServer)
|
||||
|
||||
apollo.applyMiddleware({ app: express })
|
||||
apollo.applyMiddleware({ app })
|
||||
|
||||
httpServer.listen({ port: 4000 }, () => {
|
||||
console.log(`server at http://localhost:4000${apollo.graphqlPath}`)
|
||||
|
|
@ -339,7 +337,7 @@ Nexus Framework has some builtin logging functionality. You can approximate it a
|
|||
1. Install your logger
|
||||
|
||||
```tsx
|
||||
npm add floggy
|
||||
npm install floggy
|
||||
```
|
||||
|
||||
2. Create your application logger. The logger you export here should be used across your codebase.
|
||||
|
|
@ -368,7 +366,7 @@ Nexus Framework has some builtin logging functionality. You can approximate it a
|
|||
4. You still need to make this type safe. See _"Context API Type Discovery"_ section for more detail. What follows is just a code example without explanation.
|
||||
|
||||
```tsx
|
||||
import * as Nexus from '@nexus/schema'
|
||||
import * as Nexus from 'nexus'
|
||||
import * as Floggy from 'floggy'
|
||||
|
||||
export type Context = {
|
||||
|
|
@ -376,7 +374,7 @@ Nexus Framework has some builtin logging functionality. You can approximate it a
|
|||
}
|
||||
|
||||
Nexus.makeSchema({
|
||||
contextType: { source: __filename, alias: 'ContextModule' },
|
||||
contextType: { module: __filename, alias: 'ContextModule', export: 'Context' },
|
||||
...
|
||||
})
|
||||
```
|
||||
|
|
@ -388,13 +386,13 @@ You need to explicitly setup all custom scalars yourself. To match what Nexus Fr
|
|||
1. Install the `graphql-scalars` package
|
||||
|
||||
```json
|
||||
npm add graphql-scalars
|
||||
npm install graphql-scalars
|
||||
```
|
||||
|
||||
2. Setup the `Json` and `DateTime` scalars
|
||||
|
||||
```tsx
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema, asNexusMethod } from 'nexus'
|
||||
import { DateTimeResolver, JSONObjectResolver } from 'graphql-scalars'
|
||||
|
||||
const jsonScalar = asNexusMethod(JSONObjectResolver, 'json')
|
||||
|
|
@ -428,7 +426,7 @@ schema.objectType({
|
|||
To achieve the same level of type safety you now need to do the following.
|
||||
|
||||
1. Define and export a static context type
|
||||
2. Configure Nexus Schema to use it
|
||||
2. Configure Nexus to use it
|
||||
3. Attach your data to the context. How to do this depends on the GraphQL server abstraction you are using usually. The example below uses Apollo Server.
|
||||
|
||||
Example:
|
||||
|
|
@ -445,13 +443,14 @@ export type Context = {
|
|||
```tsx
|
||||
// 2
|
||||
|
||||
import * as Nexus from '@nexus/schema'
|
||||
import * as Nexus from 'nexus'
|
||||
import * as Path from 'path'
|
||||
|
||||
Nexus.makeSchema({
|
||||
contextType: {
|
||||
source: Path.join(__dirname, './path/to/contextModule'),
|
||||
alias: 'ContextModule'
|
||||
module: Path.join(__dirname, './path/to/contextModule.ts'),
|
||||
alias: 'ContextModule',
|
||||
export: 'Context'
|
||||
},
|
||||
...
|
||||
})
|
||||
|
|
@ -472,14 +471,14 @@ const server = new ApolloServer({
|
|||
In Nexus Framework backing types worked like this:
|
||||
|
||||
1. Export a type from any module in your app
|
||||
2. Its name appears as an option among the string literal union populating the `rootTyping` field of Nexus Schema object type definitions.
|
||||
2. Its name appears as an option among the string literal union populating the `rootTyping` field of Nexus object type definitions.
|
||||
|
||||
Nexus Schema does not have this functionality. There are a few things you can do instead.
|
||||
Nexus does not have this functionality. There are a few things you can do instead.
|
||||
|
||||
- Approach A: If you have a set of exported Backing types whose names match your GraphQL objects then you can set their `modules` in `sourceTypes` and Nexus Schema will take care of the rest.
|
||||
- Approach A: If you have a set of exported Backing types whose names match your GraphQL objects then you can set their `modules` in `sourceTypes` and Nexus will take care of the rest.
|
||||
- Approach B: If you have a set of Backing types whose names having a differing pattern than your GraphQL objects then supply a Regular Expression to the `typeMatch` property in `sourceTypes`. You can for example map `BackingUser -> User` , `BackingPost -> Post` and so on.
|
||||
- Approach C: If you have a one-off mismatch then supply an arbitrary mapping to the `mapping` property of `sourceTypes`.
|
||||
- Approach D: If you want to colocate a type mapping like how it was in Nexus Framework then use the `sourceType` field on Nexus Schema type defs. Unlike framework it accepts an object with a `path` to a module and `name` of the type to look for being exported from that module.
|
||||
- Approach D: If you want to colocate a type mapping like how it was in Nexus Framework then use the `sourceType` field on Nexus type defs. Unlike framework it accepts an object with a `path` to a module and `name` of the type to look for being exported from that module.
|
||||
|
||||
Here is an example using approach A:
|
||||
|
||||
|
|
@ -495,7 +494,7 @@ export type Foo = {
|
|||
```tsx
|
||||
// 2
|
||||
|
||||
import * as Nexus from '@nexus/schema'
|
||||
import * as Nexus from 'nexus'
|
||||
import * as Path from 'path'
|
||||
|
||||
Nexus.makeSchema({
|
||||
|
|
@ -537,13 +536,13 @@ In Nexus Framework there was a testing module for system testing your app. You n
|
|||
1. Install your test framework
|
||||
|
||||
```tsx
|
||||
npm add jest
|
||||
npm install jest
|
||||
```
|
||||
|
||||
2. If you are a TypeScript user then install and configure `ts-jest`
|
||||
|
||||
```bash
|
||||
npm add ts-jest
|
||||
npm install ts-jest
|
||||
```
|
||||
|
||||
We will configure using a `jest.config.js` module in your project root. Do not use a JSON based configuration unless you know that you won't need the dynamic code used in some later steps here.
|
||||
|
|
@ -558,7 +557,7 @@ In Nexus Framework there was a testing module for system testing your app. You n
|
|||
```
|
||||
|
||||
3. Setup your project to be able to soundly run one-off tests
|
||||
In order to run your test suite you typically need your app to be type checking. Given the Nexus Schema reflection system, this means that we need to run the app before running the tests. To setup your project for running reflection see the section _Fully Abstracted Reflection System_.
|
||||
In order to run your test suite you typically need your app to be type checking. Given the Nexus reflection system, this means that we need to run the app before running the tests. To setup your project for running reflection see the section _Fully Abstracted Reflection System_.
|
||||
|
||||
Here is an example of how this might look in your project:
|
||||
|
||||
|
|
@ -572,11 +571,11 @@ In Nexus Framework there was a testing module for system testing your app. You n
|
|||
```
|
||||
|
||||
4. Understand your TDD workflow option e.g. `jest --watch`
|
||||
In this case you need Nexus Schema reflection to be running after every change to the source code. But this also typically triggers a new test run. That test run could be faster than reflection, leading to temporary type errors that don't matter to you. You don't want these type errors to block your TDD flow otherwise you get a 🐔🥚problem. To solve this you configure ts-jest to warn instead failing on type errors. The workflow then goes like this: 1. You start your test framework in watch mode 2. You edit your source code 3. Your source code under test runs. This in turn is running Nexus schema reflection. 4. Type errors from your initial test results should be ignored. Run the test suite again (e.g. in `jest` watch mode hit `enter`). Now it is running with the complete set of types and you can trust the test results.
|
||||
In this case you need Nexus reflection to be running after every change to the source code. But this also typically triggers a new test run. That test run could be faster than reflection, leading to temporary type errors that don't matter to you. You don't want these type errors to block your TDD flow otherwise you get a 🐔🥚problem. To solve this you configure ts-jest to warn instead failing on type errors. The workflow then goes like this: 1. You start your test framework in watch mode 2. You edit your source code 3. Your source code under test runs. This in turn is running Nexus reflection. 4. Type errors from your initial test results should be ignored. Run the test suite again (e.g. in `jest` watch mode hit `enter`). Now it is running with the complete set of types and you can trust the test results.
|
||||
|
||||
There are some caveats here:
|
||||
|
||||
1. Your tests need be importing the whole of your nexus schema modules and `makeSchema` code. Otherwise reflection will result in partially generated types that may other kinds of type errors you don't care about (for example a GraphQL string-literal-based object type reference becomes invalid).
|
||||
1. Your tests need be importing the whole of your nexus modules and `makeSchema` code. Otherwise reflection will result in partially generated types that may other kinds of type errors you don't care about (for example a GraphQL string-literal-based object type reference becomes invalid).
|
||||
2. And yes, every test run following change(s) potentially requiring two runs is not ideal
|
||||
|
||||
Here is the revised jest configuration you'll need.
|
||||
|
|
@ -640,7 +639,7 @@ In Nexus Framework there was a testing module for system testing your app. You n
|
|||
6. You will need a way to run your app in tests. Here is one way [adapted from the tutorial](https://todo.com).
|
||||
|
||||
```tsx
|
||||
npm add -D graphql-request
|
||||
npm install -D graphql-request
|
||||
```
|
||||
|
||||
```tsx
|
||||
|
|
@ -689,7 +688,7 @@ Nexus Framework had a CLI for scaffolding new projects. You can approximate this
|
|||
Nexus Framework has a gradual settings API with features such as automatic mapping of environment variables to settings. You can use the [`setset`](https://github.com/jasonkuhrt/setset) package manually to gain back this functionality.
|
||||
|
||||
```tsx
|
||||
npm add setset
|
||||
npm install setset
|
||||
```
|
||||
|
||||
```tsx
|
||||
|
|
@ -714,7 +713,7 @@ settings.data.server.port // 4000
|
|||
|
||||
## Other Differences
|
||||
|
||||
Some differences between Nexus Framework and Nexus Schema and cannot be easily approximated. The follow gathers these differences for your convenience.
|
||||
Some differences between Nexus Framework and Nexus and cannot be easily approximated. The follow gathers these differences for your convenience.
|
||||
|
||||
1. CLI
|
||||
2. Framework Plugins
|
||||
|
|
|
|||
|
|
@ -4,7 +4,7 @@ title: Nexus Framework Prisma Users
|
|||
|
||||
## Hello Nexus Framework Prisma User!
|
||||
|
||||
If you're looking to migrate from the Nexus Framework over to Nexus Schema and you're using the Prisma plugin, this guide is for you.
|
||||
If you're looking to migrate from the Nexus Framework over to Nexus and you're using the Prisma plugin, this guide is for you.
|
||||
|
||||
**This guide assumes you've already followed the [Framework Users adoption Guide](/adoption-guides/nexus-framework-users).**
|
||||
|
||||
|
|
@ -13,20 +13,20 @@ If you're looking to migrate from the Nexus Framework over to Nexus Schema and y
|
|||
You will need to install the Prisma dependencies yourself now.
|
||||
|
||||
```
|
||||
npm add -D @prisma/cli
|
||||
npm add @prisma/client
|
||||
npm install -D @prisma/cli
|
||||
npm install @prisma/client
|
||||
```
|
||||
|
||||
You must also make sure that you are using the version `0.20` or later of `nexus-plugin-prisma`.
|
||||
|
||||
## Enabling the plugin
|
||||
|
||||
You will now need to work with the `makeSchema` API of `@nexus/schema` directly.
|
||||
You will now need to work with the `makeSchema` API of `nexus` directly.
|
||||
|
||||
```ts diff
|
||||
-import { use } from 'nexus'
|
||||
-import { prisma } from 'nexus-plugin-prisma'
|
||||
+import { makeSchema } from '@nexus/schema'
|
||||
+import { makeSchema } from 'nexus'
|
||||
+import { nexusPrisma } from 'nexus-plugin-prisma'
|
||||
|
||||
-use(prisma())
|
||||
|
|
@ -45,7 +45,7 @@ There are a number of defaults that the framework used to provide for you. Here'
|
|||
If you were using `t.crud` with the framework, you must also explicitly enable it with the schema plugin
|
||||
|
||||
```ts diff
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { nexusPrisma } from 'nexus-plugin-prisma'
|
||||
|
||||
makeSchema({
|
||||
|
|
@ -57,10 +57,10 @@ makeSchema({
|
|||
|
||||
### Configuring Backing types
|
||||
|
||||
To let `@nexus/schema` know of the Prisma Client types so that, for instance, your resolvers expect the right types, you must point `makeSchema` to the Prisma Client where all the types are exported.
|
||||
To let `nexus` know of the Prisma Client types so that, for instance, your resolvers expect the right types, you must point `makeSchema` to the Prisma Client where all the types are exported.
|
||||
|
||||
```ts diff
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { nexusPrisma } from 'nexus-plugin-prisma'
|
||||
|
||||
export const schema = makeSchema({
|
||||
|
|
@ -82,7 +82,7 @@ export const schema = makeSchema({
|
|||
|
||||
### Configuring Context Type
|
||||
|
||||
The framework used to automatically inject and type your context so that an instance of the client would be there for you. We know need to configure that manually. To do so, we'll first create a `context.ts` file where we'll export a type containing the Prisma Client.
|
||||
The framework used to automatically inject and type your context so that an instance of the client would be there for you. We now need to configure that manually. To do so, we'll first create a `context.ts` file where we'll export a type containing the Prisma Client.
|
||||
|
||||
```tsx
|
||||
// context.ts
|
||||
|
|
@ -96,7 +96,7 @@ export type Context = {
|
|||
Then, we'll go back to the file where we're calling `makeSchema`, and add the following configuration
|
||||
|
||||
```ts diff
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { nexusPrisma } from 'nexus-plugin-prisma'
|
||||
|
||||
export const schema = makeSchema({
|
||||
|
|
@ -122,18 +122,18 @@ export const schema = makeSchema({
|
|||
|
||||
### Configuring Custom Scalars
|
||||
|
||||
If your Prisma Schema is using either the `Json` or `DateTime` type, the framework used to provide some GraphQL scalars to map these. With `@nexus/schema`, you will need to install and do the mapping yourself.
|
||||
If your Prisma Schema is using either the `Json` or `DateTime` type, the framework used to provide some GraphQL scalars to map these. With `nexus`, you will need to install and do the mapping yourself.
|
||||
|
||||
1. Start by installing the following dependency
|
||||
|
||||
```bash
|
||||
npm install graphql-scalars
|
||||
```
|
||||
```xf
|
||||
|
||||
2. Then, add the following configuration property to the Prisma plugin
|
||||
|
||||
```ts diff
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { nexusPrisma } from 'nexus-plugin-prisma'
|
||||
+import { DateTimeResolver, JSONObjectResolver } from 'graphql-scalars'
|
||||
|
||||
|
|
@ -183,14 +183,8 @@ npx prisma generate
|
|||
|
||||
Although you already had to run the command manually with the framework plugin, here's an additional quick reminder on how to run database migrations with Prisma Migrate:
|
||||
|
||||
To generate a migrate file, run:
|
||||
To generate a migrate file and apply the migration, run:
|
||||
|
||||
```
|
||||
npx prisma migrate save --experimental
|
||||
```
|
||||
|
||||
To apply the created migration file, run:
|
||||
|
||||
```
|
||||
npx prisma migrate up --experimental
|
||||
npx prisma migrate dev --preview-feature
|
||||
```
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ metaDescription: ''
|
|||
Robust, composable type definition for GraphQL in TypeScript/JavaScript.
|
||||
|
||||
> **Note:**
|
||||
> The documentation is very new and may contain some gaps, please help us fill them in by opening issues or better yet, pull-requests when you think something could be explained better. The [examples](https://github.com/graphql-nexus/schema/tree/develop/examples) are a great place to look to better understand how the library can be used.
|
||||
> The documentation is very new and may contain some gaps, please help us fill them in by opening issues or better yet, pull-requests when you think something could be explained better. The [examples](https://github.com/graphql-nexus/nexus/tree/main/examples) are a great place to look to better understand how the library can be used.
|
||||
|
||||
Nexus aims to combine the simplicity and ease of development of SDL development approaches like [graphql-tools](https://www.apollographql.com/docs/graphql-tools/generate-schema.html) with the long-term maintainability of programmatic construction, as seen in [graphene-python](https://docs.graphene-python.org/en/latest/), [graphql-ruby](https://github.com/rmosolgo/graphql-ruby), or [graphql-js](https://github.com/graphql/graphql-js).
|
||||
|
||||
|
|
@ -17,13 +17,13 @@ Nexus builds upon the primitives of `graphql-js`, and attempts to take the simpl
|
|||
|
||||
Nexus was designed with TypeScript/JavaScript intellisense in mind, and combines TypeScript generics, conditional types, and type merging to provide full auto-generated type coverage out of the box.
|
||||
|
||||
Check out the [example projects](https://github.com/graphql-nexus/schema/tree/develop/examples) to get some ideas of what this looks like in practice, or try it out in the [playground](https://nxs.li/playground) to see what we mean!
|
||||
Check out the [example projects](https://github.com/graphql-nexus/nexus/tree/main/examples) to get some ideas of what this looks like in practice, or try it out in the [playground](https://nxs.li/playground) to see what we mean!
|
||||
|
||||
## Installation
|
||||
|
||||
```sh
|
||||
npm add @nexus/schema
|
||||
npm add graphql # required as a peer dependency
|
||||
npm install nexus
|
||||
npm install graphql # required as a peer dependency
|
||||
```
|
||||
|
||||
If you are using TypeScript version `4.1` is suggested. Nexus doesn't have a hard requirement for it yet but may in a future non-breaking release.
|
||||
|
|
@ -43,7 +43,7 @@ import {
|
|||
queryType,
|
||||
stringArg,
|
||||
list,
|
||||
} from '@nexus/schema'
|
||||
} from 'nexus'
|
||||
|
||||
const Node = interfaceType({
|
||||
name: 'Node',
|
||||
|
|
|
|||
|
|
@ -214,8 +214,7 @@ const Footer = ({ footerProps }: FooterViewProps) => {
|
|||
}
|
||||
</div>
|
||||
|
||||
<p className="social-text">Prisma © 2018-2020</p>
|
||||
<p>Made with ❤️ in Berlin</p>
|
||||
<p className="social-text">Tim Griesser © 2018-2022</p>
|
||||
</div>
|
||||
</SocialWrapper>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -195,7 +195,7 @@ const Header = ({ headerProps }: HeaderViewProps) => {
|
|||
))}
|
||||
</NavLinks>
|
||||
<Link
|
||||
to={'https://github.com/graphql-nexus/schema'}
|
||||
to={'https://github.com/graphql-nexus/nexus'}
|
||||
style={{
|
||||
color: 'white',
|
||||
textDecoration: 'none',
|
||||
|
|
|
|||
|
|
@ -249,7 +249,6 @@ hr {
|
|||
|
||||
.list li {
|
||||
padding-left: 20px;
|
||||
text-indent: -1em;
|
||||
margin-top: 10px;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -34,6 +34,6 @@ npm run examples
|
|||
- [apollo-fullstack](apollo-fullstack)
|
||||
- [star-wars](star-wars)
|
||||
- [kitchen-sink](kitchen-sink)
|
||||
- [nexus-prisma](nexus-prisma)
|
||||
- [with-prisma](with-prisma)
|
||||
|
||||
> The `nexus-prisma` example is not included when all examples are ran at once. You can try it by following the instructions in its [README](nexus-prisma) instead.
|
||||
> The `with-prisma` example is not included when all examples are ran at once. You can try it by following the instructions in its [README](with-prisma) instead.
|
||||
|
|
|
|||
|
|
@ -16,16 +16,16 @@
|
|||
]
|
||||
},
|
||||
"dependencies": {
|
||||
"@nexus/schema": "0.14.0",
|
||||
"apollo-datasource": "^0.2.0",
|
||||
"apollo-datasource-rest": "^0.2.0",
|
||||
"apollo-server": "^2.18.1",
|
||||
"apollo-server-testing": "^2.18.1",
|
||||
"dedent": "^0.7.0",
|
||||
"fullstack-tutorial": "apollographql/fullstack-tutorial.git",
|
||||
"graphql": "^15.3.0",
|
||||
"graphql": "^16.3.0",
|
||||
"graphql-tools": "^4.0.7",
|
||||
"isemail": "^3.2.0",
|
||||
"nexus": "^1.0.0",
|
||||
"sequelize": "^5.21.2",
|
||||
"sqlite3": "^4.1.0"
|
||||
},
|
||||
|
|
@ -39,6 +39,6 @@
|
|||
"node-fetch": "^2.2.1",
|
||||
"prettier": "^1.19.1",
|
||||
"ts-node-dev": "^1.0.0-pre.30",
|
||||
"typescript": "^3.9"
|
||||
"typescript": "^4.5.5"
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
// @ts-check
|
||||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { ApolloServer } from 'apollo-server'
|
||||
import { Request } from 'express'
|
||||
import isEmail from 'isemail'
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { list, objectType } from '@nexus/schema'
|
||||
import { list, objectType } from 'nexus'
|
||||
import dedent from 'dedent'
|
||||
|
||||
export const Launch = objectType({
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { objectType, enumType, arg, nullable } from '@nexus/schema'
|
||||
import { objectType, enumType, arg, nullable } from 'nexus'
|
||||
|
||||
export const Mission = objectType({
|
||||
name: 'Mission',
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { idArg, list, nonNull, nullable, objectType, stringArg } from '@nexus/schema'
|
||||
import { idArg, list, nonNull, objectType, stringArg } from 'nexus'
|
||||
|
||||
export const Mutation = objectType({
|
||||
name: 'Mutation',
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
/// <reference path="../fullstack-typegen.ts" />
|
||||
import { idArg, intArg, nonNull, objectType, stringArg } from '@nexus/schema'
|
||||
import { idArg, intArg, nonNull, objectType, stringArg } from 'nexus'
|
||||
import { Utils } from '../typeDefs'
|
||||
const utils: Utils = require('fullstack-tutorial/final/server/src/utils.js')
|
||||
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { nullable, objectType } from '@nexus/schema'
|
||||
import { nullable, objectType } from 'nexus'
|
||||
|
||||
export const Rocket = objectType({
|
||||
name: 'Rocket',
|
||||
|
|
|
|||
|
|
@ -1,25 +1,25 @@
|
|||
import { objectType } from "@nexus/schema";
|
||||
import { objectType } from 'nexus'
|
||||
|
||||
export const User = objectType({
|
||||
name: "User",
|
||||
name: 'User',
|
||||
definition(t) {
|
||||
t.id("id");
|
||||
t.string("email");
|
||||
t.list.field("trips", {
|
||||
type: "Launch",
|
||||
t.id('id')
|
||||
t.string('email')
|
||||
t.list.field('trips', {
|
||||
type: 'Launch',
|
||||
async resolve(_, __, { dataSources }) {
|
||||
// get ids of launches by user
|
||||
const launchIds = await dataSources.userAPI.getLaunchIdsByUser();
|
||||
const launchIds = await dataSources.userAPI.getLaunchIdsByUser()
|
||||
if (!launchIds.length) {
|
||||
return [];
|
||||
return []
|
||||
}
|
||||
// look up those launches by their ids
|
||||
return (
|
||||
dataSources.launchAPI.getLaunchesByIds({
|
||||
launchIds,
|
||||
}) || []
|
||||
);
|
||||
)
|
||||
},
|
||||
});
|
||||
})
|
||||
},
|
||||
});
|
||||
})
|
||||
|
|
|
|||
|
|
@ -406,14 +406,6 @@
|
|||
"@types/istanbul-reports" "^1.1.1"
|
||||
"@types/yargs" "^12.0.9"
|
||||
|
||||
"@nexus/schema@0.14.0":
|
||||
version "0.14.0"
|
||||
resolved "https://registry.yarnpkg.com/@nexus/schema/-/schema-0.14.0.tgz#3242f4d02ec9458914deb638b434bcfbd5888d2e"
|
||||
integrity sha512-niJFcOm1F2s3kwj+j3ips4sIIJaTNh5Auq+zcHwOsRBqSYsFJnA/8QUKMb1wjVIEqS+Jl71Sj4xFdg3/njlm9A==
|
||||
dependencies:
|
||||
iterall "^1.2.2"
|
||||
tslib "^1.9.3"
|
||||
|
||||
"@oclif/color@^0.0.0":
|
||||
version "0.0.0"
|
||||
resolved "https://registry.yarnpkg.com/@oclif/color/-/color-0.0.0.tgz#54939bbd16d1387511bf1a48ccda1a417248e6a9"
|
||||
|
|
@ -3177,6 +3169,11 @@ graphql@^15.3.0:
|
|||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-15.3.0.tgz#3ad2b0caab0d110e3be4a5a9b2aa281e362b5278"
|
||||
integrity sha512-GTCJtzJmkFLWRfFJuoo9RWWa/FfamUHgiFosxi/X1Ani4AVWbeyBenZTNX6dM+7WSbbFfTo/25eh0LLkwHMw2w==
|
||||
|
||||
graphql@^16.3.0:
|
||||
version "16.3.0"
|
||||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-16.3.0.tgz#a91e24d10babf9e60c706919bb182b53ccdffc05"
|
||||
integrity sha512-xm+ANmA16BzCT5pLjuXySbQVFwH3oJctUVdy81w1sV0vBU0KgDdBGtxQOUd5zqOBk/JayAFeG8Dlmeq74rjm/A==
|
||||
|
||||
growly@^1.2.0, growly@^1.3.0:
|
||||
version "1.3.0"
|
||||
resolved "https://registry.yarnpkg.com/growly/-/growly-1.3.0.tgz#f10748cbe76af964b7c96c93c6bcc28af120c081"
|
||||
|
|
@ -3859,6 +3856,11 @@ iterall@^1.1.3, iterall@^1.2.1, iterall@^1.2.2:
|
|||
resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.2.2.tgz#92d70deb8028e0c39ff3164fdbf4d8b088130cd7"
|
||||
integrity sha512-yynBb1g+RFUPY64fTrFv7nsjRrENBQJaX2UL+2Szc9REFrSNm1rpSXHGzhmAy7a9uv3vlvgBlXnf9RqmPH1/DA==
|
||||
|
||||
iterall@^1.3.0:
|
||||
version "1.3.0"
|
||||
resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.3.0.tgz#afcb08492e2915cbd8a0884eb93a8c94d0d72fea"
|
||||
integrity sha512-QZ9qOMdF+QLHxy1QIpUHUU1D5pS2CG2P69LF6L6CPjPYA/XMOmKV3PZpawHoAjHNyB0swdVTRxdYT4tbBbxqwg==
|
||||
|
||||
java-properties@^0.2.9:
|
||||
version "0.2.10"
|
||||
resolved "https://registry.yarnpkg.com/java-properties/-/java-properties-0.2.10.tgz#2551560c25fa1ad94d998218178f233ad9b18f60"
|
||||
|
|
@ -4974,6 +4976,14 @@ netrc-parser@^3.1.4:
|
|||
debug "^3.1.0"
|
||||
execa "^0.10.0"
|
||||
|
||||
nexus@^1.0.0:
|
||||
version "1.0.0"
|
||||
resolved "https://registry.yarnpkg.com/nexus/-/nexus-1.0.0.tgz#633b39abae1d7e9472ca40e37bb5d3e1263f6aa3"
|
||||
integrity sha512-Toa91s9BJsX8pDX34QkOyKdnw8MmuOQkEboZMKSxvF9mWuAFkY74Zj1ssaexeV7yTQ7HoLQYUQ00FaWzXPmggQ==
|
||||
dependencies:
|
||||
iterall "^1.3.0"
|
||||
tslib "^2.0.3"
|
||||
|
||||
nice-try@^1.0.4:
|
||||
version "1.0.5"
|
||||
resolved "https://registry.yarnpkg.com/nice-try/-/nice-try-1.0.5.tgz#a3378a7696ce7d223e88fc9b764bd7ef1089e366"
|
||||
|
|
@ -6744,6 +6754,11 @@ tslib@^1.10.0:
|
|||
resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.13.0.tgz#c881e13cc7015894ed914862d276436fa9a47043"
|
||||
integrity sha512-i/6DQjL8Xf3be4K/E6Wgpekn5Qasl1usyw++dAA35Ue5orEn65VIxOA+YvNNl9HV3qv70T7CNwjODHZrLwvd1Q==
|
||||
|
||||
tslib@^2.0.3:
|
||||
version "2.0.3"
|
||||
resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.0.3.tgz#8e0741ac45fc0c226e58a17bfc3e64b9bc6ca61c"
|
||||
integrity sha512-uZtkfKblCEQtZKBF6EBXVZeQNl82yqtDQdv+eck8u7tdPxjLu2/lp5/uPW+um2tpuxINHWy3GhiccY7QgEaVHQ==
|
||||
|
||||
tty@^1.0.1:
|
||||
version "1.0.1"
|
||||
resolved "https://registry.yarnpkg.com/tty/-/tty-1.0.1.tgz#e4409ac98b0dd1c50b59ff38e86eac3f0764ee45"
|
||||
|
|
@ -6789,10 +6804,10 @@ type-is@~1.6.17, type-is@~1.6.18:
|
|||
media-typer "0.3.0"
|
||||
mime-types "~2.1.24"
|
||||
|
||||
typescript@^3.9:
|
||||
version "3.9.7"
|
||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-3.9.7.tgz#98d600a5ebdc38f40cb277522f12dc800e9e25fa"
|
||||
integrity sha512-BLbiRkiBzAwsjut4x/dsibSTB6yWpwT5qWmC2OfuCg3GgVQCSgMs4vEctYPhsaGtd0AeuuHMkjZ2h2WG8MSzRw==
|
||||
typescript@^4.5.5:
|
||||
version "4.5.5"
|
||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.5.5.tgz#d8c953832d28924a9e3d37c73d729c846c5896f3"
|
||||
integrity sha512-TCTIul70LyWe6IJWT8QSYeA54WQe8EjQFU4wY52Fasj5UKx88LNYKCgBEHcOMOrFF1rKGbD8v/xcNWVUq9SymA==
|
||||
|
||||
uglify-js@^3.1.4:
|
||||
version "3.4.9"
|
||||
|
|
|
|||
|
|
@ -9,12 +9,13 @@
|
|||
"dataloader": "tgriesser/dataloader.git#ts-types",
|
||||
"express": "^4.16.4",
|
||||
"ghost": "^3.35.3",
|
||||
"graphql": "^15.3.0",
|
||||
"graphql": "^16.3.0",
|
||||
"graphql-scalars": "^1.2.6",
|
||||
"graphql-tools": "^4.0.7",
|
||||
"knex": "^0.19.5",
|
||||
"lodash": "^4.17.11",
|
||||
"mysql": "^2.16.0"
|
||||
"mysql": "^2.16.0",
|
||||
"nexus": "^1.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@tgriesser/schemats": "^6.1.0",
|
||||
|
|
@ -26,6 +27,6 @@
|
|||
"prettier": "^1.19.1",
|
||||
"ts-node": "^8.0.2",
|
||||
"ts-node-dev": "^1.0.0-pre.30",
|
||||
"typescript": "^3.9"
|
||||
"typescript": "^4.5.5"
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,9 +1,9 @@
|
|||
/** This file was generated by Nexus Schema Do not make changes to this file directly */
|
||||
|
||||
import * as db from './ghost-db-types'
|
||||
import { core } from 'nexus'
|
||||
import { FieldAuthorizeResolver } from 'nexus/dist/plugins/fieldAuthorizePlugin'
|
||||
import { Context } from './../data-sources/Context'
|
||||
import { FieldAuthorizeResolver } from '@nexus/schema/dist/plugins/fieldAuthorizePlugin'
|
||||
import { core } from '@nexus/schema'
|
||||
import * as db from './ghost-db-types'
|
||||
declare global {
|
||||
interface NexusGenCustomInputMethods<TypeName extends string> {
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { fieldAuthorizePlugin, makeSchema } from '@nexus/schema'
|
||||
import { fieldAuthorizePlugin, makeSchema } from 'nexus'
|
||||
import path from 'path'
|
||||
import * as allTypes from './schema'
|
||||
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { objectType } from '@nexus/schema'
|
||||
import { objectType } from 'nexus'
|
||||
|
||||
export const Post = objectType({
|
||||
name: 'Post',
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { idArg, nonNull, queryType } from '@nexus/schema'
|
||||
import { idArg, nonNull, queryType } from 'nexus'
|
||||
import { Post } from './Post'
|
||||
import { User } from './User'
|
||||
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { nonNull, objectType } from '@nexus/schema'
|
||||
import { nonNull, objectType } from 'nexus'
|
||||
|
||||
export const User = objectType({
|
||||
name: 'User',
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { decorateType } from '@nexus/schema'
|
||||
import { decorateType } from 'nexus'
|
||||
import { GraphQLDate } from 'graphql-scalars'
|
||||
|
||||
export const GQLDate = decorateType(GraphQLDate, {
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load Diff
|
|
@ -4,16 +4,16 @@
|
|||
"start": "nodemon src/index.js"
|
||||
},
|
||||
"dependencies": {
|
||||
"@nexus/schema": "^0.16.0",
|
||||
"apollo-server": "^2.18.1",
|
||||
"githunt-api": "peggyrayzis/GitHunt-API",
|
||||
"graphql": "^14.5.8",
|
||||
"graphql-tools": "^4.0.7"
|
||||
"graphql": "^16.3.0",
|
||||
"graphql-tools": "^4.0.7",
|
||||
"nexus": "^1.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"nodemon": "^1.18.6",
|
||||
"prettier": "^1.19.1",
|
||||
"sqlite3": "^4.1.0",
|
||||
"typescript": "^3.9"
|
||||
"typescript": "^4.5.5"
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
// @ts-check
|
||||
const { ApolloServer } = require('apollo-server')
|
||||
const path = require('path')
|
||||
const { makeSchema } = require('@nexus/schema')
|
||||
const { makeSchema } = require('nexus')
|
||||
const types = require('./schema')
|
||||
|
||||
const schema = makeSchema({
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
// @ts-check
|
||||
const { enumType, objectType, arg, intArg, stringArg, nonNull } = require('@nexus/schema')
|
||||
const { enumType, objectType, arg, intArg, stringArg, nonNull } = require('nexus')
|
||||
|
||||
exports.FeedType = enumType({
|
||||
name: 'FeedType',
|
||||
|
|
@ -117,7 +117,7 @@ exports.Mutation = objectType({
|
|||
|
||||
/**
|
||||
* Example of using functions to mixin fields across types
|
||||
* @type {(t: import('@nexus/schema').core.ObjectDefinitionBlock<any>) => void}
|
||||
* @type {(t: import('nexus').core.ObjectDefinitionBlock<any>) => void}
|
||||
*/
|
||||
const commonFields = (t) => {
|
||||
t.int('id', { description: 'The SQL ID of this entry' })
|
||||
|
|
|
|||
|
|
@ -35,14 +35,6 @@
|
|||
dependencies:
|
||||
xss "^1.0.6"
|
||||
|
||||
"@nexus/schema@^0.16.0":
|
||||
version "0.16.0"
|
||||
resolved "https://registry.yarnpkg.com/@nexus/schema/-/schema-0.16.0.tgz#cbf2b70eb47a854e4bcec849583368d7e7048087"
|
||||
integrity sha512-H+JJDycjcilvsRtLySpwfVXp1gYiOqPPLQdq04R4Vp5S400PpdADQlKMV4EvpBJ/BCxwQ8XwP8+nrOKvDZLLUw==
|
||||
dependencies:
|
||||
iterall "^1.2.2"
|
||||
tslib "^1.9.3"
|
||||
|
||||
"@protobufjs/aspromise@^1.1.1", "@protobufjs/aspromise@^1.1.2":
|
||||
version "1.1.2"
|
||||
resolved "https://registry.yarnpkg.com/@protobufjs/aspromise/-/aspromise-1.1.2.tgz#9b8b0cc663d669a7d8f6f5d0893a14d348f30fbf"
|
||||
|
|
@ -2970,18 +2962,16 @@ graphql-upload@^8.0.2:
|
|||
dependencies:
|
||||
iterall "^1.1.0"
|
||||
|
||||
graphql@^14.5.8:
|
||||
version "14.5.8"
|
||||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-14.5.8.tgz#504f3d3114cb9a0a3f359bbbcf38d9e5bf6a6b3c"
|
||||
integrity sha512-MMwmi0zlVLQKLdGiMfWkgQD7dY/TUKt4L+zgJ/aR0Howebod3aNgP5JkgvAULiR2HPVZaP2VEElqtdidHweLkg==
|
||||
dependencies:
|
||||
iterall "^1.2.2"
|
||||
|
||||
graphql@^15.3.0:
|
||||
version "15.3.0"
|
||||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-15.3.0.tgz#3ad2b0caab0d110e3be4a5a9b2aa281e362b5278"
|
||||
integrity sha512-GTCJtzJmkFLWRfFJuoo9RWWa/FfamUHgiFosxi/X1Ani4AVWbeyBenZTNX6dM+7WSbbFfTo/25eh0LLkwHMw2w==
|
||||
|
||||
graphql@^16.3.0:
|
||||
version "16.3.0"
|
||||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-16.3.0.tgz#a91e24d10babf9e60c706919bb182b53ccdffc05"
|
||||
integrity sha512-xm+ANmA16BzCT5pLjuXySbQVFwH3oJctUVdy81w1sV0vBU0KgDdBGtxQOUd5zqOBk/JayAFeG8Dlmeq74rjm/A==
|
||||
|
||||
har-schema@^2.0.0:
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/har-schema/-/har-schema-2.0.0.tgz#a94c2224ebcac04782a0d9035521f24735b7ec92"
|
||||
|
|
@ -3524,12 +3514,12 @@ isstream@~0.1.2:
|
|||
resolved "https://registry.yarnpkg.com/isstream/-/isstream-0.1.2.tgz#47e63f7af55afa6f92e1500e690eb8b8529c099a"
|
||||
integrity sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=
|
||||
|
||||
iterall@^1.1.0, iterall@^1.1.3, iterall@^1.2.1, iterall@^1.2.2:
|
||||
iterall@^1.1.0, iterall@^1.1.3, iterall@^1.2.1:
|
||||
version "1.2.2"
|
||||
resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.2.2.tgz#92d70deb8028e0c39ff3164fdbf4d8b088130cd7"
|
||||
integrity sha512-yynBb1g+RFUPY64fTrFv7nsjRrENBQJaX2UL+2Szc9REFrSNm1rpSXHGzhmAy7a9uv3vlvgBlXnf9RqmPH1/DA==
|
||||
|
||||
iterall@^1.1.1:
|
||||
iterall@^1.1.1, iterall@^1.3.0:
|
||||
version "1.3.0"
|
||||
resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.3.0.tgz#afcb08492e2915cbd8a0884eb93a8c94d0d72fea"
|
||||
integrity sha512-QZ9qOMdF+QLHxy1QIpUHUU1D5pS2CG2P69LF6L6CPjPYA/XMOmKV3PZpawHoAjHNyB0swdVTRxdYT4tbBbxqwg==
|
||||
|
|
@ -3999,6 +3989,14 @@ negotiator@0.6.2:
|
|||
resolved "https://registry.yarnpkg.com/negotiator/-/negotiator-0.6.2.tgz#feacf7ccf525a77ae9634436a64883ffeca346fb"
|
||||
integrity sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==
|
||||
|
||||
nexus@^1.0.0:
|
||||
version "1.0.0"
|
||||
resolved "https://registry.yarnpkg.com/nexus/-/nexus-1.0.0.tgz#633b39abae1d7e9472ca40e37bb5d3e1263f6aa3"
|
||||
integrity sha512-Toa91s9BJsX8pDX34QkOyKdnw8MmuOQkEboZMKSxvF9mWuAFkY74Zj1ssaexeV7yTQ7HoLQYUQ00FaWzXPmggQ==
|
||||
dependencies:
|
||||
iterall "^1.3.0"
|
||||
tslib "^2.0.3"
|
||||
|
||||
node-fetch@^2.1.2:
|
||||
version "2.3.0"
|
||||
resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.3.0.tgz#1a1d940bbfb916a1d3e0219f037e89e71f8c5fa5"
|
||||
|
|
@ -5555,6 +5553,11 @@ tslib@^1.9.3:
|
|||
resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.10.0.tgz#c3c19f95973fb0a62973fb09d90d961ee43e5c8a"
|
||||
integrity sha512-qOebF53frne81cf0S9B41ByenJ3/IuH8yJKngAX35CmiZySA0khhkovshKK+jGCaMnVomla7gVlIcc3EvKPbTQ==
|
||||
|
||||
tslib@^2.0.3:
|
||||
version "2.0.3"
|
||||
resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.0.3.tgz#8e0741ac45fc0c226e58a17bfc3e64b9bc6ca61c"
|
||||
integrity sha512-uZtkfKblCEQtZKBF6EBXVZeQNl82yqtDQdv+eck8u7tdPxjLu2/lp5/uPW+um2tpuxINHWy3GhiccY7QgEaVHQ==
|
||||
|
||||
tunnel-agent@^0.6.0:
|
||||
version "0.6.0"
|
||||
resolved "https://registry.yarnpkg.com/tunnel-agent/-/tunnel-agent-0.6.0.tgz#27a5dea06b36b04a0a9966774b290868f0fc40fd"
|
||||
|
|
@ -5583,10 +5586,10 @@ type-is@~1.6.14, type-is@~1.6.17, type-is@~1.6.18:
|
|||
media-typer "0.3.0"
|
||||
mime-types "~2.1.24"
|
||||
|
||||
typescript@^3.9:
|
||||
version "3.9.7"
|
||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-3.9.7.tgz#98d600a5ebdc38f40cb277522f12dc800e9e25fa"
|
||||
integrity sha512-BLbiRkiBzAwsjut4x/dsibSTB6yWpwT5qWmC2OfuCg3GgVQCSgMs4vEctYPhsaGtd0AeuuHMkjZ2h2WG8MSzRw==
|
||||
typescript@^4.5.5:
|
||||
version "4.5.5"
|
||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.5.5.tgz#d8c953832d28924a9e3d37c73d729c846c5896f3"
|
||||
integrity sha512-TCTIul70LyWe6IJWT8QSYeA54WQe8EjQFU4wY52Fasj5UKx88LNYKCgBEHcOMOrFF1rKGbD8v/xcNWVUq9SymA==
|
||||
|
||||
uid-safe@~2.1.4:
|
||||
version "2.1.5"
|
||||
|
|
|
|||
|
|
@ -19,24 +19,24 @@ interface Baz {
|
|||
|
||||
type BooleanConnection {
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-Edge-Types
|
||||
https://relay.dev/graphql/connections.htm#sec-Edge-Types
|
||||
"""
|
||||
edges: [BooleanEdge]
|
||||
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-undefined.PageInfo
|
||||
https://relay.dev/graphql/connections.htm#sec-undefined.PageInfo
|
||||
"""
|
||||
pageInfo: PageInfo!
|
||||
}
|
||||
|
||||
type BooleanEdge {
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-Cursor
|
||||
https://relay.dev/graphql/connections.htm#sec-Cursor
|
||||
"""
|
||||
cursor: String!
|
||||
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-Node
|
||||
https://relay.dev/graphql/connections.htm#sec-Node
|
||||
"""
|
||||
node: Boolean
|
||||
}
|
||||
|
|
@ -49,24 +49,24 @@ scalar Date
|
|||
|
||||
type DateConnection {
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-Edge-Types
|
||||
https://relay.dev/graphql/connections.htm#sec-Edge-Types
|
||||
"""
|
||||
edges: [DateEdge]
|
||||
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-undefined.PageInfo
|
||||
https://relay.dev/graphql/connections.htm#sec-undefined.PageInfo
|
||||
"""
|
||||
pageInfo: PageInfo!
|
||||
}
|
||||
|
||||
type DateEdge {
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-Cursor
|
||||
https://relay.dev/graphql/connections.htm#sec-Cursor
|
||||
"""
|
||||
cursor: String!
|
||||
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-Node
|
||||
https://relay.dev/graphql/connections.htm#sec-Node
|
||||
"""
|
||||
node: Date
|
||||
}
|
||||
|
|
@ -104,7 +104,7 @@ interface Node {
|
|||
}
|
||||
|
||||
"""
|
||||
PageInfo cursor, as defined in https://facebook.github.io/relay/graphql/connections.htm#sec-undefined.PageInfo
|
||||
PageInfo cursor, as defined in https://relay.dev/graphql/connections.htm#sec-undefined.PageInfo
|
||||
"""
|
||||
type PageInfo {
|
||||
"""
|
||||
|
|
@ -306,24 +306,24 @@ type User {
|
|||
|
||||
type UserConnection {
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-Edge-Types
|
||||
https://relay.dev/graphql/connections.htm#sec-Edge-Types
|
||||
"""
|
||||
edges: [UserEdge]
|
||||
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-undefined.PageInfo
|
||||
https://relay.dev/graphql/connections.htm#sec-undefined.PageInfo
|
||||
"""
|
||||
pageInfo: PageInfo!
|
||||
}
|
||||
|
||||
type UserEdge {
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-Cursor
|
||||
https://relay.dev/graphql/connections.htm#sec-Cursor
|
||||
"""
|
||||
cursor: String!
|
||||
|
||||
"""
|
||||
https://facebook.github.io/relay/graphql/connections.htm#sec-Node
|
||||
https://relay.dev/graphql/connections.htm#sec-Node
|
||||
"""
|
||||
node: User
|
||||
}
|
||||
|
|
|
|||
|
|
@ -9,17 +9,17 @@
|
|||
"start": "ts-node --transpile-only src/index.ts"
|
||||
},
|
||||
"dependencies": {
|
||||
"@nexus/schema": "^0.16.0",
|
||||
"apollo-server": "^2.18.1",
|
||||
"graphql": "^15.3.0",
|
||||
"graphql": "^16.3.0",
|
||||
"graphql-query-complexity": "^0.4.1",
|
||||
"graphql-relay": "^0.6.0",
|
||||
"graphql-subscriptions": "^1.0.0",
|
||||
"graphql-tools": "^4.0.7",
|
||||
"lodash": "^4.17.15",
|
||||
"nexus": "^1.0.0",
|
||||
"subscriptions-transport-ws": "^0.9.15",
|
||||
"ts-node": "^8.5.4",
|
||||
"typescript": "^3.9"
|
||||
"typescript": "^4.5.5"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/graphql-relay": "^0.4.11",
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { plugin, interfaceType, FieldResolver, nonNull } from '@nexus/schema'
|
||||
import { plugin, interfaceType, FieldResolver, nonNull } from 'nexus'
|
||||
|
||||
export const logMutationTimePlugin = plugin({
|
||||
name: 'LogMutationTime',
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ import {
|
|||
makeSchema,
|
||||
nullabilityGuardPlugin,
|
||||
queryComplexityPlugin,
|
||||
} from '@nexus/schema'
|
||||
} from 'nexus'
|
||||
import { ApolloServer } from 'apollo-server'
|
||||
import { separateOperations } from 'graphql'
|
||||
import { fieldExtensionsEstimator, getComplexity, simpleEstimator } from 'graphql-query-complexity'
|
||||
|
|
@ -21,7 +21,11 @@ const schema = makeSchema({
|
|||
types,
|
||||
outputs: {
|
||||
schema: path.join(__dirname, '../kitchen-sink-schema.graphql'),
|
||||
typegen: path.join(__dirname, './kitchen-sink.gen.ts'),
|
||||
typegen: {
|
||||
outputPath: path.join(__dirname, './kitchen-sink.gen.ts'),
|
||||
globalsPath: path.join(__dirname, './kitchen-sink-globals.gen.ts'),
|
||||
declareInputs: true,
|
||||
},
|
||||
},
|
||||
plugins: [
|
||||
NodePlugin,
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ import {
|
|||
queryField,
|
||||
scalarType,
|
||||
unionType,
|
||||
} from '@nexus/schema'
|
||||
} from 'nexus'
|
||||
import { connectionFromArray } from 'graphql-relay'
|
||||
import _ from 'lodash'
|
||||
|
||||
|
|
@ -391,9 +391,17 @@ export const MoreQueryFields = extendType({
|
|||
|
||||
export const DateScalar = scalarType({
|
||||
name: 'Date',
|
||||
serialize: (value) => value.getTime(),
|
||||
parseValue: (value) => new Date(value),
|
||||
parseLiteral: (ast) => (ast.kind === 'IntValue' ? new Date(ast.value) : null),
|
||||
serialize: (value) => (value as Date).toISOString(),
|
||||
parseValue: (value) => new Date(value as string | number),
|
||||
parseLiteral: (ast) => {
|
||||
if (ast.kind === 'IntValue' || ast.kind === 'StringValue') {
|
||||
const d = new Date(ast.value)
|
||||
if (!isNaN(d.valueOf())) {
|
||||
return d
|
||||
}
|
||||
}
|
||||
throw new Error('Invalid date')
|
||||
},
|
||||
asNexusMethod: 'date',
|
||||
sourceType: 'Date',
|
||||
})
|
||||
|
|
|
|||
|
|
@ -0,0 +1,65 @@
|
|||
/** This file was generated by Nexus Schema Do not make changes to this file directly */
|
||||
|
||||
import type { NexusGenTypes } from './kitchen-sink.gen'
|
||||
declare global {
|
||||
interface NexusGenCustomInputMethods<TypeName extends string> {
|
||||
date<FieldName extends string>(
|
||||
fieldName: FieldName,
|
||||
opts?: core.CommonInputFieldConfig<TypeName, FieldName>
|
||||
): void // "Date";
|
||||
}
|
||||
}
|
||||
declare global {
|
||||
interface NexusGenCustomOutputMethods<TypeName extends string> {
|
||||
date<FieldName extends string>(
|
||||
fieldName: FieldName,
|
||||
...opts: core.ScalarOutSpread<TypeName, FieldName>
|
||||
): void // "Date";
|
||||
/**
|
||||
* Adds a Relay-style connection to the type, with numerous options for configuration
|
||||
*
|
||||
* @see https://nexusjs.org/docs/plugins/connection
|
||||
*/
|
||||
connectionField<FieldName extends string>(
|
||||
fieldName: FieldName,
|
||||
config: connectionPluginCore.ConnectionFieldConfig<TypeName, FieldName>
|
||||
): void
|
||||
}
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface NexusGen extends NexusGenTypes {}
|
||||
}
|
||||
|
||||
import type { core, connectionPluginCore } from 'nexus'
|
||||
import type { QueryComplexity } from 'nexus/dist/plugins/queryComplexityPlugin'
|
||||
import type { FieldAuthorizeResolver } from 'nexus/dist/plugins/fieldAuthorizePlugin'
|
||||
|
||||
declare global {
|
||||
interface NexusGenPluginTypeConfig<TypeName extends string> {
|
||||
node?: string | core.FieldResolver<TypeName, any>
|
||||
}
|
||||
interface NexusGenPluginInputTypeConfig<TypeName extends string> {}
|
||||
interface NexusGenPluginFieldConfig<TypeName extends string, FieldName extends string> {
|
||||
/**
|
||||
* The complexity for an individual field. Return a number or a function that returns a number to specify
|
||||
* the complexity for this field.
|
||||
*/
|
||||
complexity?: QueryComplexity<TypeName, FieldName>
|
||||
/**
|
||||
* Authorization for an individual field. Returning "true" or "Promise<true>" means the field can be
|
||||
* accessed. Returning "false" or "Promise<false>" will respond with a "Not Authorized" error for the
|
||||
* field. Returning or throwing an error will also prevent the resolver from executing.
|
||||
*/
|
||||
authorize?: FieldAuthorizeResolver<TypeName, FieldName>
|
||||
/**
|
||||
* The nullability guard can be helpful, but is also a potentially expensive operation for lists. We need
|
||||
* to iterate the entire list to check for null items to guard against. Set this to true to skip the null
|
||||
* guard on a specific field if you know there's no potential for unsafe types.
|
||||
*/
|
||||
skipNullGuard?: boolean
|
||||
}
|
||||
interface NexusGenPluginInputFieldConfig<TypeName extends string, FieldName extends string> {}
|
||||
interface NexusGenPluginSchemaConfig {}
|
||||
interface NexusGenPluginArgConfig {}
|
||||
}
|
||||
|
|
@ -1,61 +1,34 @@
|
|||
/** This file was generated by Nexus Schema Do not make changes to this file directly */
|
||||
|
||||
import { UnusedInterfaceTypeDef } from './kitchen-sink-definitions'
|
||||
import { core, connectionPluginCore } from '@nexus/schema'
|
||||
import { QueryComplexity } from '@nexus/schema/dist/plugins/queryComplexityPlugin'
|
||||
import { FieldAuthorizeResolver } from '@nexus/schema/dist/plugins/fieldAuthorizePlugin'
|
||||
declare global {
|
||||
interface NexusGenCustomInputMethods<TypeName extends string> {
|
||||
date<FieldName extends string>(
|
||||
fieldName: FieldName,
|
||||
opts?: core.CommonInputFieldConfig<TypeName, FieldName>
|
||||
): void // "Date";
|
||||
}
|
||||
}
|
||||
declare global {
|
||||
interface NexusGenCustomOutputMethods<TypeName extends string> {
|
||||
date<FieldName extends string>(
|
||||
fieldName: FieldName,
|
||||
...opts: core.ScalarOutSpread<TypeName, FieldName>
|
||||
): void // "Date";
|
||||
/**
|
||||
* Adds a Relay-style connection to the type, with numerous options for configuration
|
||||
*
|
||||
* @see https://nexusjs.org/docs/plugins/connection
|
||||
*/
|
||||
connectionField<FieldName extends string>(
|
||||
fieldName: FieldName,
|
||||
config: connectionPluginCore.ConnectionFieldConfig<TypeName, FieldName>
|
||||
): void
|
||||
}
|
||||
import type { UnusedInterfaceTypeDef } from './kitchen-sink-definitions'
|
||||
import type { core } from 'nexus'
|
||||
|
||||
export interface InputType {
|
||||
answer?: number | null // Int
|
||||
key: string // String!
|
||||
nestedInput?: InputType2 | null // InputType2
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface NexusGen extends NexusGenTypes {}
|
||||
export interface InputType2 {
|
||||
answer?: number | null // Int
|
||||
key: string // String!
|
||||
someDate: NexusGenScalars['Date'] // Date!
|
||||
}
|
||||
|
||||
export interface NestedType {
|
||||
veryNested?: string | null // String
|
||||
}
|
||||
|
||||
export interface SomeArg {
|
||||
arg?: NestedType | null // NestedType
|
||||
someField?: string | null // String
|
||||
}
|
||||
|
||||
export interface NexusGenInputs {
|
||||
InputType: {
|
||||
// input type
|
||||
answer?: number | null // Int
|
||||
key: string // String!
|
||||
nestedInput?: NexusGenInputs['InputType2'] | null // InputType2
|
||||
}
|
||||
InputType2: {
|
||||
// input type
|
||||
answer?: number | null // Int
|
||||
key: string // String!
|
||||
someDate: NexusGenScalars['Date'] // Date!
|
||||
}
|
||||
NestedType: {
|
||||
// input type
|
||||
veryNested?: string | null // String
|
||||
}
|
||||
SomeArg: {
|
||||
// input type
|
||||
arg?: NexusGenInputs['NestedType'] | null // NestedType
|
||||
someField?: string | null // String
|
||||
}
|
||||
InputType: InputType
|
||||
InputType2: InputType2
|
||||
NestedType: NestedType
|
||||
SomeArg: SomeArg
|
||||
}
|
||||
|
||||
export interface NexusGenEnums {}
|
||||
|
|
@ -390,100 +363,117 @@ export interface NexusGenFieldTypeNames {
|
|||
}
|
||||
}
|
||||
|
||||
export interface FooArgsTestArgs {
|
||||
a: InputType | null // InputType
|
||||
}
|
||||
|
||||
export interface MutationSomeMutationFieldArgs {
|
||||
id: string // ID!
|
||||
}
|
||||
|
||||
export interface QueryAsArgExampleArgs {
|
||||
testAsArg: InputType // InputType!
|
||||
}
|
||||
|
||||
export interface QueryBooleanConnectionArgs {
|
||||
after?: string | null // String
|
||||
first: number // Int!
|
||||
}
|
||||
|
||||
export interface QueryComplexQueryArgs {
|
||||
count: number // Int!
|
||||
}
|
||||
|
||||
export interface QueryDeprecatedConnectionArgs {
|
||||
after?: string | null // String
|
||||
before?: string | null // String
|
||||
first?: number | null // Int
|
||||
last?: number | null // Int
|
||||
}
|
||||
|
||||
export interface QueryGetNumberOrNullArgs {
|
||||
a: number // Int!
|
||||
}
|
||||
|
||||
export interface QueryGuardedConnectionArgs {
|
||||
after?: string | null // String
|
||||
first: number // Int!
|
||||
}
|
||||
|
||||
export interface QueryInlineArgsArgs {
|
||||
someArg?: SomeArg | null // SomeArg
|
||||
}
|
||||
|
||||
export interface QueryInputAsArgExampleArgs {
|
||||
testInput?: InputType | null // InputType
|
||||
testScalar?: string | null // String
|
||||
}
|
||||
|
||||
export interface QueryUserConnectionAdditionalArgsArgs {
|
||||
after?: string | null // String
|
||||
first: number // Int!
|
||||
isEven?: boolean | null // Boolean
|
||||
}
|
||||
|
||||
export interface QueryUserConnectionBackwardOnlyArgs {
|
||||
before?: string | null // String
|
||||
last: number // Int!
|
||||
}
|
||||
|
||||
export interface QueryUserConnectionForwardOnlyArgs {
|
||||
after?: string | null // String
|
||||
first: number // Int!
|
||||
}
|
||||
|
||||
export interface QueryUsersConnectionNodesArgs {
|
||||
after?: string | null // String
|
||||
before?: string | null // String
|
||||
first?: number | null // Int
|
||||
last?: number | null // Int
|
||||
}
|
||||
|
||||
export interface QueryUsersConnectionResolveArgs {
|
||||
after?: string | null // String
|
||||
before?: string | null // String
|
||||
first?: number | null // Int
|
||||
last?: number | null // Int
|
||||
}
|
||||
|
||||
export interface TestObjArgsTestArgs {
|
||||
a: InputType | null // InputType
|
||||
}
|
||||
|
||||
export interface BarArgsTestArgs {
|
||||
a: InputType | null // InputType
|
||||
}
|
||||
|
||||
export interface NexusGenArgTypes {
|
||||
Foo: {
|
||||
argsTest: {
|
||||
// args
|
||||
a: NexusGenInputs['InputType'] | null // InputType
|
||||
}
|
||||
argsTest: FooArgsTestArgs
|
||||
}
|
||||
Mutation: {
|
||||
someMutationField: {
|
||||
// args
|
||||
id: string // ID!
|
||||
}
|
||||
someMutationField: MutationSomeMutationFieldArgs
|
||||
}
|
||||
Query: {
|
||||
asArgExample: {
|
||||
// args
|
||||
testAsArg: NexusGenInputs['InputType'] // InputType!
|
||||
}
|
||||
booleanConnection: {
|
||||
// args
|
||||
after?: string | null // String
|
||||
first: number // Int!
|
||||
}
|
||||
complexQuery: {
|
||||
// args
|
||||
count: number // Int!
|
||||
}
|
||||
deprecatedConnection: {
|
||||
// args
|
||||
after?: string | null // String
|
||||
before?: string | null // String
|
||||
first?: number | null // Int
|
||||
last?: number | null // Int
|
||||
}
|
||||
getNumberOrNull: {
|
||||
// args
|
||||
a: number // Int!
|
||||
}
|
||||
guardedConnection: {
|
||||
// args
|
||||
after?: string | null // String
|
||||
first: number // Int!
|
||||
}
|
||||
inlineArgs: {
|
||||
// args
|
||||
someArg?: NexusGenInputs['SomeArg'] | null // SomeArg
|
||||
}
|
||||
inputAsArgExample: {
|
||||
// args
|
||||
testInput?: NexusGenInputs['InputType'] | null // InputType
|
||||
testScalar?: string | null // String
|
||||
}
|
||||
userConnectionAdditionalArgs: {
|
||||
// args
|
||||
after?: string | null // String
|
||||
first: number // Int!
|
||||
isEven?: boolean | null // Boolean
|
||||
}
|
||||
userConnectionBackwardOnly: {
|
||||
// args
|
||||
before?: string | null // String
|
||||
last: number // Int!
|
||||
}
|
||||
userConnectionForwardOnly: {
|
||||
// args
|
||||
after?: string | null // String
|
||||
first: number // Int!
|
||||
}
|
||||
usersConnectionNodes: {
|
||||
// args
|
||||
after?: string | null // String
|
||||
before?: string | null // String
|
||||
first?: number | null // Int
|
||||
last?: number | null // Int
|
||||
}
|
||||
usersConnectionResolve: {
|
||||
// args
|
||||
after?: string | null // String
|
||||
before?: string | null // String
|
||||
first?: number | null // Int
|
||||
last?: number | null // Int
|
||||
}
|
||||
asArgExample: QueryAsArgExampleArgs
|
||||
booleanConnection: QueryBooleanConnectionArgs
|
||||
complexQuery: QueryComplexQueryArgs
|
||||
deprecatedConnection: QueryDeprecatedConnectionArgs
|
||||
getNumberOrNull: QueryGetNumberOrNullArgs
|
||||
guardedConnection: QueryGuardedConnectionArgs
|
||||
inlineArgs: QueryInlineArgsArgs
|
||||
inputAsArgExample: QueryInputAsArgExampleArgs
|
||||
userConnectionAdditionalArgs: QueryUserConnectionAdditionalArgsArgs
|
||||
userConnectionBackwardOnly: QueryUserConnectionBackwardOnlyArgs
|
||||
userConnectionForwardOnly: QueryUserConnectionForwardOnlyArgs
|
||||
usersConnectionNodes: QueryUsersConnectionNodesArgs
|
||||
usersConnectionResolve: QueryUsersConnectionResolveArgs
|
||||
}
|
||||
TestObj: {
|
||||
argsTest: {
|
||||
// args
|
||||
a: NexusGenInputs['InputType'] | null // InputType
|
||||
}
|
||||
argsTest: TestObjArgsTestArgs
|
||||
}
|
||||
Bar: {
|
||||
argsTest: {
|
||||
// args
|
||||
a: NexusGenInputs['InputType'] | null // InputType
|
||||
}
|
||||
argsTest: BarArgsTestArgs
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -554,99 +544,3 @@ export interface NexusGenTypes {
|
|||
abstractsUsingStrategyResolveType: NexusGenAbstractsUsingStrategyResolveType
|
||||
features: NexusGenFeaturesConfig
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface NexusGenPluginTypeConfig<TypeName extends string> {
|
||||
node?: string | core.FieldResolver<TypeName, any>
|
||||
}
|
||||
interface NexusGenPluginFieldConfig<TypeName extends string, FieldName extends string> {
|
||||
/**
|
||||
* The complexity for an individual field. Return a number or a function that returns a number to specify
|
||||
* the complexity for this field.
|
||||
*/
|
||||
complexity?: QueryComplexity<TypeName, FieldName>
|
||||
/**
|
||||
* Authorization for an individual field. Returning "true" or "Promise<true>" means the field can be
|
||||
* accessed. Returning "false" or "Promise<false>" will respond with a "Not Authorized" error for the
|
||||
* field. Returning or throwing an error will also prevent the resolver from executing.
|
||||
*/
|
||||
authorize?: FieldAuthorizeResolver<TypeName, FieldName>
|
||||
/**
|
||||
* The nullability guard can be helpful, but is also a potentially expensive operation for lists. We need
|
||||
* to iterate the entire list to check for null items to guard against. Set this to true to skip the null
|
||||
* guard on a specific field if you know there's no potential for unsafe types.
|
||||
*/
|
||||
skipNullGuard?: boolean
|
||||
/**
|
||||
* Whether the type can be null
|
||||
*
|
||||
* @default (depends on whether nullability is configured in type or schema)
|
||||
* @see declarativeWrappingPlugin
|
||||
*/
|
||||
nullable?: boolean
|
||||
/**
|
||||
* Whether the type is list of values, or just a single value. If list is true, we assume the type is a
|
||||
* list. If list is an array, we'll assume that it's a list with the depth. The boolean indicates whether
|
||||
* the type is required (non-null), where true = nonNull, false = nullable.
|
||||
*
|
||||
* @see declarativeWrappingPlugin
|
||||
*/
|
||||
list?: true | boolean[]
|
||||
/**
|
||||
* Whether the type should be non null, `required: true` = `nullable: false`
|
||||
*
|
||||
* @default (depends on whether nullability is configured in type or schema)
|
||||
* @see declarativeWrappingPlugin
|
||||
*/
|
||||
required?: boolean
|
||||
}
|
||||
interface NexusGenPluginInputFieldConfig<TypeName extends string, FieldName extends string> {
|
||||
/**
|
||||
* Whether the type can be null
|
||||
*
|
||||
* @default (depends on whether nullability is configured in type or schema)
|
||||
* @see declarativeWrappingPlugin
|
||||
*/
|
||||
nullable?: boolean
|
||||
/**
|
||||
* Whether the type is list of values, or just a single value. If list is true, we assume the type is a
|
||||
* list. If list is an array, we'll assume that it's a list with the depth. The boolean indicates whether
|
||||
* the type is required (non-null), where true = nonNull, false = nullable.
|
||||
*
|
||||
* @see declarativeWrappingPlugin
|
||||
*/
|
||||
list?: true | boolean[]
|
||||
/**
|
||||
* Whether the type should be non null, `required: true` = `nullable: false`
|
||||
*
|
||||
* @default (depends on whether nullability is configured in type or schema)
|
||||
* @see declarativeWrappingPlugin
|
||||
*/
|
||||
required?: boolean
|
||||
}
|
||||
interface NexusGenPluginSchemaConfig {}
|
||||
interface NexusGenPluginArgConfig {
|
||||
/**
|
||||
* Whether the type can be null
|
||||
*
|
||||
* @default (depends on whether nullability is configured in type or schema)
|
||||
* @see declarativeWrappingPlugin
|
||||
*/
|
||||
nullable?: boolean
|
||||
/**
|
||||
* Whether the type is list of values, or just a single value. If list is true, we assume the type is a
|
||||
* list. If list is an array, we'll assume that it's a list with the depth. The boolean indicates whether
|
||||
* the type is required (non-null), where true = nonNull, false = nullable.
|
||||
*
|
||||
* @see declarativeWrappingPlugin
|
||||
*/
|
||||
list?: true | boolean[]
|
||||
/**
|
||||
* Whether the type should be non null, `required: true` = `nullable: false`
|
||||
*
|
||||
* @default (depends on whether nullability is configured in type or schema)
|
||||
* @see declarativeWrappingPlugin
|
||||
*/
|
||||
required?: boolean
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -51,14 +51,6 @@
|
|||
esutils "^2.0.2"
|
||||
js-tokens "^4.0.0"
|
||||
|
||||
"@nexus/schema@^0.16.0":
|
||||
version "0.16.0"
|
||||
resolved "https://registry.yarnpkg.com/@nexus/schema/-/schema-0.16.0.tgz#cbf2b70eb47a854e4bcec849583368d7e7048087"
|
||||
integrity sha512-H+JJDycjcilvsRtLySpwfVXp1gYiOqPPLQdq04R4Vp5S400PpdADQlKMV4EvpBJ/BCxwQ8XwP8+nrOKvDZLLUw==
|
||||
dependencies:
|
||||
iterall "^1.2.2"
|
||||
tslib "^1.9.3"
|
||||
|
||||
"@protobufjs/aspromise@^1.1.1", "@protobufjs/aspromise@^1.1.2":
|
||||
version "1.1.2"
|
||||
resolved "https://registry.yarnpkg.com/@protobufjs/aspromise/-/aspromise-1.1.2.tgz#9b8b0cc663d669a7d8f6f5d0893a14d348f30fbf"
|
||||
|
|
@ -2148,6 +2140,11 @@ graphql@^15.3.0:
|
|||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-15.3.0.tgz#3ad2b0caab0d110e3be4a5a9b2aa281e362b5278"
|
||||
integrity sha512-GTCJtzJmkFLWRfFJuoo9RWWa/FfamUHgiFosxi/X1Ani4AVWbeyBenZTNX6dM+7WSbbFfTo/25eh0LLkwHMw2w==
|
||||
|
||||
graphql@^16.3.0:
|
||||
version "16.3.0"
|
||||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-16.3.0.tgz#a91e24d10babf9e60c706919bb182b53ccdffc05"
|
||||
integrity sha512-xm+ANmA16BzCT5pLjuXySbQVFwH3oJctUVdy81w1sV0vBU0KgDdBGtxQOUd5zqOBk/JayAFeG8Dlmeq74rjm/A==
|
||||
|
||||
growly@^1.2.0, growly@^1.3.0:
|
||||
version "1.3.0"
|
||||
resolved "https://registry.yarnpkg.com/growly/-/growly-1.3.0.tgz#f10748cbe76af964b7c96c93c6bcc28af120c081"
|
||||
|
|
@ -2727,6 +2724,11 @@ iterall@^1.1.3, iterall@^1.2.1, iterall@^1.2.2:
|
|||
resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.2.2.tgz#92d70deb8028e0c39ff3164fdbf4d8b088130cd7"
|
||||
integrity sha512-yynBb1g+RFUPY64fTrFv7nsjRrENBQJaX2UL+2Szc9REFrSNm1rpSXHGzhmAy7a9uv3vlvgBlXnf9RqmPH1/DA==
|
||||
|
||||
iterall@^1.3.0:
|
||||
version "1.3.0"
|
||||
resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.3.0.tgz#afcb08492e2915cbd8a0884eb93a8c94d0d72fea"
|
||||
integrity sha512-QZ9qOMdF+QLHxy1QIpUHUU1D5pS2CG2P69LF6L6CPjPYA/XMOmKV3PZpawHoAjHNyB0swdVTRxdYT4tbBbxqwg==
|
||||
|
||||
jest-changed-files@^23.4.2:
|
||||
version "23.4.2"
|
||||
resolved "https://registry.yarnpkg.com/jest-changed-files/-/jest-changed-files-23.4.2.tgz#1eed688370cd5eebafe4ae93d34bb3b64968fe83"
|
||||
|
|
@ -3651,6 +3653,14 @@ negotiator@0.6.2:
|
|||
resolved "https://registry.yarnpkg.com/negotiator/-/negotiator-0.6.2.tgz#feacf7ccf525a77ae9634436a64883ffeca346fb"
|
||||
integrity sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==
|
||||
|
||||
nexus@^1.0.0:
|
||||
version "1.0.0"
|
||||
resolved "https://registry.yarnpkg.com/nexus/-/nexus-1.0.0.tgz#633b39abae1d7e9472ca40e37bb5d3e1263f6aa3"
|
||||
integrity sha512-Toa91s9BJsX8pDX34QkOyKdnw8MmuOQkEboZMKSxvF9mWuAFkY74Zj1ssaexeV7yTQ7HoLQYUQ00FaWzXPmggQ==
|
||||
dependencies:
|
||||
iterall "^1.3.0"
|
||||
tslib "^2.0.3"
|
||||
|
||||
node-emoji@^1.4.1:
|
||||
version "1.8.1"
|
||||
resolved "https://registry.yarnpkg.com/node-emoji/-/node-emoji-1.8.1.tgz#6eec6bfb07421e2148c75c6bba72421f8530a826"
|
||||
|
|
@ -5025,6 +5035,11 @@ tslib@^1.9.3:
|
|||
resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.11.1.tgz#eb15d128827fbee2841549e171f45ed338ac7e35"
|
||||
integrity sha512-aZW88SY8kQbU7gpV19lN24LtXh/yD4ZZg6qieAJDDg+YBsJcSmLGK9QpnUjAKVG/xefmvJGd1WUmfpT/g6AJGA==
|
||||
|
||||
tslib@^2.0.3:
|
||||
version "2.0.3"
|
||||
resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.0.3.tgz#8e0741ac45fc0c226e58a17bfc3e64b9bc6ca61c"
|
||||
integrity sha512-uZtkfKblCEQtZKBF6EBXVZeQNl82yqtDQdv+eck8u7tdPxjLu2/lp5/uPW+um2tpuxINHWy3GhiccY7QgEaVHQ==
|
||||
|
||||
tunnel-agent@^0.6.0:
|
||||
version "0.6.0"
|
||||
resolved "https://registry.yarnpkg.com/tunnel-agent/-/tunnel-agent-0.6.0.tgz#27a5dea06b36b04a0a9966774b290868f0fc40fd"
|
||||
|
|
@ -5060,10 +5075,10 @@ type-is@~1.6.16:
|
|||
media-typer "0.3.0"
|
||||
mime-types "~2.1.18"
|
||||
|
||||
typescript@^3.9:
|
||||
version "3.9.7"
|
||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-3.9.7.tgz#98d600a5ebdc38f40cb277522f12dc800e9e25fa"
|
||||
integrity sha512-BLbiRkiBzAwsjut4x/dsibSTB6yWpwT5qWmC2OfuCg3GgVQCSgMs4vEctYPhsaGtd0AeuuHMkjZ2h2WG8MSzRw==
|
||||
typescript@^4.5.5:
|
||||
version "4.5.5"
|
||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.5.5.tgz#d8c953832d28924a9e3d37c73d729c846c5896f3"
|
||||
integrity sha512-TCTIul70LyWe6IJWT8QSYeA54WQe8EjQFU4wY52Fasj5UKx88LNYKCgBEHcOMOrFF1rKGbD8v/xcNWVUq9SymA==
|
||||
|
||||
uglify-js@^3.1.4:
|
||||
version "3.4.9"
|
||||
|
|
|
|||
|
|
@ -2,19 +2,19 @@
|
|||
"name": "@graphql-nexus/example-swapi-example",
|
||||
"version": "0.0.0",
|
||||
"scripts": {
|
||||
"start": "ts-node-dev --ignore-watch star-wars-typegen.ts --no-notify --transpileOnly --respawn ./src"
|
||||
"start": "ts-node-dev --ignore-watch star-wars-typegen.ts --no-notify --transpile-only --respawn ./src"
|
||||
},
|
||||
"dependencies": {
|
||||
"@nexus/schema": "^0.16.0",
|
||||
"apollo-server": "^2.18.1",
|
||||
"graphql": "^15.3.0",
|
||||
"graphql": "^16.3.0",
|
||||
"graphql-tools": "^4.0.7",
|
||||
"nexus": "^1.0.0",
|
||||
"ts-node-dev": "^1.0.0-pre.30"
|
||||
},
|
||||
"devDependencies": {
|
||||
"jest": "^23.6.0",
|
||||
"prettier": "^1.19.1",
|
||||
"ts-jest": "^24.1.0",
|
||||
"typescript": "^3.9"
|
||||
"typescript": "^4.5.5"
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { interfaceType, idArg, nonNull } from '@nexus/schema'
|
||||
import { interfaceType, idArg, nonNull } from 'nexus'
|
||||
import { getFriends } from '../data'
|
||||
|
||||
export const Character = interfaceType({
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { objectType } from '@nexus/schema'
|
||||
import { objectType } from 'nexus'
|
||||
|
||||
export const Droid = objectType({
|
||||
name: 'Droid',
|
||||
|
|
|
|||
|
|
@ -1,18 +1,18 @@
|
|||
import { enumType } from "@nexus/schema";
|
||||
import { enumType } from 'nexus'
|
||||
|
||||
const OriginalEpisodes = [
|
||||
{ name: "NEWHOPE", value: 4, description: "Released in 1977." },
|
||||
{ name: "EMPIRE", value: 5, description: "Released in 1980." },
|
||||
{ name: "JEDI", value: 6, description: "Released in 1983" },
|
||||
];
|
||||
{ name: 'NEWHOPE', value: 4, description: 'Released in 1977.' },
|
||||
{ name: 'EMPIRE', value: 5, description: 'Released in 1980.' },
|
||||
{ name: 'JEDI', value: 6, description: 'Released in 1983' },
|
||||
]
|
||||
|
||||
export const Episode = enumType({
|
||||
name: "Episode",
|
||||
description: "One of the films in the Star Wars Trilogy",
|
||||
name: 'Episode',
|
||||
description: 'One of the films in the Star Wars Trilogy',
|
||||
members: OriginalEpisodes,
|
||||
});
|
||||
})
|
||||
|
||||
export const MoreEpisodes = enumType({
|
||||
name: "MoreEpisodes",
|
||||
members: [...OriginalEpisodes, "OTHER"],
|
||||
});
|
||||
name: 'MoreEpisodes',
|
||||
members: [...OriginalEpisodes, 'OTHER'],
|
||||
})
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { objectType } from '@nexus/schema'
|
||||
import { objectType } from 'nexus'
|
||||
|
||||
export const Human = objectType({
|
||||
name: 'Human',
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { objectType, arg, stringArg, nonNull } from '@nexus/schema'
|
||||
import { objectType, arg, stringArg, nonNull } from 'nexus'
|
||||
import { getHero, getHuman, getDroid } from '../data'
|
||||
|
||||
const characterArgs = {
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { makeSchema, nullabilityGuardPlugin } from '@nexus/schema'
|
||||
import { makeSchema, nullabilityGuardPlugin } from 'nexus'
|
||||
import * as path from 'path'
|
||||
import * as allTypes from './graphql'
|
||||
|
||||
|
|
|
|||
|
|
@ -51,14 +51,6 @@
|
|||
esutils "^2.0.2"
|
||||
js-tokens "^4.0.0"
|
||||
|
||||
"@nexus/schema@^0.16.0":
|
||||
version "0.16.0"
|
||||
resolved "https://registry.yarnpkg.com/@nexus/schema/-/schema-0.16.0.tgz#cbf2b70eb47a854e4bcec849583368d7e7048087"
|
||||
integrity sha512-H+JJDycjcilvsRtLySpwfVXp1gYiOqPPLQdq04R4Vp5S400PpdADQlKMV4EvpBJ/BCxwQ8XwP8+nrOKvDZLLUw==
|
||||
dependencies:
|
||||
iterall "^1.2.2"
|
||||
tslib "^1.9.3"
|
||||
|
||||
"@protobufjs/aspromise@^1.1.1", "@protobufjs/aspromise@^1.1.2":
|
||||
version "1.1.2"
|
||||
resolved "https://registry.yarnpkg.com/@protobufjs/aspromise/-/aspromise-1.1.2.tgz#9b8b0cc663d669a7d8f6f5d0893a14d348f30fbf"
|
||||
|
|
@ -2105,6 +2097,11 @@ graphql@^15.3.0:
|
|||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-15.3.0.tgz#3ad2b0caab0d110e3be4a5a9b2aa281e362b5278"
|
||||
integrity sha512-GTCJtzJmkFLWRfFJuoo9RWWa/FfamUHgiFosxi/X1Ani4AVWbeyBenZTNX6dM+7WSbbFfTo/25eh0LLkwHMw2w==
|
||||
|
||||
graphql@^16.3.0:
|
||||
version "16.3.0"
|
||||
resolved "https://registry.yarnpkg.com/graphql/-/graphql-16.3.0.tgz#a91e24d10babf9e60c706919bb182b53ccdffc05"
|
||||
integrity sha512-xm+ANmA16BzCT5pLjuXySbQVFwH3oJctUVdy81w1sV0vBU0KgDdBGtxQOUd5zqOBk/JayAFeG8Dlmeq74rjm/A==
|
||||
|
||||
growly@^1.2.0, growly@^1.3.0:
|
||||
version "1.3.0"
|
||||
resolved "https://registry.yarnpkg.com/growly/-/growly-1.3.0.tgz#f10748cbe76af964b7c96c93c6bcc28af120c081"
|
||||
|
|
@ -2679,11 +2676,16 @@ istanbul-reports@^1.5.1:
|
|||
dependencies:
|
||||
handlebars "^4.0.3"
|
||||
|
||||
iterall@^1.1.3, iterall@^1.2.1, iterall@^1.2.2:
|
||||
iterall@^1.1.3, iterall@^1.2.1:
|
||||
version "1.2.2"
|
||||
resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.2.2.tgz#92d70deb8028e0c39ff3164fdbf4d8b088130cd7"
|
||||
integrity sha512-yynBb1g+RFUPY64fTrFv7nsjRrENBQJaX2UL+2Szc9REFrSNm1rpSXHGzhmAy7a9uv3vlvgBlXnf9RqmPH1/DA==
|
||||
|
||||
iterall@^1.3.0:
|
||||
version "1.3.0"
|
||||
resolved "https://registry.yarnpkg.com/iterall/-/iterall-1.3.0.tgz#afcb08492e2915cbd8a0884eb93a8c94d0d72fea"
|
||||
integrity sha512-QZ9qOMdF+QLHxy1QIpUHUU1D5pS2CG2P69LF6L6CPjPYA/XMOmKV3PZpawHoAjHNyB0swdVTRxdYT4tbBbxqwg==
|
||||
|
||||
jest-changed-files@^23.4.2:
|
||||
version "23.4.2"
|
||||
resolved "https://registry.yarnpkg.com/jest-changed-files/-/jest-changed-files-23.4.2.tgz#1eed688370cd5eebafe4ae93d34bb3b64968fe83"
|
||||
|
|
@ -3598,6 +3600,14 @@ negotiator@0.6.2:
|
|||
resolved "https://registry.yarnpkg.com/negotiator/-/negotiator-0.6.2.tgz#feacf7ccf525a77ae9634436a64883ffeca346fb"
|
||||
integrity sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==
|
||||
|
||||
nexus@^1.0.0:
|
||||
version "1.0.0"
|
||||
resolved "https://registry.yarnpkg.com/nexus/-/nexus-1.0.0.tgz#633b39abae1d7e9472ca40e37bb5d3e1263f6aa3"
|
||||
integrity sha512-Toa91s9BJsX8pDX34QkOyKdnw8MmuOQkEboZMKSxvF9mWuAFkY74Zj1ssaexeV7yTQ7HoLQYUQ00FaWzXPmggQ==
|
||||
dependencies:
|
||||
iterall "^1.3.0"
|
||||
tslib "^2.0.3"
|
||||
|
||||
node-emoji@^1.4.1:
|
||||
version "1.8.1"
|
||||
resolved "https://registry.yarnpkg.com/node-emoji/-/node-emoji-1.8.1.tgz#6eec6bfb07421e2148c75c6bba72421f8530a826"
|
||||
|
|
@ -4961,6 +4971,11 @@ tslib@^1.9.3:
|
|||
resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.11.1.tgz#eb15d128827fbee2841549e171f45ed338ac7e35"
|
||||
integrity sha512-aZW88SY8kQbU7gpV19lN24LtXh/yD4ZZg6qieAJDDg+YBsJcSmLGK9QpnUjAKVG/xefmvJGd1WUmfpT/g6AJGA==
|
||||
|
||||
tslib@^2.0.3:
|
||||
version "2.0.3"
|
||||
resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.0.3.tgz#8e0741ac45fc0c226e58a17bfc3e64b9bc6ca61c"
|
||||
integrity sha512-uZtkfKblCEQtZKBF6EBXVZeQNl82yqtDQdv+eck8u7tdPxjLu2/lp5/uPW+um2tpuxINHWy3GhiccY7QgEaVHQ==
|
||||
|
||||
tunnel-agent@^0.6.0:
|
||||
version "0.6.0"
|
||||
resolved "https://registry.yarnpkg.com/tunnel-agent/-/tunnel-agent-0.6.0.tgz#27a5dea06b36b04a0a9966774b290868f0fc40fd"
|
||||
|
|
@ -4996,10 +5011,10 @@ type-is@~1.6.16:
|
|||
media-typer "0.3.0"
|
||||
mime-types "~2.1.18"
|
||||
|
||||
typescript@^3.9:
|
||||
version "3.9.7"
|
||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-3.9.7.tgz#98d600a5ebdc38f40cb277522f12dc800e9e25fa"
|
||||
integrity sha512-BLbiRkiBzAwsjut4x/dsibSTB6yWpwT5qWmC2OfuCg3GgVQCSgMs4vEctYPhsaGtd0AeuuHMkjZ2h2WG8MSzRw==
|
||||
typescript@^4.5.5:
|
||||
version "4.5.5"
|
||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.5.5.tgz#d8c953832d28924a9e3d37c73d729c846c5896f3"
|
||||
integrity sha512-TCTIul70LyWe6IJWT8QSYeA54WQe8EjQFU4wY52Fasj5UKx88LNYKCgBEHcOMOrFF1rKGbD8v/xcNWVUq9SymA==
|
||||
|
||||
uglify-js@^3.1.4:
|
||||
version "3.4.9"
|
||||
|
|
|
|||
|
|
@ -6,13 +6,13 @@
|
|||
"start": "ts-node-dev --no-notify --transpileOnly --respawn ./src"
|
||||
},
|
||||
"dependencies": {
|
||||
"@nexus/schema": "^0.16.0",
|
||||
"apollo-server": "^2.18.1",
|
||||
"fs-extra": "^7.0.1",
|
||||
"graphql": "^15.3.0",
|
||||
"graphql": "^16.3.0",
|
||||
"graphql-tools": "^4.0.7",
|
||||
"nexus": "^1.0.0",
|
||||
"ts-node-dev": "1.0.0-pre.31",
|
||||
"typescript": "^3.9"
|
||||
"typescript": "^4.5.5"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/fs-extra": "^5.0.4"
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { makeSchema } from '@nexus/schema'
|
||||
import { makeSchema } from 'nexus'
|
||||
import { GraphQLNamedType, isObjectType } from 'graphql'
|
||||
import path from 'path'
|
||||
import * as types from './types'
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import * as ts from 'typescript'
|
||||
import type * as ts from 'typescript'
|
||||
|
||||
export interface ContextType {
|
||||
source: ts.SourceFile
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
import { objectType, arg, list, nullable } from '@nexus/schema'
|
||||
import { objectType, arg, list, nullable, core } from 'nexus'
|
||||
import ts from 'typescript'
|
||||
import { nodeType, functionLikeDeclaration, hasTypeParameters } from './mixins'
|
||||
import { filteredNodesList } from './utils'
|
||||
|
||||
|
|
@ -21,7 +22,7 @@ export const SourceFile = objectType({
|
|||
t.list.field('statements', {
|
||||
type: 'Node',
|
||||
args: nodeSkipSyntax,
|
||||
resolve: (root, args) => filteredNodesList(args, Array.from(root.statements)),
|
||||
resolve: (root, args) => filteredNodesList<ts.Statement>(args, Array.from(root.statements)),
|
||||
})
|
||||
},
|
||||
})
|
||||
|
|
@ -156,7 +157,7 @@ export const ClassDeclaration = objectType({
|
|||
t.list.field('members', {
|
||||
type: 'Node',
|
||||
args: nodeSkipSyntax,
|
||||
resolve: (root, args) => filteredNodesList(args, Array.from(root.members)),
|
||||
resolve: (root, args) => filteredNodesList<ts.ClassElement>(args, Array.from(root.members)),
|
||||
})
|
||||
},
|
||||
})
|
||||
|
|
|
|||
|
|
@ -1,16 +1,16 @@
|
|||
import ts from "typescript";
|
||||
import { enumType } from "@nexus/schema";
|
||||
import { convertTsEnum } from "./utils";
|
||||
import ts from 'typescript'
|
||||
import { enumType } from 'nexus'
|
||||
import { convertTsEnum } from './utils'
|
||||
|
||||
export const SyntaxKind = enumType({
|
||||
name: "SyntaxKind",
|
||||
name: 'SyntaxKind',
|
||||
members: convertTsEnum(ts.SyntaxKind),
|
||||
});
|
||||
})
|
||||
|
||||
export const NodeFlags = enumType({
|
||||
name: "NodeFlags",
|
||||
name: 'NodeFlags',
|
||||
members: {
|
||||
...convertTsEnum(ts.NodeFlags),
|
||||
UNKNOWN: 4194816,
|
||||
},
|
||||
});
|
||||
})
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { nonNull, objectType, stringArg } from '@nexus/schema'
|
||||
import { nonNull, objectType, stringArg } from 'nexus'
|
||||
import ts from 'typescript'
|
||||
import fs from 'fs-extra'
|
||||
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
import { arg, interfaceType, list, nullable } from '@nexus/schema'
|
||||
import { JSDoc, SyntaxKind } from 'typescript'
|
||||
import { arg, interfaceType, list, nullable } from 'nexus'
|
||||
import ts, { JSDoc, SyntaxKind } from 'typescript'
|
||||
import { allKnownNodes, syntaxKindFilter } from './utils'
|
||||
|
||||
const syntaxKindArgs = {
|
||||
|
|
@ -50,7 +50,7 @@ export const Node = interfaceType({
|
|||
if (!root.modifiers) {
|
||||
return null
|
||||
}
|
||||
return syntaxKindFilter(args, Array.from(root.modifiers))
|
||||
return syntaxKindFilter<ts.Modifier>(args, Array.from(root.modifiers))
|
||||
},
|
||||
})
|
||||
t.field('parent', { type: 'Node' })
|
||||
|
|
@ -78,7 +78,7 @@ export const JSDocInterface = interfaceType({
|
|||
resolve(root) {
|
||||
if ('jsDoc' in root) {
|
||||
// https://github.com/Microsoft/TypeScript/issues/19856
|
||||
return ((root as unknown) as { jsDoc: JSDoc[] }).jsDoc
|
||||
return (root as unknown as { jsDoc: JSDoc[] }).jsDoc
|
||||
}
|
||||
return null
|
||||
},
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { interfaceType, objectType, blocks, nullable } from '@nexus/schema'
|
||||
import { interfaceType, objectType, blocks, nullable } from 'nexus'
|
||||
import ts from 'typescript'
|
||||
|
||||
export const JSDoc = objectType({
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { core, list, nullable } from '@nexus/schema'
|
||||
import { core, list, nullable } from 'nexus'
|
||||
|
||||
export function withTypeArguments(t: core.OutputDefinitionBlock<any>) {
|
||||
t.list.field('typeArguments', { type: nullable('Node') })
|
||||
|
|
|
|||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue