Сервер Apollo в качестве Nuxt serverMiddleware - PullRequest
1 голос
/ 27 января 2020

Мне удалось использовать express + Apollo Backend в качестве серверного ПО в Nuxt js. Все работает нормально (аутентификация, кеш, источники данных, запросы, мутации), но теперь я пытаюсь запустить подписки (веб-сокеты) и это доставляет мне затруднения.

Я попробовал этот пример https://www.apollographql.com/docs/apollo-server/data/subscriptions/#subscriptions -with-Additional-Middleware , но даже прослушивание httpServer не помогло.

Это мой файл API, который мне требуется через nuxt.config. js с '~/api/index':

module.exports = async () => {
  const app = require('express')()
  const server = await require("./apollo")() // apollo-server-express w/ typeDefs and resolvers

  // apply Apollo to Express
  server.applyMiddleware({ app });
  console.log(`? ApolloServer ready at ${server.graphqlPath}`);

  const httpServer = http.createServer(app);
  server.installSubscriptionHandlers(httpServer);
  console.log(`? ApolloSubscriptions ready at ${server.subscriptionsPath}`);

  return {
    path: '/api',
    handler: httpServer
  }
}

Теперь моя игровая площадка выдает мне эту ошибку: "Could not connect to websocket endpoint ws://192.168.150.98:3000/api/graphql. Please check if the endpoint url is correct."

TypeDefs:

type Subscription {
  postAdded: Post
}
type Post {
  author: String
  comment: String
}
type Query {
  posts: [Post]
}
type Mutation {
  addPost(author: String, comment: String): Post
}

Resolvers:

Query: {
  posts(root, args, context) {
    return Posts;
  }
}
Mutation: {
  addPost(root, args, context) {
    pubsub.publish(POST_ADDED, { postAdded: args });
    return Posts.add(args);
  }
},
Subscription: {
  postAdded: {
    // Additional event labels can be passed to asyncIterator creation
    subscribe: () => pubsub.asyncIterator([POST_ADDED]),
  },
}

Первый вопрос здесь, спасибо заранее! :)

1 Ответ

1 голос
/ 31 января 2020

Я нашел хакерский способ добиться этого , импортировать код в виде текстового модуля:

import http from 'http'

export default function () {
  this.nuxt.hook('render:before', async () => {
    const server = require("./apollo")()

    // apply Apollo to Express
    server.applyMiddleware({ app: this.nuxt.renderer.app });
    console.log(`? ApolloServer ready at ${server.graphqlPath}`);

    const httpServer = http.createServer(this.nuxt.renderer.app);

    // apply SubscriptionHandlers to httpServer
    server.installSubscriptionHandlers(httpServer);
    console.log(`? ApolloSubscriptions ready at ${server.subscriptionsPath}`);

    // overwrite nuxt.server.listen()
    this.nuxt.server.listen = (port, host) => new Promise(resolve => httpServer.listen(port || 3000, host || 'localhost', resolve))

    // close this httpServer on 'close' event
    this.nuxt.hook('close', () => new Promise(httpServer.close))
  })
}

То есть я сейчас использую, вероятно, более стабильный способ, используя nuxt программно ! С хапи вместо express, поскольку express доставляет мне проблемы при компиляции и не отображает экран загрузки (прогресс сборки). Просто используйте npx create-nuxt-app и создайте приложение с серверной частью хапи.

Код с хапи выглядел бы так:

const consola = require('consola')
const Hapi = require('@hapi/hapi')
const HapiNuxt = require('@nuxtjs/hapi')

async function start () {
  const server = require('./apollo/index')()
  const app = new Hapi.Server({
    host: process.env.HOST || '127.0.0.1',
    port: process.env.PORT || 3000
  })

  await app.register({
    plugin: HapiNuxt
  })

  app.route(await require('./routes')())

  await server.applyMiddleware({
    app,
    path: '/graphql'
  });
  console.log(`? ApolloServer ready at ${server.graphqlPath}`);
  await server.installSubscriptionHandlers(app.listener)
  console.log(`? ApolloSubscriptions ready at ${server.subscriptionsPath}`);

  await app.start()

  consola.ready({
    message: `Server running at: ${app.info.uri}`,
    badge: true
  })
}
process.on('unhandledRejection', error => consola.error(error))
start().catch(error => console.log(error))

Может быть, я могу кому-нибудь помочь

...