Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Request logging in Apollo GraphQL

Environment: Node app based on Apollo GraphQL server (direct Apollo server, no express middleware)

I need to intercept requests and log log them at certain points of the processing pipelines. Here is what I have so far:

const server = new ApolloServer({
  // code removed for clarity

  context: async ({ req }) => {
// here is the first request log, preparing the context for the upcoming calls (traceability)
},
  formatError:  async (err: any) => {
// Here I would like to finish logging, but no context is available
},

Problems are traceability of different logs from the same end user request and logging of the successful requests.

1- How can I relate the request context within the formatError method?

2- Where should I implement the logging of the successfully executed requests?

like image 983
Aleks Avatar asked May 25 '26 10:05

Aleks


1 Answers

Aleks,

  1. You can create custom error classes which can be extended from ApolloError or node Error classes. By assigning context to the error object from the resolver function, you can use it from formatError method.
  2. formatResponse method can be used here which provides requestContext as as argument.

formatError and formatResponse methods usage:

const { ApolloServer, gql, makeExecutableSchema } = require("apollo-server");

const typeDefs = gql`
  type User {
    name: String
    username: String
    statusCode: Int
  }

  type Query {
    user: User
  }
`;

const dummyUser = { username: "dummyUser", name: "Dummy user" };

const user = () => {
  // throw new Error('Test error');
  return dummyUser;
};

const resolvers = {
  Query: { user }
};

const schema = makeExecutableSchema({
  typeDefs,
  resolvers,
});

const server = new ApolloServer({
  context: ({ req }) => ({ headers: req.headers }),
  schema,
  introspection: true,
  playground: true,
  formatResponse: (response) => {
    response.data.user.statusCode = 200;
    return response;
  },
  formatError: (error) => {
    error.message = "Error name";
    return error;
  }
});

server.listen().then(({ url }) => {
  console.log(`🚀  Server ready at ${url}`);
});

Trying out in middleware might be an alternate approach for both(not sure about this).

like image 111
Deepak Kumar Avatar answered May 28 '26 04:05

Deepak Kumar



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!