Set up a project using Express, Graphql, and Typescript
By: Rémy Villulles
Tags: GraphQL, JavaScript, Typescript, Expressjs, Nodejs

Let’s get started

First, let’s set up a new project by simply running npm init -y

Then install typescript and initialize your typescript project by doing

npm install -D typescript && tsc --init

If tsc --init is not working, run npx tsc --init instead

Setting up codegen

We are then going to set up codegen to start generating our typescript file based on our schemas.

For that, we’ll need to add a graphql file so that we have something to scan. For the purpose of the article. We’ll create a very simple file to login/register and get the token from a fake user.

Create some folders so that your hierarchy looks like this:

- src

- graphql

- schemas

- resolvers

In the schemas folder, create a user.graphql file and this content in it:

src/graphql/schemas/user.graphql

In the graphql file, we are simply adding one request of each time (mutation and query) and a type (AuthenticateResponse) so that we can fully take the benefit of codegen.

Now, in your terminal, run the following command to install the new packages we need: npm install -D @graphql-codegen/cli graphql and then run the following command to setup codegen: npx graphql-codegen init

This command is going to start a wizard to create your new codegen configuration.

The first question is about the type of environment you’d like to run codegen. As we are targeting nodeJS here, use space to select the first option (API or server) and hit enter to go to the next step.

The second question is about where the schemas are. You can either use an URL (but you’ll have to have your server running to update the typescript file) or you can specify a file path to the graphql files. In our case, we’d like to target all the .graphql files located under src/graphql/schemas .

Simply type the following value: src/graphql/schemas/**/*.graphql .

The third question is about plugins that you maybe need to generate the typescript file. In our case, the default options are more than fine. If you’d like to use codegen for mongodb, then you can check the third option. Otherwise, just hit enter

The fourth question is the path where our typescript file will be generated. You can put it wherever you’d like. In my case, I’ll choose src/graphql/generated.ts

For the fifth question, choose no (type N then hit enter)

For the last one, just keep it by default and hit enter

Finally, for the last question, codegen is asking the script name to run the codegen command. In my case, I’m just going to type codegen and hit enter

Once the setup is done, run npm install as asked by codegen and then run npm run codegen to generate the typescript file.

If the setup has been done correctly, then you’ll find a new typescript file to the path specified in step four of the wizard!

If you open the file codegen.yml at the root of you project, you are going to see how the configuration has been generated by the cli.

Setup the resolver mapper

I like to be able to split my files for better maintenance. This is why I’d like to show you straight away how to set up a resolver mapper (which will merge multiple resolvers into one) instead of just using one only file for all resolvers.

First, in our folder resolvers create a new typescript file called UserResolver.ts this file will contain all resolvers related to the user.graphql file.

You can fill it with the following content:

src/graphql/resolvers/UserResolver.ts

Donc forget to run npm install -D graphql-tools to have access to the graphql-tools package used in this file. Graphql-tools provides a lot of types and helpers to deal with graphql.

This file contains two resolvers corresponding to the query and the mutation in the corresponding graphql file. Also, we are getting the types from the generated file and use them in our resolvers.

I’ve decided to make our resolvers simple but just return a simple object with a token.

As you can see, codegen is using a pattern to generate the types. In your graphql file, if you define a type, the name is not going to change. However, for a query or mutation, it’s going to follow the pattern <requestType><RequestName>Args

Now that are resolver is ready, we’ll use it to merge it (alone for the moment) in a dedicated file. Create this file named resolversMap.ts in the folder graphql and put this content in it:

src/graphql/resolversMap.ts

Don’t forget to run npm install --save lodash and npm install -D @types/lodash to have access to the merge function and its types.

The purpose of this file is to get all your resolvers and merge them into one. This new resolver is going to be used by your graphql server later.

Setup the schemas mapper

Now, we are going to do the same with our schemas. Next to your resolversMap.ts, create a new file called schemasMap.ts and put the following content in it

src/graphql/schemasMap.ts

Don’t forget to run npm install --save graphql-import-node . This package allows you to import in your application .graphql files. Without it, you are more likely going to have an error when importing them.

Do not worry about the empty.graphql import just yet, I’m going to show it to you after finishing with this file.

The function makeExecutableSchema is the key function to manage the whole merging. It takes the schemas (or typeDefs) and the resolvers as parameters and generate a new, standard Graphql schema.

Be careful here with the order in the typeDefs array. the emptyTypeDefs MUST be the first in the array or this is not going to work.

Now, for the empty.graphql file. Create it next to the user.graphl one and put this content in it

src/graphql/schemas/empty.graphql

The goal of this file is defining the types Query and Mutation so that all the other schema files can extend from them. This is why the emptyTypeDefs must be first in the array as mentioned earlier.

The _empty values are here as placeholders as graphql do not authorise empty objects

We also have a small change to do in our user.graphql file. As we are merging now, you have to add the keyword extend before type Query and type Mutation and you’ll have to do it in any file using this type in the future. Only empty.graphql is not using extend as it’s defining the original types.

Setup the Express/Apollo server and test our API

We are almost there! Now that all our tools are now ready, we just have to link them all together.

In your src folder, create an index.ts file with the following content in it

src/index.ts

Don’t forget to install the new dependencies by running npm install --save express apollo-server-express and npm install -D @types/express

This file is the entry point of your app. It’s going to first setup an express app, then create a new Apollo server by giving to it the schemaMap created earlier. We are then applying to the Apollo server express as middleware and we set the graphql path to be /graphql

Finally, we start listening!

Now, if we want to test our application, we’ll have to be able to run it. For that, we are going to install nodemon and ts-node by running the command npm install -D nodemon ts-node .

Then add a new script in your package.json with the name you’d like and make it run this command: nodemon src/index.ts

If everything went fine, you have in the console a message saying that Apollo is running on port 4000

Testing our graphql application

GraphiQL

It’s now testing time! There are plenty of way to connect to a graphql application. The most straight forward for beginners stays Graphiql, an open source GUI for graphql. You can download it here

Once downloaded and opened, you can type in the GraphQL Endpoint field the url to your graphql application, which should be http://localhost:4000/graphql

Make sure that Method on the right hand side is set to POST.

If everything is well configured, you are going to see the documentation of your graphql API on the right

Documentation of your application

You are then able to click on the different types to see what they contains. You should have a play around to make yourself familiar with GraphiQL!

Run a query

The main part of the application is a multiline field to type your query (on the left) and the result area (middle of the screen)

To run a query, you have to first enter it’s type (query or mutation) followed by the name you’d like to give to the query.

Then, within the object, you are going to call the query you’d like to do. We are going to call login . As defined in the schema, login takes an email and a password as parameters. We are going to give them in our query.

And finally, within the second object, you are going to put the values that you’d like to fetch from this request.

The great thing in Graphql is that you can select the parameters that you are interested in and not getting the ones you don’t want. This allows to save data and reduce the complexity of some objects. If you’d like for example to get only the token for the user without getting the full user, you can only specify token!

Your final request

Here is our request! Now, all you have to do is press the Play button and see the result on the middle panel!

Our result

Here we go! Our graphql application sent us the expect response from the resolver!

Conclusion

Here is what’s for me the perfect Apollo/Typescript server. It already get you the possibility to split your files and start on good base!

If you’d like to get the whole project already ready, you can get it on my github.

I hope you liked reading the article as much as I liked writing it :)

See you in the next one!

Remy