Back to Blog
Lesson 14 of the GraphQL: Your First GraphQL Schema & Server course
API ArchitectureAugust 1, 20264 min read

Defining the TypeDefs for your Apollo Server Project

Learn how to define your GraphQL schema using the `gql` tag and structure your `typeDefs` for use in an Apollo Server project.

GraphQLApollo ServertypeDefsschemaSDLNode.js
Close-up of a computer screen displaying programming code in a dark environment.

Previously in this course, we covered installing Apollo Server: your GraphQL API foundation to prepare our Node.js environment. Now that our dependencies are installed, we need to bridge the gap between our conceptual data models—like those we discussed in defining custom object types: mastering data modeling in GraphQL—and our actual running server.

In this lesson, we will translate your Schema Definition Language (SDL) into a JavaScript object using the gql template literal. This typeDefs constant will serve as the single source of truth for your API's structure.

What are typeDefs?

In Apollo Server, typeDefs (short for Type Definitions) is the variable that holds your entire GraphQL schema. It is a string—but not just any string. It must be wrapped in a special tagged template literal called gql.

The gql tag performs two critical functions:

  1. Parsing: It parses your SDL string into an Abstract Syntax Tree (AST) that Apollo Server can understand.
  2. Validation: It provides syntax highlighting and validation in your IDE, ensuring you don't have typos in your schema structure.

Without this, your schema would just be a static string, and the server wouldn't know how to validate incoming queries against your types.

Defining your schema in code

Detailed close-up of HTML code on a computer monitor, showcasing web development.

To define your typeDefs, you'll typically create a file named schema.js or typeDefs.js in your project root. Here is how you structure that file.

JAVASCRIPT
// schema.js
const { gql } = require(CE9178">'apollo-server');

const typeDefs = gqlCE9178">`
  type Task {
    id: ID!
    title: String!
    completed: Boolean!
  }

  type Query {
    tasks: [Task]
  }
`;

module.exports = typeDefs;

Breaking down the export

  1. The Import: We import gql from the apollo-server package. If you are using newer versions of Apollo Server (v4+), this may be imported from @apollo/server.
  2. The Tagged Template: We use the backtick (`) syntax followed by the gql tag. This allows us to write multi-line strings that the server can parse as valid GraphQL.
  3. The Export: By using module.exports, we make this schema available to our main server entry point (usually index.js or server.js).

Advancing the project: Initializing the schema

In our ongoing task manager API project, we are ready to define our first core entity. Open your project and create a file named schema.js.

Practice Exercise:

  1. Create a schema.js file.
  2. Define a Task type with the following fields: id (ID), title (String), and isDone (Boolean).
  3. Add a Query type with a field called getTasks that returns a list of Task objects.
  4. Export your typeDefs.

Hint: Remember that non-nullable fields use the ! syntax, which we explored in enforcing data with non-null fields in GraphQL.

Common Pitfalls

  • Forgetting the gql tag: If you pass a standard string to Apollo Server instead of a gql-tagged template, the server will throw an error because it cannot parse the raw string.
  • Case sensitivity: GraphQL types are case-sensitive. If you define a type Task but try to return a task type in your resolver, the server will fail to match them.
  • Missing Query type: A GraphQL schema must have a Query type defined if you want to perform any read operations. Even if your API is simple, always include at least an empty Query type.

FAQ

Q: Can I split my typeDefs into multiple files? Yes, but you'll need to combine them before passing them to the Apollo Server constructor. You can store them in an array and use gql to parse them collectively.

Q: Does the order of types matter in the typeDefs? Generally, no. As long as all referenced types are defined somewhere in the typeDefs string, the order does not matter.

Q: Should I put my typeDefs in the same file as my server code? For very small projects, yes. However, as your API grows, it is best practice to keep your schema in a dedicated schema.js file to maintain a clean codebase.

Recap

We have successfully moved from conceptual modeling to concrete code. By wrapping our SDL in the gql tag, we created a typeDefs constant that serves as the contract for our API. This structure is now ready to be imported into our server and paired with the logic that will actually fetch our data.

Up next, we will move to Creating Basic Resolvers, where we will write the functions that actually fulfill the requests defined in this schema.

Similar Posts