简体   繁体   中英

Is it possible to define a field containing the hashtag character (#) in a GraphQL Object Type? Ordinarily used to write a comment

CONTEXT

Using the Last.fm API endpoints to convert them to a GraphQL Object Type. Each key from the JSON object from the API will match its corresponding field in the GraphQL Object. Example in the link below.
API endpoint to GraphQL Object

THE PROBLEM

Some JSON keys in the API start with the # character which is used in GraphQL to write comments. As a result, they can not be used as a field in a GraphQL Object. As shown in the link below.
The problem

The resolver for clarification

const songResolvers = {
  Query: {
    async track(_, { mbid }) {
      const response = await axios.get(`${BASE_URL}?method=track.getInfo&api_key=${API_KEY}&mbid=${mbid}&format=json`);
      return response.data.track;
    },
  },
};

THE SOLUTION?

I have found a workaround but imo, pretty darn ugly. Basically I rename the keys before returning the response and of course edit the field from the object from '#text' to 'text'.

const images = response.data.track.album.image;
images.forEach(async (image) => {
  Object.defineProperty(
    image, 'text',
    Object.getOwnPropertyDescriptor(image, '#text'),
  );
  await delete image['#text'];
});

I doubt this is the way to go so is there any way to use the # character as a field in a GraphQL Object Type? Or is there a cleaner solution to not use the # character in a GraphQL Object Type than the one above?

PS My first question on stackoverflow so if there's anything wrong with how I structured, asked the question etc. Please let me know

There are two main things here:

  1. No, it's not possible to have special characters in GraphQL field names, you're limited to alphanumerics: http://facebook.github.io/graphql/June2018/#sec-Names

  2. I generally consider it a best practice to always provide a mapping function from data that comes from a downstream source (such as the Last.fm api, or even your own internal endpoints), to an object representing a canonical "type" in your GraphQL schema. In many cases this may just be an identify function, but in others (like yours) it may require some actual code.

I've had to massage some truly nasty legacy data sources into a shape suitable for the GraphQL schema, so what I usually do is integrate the transformations into a service-calling layer, rather than into my resolvers. The other reason to wrap the API calls, is that you may have data representing the same schema type coming from differing downstream APIs which return different data shapes (urgh). This is a scenario you really don't want to have to deal with in your resolvers.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM