---
title: 1. Setup and first query
---

## Overview

In this first chapter we're just going to get the bare minimum of a Nexus project setup. You'll learn about:

- The `nexus` package
- The `ts-node-dev` package to run your app
- 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
mkdir nexus-tutorial && cd nexus-tutorial
npm init -y
npm add nexus graphql apollo-server
```

> 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
```

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
{
  "compilerOptions": {
    "target": "ES2018",
    "module": "commonjs",
    "lib": ["esnext"],
    "strict": true,
    "rootDir": ".",
    "outDir": "dist",
    "sourceMap": true,
    "esModuleInterop": true
  }
}
```

Let's finally add some npm scripts to simplify our future workflows

<TabbedContent tabs={['Diff', 'Code']}>

<tab>

```json
"scripts": {
  "test": "echo \"Error: no test specified\" && exit 1",
+  "dev": "ts-node-dev --transpile-only --no-notify api/app.ts",
+  "build": "tsc"
}
```

</tab>

<tab>

```json
"scripts": {
  "test": "echo \"Error: no test specified\" && exit 1",
  "dev": "ts-node-dev --transpile-only --no-notify api/app.ts",
  "build": "tsc"
}
```

</tab>

</TabbedContent>

## Creating our app layout

We'll now create our first module at `api/schema.ts`:

```bash-symbol
mkdir api && touch api/schema.ts
```

We'll then setup `nexus` to create an empty schema

```ts
// api/schema.ts
import { makeSchema } from 'nexus'
import { join } from 'path'

export const schema = makeSchema({
  types: [], // 1
  outputs: {
    typegen: join(__dirname, '..', 'nexus-typegen.ts'), // 2
    schema: join(__dirname, '..', 'schema.graphql'), // 3
  },
})
```

1. GraphQL types that will be used to construct your GraphQL schema. It's voluntarily empty for now.
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

```ts
// api/server.ts
import { ApolloServer } from 'apollo-server'
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
import { server } from './server'

server.listen().then(({ url }) => {
  console.log(`🚀 Server ready at ${url}`)
})
```

## Running our app

Ok, with our entrypoint setup, let's boot up dev mode and see what happens.

```bash-symbol
npm run dev
```

You should also see a message indicating that your server is running, and where

```bash-symbol
🚀 Server ready at http://localhost:4000
```

## Try it out

Open it up, what do you see? It should be an instance of [GraphQL Playground](https://github.com/graphql/graphql-playground).

![image](https://user-images.githubusercontent.com/284476/83534302-ae1b7d00-a4be-11ea-9a13-2665bf152e2a.png)

This is a graphical user interface for interacting with GraphQL APIs. If you prefer you can run a [standalone](https://www.electronjs.org/apps/graphql-playground) version as an app on your machine, or another GraphQL GUI entirely. Nexus ships with one out of the box for your convenience.

Take a look at the right-hand side SCHEMA tab. There you'll see a default schema that Nexus has provided for you. This, along with the warning you saw before, will go away once you begin your own schema.

Note that Nexus will serve GraphQL requests on this same path. Only client `GET` requests with the `accept: text/html` header will get back the Playground response.

## Wrapping up

That's it! In the next chapter you'll begin working on your app's schema.

<ButtonLink
  color="dark"
  type="primary"
  href="/getting-started/tutorial/chapter-writing-your-first-schema"
>
  Next &rarr;
</ButtonLink>
