apollo-server-integrations / apollo-server-integration-next

An Apollo Server integration for use with Next.js
MIT License
196 stars 21 forks source link

Changes to the incremental responses #204

Closed jer-k closed 2 months ago

jer-k commented 2 months ago

Fixes: https://github.com/apollo-server-integrations/apollo-server-integration-next/issues/203

Preface: This is my first exposure to working with these Node objects on the server side so I'm not entirely sure if what I've done is correct.

I changed the way the incremental responses are sent back to the client. In the issue I noted

      for await (const chunk of httpGraphQLResponse.body.asyncIterator) {
        body.push(chunk);
      }

this await is stopping the server from incrementally delivering the responses and instead they're all delivered at once.

These changes allow the responses to be streamed back instead of all at once.

The logs in the client now show

what is data? {book: {…}} false 12:22:18
what is data? {book: {…}} false 12:22:19

Where the second book: {} has the deferred data and is delivered 1 second after the first in which the 1 second is hard coded in my project using this package.

jer-k commented 2 months ago

A couple things I've noticed. With these changes the Preview and Response panes in the Chrome DevTools aren't showing any data even though the response is working

image image image

I'm guessing something I've changed messed this up.

martinnabhan commented 2 months ago

Thank you for the thorough explanation! I'll try to take a closer look this week.

jer-k commented 2 months ago

Thank you for all the feedback! It is a much cleaner implementation.

On the Preview panel, there definitely is some way for the data to show up. This screenshot is from my work's application, which uses Apollo Client + graphql-ruby. I'll spend some time this morning and see if I can't uncover any information as to what is going on

image

jer-k commented 2 months ago

Okay I figured it out and I believe it is an upstream issue in Apollo Server and improperly setting the header.

what are raw headers? HeaderMap(2) [Map] {
  'cache-control' => 'no-store',
  'content-type' => 'multipart/mixed; boundary="-"; deferSpec=20220824',
  __identity: Symbol(HeaderMap)
}

When the headers are written in and the deferSpec=20220824', portion is retained, we do not get the Preview response.

I changed the code to

    const headers: Record<string, string> = {
      'content-type': 'multipart/mixed; boundary="-"',
    };
    // console.log('what are raw headers?', httpGraphQLResponse.headers);
    // for (const [key, value] of httpGraphQLResponse.headers) {
    //   headers[key] = value;
    // }

And the preview correctly displays image

martinnabhan commented 2 months ago

Thank you for looking into this. I don't think we want to change any headers coming from Apollo Server, so I'll go ahead and add a changeset and release this as is.

Thank you for the pull request!