GraphQL Basics in IZI
GraphQL Basics in IZI
Section titled “GraphQL Basics in IZI”GraphQL is a query language where you define exactly what you want to receive. Unlike REST, there are no multiple endpoints: one URL, one POST, and you select the fields you need.
If you come from REST, the main mental shift: forget URL as a resource. The URL is always https://api.izi.is/graphql — what to do is described in the request body.
Anatomy of a Request
Section titled “Anatomy of a Request”query GetClub($clubId: ID!) { club(id: $clubId) { id name timezone devices { id name status } }}Breaking it down:
query— operation type (read data)GetClub— operation name (useful for logs and debugging, optional but recommended)$clubId: ID!— variable of type ID, required (!)club(id: $clubId)— field invocation with argument- Nested fields — select only what you need
Three Operation Types
Section titled “Three Operation Types”query — reading data
Section titled “query — reading data”query ActiveSessions($clubId: ID!) { activeSessions(clubId: $clubId) { id deviceName clientName startedAt balance }}Variables are passed as a separate object:
{ "clubId": "club_abc123"}mutation — changing data
Section titled “mutation — changing data”mutation TopUpClientBalance($input: TopUpInput!) { topUpBalance(input: $input) { success newBalance transactionId }}{ "input": { "clientId": "client_xyz", "amount": 500, "clubId": "club_abc123" }}Mutations always return the operation result. Check the success field — don’t rely solely on HTTP 200.
subscription — real-time events
Section titled “subscription — real-time events”subscription SessionUpdates($clubId: ID!) { sessionUpdated(clubId: $clubId) { id status deviceId updatedAt }}Subscriptions use WebSocket. Subscription endpoint: wss://api.izi.is/graphql.
Variables
Section titled “Variables”Never interpolate data directly into query strings — it’s both a security risk and inconvenient:
# ❌ Bad — string interpolationquery { club(id: "club_abc123") { name } }
# ✅ Good — variablesquery GetClub($id: ID!) { club(id: $id) { name }}# Variables: { "id": "club_abc123" }Fragments
Section titled “Fragments”If the same fields appear in multiple queries, extract them into fragments:
fragment DeviceFields on Device { id name status zone { id name }}
query AllDevices($clubId: ID!) { devices(clubId: $clubId) { ...DeviceFields }}Error Handling
Section titled “Error Handling”IZI API responses always include data and optionally errors:
{ "data": { "topUpBalance": null }, "errors": [ { "message": "Insufficient permissions", "extensions": { "code": "FORBIDDEN", "field": "topUpBalance" } } ]}HTTP status may be 200 even on error. Handle the errors field explicitly — don’t rely on HTTP codes for business errors. Full list — API Error Codes.
Introspection
Section titled “Introspection”View the full schema:
{ __schema { types { name kind description } }}View fields of a specific type:
{ __type(name: "Club") { fields { name type { name kind } description isDeprecated deprecationReason } }}Batch Requests
Section titled “Batch Requests”Multiple operations in one HTTP request:
[ { "query": "query { me { id } }" }, { "query": "query { clubs { id name } }" }]Response is an array in the same order. Limit: 10 operations per batch.
Recommended Clients
Section titled “Recommended Clients”| Client | Use Case |
|---|---|
| Insomnia | Development and debugging |
| Apollo Client | Frontend (React/Vue) |
graphql-request | Node.js scripts and backend |
gql + httpx | Python |
Related Pages
Section titled “Related Pages”- IZI API: Overview — general architecture
- Authentication & Tokens — how to get a token
- API Error Codes — what errors mean
- SDK Examples — ready wrappers for JS/Python
Frequently asked questions
What is the difference between query and mutation in IZI API?
A query reads data without changing state. A mutation changes data: starts a session, tops up a balance, updates a tariff. Simple rule: if the operation changes something — it's a mutation.
Can I send multiple operations in one POST?
Yes, this is called batching. Send an array of operations in the request body. IZI API supports batches of up to 10 operations.
How do I discover all available fields and types?
Use introspection: send a __schema or __type query. Most GraphQL clients (Insomnia, Apollo Studio) do this automatically.
What is the N+1 problem and how does IZI handle it?
N+1 occurs when fetching N objects triggers N additional requests for related data. IZI API uses DataLoader to batch related object loads automatically.