Create agent
Admin only. Creates an agent record without a registration token, optionally with a DID and user bindings. Agents normally register themselves through the gateway with a token from POST /v1/agent-registration-tokens. Supply one of agent_name, agent_handle, or agent_id. The agent is stored under a urn:uuid: ID derived from the resolved agent: ID, not the agent: ID itself; use the returned agent_id for later calls. A given agent_handle or agent_id always maps to the same URN, so repeating the request returns 409.
https://<host>/api/v1/agentscurl --request POST \
--url 'https://<host>/api/v1/agents' \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '{"agent_handle":"string","agent_id":"string","agent_name":"string","did":"string","display_name":"string","users":[{"display_name":"string","email":"string","external_subject":"string","role":"string"}]}'const response = await fetch("https://<host>/api/v1/agents", {
method: "POST",
headers: {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
},
body: JSON.stringify({
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string"
}
]
})
});
const data = await response.json();interface CreateAgentResponse {
agent?: Record<string, unknown>;
correlation_id?: string;
keys?: Record<string, unknown>[];
users?: Record<string, unknown>[];
}
const response = await fetch("https://<host>/api/v1/agents", {
method: "POST",
headers: {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
},
body: JSON.stringify({
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string"
}
]
})
});
if (!response.ok) throw new Error(`${response.status} ${response.statusText}`);
const data: CreateAgentResponse = await response.json();import requests
response = requests.post(
"https://<host>/api/v1/agents",
headers={
"Authorization": "Bearer <token>",
"Content-Type": "application/json",
},
json={
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string",
},
],
},
)
response.raise_for_status()
print(response.json())package main
import (
"fmt"
"io"
"net/http"
"strings"
)
func main() {
body := strings.NewReader(`{
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string"
}
]
}`)
req, err := http.NewRequest(http.MethodPost, "https://<host>/api/v1/agents", body)
if err != nil {
panic(err)
}
req.Header.Set("Authorization", "Bearer <token>")
req.Header.Set("Content-Type", "application/json")
res, err := http.DefaultClient.Do(req)
if err != nil {
panic(err)
}
defer res.Body.Close()
data, err := io.ReadAll(res.Body)
if err != nil {
panic(err)
}
fmt.Println(res.Status, string(data))
}import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
public class Example {
public static void main(String[] args) throws Exception {
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create("https://<host>/api/v1/agents"))
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.method("POST", HttpRequest.BodyPublishers.ofString("""
{
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string"
}
]
}
"""))
.build();
HttpResponse<String> response = HttpClient.newHttpClient()
.send(request, HttpResponse.BodyHandlers.ofString());
System.out.println(response.statusCode() + " " + response.body());
}
}using System.Net.Http.Headers;
using System.Text;
using var client = new HttpClient();
using var request = new HttpRequestMessage(HttpMethod.Post, "https://<host>/api/v1/agents");
request.Headers.Authorization = new AuthenticationHeaderValue("Bearer", "<token>");
request.Content = new StringContent("""
{
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string"
}
]
}
""", Encoding.UTF8, "application/json");
using var response = await client.SendAsync(request);
Console.WriteLine($"{(int)response.StatusCode} {await response.Content.ReadAsStringAsync()}");<?php
$ch = curl_init('https://<host>/api/v1/agents');
curl_setopt_array($ch, [
CURLOPT_CUSTOMREQUEST => 'POST',
CURLOPT_HTTPHEADER => [
'Authorization: Bearer <token>',
'Content-Type: application/json',
],
CURLOPT_POSTFIELDS => <<<'JSON'
{
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string"
}
]
}
JSON,
CURLOPT_RETURNTRANSFER => true,
]);
$response = curl_exec($ch);
$status = curl_getinfo($ch, CURLINFO_RESPONSE_CODE);
echo $status . " " . $response . PHP_EOL;require "net/http"
uri = URI("https://<host>/api/v1/agents")
request = Net::HTTP::Post.new(uri)
request["Authorization"] = "Bearer <token>"
request["Content-Type"] = "application/json"
request.body = <<~'JSON'
{
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string"
}
]
}
JSON
response = Net::HTTP.start(uri.hostname, uri.port, use_ssl: uri.scheme == "https") do |http|
http.request(request)
end
puts "#{response.code} #{response.body}"// Cargo.toml dependencies: reqwest (features "json"), serde_json, tokio (features "full")
use serde_json::json;
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
let response = reqwest::Client::new()
.post("https://<host>/api/v1/agents")
.header("Authorization", "Bearer <token>")
.json(&json!({
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string"
}
]
}))
.send()
.await?;
println!("{} {}", response.status(), response.text().await?);
Ok(())
}Authorizations
BearerAuth· API key in header "Authorization" — Type "Bearer" followed by a space and a sign-in token: a Guardian Platform JWT, or an OIDC ID token in a standalone deployment.
Request bodyrequired
Agent to create
agent_handlestringagent_idstringagent_namestringdidstringdisplay_namestringusersinternal_controlhttp.agentUserBindingRequest[]Show properties
Array of
internal_controlhttp.agentUserBindingRequestdisplay_namestringemailstringexternal_subjectstringrolestring
{
"agent_handle": "string",
"agent_id": "string",
"agent_name": "string",
"did": "string",
"display_name": "string",
"users": [
{
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string"
}
]
}Responses
201Created
agentgithub_com_eqtylab_gateway_control-plane_service_internal_discovery.AgentSummaryShow github_com_eqtylab_gateway_control-plane_service_internal_discovery.AgentSummary
active_key_countintegeractive_user_binding_countintegeragent_idstringapp_typestringbadgesgithub_com_eqtylab_gateway_control-plane_service_internal_discovery.AgentBadge[]Show properties
Array of
github_com_eqtylab_gateway_control-plane_service_internal_discovery.AgentBadgedescriptionstringfirst_observed_atstringkeystringlabelstringlast_observed_atstringmetadataobjectShow properties
Map of
anymetadata_typestringplugin_idstringstatusstringsubject_didstring
created_atstringdid_sourcestringdisplay_namestringframeworkobjectFramework is the framework named by the definition the agent's newest state names, as the definition gives it, read from the verified state rather than the app type a request declares. It is nil when the newest state names no definition (another app type, or recorded before the gateway recorded definitions) or the gateway couldn't record the definition's framework.
Show properties
namestringpackagesobjectShow properties
Map of
string
last_audit_atstringprimary_didstringprimary_user_display_namestringstatusstringthroughputinteger[]total_audit_eventsintegerupdated_atstring
correlation_idstringkeysgithub_com_eqtylab_gateway_control-plane_service_internal_discovery.AgentKey[]Show properties
Array of
github_com_eqtylab_gateway_control-plane_service_internal_discovery.AgentKeyadded_bystringWho added it; told only to an admin and the agent's operators
added_by_api_key_idstringThe API key's public ID; told only to an admin and the agent's operators
added_by_emailstringTheir email; told only to an admin and the agent's operators
added_viastring (enum)AddedVia is how the key joined its agent: registration_token, api_key or control_plane; empty when no record of it survives. AddedBy is the subject of whoever added it, the registering principal or the admin, and AddedByAPIKeyID the API key's public ID.
One of
registration_tokenapi_keycontrol_planecreated_atstringdidstringstatusstringupdated_atstring
usersgithub_com_eqtylab_gateway_control-plane_service_internal_discovery.AgentUser[]Show properties
Array of
github_com_eqtylab_gateway_control-plane_service_internal_discovery.AgentUsercreated_atstringdisplay_namestringemailstringexternal_subjectstringrolestringstatusstringupdated_atstring
{
"agent": {
"active_key_count": 0,
"active_user_binding_count": 0,
"agent_id": "string",
"app_type": "string",
"badges": [
{
"description": "string",
"first_observed_at": "string",
"key": "string",
"label": "string",
"last_observed_at": "string",
"metadata": {
"key": null
},
"metadata_type": "string",
"plugin_id": "string",
"status": "string",
"subject_did": "string"
}
],
"created_at": "string",
"did_source": "string",
"display_name": "string",
"framework": {
"name": "string",
"packages": {
"key": "string"
}
},
"last_audit_at": "string",
"primary_did": "string",
"primary_user_display_name": "string",
"status": "string",
"throughput": [
0
],
"total_audit_events": 0,
"updated_at": "string"
},
"correlation_id": "string",
"keys": [
{
"added_by": "string",
"added_by_api_key_id": "string",
"added_by_email": "string",
"added_via": "registration_token",
"created_at": "string",
"did": "string",
"status": "string",
"updated_at": "string"
}
],
"users": [
{
"created_at": "string",
"display_name": "string",
"email": "string",
"external_subject": "string",
"role": "string",
"status": "string",
"updated_at": "string"
}
]
}400Bad Request
codestringcorrelation_idstringmessagestring
{
"code": "string",
"correlation_id": "string",
"message": "string"
}401Unauthorized
codestringcorrelation_idstringmessagestring
{
"code": "string",
"correlation_id": "string",
"message": "string"
}403Forbidden
codestringcorrelation_idstringmessagestring
{
"code": "string",
"correlation_id": "string",
"message": "string"
}409Agent ID or DID already registered
codestringcorrelation_idstringmessagestring
{
"code": "string",
"correlation_id": "string",
"message": "string"
}500Internal Server Error
codestringcorrelation_idstringmessagestring
{
"code": "string",
"correlation_id": "string",
"message": "string"
}