-
Notifications
You must be signed in to change notification settings - Fork 0
GraphQL
Every Goldsky Subgraph has a GraphQL interface. The SDK’s GraphQL service builds documented public and private endpoint URLs and sends standard GraphQL HTTP requests. Choose the endpoint type based on who should be able to query the subgraph, not merely on convenience.
| Endpoint type | URL prefix | Authentication | Use case |
|---|---|---|---|
| Public | /api/public/{project_id}/subgraphs/{name}/{version_or_tag}/gn |
None | Open data, prototypes, or deliberately public frontends. |
| Private | /api/private/{project_id}/subgraphs/{name}/{version_or_tag}/gn |
Project Bearer token | Backend services and data that should be limited to the project. |
Goldsky documents a default public-endpoint rate limit of 50 requests per 10 seconds. Public endpoints are intentionally accessible to anyone. Private endpoints require a token belonging to the same project as the subgraph.1
New subgraphs default to public endpoint enabled and private endpoint disabled. An Editor can change endpoint exposure for a version or tag through Goldsky tooling; in the SDK, use Subgraphs.UpdateVersion. See Subgraphs.
Prefer the helpers when you need to display or pass an endpoint URL to a generic GraphQL client. The helpers escape each path component.
publicURL := client.GraphQL.PublicURL(projectID, "dex-analytics", "prod")
privateURL := client.GraphQL.PrivateURL(projectID, "dex-analytics", "prod")
fmt.Println(publicURL)
// https://api.goldsky.com/api/public/<project>/subgraphs/dex-analytics/prod/gnUse a tag such as prod when you want consumers to retain a stable endpoint through deployments. Use a version when reproducibility at an exact indexed deployment is more important.
QueryPrivate adds Authorization: Bearer <project-token> automatically. GraphQLRequest supports a query string, variables, and operation name.
request := goldsky.GraphQLRequest{
OperationName: "RecentTrades",
Query: `query RecentTrades($first: Int!) {
trades(first: $first, orderBy: timestamp, orderDirection: desc) {
id
timestamp
amount
}
}`,
Variables: map[string]any{"first": 10},
}
response, err := client.GraphQL.QueryPrivate(ctx, projectID, "dex-analytics", "prod", request)
if err != nil {
return err // HTTP failure or transport/decode failure
}
if response.HasErrors() {
for _, graphqlErr := range response.Errors {
log.Printf("GraphQL error: %s", graphqlErr.Message)
}
return fmt.Errorf("query returned GraphQL errors")
}
var data struct {
Trades []struct {
ID string `json:"id"`
Timestamp string `json:"timestamp"`
Amount string `json:"amount"`
} `json:"trades"`
}
if err := json.Unmarshal(response.Data, &data); err != nil {
return err
}The response separates the raw Data, GraphQL Errors, Extensions, HTTP status, and response headers. This lets callers use server-provided pagination or rate-limit metadata without losing the GraphQL protocol semantics.
QueryPublic uses the public URL and sends no project bearer token.
response, err := client.GraphQL.QueryPublic(ctx, projectID, "dex-analytics", "prod", goldsky.GraphQLRequest{
Query: `{ _meta { block { number } } }`,
})
if err != nil {
return err
}
if response.HasErrors() {
return fmt.Errorf("GraphQL errors: %s", response.Errors[0].Message)
}
fmt.Println(string(response.Data))Never put a private token in a browser bundle as a workaround for a private endpoint. Proxy private GraphQL queries through an authenticated backend or establish a client-facing authorization design that keeps the Goldsky project token server-side.
Query(ctx, endpoint, request, auth) is available when you already have an endpoint URL or need a custom routing layer. Set auth to true only for a trusted endpoint that should receive the client’s project token.
response, err := client.GraphQL.Query(ctx, privateURL, goldsky.GraphQLRequest{
Query: `query { _meta { block { number } } }`,
}, true)Treat the endpoint parameter as a security boundary. Passing an untrusted URL with auth == true could send the project Bearer token to that URL. For ordinary Goldsky endpoints, prefer QueryPublic and QueryPrivate.
GraphQL distinguishes transport/HTTP failures from GraphQL execution errors.
| Outcome | What Query* returns |
What to do |
|---|---|---|
Valid 2xx GraphQL response with errors
|
err == nil; response.Errors populated |
Check HasErrors(); decide whether partial data is acceptable. |
| Non-2xx HTTP response | *goldsky.ProblemDetails |
Inspect status and headers; handle 429 using RetryAfter. |
| Network/cancellation/malformed JSON | *goldsky.TransportError |
Respect the context and apply an application policy. |
The SDK does not use aggressive hidden GraphQL retries. For a read query that may be safely replayed, a calling application can retry a small bounded number of times on 429 or transient transport errors while honoring the overall context deadline.
Use GraphQL variables rather than concatenating user data into a query string. Request only fields the application uses. In a polling application, record the subgraph’s _meta block and deduplicate results at the business layer. For a continuously changing data set, design cursor or block-based pagination in the query rather than repeatedly requesting an unbounded list.
If the product needs an endpoint rollout, use a tag. First deploy and verify a new version, then move the tag; clients that query the tag can switch without editing every configured endpoint URL.