SQL over JSON
@Korev You're not wrong.
Twelve years ago, I got so frustrated with our SOAP implementation that I created an api that took a string (a Rails object query) and returned a string (json of the result) in about an hour. One of those absolutely-only-dev things that you do to blow off steam & speed development.
I have worked with the GitHub REST & GraphQL APIs, running on the standard libraries, for Ruby and for Go.
GraphQL permits users to specify in a single query, and to a high degree of detail, exactly what data they need. This is REALLY GOOD for the API providers because 1) it reduces load on the servers and 2) as mentioned, there is no dealing with the cost of fielding, vetting, accepting, designing.... new APIs.
One thing that was always a problem, however, gets a lot worse with GraphQL. A user can request a LOT of data with a simple request. Strategies to limit the amount of data returned per call, and to continue a prior call, are much more sophisticated under GraphQL.
For consumers, it can be good (especially for not requested unneeded data), however...
1) I found the GraphQL specification FAR from easy to grok. I seriously want to see about 50 examples to work out just what you are supposed to do.
2) Working with GraphQL in Go was worse than working with SOAP in Ruby all those years ago. Each call-query requires its own set of class definitions.
3) There is a huge dependency on the provider doing things right. This is true in general, but for GitHub, GraphQL lacked critical things REST supported & vice versa. Which means I needed to operate two (very) different sets of APIs. I mean three. Because the website allowed stuff you could not do with either REST or GraphQL.
Not only that, but the base libraries lacked the continuation wrappers needed to preserve the sanity of people making these calls. The REST libraries lacked these as well, but continuation in REST at least feels a lot easier to manage. Of course, given that in Go, you have to define a new set of classes for each call, and Go lack generics, I understand that this might be tricky--all the more reason to have competent people on the provider's end assemble a library that manages that directly.
Having written this out, I really think straight-up SQL is the correct solution. Of course, the provider needs to sanitize the calls. And limits on the number of items returned, as well as server costs, imposed. But SQL is FAR easier to work with than GraphQL, and has its advantages. Furthermore, GraphQL IS getting translated into SQL.