Getting started
Who can use the API
Section titled “Who can use the API”An organization administrator of an approved Simblia organization creates API clients for their own organization in the Simblia app. There is no separate sign-up and no approval step: the client works as soon as it is created. An organization can have at most 5 clients that are not revoked. Simblia can suspend or revoke a client, for example if it is misused.
A client can only ever read data from its own organization. In v1 it can read the organization itself
(organization.read). Published lessons come in v1.1. The API never returns personal data about pupils or
staff.
Environments
Section titled “Environments”| Environment | API base URL | Data | Credentials start with |
|---|---|---|---|
| Sandbox | https://api-dev.simblia.com/v1 |
Synthetic data only | sim_dev_ |
| Production | https://api.simblia.com/v1 |
Your organization’s real data | sim_prod_ |
The two environments are separate. A client ID, secret or token from one never works in the other. Build and test against the sandbox first.
1. Create a client
Section titled “1. Create a client”In the Simblia app, open your organization’s settings and create an API client. Give it a name and choose
its scopes; in v1 that is organization.read.
You get a client ID (for example sim_dev_c_…) and a client secret (sim_dev_s_…). Copy the secret
straight away: it is shown once, and Simblia keeps only a hash of it. Store it in a secret store or an
environment variable on your server, never in source code, a browser, a mobile app or any other client-side
code.
2. Get an access token
Section titled “2. Get an access token”Send the client ID and secret with HTTP Basic authentication to the token endpoint, with the form field
grant_type=client_credentials.
curl -s https://api-dev.simblia.com/v1/oauth/token \ -u "$SIMBLIA_CLIENT_ID:$SIMBLIA_CLIENT_SECRET" \ -d grant_type=client_credentials \ -d scope=organization.read{ "access_token": "sim_dev_at_…", "token_type": "Bearer", "expires_in": 900, "scope": "organization.read"}The token is valid for 15 minutes (expires_in is in seconds). Treat it as an opaque string.
3. Call the API
Section titled “3. Call the API”curl -s https://api-dev.simblia.com/v1/organization \ -H "Authorization: Bearer $ACCESS_TOKEN"{ "organization_id": "0b8f2c1e-6d3a-4f7b-9c2d-5e1a8b4c7d90", "name": "Example School", "type": "education", "institution_type": "secondary", "country": "DK"}Every response also carries the header Simblia-API-Status: preview while v1 is in preview.
The same in Python and C#
Section titled “The same in Python and C#”Python with the requests library:
import osimport requests
BASE = "https://api-dev.simblia.com"
token = requests.post( f"{BASE}/v1/oauth/token", auth=(os.environ["SIMBLIA_CLIENT_ID"], os.environ["SIMBLIA_CLIENT_SECRET"]), data={"grant_type": "client_credentials", "scope": "organization.read"}, timeout=10,)token.raise_for_status()access_token = token.json()["access_token"]
org = requests.get( f"{BASE}/v1/organization", headers={"Authorization": f"Bearer {access_token}"}, timeout=10,)org.raise_for_status()print(org.json()["name"])C# with HttpClient (.NET 8 or later):
using System.Net.Http.Headers;using System.Net.Http.Json;using System.Text;
using var http = new HttpClient { BaseAddress = new Uri("https://api-dev.simblia.com") };
var id = Environment.GetEnvironmentVariable("SIMBLIA_CLIENT_ID")!;var secret = Environment.GetEnvironmentVariable("SIMBLIA_CLIENT_SECRET")!;var basic = Convert.ToBase64String(Encoding.UTF8.GetBytes($"{id}:{secret}"));
using var tokenRequest = new HttpRequestMessage(HttpMethod.Post, "/v1/oauth/token"){ Content = new FormUrlEncodedContent(new Dictionary<string, string> { ["grant_type"] = "client_credentials", ["scope"] = "organization.read", }),};tokenRequest.Headers.Authorization = new AuthenticationHeaderValue("Basic", basic);using var tokenResponse = await http.SendAsync(tokenRequest);tokenResponse.EnsureSuccessStatusCode();var token = (await tokenResponse.Content.ReadFromJsonAsync<TokenResponse>())!;
using var orgRequest = new HttpRequestMessage(HttpMethod.Get, "/v1/organization");orgRequest.Headers.Authorization = new AuthenticationHeaderValue("Bearer", token.access_token);using var orgResponse = await http.SendAsync(orgRequest);orgResponse.EnsureSuccessStatusCode();var org = (await orgResponse.Content.ReadFromJsonAsync<Organization>())!;Console.WriteLine(org.name);
record TokenResponse(string access_token, string token_type, int expires_in, string scope);record Organization(Guid organization_id, string name, string type, string institution_type, string country);Next steps
Section titled “Next steps”- Authentication: token lifetime, rotation, revocation and metadata.
- Errors and rate limits.
- The API reference, generated from the OpenAPI contract.