It _is_ pretty much like a stored procedure. But I don't think that's inherently a bad thing at all. The procedures are effectively version controlled right within your application code, and I'm guessing they're persisted at deploy-time.
If you end up putting that on the server anyway, you're back to fixed responses, no better than a REST API.
If so, there's still a huge difference. In the REST super-endpoint world, you have to modify your API service to suit the desires of individual clients. In GraphQL, the client controls the shape of the query. The detail that the client is sending that query at deploy-time, instead of request-time, doesn't change that.
This also recognizes that queries tend to be parametric, but not fully dynamic. That's kind of built-in to Relay, since the fragments are statically attached to React components.
It's more akin to HTTP caching, to me.
"The native app teams discovered that using GraphQL came with the additional overhead of building queries by concatenating a bunch of strings and then uploading those queries over slow connections. These queries could sometimes grow into the tens of thousands of lines of GraphQL. Also, every mobile device running the same app was sending largely the same queries.
The teams realized that if the GraphQL queries instead were statically known — that is, they were not altered by runtime conditions — then they could be constructed once during development time and saved on the Facebook servers, and replaced in the mobile app with a tiny identifier. With this approach, the app sends the identifier along with some GraphQL variables, and the Facebook server knows which query to run. No more overhead, massively reduced network traffic, and much faster mobile apps."
Firstly, what query could be 10k lines? Secondly, if you're defining the query just by an id, how is that then any different to a fixed REST endpoint or stored procedure?