Absinthe - Customize All Errors in Return Payload

I’m the backend developer on a graphql/absinthe project, and the front end dev would like to have custom codes added to ALL error responses, including syntax errors. This failed test output illustrates what I’m envisioning:

 1) test malformed request (missing closing `}`) includes 422 status code (MyAppWeb.Schema.Mutation.LoginTest)
     test/my_app_web/schema/mutation/login_test.exs:51
     match (=) failed
     code:  assert %{"errors" => [%{"status_code" => 422}]} = json_response(response, 200)
     left:  %{"errors" => [%{"status_code" => 422}]}
     right: %{"errors" => [%{"locations" => [%{"column" => 0, "line" => 4}], "message" => "syntax error before: "}]}

I’m able to add a custom “status_code” to errors inside middleware, but syntax errors and errors of requesting undefined schema fields are returned before any middleware, I’m guessing in the asbinthe plug. How can I added a custom “status_code” to these types of errors? Is it ill-advised?

Thank you!

I’m reposting this answer I got from Ben Wilson (co-creator) of Absinthe on Slack:

Absinthe middleware is per field, so if the syntax is invalid it is unknowable which middleware to run

if you want to customize the document handling you can modify the document execution pipeline

you can supply a pipeline option Absinthe.Plug — absinthe_plug v1.5.8 as documented here to your Absinthe.Plug invocation that lets you introduce custom phases

plug Absinthe.Plug,
  schema: YourAppWeb.Schema,
  pipeline: {__MODULE__, :absinthe_pipeline}
def absinthe_pipeline(config, opts) do
  config
  |> Absinthe.Plug.default_pipeline(opts)
  |> IO.inspect(label: :default_pipeline)
  |> Absinthe.Pipeline.insert_after(SomeAbsinthePhaseModule, YourPhaseModule)
end

as far as which SomeAbsinthePhaseModule to use, probably I’d go with Phase.Document.Result and then look in the blueprint.execution.result value

but it depends a lot on what you are trying to do