<p>apollo-link-http não respeita uma substituição de método GET</p>

Criado em 12 nov. 2017  ·  20Comentários  ·  Fonte: apollographql/apollo-link

De acordo com os documentos , a opção fetchOptions nos permite definir o método da solicitação como GET . Eu esperava que, depois de fazer isso, a consulta fosse incluída como um parâmetro de string de consulta em vez do corpo da solicitação; O Chrome gera um erro se você tentar fazer uma solicitação GET com um corpo.

Resultado pretendido:
Uma string de consulta deve ser construída se o método de solicitação for GET.

Resultado real:
O corpo da solicitação é usado.

Como reproduzir o problema:

client.query({
  context: {
    fetchOptions: {
      method: 'GET',
    },
  },
  query: QUERY,
  variables: { query },
})
enhancement

Comentários muito úteis

@szdc @ Outlaw11A @arackaf aqui está como fazer:

const customFetch = (uri, options) => {
  const { body, ...newOptions } = options;
  const queryString = objectToQuery(JSON.parse(body));
  requestedString = uri + queryString;
  return fetch(requestedString, newOptions);
};
const link = createHttpLink({
  uri: "data",
  fetchOptions: { method: "GET" },
  fetch: customFetch
});

Todos 20 comentários

@szdc sim, isso definitivamente não funciona! Você estaria aberto para adicioná-lo? Algo como https://github.com/apollographql/apollo-link/issues/257 pode ser uma boa solução também para transformar a solicitação antes de ser enviada?

cc @arackaf @ outlaw11a @puttyman que todos têm interesse nisso! Deve ser uma pequena mudança para adicionar!

Vou adicioná-lo se ninguém mais quiser.

@szdc @arackaf então descobrimos que isso já é possível! Vou fazer um teste e documentos em breve mostrando como isso pode ser feito sem mudanças internas

@szdc @ Outlaw11A @arackaf aqui está como fazer:

const customFetch = (uri, options) => {
  const { body, ...newOptions } = options;
  const queryString = objectToQuery(JSON.parse(body));
  requestedString = uri + queryString;
  return fetch(requestedString, newOptions);
};
const link = createHttpLink({
  uri: "data",
  fetchOptions: { method: "GET" },
  fetch: customFetch
});

@jbaxleyiii que parece incrível! Apenas curioso de onde objectToQuery está vindo? Existe um utilitário no npm para isso? Eu imagino que seria muito fácil apenas rolar o seu próprio, se necessário - basicamente mapear Object.keys para

escapeUriComponnt(`${k}=${obj[k]}`).join("&");

ou algo semelhante

https://www.apollographql.com/docs/link/links/http.html#Sending -GET-requests-custom-fetching

@arackaf veja o comentário:

// turn the object into a query string, try object-to-querystring package

https://github.com/Cyberlane/object-to-querystring

@jbaxleyiii funciona! É incrível!

Eu só tenho um problema.

A string de consulta criada:

http://localhost/graphql?operationName=AllPlayersQuery&variables=%5Bobject%20Object%5D&query=query%20All...

contém este: variables=%5Bobject%20Object%5D que é um problema.

Como consertar isto?

Isso se parece com a serialização de URI padrão - não pense que você pode evitá-la - por que é um problema?

URI padrão? Este: %5Bobject%20Object%5D ?

encodeURIComponent ('books (title: "Hello World") {Book {title}}')

books(title%3A%22Hello%20World%22)%7BBook%7Btitle%7D%7D

Minha consulta no Apollo é:

query AllPlayers {
  players {
    id
    name
    surname
}

e então eu tenho o problema com [Object object] variáveis ​​vazias com o código postado por @jbaxleyiii.

Aqui está um aplicativo de reação barebones (criado usando create-react-app) que busca via GET e funciona - consulte index.js : https://github.com/usefulio/example-graphql-via-get-react-app

@johnunclesam obviamente variables não é serializado antes da codificação. Eu simplesmente ajustei meu método de busca personalizado (obtido do repositório de exemplo) adicionando um JSON.stringify condicional:

const customFetch = (uri, options) => {
  const {body, ...newOptions} = options;
  const parsedBody = JSON.parse(body);
  const command = omitBy(parsedBody, isEmpty);

  if (command.variables) {
    command.variables = JSON.stringify(command.variables);
  }

  const requestedString = uri + '?' + queryString.stringify(command);

  return fetch(requestedString, newOptions);
};

Então, para que useGETForQueries usado? Por que a busca personalizada não está embutida quando useGETForQueries=true ?
Como diferencio consulta e mutação? Eu só quero usar GET para consulta (para cache DNS).

Este é um problema antigo anterior a useGETForQueries, que foi adicionado um pouco depois de ser corrigido por https://github.com/apollographql/apollo-link/pull/510

umm, useGETForQueries parece não estar funcionando.

Especificamente nesta linha, parece haver um bug:

https://github.com/apollographql/apollo-link/blob/f94b1c6b984619ec1ef68cca3224be788ea140e4/packages/apollo-link-http/src/httpLink.ts#L41

let {
    uri = '/graphql',
    // use default global fetch if nothing passed in
    fetch: fetcher,
    includeExtensions,
    useGETForQueries,
    ...requestOptions
  } = linkOptions;

deve ser algo como:

let {
    uri = '/graphql',
    // use default global fetch if nothing passed in
    fetch: fetcher,
    includeExtensions,
    fetchOptions,
    ...requestOptions
  } = linkOptions;

let {
  useGETForQueries
} = fetchOptions;

O que te faz dizer isso? Como você está chamando createHttpLink ?

Minha observação acima foi de percorrer o código com um depurador, mas eu teria que fazer isso novamente para reproduzir.

O código que decidimos é este:

import omitBy from 'lodash.omitby';
import isEmpty from 'lodash.isempty';

const graphQLUrl = 'http://the.server.com/graphql';

const customFetch = (uri, options) => {
  const { body, credentials, headers, ...newOptions } = options;
  let fetchUri = uri;
  if (body) {
    const parsedBody = JSON.parse(body);
    const command = omitBy(parsedBody, isEmpty);
    fetchUri = uri + "?" + queryString.stringify(command);
  }
  return fetch(fetchUri, newOptions);
};

const link = createHttpLink({
  uri: graphQLUrl,
  fetchOptions: { method: "GET" },
  fetch: customFetch
});

Acho que minha pergunta é, se você estivesse passando useGETForQueries dentro de fetchOptions vez de diretamente dentro de createHttpLink , então esse seria o comportamento que você observaria, mas também não seria como a API funciona. Eu sugiro tentar novamente!

Esta página foi útil?
0 / 5 - 0 avaliações