<!-- llms.txt: https://workos.com/llms.txt -->

# Getting started

The Widgets API is a GraphQL API that allows you to build custom user interfaces for enterprise application workflows using WorkOS tools and services, giving you full control over the user experience.

Unlike the [WorkOS REST API](https://workos.com/docs/reference), the Widgets API can be called directly from the browser on behalf of a signed-in user. Every request is authorized by a short-lived session token, so a user can only ever read and write what they are entitled to based on their [role and permissions](https://workos.com/docs/authkit/roles-and-permissions). All operations are sent as `POST` requests to a single endpoint.

```url title="Widgets API Endpoint"
https://api.workos.com/client/graphql
```

## Making a request

Send the query and its variables as a JSON body, with the Widget token in the `Authorization` header.

:::code-group

```bash language="curl" title="Request" tab="1"
curl --request POST \
  --url "https://api.workos.com/client/graphql" \
  --header "Authorization: Bearer <Widget token>" \
  --header "Content-Type: application/json" \
  -d @- <<'BODY'
{
  "query": "query Organization($id: ID!) { organization(id: $id) { id name } }",
  "variables": { "id": "org_01EHZNVPK3SFK441A1RGBFSHRT" }
}
BODY
```

```js language="js" title="Request" tab="1"
const response = await fetch('https://api.workos.com/client/graphql', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    'Authorization': 'Bearer <Widget token>',
  },
  body: JSON.stringify({
    query: 'query Organization($id: ID!) { organization(id: $id) { id name } }',
    variables: {
      id: 'org_01EHZNVPK3SFK441A1RGBFSHRT',
    },
  }),
});
```

```rb language="ruby" title="Request" tab="1"
require "json"
require "net/http"

uri = URI("https://api.workos.com/client/graphql")

request = Net::HTTP::Post.new(uri)
request["Content-Type"] = "application/json"
request["Authorization"] = "Bearer <Widget token>"
request.body = JSON.generate(
  query: "query Organization($id: ID!) { organization(id: $id) { id name } }",
  variables: { id: "org_01EHZNVPK3SFK441A1RGBFSHRT" }
)

response = Net::HTTP.start(uri.hostname, uri.port, use_ssl: true) do |http|
  http.request(request)
end
```

```py language="python" title="Request" tab="1"
import requests

response = requests.post(
    "https://api.workos.com/client/graphql",
    headers={
        "Content-Type": "application/json",
        "Authorization": "Bearer <Widget token>",
    },
    json={
        "query": "query Organization($id: ID!) { organization(id: $id) { id name } }",
        "variables": {"id": "org_01EHZNVPK3SFK441A1RGBFSHRT"},
    },
)
```

```go language="go" title="Request" tab="1"
package main

import (
	"net/http"
	"strings"
)

func main() {
	body := strings.NewReader(`{
  "query": "query Organization($id: ID!) { organization(id: $id) { id name } }",
  "variables": { "id": "org_01EHZNVPK3SFK441A1RGBFSHRT" }
}`)

	request, err := http.NewRequest(http.MethodPost, "https://api.workos.com/client/graphql", body)
	if err != nil {
		// Handle the error...
	}

	request.Header.Set("Content-Type", "application/json")
	request.Header.Set("Authorization", "Bearer <Widget token>")

	response, err := http.DefaultClient.Do(request)
	if err != nil {
		// Handle the error...
	}
	defer response.Body.Close()
}
```

```php language="php" title="Request" tab="1"
<?php

$body = json_encode([
    "query" =>
        'query Organization($id: ID!) { organization(id: $id) { id name } }',
    "variables" => ["id" => "org_01EHZNVPK3SFK441A1RGBFSHRT"],
]);

$curl = curl_init("https://api.workos.com/client/graphql");

curl_setopt_array($curl, [
    CURLOPT_POST => true,
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_HTTPHEADER => [
        "Content-Type: application/json",
        "Authorization: Bearer <Widget token>",
    ],
    CURLOPT_POSTFIELDS => $body,
]);

$response = curl_exec($curl);

curl_close($curl);
```

```java language="java" title="Request" tab="1"
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;

String body = """
    {
      "query": "query Organization($id: ID!) { organization(id: $id) { id name } }",
      "variables": { "id": "org_01EHZNVPK3SFK441A1RGBFSHRT" }
    }
    """;

HttpRequest request =
    HttpRequest.newBuilder()
        .uri(URI.create("https://api.workos.com/client/graphql"))
        .header("Content-Type", "application/json")
        .header("Authorization", "Bearer <Widget token>")
        .POST(HttpRequest.BodyPublishers.ofString(body))
        .build();

HttpResponse<String> response =
    HttpClient.newHttpClient().send(request, HttpResponse.BodyHandlers.ofString());
```

```cs language="dotnet" title="Request" tab="1"
using System.Net.Http;
using System.Text;
using System.Text.Json;

var body = JsonSerializer.Serialize(new {
    query = "query Organization($id: ID!) { organization(id: $id) { id name } }",
    variables = new { id = "org_01EHZNVPK3SFK441A1RGBFSHRT" },
});

var request = new HttpRequestMessage(HttpMethod.Post, "https://api.workos.com/client/graphql") {
    Content = new StringContent(body, Encoding.UTF8, "application/json"),
};

request.Headers.Add("Authorization", "Bearer <Widget token>");

var response = await new HttpClient().SendAsync(request);
```

```rust language="rust" title="Request" tab="1"
use serde_json::json;

#[tokio::main]
async fn main() -> Result<(), reqwest::Error> {
    let _response = reqwest::Client::new()
        .post("https://api.workos.com/client/graphql")
        .header("Content-Type", "application/json")
        .header("Authorization", "Bearer <Widget token>")
        .json(&json!({
            "query": "query Organization($id: ID!) { organization(id: $id) { id name } }",
            "variables": { "id": "org_01EHZNVPK3SFK441A1RGBFSHRT" }
        }))
        .send()
        .await?;

    Ok(())
}
```

```json language="json" title="Response" tab="2"
{
  "data": {
    "organization": {
      "id": "org_01EHZNVPK3SFK441A1RGBFSHRT",
      "name": "Foo Corp"
    }
  }
}
```

:::

## Schema and introspection

The full schema is published as a downloadable file, so GraphQL tooling such as editor plugins and code generators can be pointed at a file instead of a live endpoint.

[Download the Widgets API schema](https://workos.com/docs/assets/widgets-api-schema.graphql)

Introspection queries are disabled in production. If your workflow requires introspecting the live endpoint, [contact support](mailto:support@workos.com) to have it enabled for a specific environment.

## What you can do

The API is grouped by the resource it operates on:

- [Users](https://workos.com/docs/widgets-api/users) — read and update the signed-in user's profile and email address.
- [Organizations](https://workos.com/docs/widgets-api/organizations) — manage members, invitations, and role assignments.
- [Domain verification](https://workos.com/docs/widgets-api/domain-verification) — add organization domains and track their DNS verification.
- [Roles and permissions](https://workos.com/docs/widgets-api/roles-and-permissions) — define roles and inspect the permissions a member holds.
- [Authentication](https://workos.com/docs/widgets-api/authentication) — manage passwords, MFA factors, passkeys, and sessions.
- [Single Sign-On](https://workos.com/docs/widgets-api/single-sign-on) — manage an organization's SSO connections.
- [Directory Sync](https://workos.com/docs/widgets-api/directory-sync) — read directory connections and their synced users and groups.
- [Audit logs](https://workos.com/docs/widgets-api/audit-logs) — search and export audit events.
- [Data providers](https://workos.com/docs/widgets-api/data-providers) — browse data providers and the user's connections to them.