import { ServerOptions, createExpressServer } from "@nimbus/server"; import { ApolloServer } from "apollo-server-express"; import { GetMiddlewareOptions } from "apollo-server-express/src/ApolloServer"; import { Application } from "express"; import { createServer, Server, ClientRequest } from "http"; import { ApolloServerConfig, createApolloServer } from "./apollo"; export interface ApolloServerExpress extends ApolloServerConfig { server?: GetMiddlewareOptions & ServerOptions, } /** * A configured ready to use graphql server */ export class GraphQLServer { _server: Server; private readonly _express: Application; private readonly _apollo: ApolloServer; constructor( private readonly _serverOptions: ApolloServerExpress, _express?: Application, ) { this._express = _express || createExpressServer(_serverOptions.server); this._server = createServer(this._express); this._apollo = createApolloServer(_serverOptions); } public prepare() { this.apollo.applyMiddleware({ app: this.express, ...this._serverOptions.server }); if (this._serverOptions.subscriptions) { this.apollo.installSubscriptionHandlers(this._server); } return this; } get server() { return this._server; } get express() { return this._express; } get apollo() { return this._apollo; } on: Server["on"] = (...args: Parameters) => { return this._server.on(args[0] as string, args[1]); }; listen(port: number) { this.prepare(); return new Promise((resolve, reject) => { this._server.on('listening', () => { resolve(); }); this._server.on("error", (error: Error) => { reject(error); }); this._server.listen(port); }); } close() { return new Promise((resolve, reject) => { this._server.close((err) => { if (err) { reject(err); } else { resolve(); } }); setImmediate(() => { this._server.emit('close'); }); }); } }