GraphQl代码生成器:用查询字符串装饰URL

发布于 2025-02-13 08:41:03 字数 3332 浏览 1 评论 0 原文

我正在使用 graphql-codegen 纱软件包来生成React Hooks graphql-codegen --config codegen.yml

I want to decorate every GraphQL endpoint call with an operation name, so I could see the operation name in the DevTools console:

I have tried to find a Code Generator plugin for this purpose but with no luck. 我该如何实现所需的目标?

config codegen.yml:

schema: 'https://localhost:5001/api/graphql/'

overwrite: true
documents: './src/**/*.graphql'
generates:
  ./src/graphql/schema.graphql:
    plugins:
      - schema-ast
  ./src/graphql/graphqlTypes.ts:
    - typescript
  ./src/graphql/:
    preset: near-operation-file
    presetConfig:
      extension: .ts
      folder: ../hooks
      baseTypesPath: graphqlTypes.ts
    plugins:
      - typescript-operations
      - typescript-rtk-query:
          importBaseApiFrom: 'graphql/baseApi'
          exportHooks: true

My baseApi.ts looks like this:

import { createApi, retry } from '@reduxjs/toolkit/query/react';
import { graphqlRequestBaseQuery } from '@rtk-query/graphql-request-base-query';
import { Cookies } from 'react-cookie';
import { GraphQLClient } from 'graphql-request';

const client = new GraphQLClient(
  `${process.env.REACT_APP_API_URL}/api/graphql`
);
const cookies = new Cookies();
const token = cookies.get('.AspNetCore.Application.Id');
client.setHeader('authorization', `Bearer ${token}`);
client.setHeader('Content-Type', 'application/json');
client.setHeader('X-Requested-With', 'XMLHttpRequest');

export default client;

const staggeredBaseQuery = retry(graphqlRequestBaseQuery({ client }), {
  maxRetries: 2,
});

export const api = createApi({
  baseQuery: staggeredBaseQuery,
  endpoints: () => ({}),
  keepUnusedDataFor: 5,
  refetchOnMountOrArgChange: false,
});

My generated hook looks like this:

import * as Types from '../graphqlTypes';

import { api } from 'graphql/baseApi';
export type SetPreferenceMutationVariables = Types.Exact<{
  name: Types.Scalars['String'];
  value: Types.Scalars['String'];
}>;

export type SetPreferenceMutation = {
  __typename?: 'Mutation';
  setPreference?: boolean | null | undefined;
};

export const SetPreferenceDocument = `
    mutation setPreference($name: String!, $value: String!) {
  setPreference(name: $name, value: $value)
}
    `;

const injectedRtkApi = api.injectEndpoints({
  endpoints: (build) => ({
    setPreference: build.mutation<
      SetPreferenceMutation,
      SetPreferenceMutationVariables
    >({
      query: (variables) => ({ document: SetPreferenceDocument, variables }),
    }),
  }),
});

export { injectedRtkApi as api };
export const { useSetPreferenceMutation } = injectedRtkApi;

I found this piece of code: graphql-code-generator/packages/plugins/typecript/rtk-query/src/visitor.ts ,但我找不到更新URL的选项。 看来我需要编写自己的插件。

I am using graphql-codegen yarn package to generate React hooks
graphql-codegen --config codegen.yml

I want to decorate every GraphQL endpoint call with an operation name, so I could see the operation name in the DevTools console:
DevTools Network tab

I have tried to find a Code Generator plugin for this purpose but with no luck.
How can I achieve my desired goal?

config codegen.yml:

schema: 'https://localhost:5001/api/graphql/'

overwrite: true
documents: './src/**/*.graphql'
generates:
  ./src/graphql/schema.graphql:
    plugins:
      - schema-ast
  ./src/graphql/graphqlTypes.ts:
    - typescript
  ./src/graphql/:
    preset: near-operation-file
    presetConfig:
      extension: .ts
      folder: ../hooks
      baseTypesPath: graphqlTypes.ts
    plugins:
      - typescript-operations
      - typescript-rtk-query:
          importBaseApiFrom: 'graphql/baseApi'
          exportHooks: true

My baseApi.ts looks like this:

import { createApi, retry } from '@reduxjs/toolkit/query/react';
import { graphqlRequestBaseQuery } from '@rtk-query/graphql-request-base-query';
import { Cookies } from 'react-cookie';
import { GraphQLClient } from 'graphql-request';

const client = new GraphQLClient(
  `${process.env.REACT_APP_API_URL}/api/graphql`
);
const cookies = new Cookies();
const token = cookies.get('.AspNetCore.Application.Id');
client.setHeader('authorization', `Bearer ${token}`);
client.setHeader('Content-Type', 'application/json');
client.setHeader('X-Requested-With', 'XMLHttpRequest');

export default client;

const staggeredBaseQuery = retry(graphqlRequestBaseQuery({ client }), {
  maxRetries: 2,
});

export const api = createApi({
  baseQuery: staggeredBaseQuery,
  endpoints: () => ({}),
  keepUnusedDataFor: 5,
  refetchOnMountOrArgChange: false,
});

My generated hook looks like this:

import * as Types from '../graphqlTypes';

import { api } from 'graphql/baseApi';
export type SetPreferenceMutationVariables = Types.Exact<{
  name: Types.Scalars['String'];
  value: Types.Scalars['String'];
}>;

export type SetPreferenceMutation = {
  __typename?: 'Mutation';
  setPreference?: boolean | null | undefined;
};

export const SetPreferenceDocument = `
    mutation setPreference($name: String!, $value: String!) {
  setPreference(name: $name, value: $value)
}
    `;

const injectedRtkApi = api.injectEndpoints({
  endpoints: (build) => ({
    setPreference: build.mutation<
      SetPreferenceMutation,
      SetPreferenceMutationVariables
    >({
      query: (variables) => ({ document: SetPreferenceDocument, variables }),
    }),
  }),
});

export { injectedRtkApi as api };
export const { useSetPreferenceMutation } = injectedRtkApi;

I found this piece of code: graphql-code-generator/packages/plugins/typescript/rtk-query/src/visitor.ts but I could not find the option to update the URL.
Looks like I need to write my own plugin.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

把昨日还给我 2025-02-20 08:41:03

希望以下信息会有所帮助。

如果您想能够使用多个端点,则可以创建您的链接,例如:

const link = new RestLink({ endpoints: { v1: 'api.com/v1', v2: 'api.com/v2' } });

必须向每个查询提供额外的代码:

const postTitleQuery1 = gql`
  query PostTitle {
    post @rest(type: "Post", path: "/post", endpoint: "v1") {
      id
      title
    }
  }
`;
const postTitleQuery2 = gql`
  query PostTitle {
    post @rest(type: "[Tag]", path: "/tags", endpoint: "v2") {
      id
      tags
    }
  }
`;

源:官方文档

Hope below info will help.

If you want to be able to use multiple endpoints, you can create your link like:

const link = new RestLink({ endpoints: { v1: 'api.com/v1', v2: 'api.com/v2' } });

Extra code has to be provided to each query:

const postTitleQuery1 = gql`
  query PostTitle {
    post @rest(type: "Post", path: "/post", endpoint: "v1") {
      id
      title
    }
  }
`;
const postTitleQuery2 = gql`
  query PostTitle {
    post @rest(type: "[Tag]", path: "/tags", endpoint: "v2") {
      id
      tags
    }
  }
`;

Source: official docs.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文