Apollo-link-rest: "Header ist nicht definiert" tritt auf, wenn Apollo-Link-Rest im Weixin Mini-Programm verwendet wird

Erstellt am 16. Juli 2019  ·  25Kommentare  ·  Quelle: apollographql/apollo-link-rest

  • [x] hat-Reproduktion

Wenn wir versuchen, Apollo-Link-Rest im Weixin Mini-Programm zu verwenden, sind wir auf ein Problem gestoßen, bei dem ein Fehler wie folgt aufgetreten ist:

 Headers is not defined 
 ReferenceError: Headers is not defined

Da ich den Quellcode in RestLink.ts gefunden habe, wird versucht, die Header zu finden, aber es gibt absolut keine Header in der Weixin-Umgebung. Kann also jemand helfen, einen Hack oder Lösungen zur Lösung dieses Problems bereitzustellen? Vielen Dank, wenn Sie helfen könnten, danke.

help wanted 🛠 question❔

Hilfreichster Kommentar

Folgendes hat bei mir funktioniert:

import clientFetch from 'unfetch';
import serverFetch, { Headers as ServerHeaders } from 'node-fetch';

const client = typeof document !== 'undefined';
global.Headers = client ? global.Headers : ServerHeaders;
const customFetch = client ? clientFetch : serverFetch;

const acmeLink = new JsonApiLink({
  …
  credentials: 'same-origin',
  customFetch,
});

Alle 25 Kommentare

Hi @ Janice1114 , ich bin mit Weixin nicht vertraut, aber vielleicht können Sie eine Header-Polyfüllung verwenden?

Wenn Header nicht verfügbar sind, ist Fetch häufig auch nicht verfügbar. Eine Polyfüllung, die für beide funktionieren könnte, ist die folgende: https://github.com/bitinn/node-fetch

Hallo @fbartho , danke für deine schnelle Antwort. Ich habe versucht, die Polyfill zu verwenden, um Abrufheader zu aktivieren, erhalte aber immer noch die Fehler.

Und ich habe festgestellt, dass unter weixin wx.request für den Abruf verwendet wird, der keine fensterbezogenen Variablen unterstützt, daher befürchte ich, dass die Polyfüllung nicht funktioniert.

Und darf ich wissen, ob es Hack oder Implementierungen gibt, die helfen, die Header-Schleife im Quellcode von Apollo-Link-Rest zu überspringen? Oder können Sie bitte einige benutzerdefinierte Optionen angeben, die für verschiedene Szenarien geeignet sind?

Sie können den Parameter customFetch für ApolloLinkRest verwenden, um eine Wrapper-Funktion bereitzustellen. Diese Wrapper-Funktion kann die fensterbasierten Header aus der Polyfill übernehmen und in einen herkömmlichen Objekt-Hash reduzieren.

So etwas wie das Folgende (ungetestet, in meinem Browser geschrieben):

function customFetch(url, options) {
   const headers = options.headers.entries().reduce((accumulator, h) => { accumulator[h[0]] = h[1];  return accumulator;}, {})
   return fetch(url, {…options, headers});
}
// Elsewhere: new RestLink({ customFetch, ...

Ich freue mich sehr über Ihre freundliche Antwort und werde versuchen, diese Polyfüllung in der Weixin-Entwicklung zu verwenden.

Und wenn ich den Quellcode in RestLink.ts lese, wird versucht, auf die Header zuzugreifen, die in weixin nicht verfügbar sind. Es könnte die Variablen in global zuweisen.

Ich frage mich also, ob benutzerdefinierte oder überschriebene Einstellungen während des RestLink-Konstruktorprozesses angewendet werden könnten.

Nochmals herzliche Grüße für Ihre so wunderbaren Tipps.

Hallo @fbartho ,, um dieses Problem in Weixin und einem verwandten speziellen Browser zu beheben. Ich habe eine PR wie folgt erstellt:
Problembehebung bei Headern

Könnten Sie bitte helfen und prüfen, ob der Code PR für die Zusammenführung mit Master verfügbar ist?
Vielen Dank und vielen Dank, wenn das helfen könnte.

Ich habe das gleiche Problem in "next": "^9.0.3"

Ich habe auch dieses Problem mit der nächsten Version ^8.1.0 . Für meine Grafik-API verwende ich isomorphic-unfetch , Version ^3.0.0 um wie folgt zu füllen:

import fetch from 'isomorphic-unfetch'
const graphLink = createHttpLink({ uri, fetch })

Die Verwendung des gleichen Pakets zum Polyfill mit dem Restlink funktionierte jedoch nicht:

const restLink = new RestLink({
  uri,
  customFetch: fetch,
})

Ich habe auch node-fetch mit Ihrer customFetch-Methode ausprobiert:

import fetch from 'node-fetch'

function customFetch(url, options) {
  const headers = options.headers.entries().reduce((accumulator, h) => {
    accumulator[h[0]] = h[1]
    return accumulator
  }, {})
  return fetch(url, { ...options, headers })
}

const restLink = new RestLink({
  uri: CONTENTFUL_CONTENT_DELIVERY_API,
  customFetch,
})

In beiden Fällen bekam ich ReferenceError: Headers is not defined wenn ich als nächstes im Dev-Modus lief.

Ich würde die Idee hier lieben und würde mich freuen, wenn Sie eine Anleitung für die Implementierung in Serverumgebungen geben könnten. Vielen Dank!

Sie können die Header-API mehrfach ausfüllen, während Sie weiterhin Ihre eigene customFetch-API verwenden!

Lassen Sie mich wissen, ob Sie dort einen Beispielcode wünschen, aber ich bin zuversichtlich, dass dies ohne allzu großen Aufwand möglich ist. Ich bin gerade nicht an meinem Computer.

@fbartho Einige Beispielcodes wären großartig, wenn Sie eine Chance hätten! Ich habe es versucht, war aber nicht erfolgreich. Vielen Dank!

import * as Polyfillheaders from 'fetch-headers'
import fetch from 'isomorphic-unfetch'

// hook in the Headers polyfill for your environment!
global.Headers = global.Headers || Polyfillheaders;

function customFetch(url, options) {
  const headers = options.headers.entries().reduce((accumulator, h) => {
    accumulator[h[0]] = h[1]
    return accumulator
  }, {})
  return fetch(url, { ...options, headers })
}

const restLink = new RestLink({
  uri: CONTENTFUL_CONTENT_DELIVERY_API,
  customFetch,
})

So etwas wie das oben Genannte könnte den Trick @ 2wheelcoder machen

Vielen Dank! Ich melde mich hier zurück, nachdem ich die Gelegenheit habe, dies zu versuchen.

@fbartho Hallo! Ich habe dieses Problem auf iOS 9.3.5. Ich habe versucht, die Polyfill fetch-headers importieren, aber es funktioniert nicht.
Ich habe festgestellt, dass die Header-Instanz von fetch-headers nicht über die Methode forEach (siehe unten).
image

Gibt es noch andere Lösungen?

@fbartho Hallo! Ich habe dieses Problem auf iOS 9.3.5. Ich habe versucht, die Polyfill fetch-headers importieren, aber es funktioniert nicht.
Ich habe festgestellt, dass die Header-Instanz von fetch-headers nicht über die Methode forEach (siehe unten).
image

Gibt es noch andere Lösungen?

Ich habe dieses Problem mithilfe der Abruf- Polyfüllung gelöst.

Ich werde dies schließen, da ich glaube, dass wir dies mit einer Polyfüllung auf der App-Seite beheben können, und wir möchten die Polyfüllung nicht zu einer Abhängigkeit dieses Repositorys machen.

Ich konnte dies nicht mit einer Polyfüllung lösen. Ich habe versucht, isomorphes Abrufen, isomorphes Abrufen, Abrufen von Headern usw. durchzuführen und habe immer ein Problem damit, dass current.forEach nicht definiert ist oder TypeError: Right-hand side of 'instanceof' is not an object . Irgendeine Hilfe?

@VinSpee Haben Sie schon einmal versucht, diese Polyfill abzurufen ?

@lintuming ja, aber es funktioniert nicht auf dem Server.

@VinSpee Vielleicht können Sie verwenden diese , wie es scheint sie haben forEach Methode.
image
Hoffe diese Arbeit.

@lintuming danke für den Versuch zu helfen. Mit diesem bekomme ich:

Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client

scheint ein Wirrwarr von Problemen zu sein 🤣

@VinSpee Entschuldigung, ich habe keine Ahnung, warum dies passiert. Aber ich denke, das könnte helfen:
https://stackoverflow.com/questions/7042340/error-cant-set-headers-after-they-are-sent-to-the-client

Folgendes hat bei mir funktioniert:

import clientFetch from 'unfetch';
import serverFetch, { Headers as ServerHeaders } from 'node-fetch';

const client = typeof document !== 'undefined';
global.Headers = client ? global.Headers : ServerHeaders;
const customFetch = client ? clientFetch : serverFetch;

const acmeLink = new JsonApiLink({
  …
  credentials: 'same-origin',
  customFetch,
});

@VinSpee Ich habe das gleiche Problem und ich habe versucht, dieses Problem mit Ihrer Lösung zu beheben, aber es ist mir nicht gelungen.
Können Sie bitte Ihren Arbeitscode teilen?

Danke @VinSpee - das war genau das, was ich brauchte

Ich konnte dieses Problem mithilfe eines benutzerdefinierten Abrufs beheben

import fetch from "isomorphic-fetch"

const restLink = new RestLink({
  uri: "https://...",
  customFetch: fetch,
  headers: {
    "Content-Type": "application/json",
  },
})

Die Lösung von @VinSpee funktionierte auch für eine Gatsby JS-Anwendung.

War diese Seite hilfreich?
0 / 5 - 0 Bewertungen