apollo-server/packages/apollo-server-lambda
Jesse Rosenberger 8e594d47f5
Revert #1698 renovate/graphql tools 4.x (#1716)
I'm reverting apollographql/apollo-server#1698 not because it's been problematic in any way, but because I'd like to give it a bit more thought and don't want this to accidentally get cut into a release prior to that consideration.

More specifically: The `graphql-tools` update on its own shouldn't really cause any problems, but the [4.x version of `graphql-tools`](https://github.com/apollographql/graphql-tools/releases/tag/4.0.0) is intended to support and enable the latest `graphql@14` which contains [breaking changes](https://github.com/graphql/graphql-js/releases/tag/v14.0.0).

I believe most of those breaking changes would be show-stoppers and the failures would surface immediately (meaning that servers would completely fail to start, rather than being a surprise in other, more delayed scenarios), but it's still worth pausing and carefully considering versioning to avoid any surprises.

That said, the 14.x version of `graphql` has been an acceptable range in the `peerDependencies` of `apollo-server-*` since before its final release came out, and I don't believe we've caught wind of anything that a major version bump would have prevented or made more clear.  In the end, `graphql` is a peer dependency and any problems should only surface if consumers also update their `graphql` dependency — a clear major version bump, which deserves review by the upgrader — so perhaps we can avoid bumping the major version after all?

Input welcomed, but again, merging this now to give this a bit more thought first.

cc @hwillson
2018-09-24 20:47:18 +03:00
..
src Re-enable Typescript esModuleInterop (#1699) 2018-09-21 16:43:33 +03:00
.npmignore Apollo Server 2.0: AWS Lambda Integration (#1188) 2018-06-21 13:54:53 -07:00
package.json Revert #1698 renovate/graphql tools 4.x (#1716) 2018-09-24 20:47:18 +03:00
README.md lambda: fix cors documentation and default allowed headers (#1367) 2018-07-17 15:37:34 -07:00
tsconfig.json Use strict top-level tsconfig and fix type issues or override per-package 2018-08-11 16:45:03 +02:00

title description
Lambda Setting up Apollo Server with AWS Lambda

npm version Build Status Coverage Status Get on Slack

This is the AWS Lambda integration of GraphQL Server. Apollo Server is a community-maintained open-source GraphQL server that works with many Node.js HTTP server frameworks. Read the docs. Read the CHANGELOG.

npm install apollo-server-lambda@rc graphql

Deploying with AWS Serverless Application Model (SAM)

To deploy the AWS Lambda function we must create a Cloudformation Template and a S3 bucket to store the artifact (zip of source code) and template. We will use the AWS Command Line Interface.

1. Write the API handlers

In a file named graphql.js, place the following code:

const { ApolloServer, gql } = require('apollo-server-lambda');

// Construct a schema, using GraphQL schema language
const typeDefs = gql`
  type Query {
    hello: String
  }
`;

// Provide resolver functions for your schema fields
const resolvers = {
  Query: {
    hello: () => 'Hello world!',
  },
};

const server = new ApolloServer({
  typeDefs,
  resolvers,
});

exports.handler = server.createHandler();

2. Create an S3 bucket

The bucket name must be universally unique.

aws s3 mb s3://<bucket name>

3. Create the Template

This will look for a file called graphql.js with the export graphqlHandler. It creates one API endpoints:

  • /graphql (GET and POST)

In a file called template.yaml:

AWSTemplateFormatVersion: '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Resources:
  GraphQL:
    Type: AWS::Serverless::Function
    Properties:
      Handler: graphql.handler
      Runtime: nodejs8.10
      Events:
        AnyRequest:
          Type: Api
          Properties:
            Path: /graphql
            Method: ANY

4. Package source code and dependencies

This will read and transform the template, created in previous step. Package and upload the artifact to the S3 bucket and generate another template for the deployment.

aws cloudformation package \
  --template-file template.yaml \
  --output-template-file serverless-output.yaml \
  --s3-bucket <bucket-name>

5. Deploy the API

The will create the Lambda Function and API Gateway for GraphQL. We use the stack-name prod to mean production but any stack name can be used.

aws cloudformation deploy \
  --template-file serverless-output.yaml \
  --stack-name prod \
  --capabilities CAPABILITY_IAM

Getting request info

To read information about the current request from the API Gateway event (HTTP headers, HTTP method, body, path, ...) or the current Lambda Context (Function Name, Function Version, awsRequestId, time remaining, ...) use the options function. This way they can be passed to your schema resolvers using the context option.

const { ApolloServer, gql } = require('apollo-server-lambda');

// Construct a schema, using GraphQL schema language
const typeDefs = gql`
  type Query {
    hello: String
  }
`;

// Provide resolver functions for your schema fields
const resolvers = {
  Query: {
    hello: () => 'Hello world!',
  },
};

const server = new ApolloServer({
  typeDefs,
  resolvers,
  context: ({ event, context }) => ({
    headers: event.headers,
    functionName: context.functionName,
    event,
    context,
  }),
});

exports.handler = server.createHandler();

Modifying the Lambda Response (Enable CORS)

To enable CORS the response HTTP headers need to be modified. To accomplish this use the cors option.

const { ApolloServer, gql } = require('apollo-server-lambda');

// Construct a schema, using GraphQL schema language
const typeDefs = gql`
  type Query {
    hello: String
  }
`;

// Provide resolver functions for your schema fields
const resolvers = {
  Query: {
    hello: () => 'Hello world!',
  },
};

const server = new ApolloServer({
  typeDefs,
  resolvers,
});

exports.handler = server.createHandler({
  cors: {
    origin: '*',
    credentials: true,
  },
});

To enable CORS response for requests with credentials (cookies, http authentication) the allow origin header must equal the request origin and the allow credential header must be set to true.

const { ApolloServer, gql } = require('apollo-server-lambda');

// Construct a schema, using GraphQL schema language
const typeDefs = gql`
  type Query {
    hello: String
  }
`;

// Provide resolver functions for your schema fields
const resolvers = {
  Query: {
    hello: () => 'Hello world!',
  },
};

const server = new ApolloServer({
  typeDefs,
  resolvers,
});

exports.handler = server.createHandler({
  cors: {
    origin: true,
    credentials: true,
  },
});

Cors Options

The options correspond to the express cors configuration with the following fields(all are optional):

  • origin: boolean | string | string[]
  • methods: string | string[]
  • allowedHeaders: string | string[]
  • exposedHeaders: string | string[]
  • credentials: boolean
  • maxAge: number

Principles

GraphQL Server is built with the following principles in mind:

  • By the community, for the community: GraphQL Server's development is driven by the needs of developers
  • Simplicity: by keeping things simple, GraphQL Server is easier to use, easier to contribute to, and more secure
  • Performance: GraphQL Server is well-tested and production-ready - no modifications needed

Anyone is welcome to contribute to GraphQL Server, just read CONTRIBUTING.md, take a look at the roadmap and make your first PR!