Skip to content

Commit 499ee20

Browse files
api-clients-generation-pipeline[bot]PROFeNoMci.datadog-api-spec
authored
Add public API spec for LLM Observability prompt registry CRUD endpoints (#4090)
* Fix oneOf array alias examples * Regenerate client from commit 8113261 of spec repo --------- Co-authored-by: Alexandre Choura <alexandre.choura@datadoghq.com> Co-authored-by: ci.datadog-api-spec <packages@datadoghq.com>
1 parent 149fcd3 commit 499ee20

96 files changed

Lines changed: 15665 additions & 2919 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.generator/schemas/v2/openapi.yaml

Lines changed: 1665 additions & 220 deletions
Large diffs are not rendered by default.

.generator/src/generator/formatter.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -530,6 +530,11 @@ def format_data_with_schema_list(
530530
except (KeyError, ValueError):
531531
continue
532532

533+
if matched_sub_schema.get("x-generate-alias-as-model"):
534+
alias_name = schema_name(matched_sub_schema)
535+
one_of_imports.add(alias_name)
536+
value = f"new {alias_name}({value})"
537+
533538
if name:
534539
one_of_imports.add(f"{name}")
535540
# Detect if we need to use factory method due to type erasure collision

.generator/src/generator/templates/modelSimple.j2

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,14 @@
1616
public class {{ name }} {%- if model.get("x-generate-alias-as-model") %} extends {% if "items" in model %}ArrayList<{{ get_type(model["items"]) }}>{% else %}{{ get_type(model) }}{% endif %}{% endif %} {
1717
@JsonIgnore
1818
public boolean unparsed = false;
19+
{%- if model.get("x-generate-alias-as-model") and "items" in model %}
20+
21+
public {{ name }}() {}
22+
23+
public {{ name }}(List<{{ get_type(model["items"]) }}> items) {
24+
super(items);
25+
}
26+
{%- endif %}
1927
{%- for attr, schema in model.get("properties", {}).items() %}
2028
{%- set attributeName = attr|attribute_name %}
2129
{%- set variableName = attr|variable_name %}
@@ -46,7 +54,9 @@ public class {{ name }} {%- if model.get("x-generate-alias-as-model") %} extends
4654

4755
{%- set requiredAttr = model|get_required_attributes %}
4856
{%- if requiredAttr %}
57+
{%- if not (model.get("x-generate-alias-as-model") and "items" in model) %}
4958
public {{ name }}() {}
59+
{%- endif %}
5060

5161
@JsonCreator
5262
public {{ name }}(

.generator/tests/test_formatter.py

Lines changed: 117 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,117 @@
1+
# coding=utf-8
2+
"""Unit tests for the formatter module."""
3+
4+
import yaml
5+
from click.testing import CliRunner
6+
7+
from generator.cli import cli
8+
from generator.formatter import format_data_with_schema
9+
10+
11+
class SchemaWithRef(dict):
12+
"""A schema dict that carries a $ref, as the generator produces after resolving references."""
13+
14+
def __init__(self, *args, ref=None, **kwargs):
15+
super().__init__(*args, **kwargs)
16+
if ref:
17+
self.__reference__ = {"$ref": ref}
18+
19+
20+
def test_named_array_alias_in_oneof_uses_generated_wrapper():
21+
message_schema = SchemaWithRef(
22+
{
23+
"type": "object",
24+
"properties": {
25+
"role": {"type": "string"},
26+
"content": {"type": "string"},
27+
},
28+
"required": ["role", "content"],
29+
},
30+
ref="#/components/schemas/LLMObsPromptChatMessage",
31+
)
32+
chat_schema = SchemaWithRef(
33+
{
34+
"type": "array",
35+
"items": message_schema,
36+
"x-generate-alias-as-model": True,
37+
},
38+
ref="#/components/schemas/LLMObsPromptChatTemplate",
39+
)
40+
template_schema = SchemaWithRef(
41+
{"oneOf": [{"type": "string"}, chat_schema]},
42+
ref="#/components/schemas/LLMObsPromptTemplate",
43+
)
44+
45+
_, result, imports = format_data_with_schema(
46+
[
47+
{"role": "system", "content": "You help {{company_name}} customers."},
48+
{"role": "user", "content": "Answer {{question}}"},
49+
],
50+
template_schema,
51+
)
52+
53+
assert (
54+
"new LLMObsPromptTemplate(new LLMObsPromptChatTemplate("
55+
"Arrays.asList(" in result
56+
)
57+
assert "new LLMObsPromptTemplate(Arrays.asList(" not in result
58+
assert "LLMObsPromptChatTemplate" in imports
59+
60+
61+
def test_named_array_alias_model_accepts_formatted_list(tmp_path):
62+
spec_dir = tmp_path / "v2"
63+
spec_dir.mkdir()
64+
spec_path = spec_dir / "openapi.yaml"
65+
spec_path.write_text(
66+
yaml.safe_dump(
67+
{
68+
"openapi": "3.0.0",
69+
"info": {"title": "test", "version": "1"},
70+
"servers": [{"url": "https://api.example.com", "variables": {}}],
71+
"paths": {
72+
"/test": {
73+
"post": {
74+
"operationId": "TestArrayAlias",
75+
"tags": ["Test"],
76+
"requestBody": {
77+
"content": {
78+
"application/json": {
79+
"schema": {
80+
"$ref": "#/components/schemas/LLMObsPromptChatTemplate"
81+
}
82+
}
83+
}
84+
},
85+
"responses": {"200": {"description": "OK"}},
86+
}
87+
}
88+
},
89+
"components": {
90+
"securitySchemes": {},
91+
"schemas": {
92+
"LLMObsPromptChatMessage": {
93+
"type": "object",
94+
"properties": {
95+
"role": {"type": "string"},
96+
"content": {"type": "string"},
97+
},
98+
},
99+
"LLMObsPromptChatTemplate": {
100+
"type": "array",
101+
"items": {"$ref": "#/components/schemas/LLMObsPromptChatMessage"},
102+
"x-generate-alias-as-model": True,
103+
},
104+
}
105+
},
106+
}
107+
)
108+
)
109+
output = tmp_path / "generated"
110+
111+
result = CliRunner().invoke(cli, [str(spec_path), "--output", str(output)])
112+
113+
assert result.exit_code == 0
114+
model = (output / "v2/model/LLMObsPromptChatTemplate.java").read_text()
115+
assert "public LLMObsPromptChatTemplate() {}" in model
116+
assert "public LLMObsPromptChatTemplate(List<LLMObsPromptChatMessage> items)" in model
117+
assert "super(items);" in model
Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
// Create an LLM Observability prompt returns "OK" response
2+
3+
import com.datadog.api.client.ApiClient;
4+
import com.datadog.api.client.ApiException;
5+
import com.datadog.api.client.v2.api.LlmObservabilityApi;
6+
import com.datadog.api.client.v2.model.LLMObsCreatePromptData;
7+
import com.datadog.api.client.v2.model.LLMObsCreatePromptDataAttributes;
8+
import com.datadog.api.client.v2.model.LLMObsCreatePromptRequest;
9+
import com.datadog.api.client.v2.model.LLMObsPromptChatMessage;
10+
import com.datadog.api.client.v2.model.LLMObsPromptChatTemplate;
11+
import com.datadog.api.client.v2.model.LLMObsPromptResponse;
12+
import com.datadog.api.client.v2.model.LLMObsPromptTemplate;
13+
import com.datadog.api.client.v2.model.LLMObsPromptType;
14+
import java.util.Arrays;
15+
16+
public class Example {
17+
public static void main(String[] args) {
18+
ApiClient defaultClient = ApiClient.getDefaultApiClient();
19+
defaultClient.setUnstableOperationEnabled("v2.createLLMObsPrompt", true);
20+
LlmObservabilityApi apiInstance = new LlmObservabilityApi(defaultClient);
21+
22+
LLMObsCreatePromptRequest body =
23+
new LLMObsCreatePromptRequest()
24+
.data(
25+
new LLMObsCreatePromptData()
26+
.attributes(
27+
new LLMObsCreatePromptDataAttributes()
28+
.promptId("Example-LLM-Observability")
29+
.title("Customer Support Assistant")
30+
.template(
31+
new LLMObsPromptTemplate(
32+
new LLMObsPromptChatTemplate(
33+
Arrays.asList(
34+
new LLMObsPromptChatMessage()
35+
.content(
36+
"You are a helpful customer support assistant"
37+
+ " for {{company_name}}.")
38+
.role("system"),
39+
new LLMObsPromptChatMessage()
40+
.content(
41+
"Help {{customer_name}} with this question:"
42+
+ " {{question}}")
43+
.role("user"))))))
44+
.type(LLMObsPromptType.PROMPT_TEMPLATES));
45+
46+
try {
47+
LLMObsPromptResponse result = apiInstance.createLLMObsPrompt(body);
48+
System.out.println(result);
49+
} catch (ApiException e) {
50+
System.err.println("Exception when calling LlmObservabilityApi#createLLMObsPrompt");
51+
System.err.println("Status code: " + e.getCode());
52+
System.err.println("Reason: " + e.getResponseBody());
53+
System.err.println("Response headers: " + e.getResponseHeaders());
54+
e.printStackTrace();
55+
}
56+
}
57+
}
Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
// Create a new LLM Observability prompt version returns "OK" response
2+
3+
import com.datadog.api.client.ApiClient;
4+
import com.datadog.api.client.ApiException;
5+
import com.datadog.api.client.v2.api.LlmObservabilityApi;
6+
import com.datadog.api.client.v2.model.LLMObsCreatePromptVersionData;
7+
import com.datadog.api.client.v2.model.LLMObsCreatePromptVersionDataAttributes;
8+
import com.datadog.api.client.v2.model.LLMObsCreatePromptVersionRequest;
9+
import com.datadog.api.client.v2.model.LLMObsPromptChatMessage;
10+
import com.datadog.api.client.v2.model.LLMObsPromptChatTemplate;
11+
import com.datadog.api.client.v2.model.LLMObsPromptTemplate;
12+
import com.datadog.api.client.v2.model.LLMObsPromptVersionResponse;
13+
import com.datadog.api.client.v2.model.LLMObsPromptVersionType;
14+
import java.util.Arrays;
15+
16+
public class Example {
17+
public static void main(String[] args) {
18+
ApiClient defaultClient = ApiClient.getDefaultApiClient();
19+
defaultClient.setUnstableOperationEnabled("v2.createLLMObsPromptVersion", true);
20+
LlmObservabilityApi apiInstance = new LlmObservabilityApi(defaultClient);
21+
22+
// there is a valid "prompt" in the system
23+
String PROMPT_DATA_ATTRIBUTES_PROMPT_ID = System.getenv("PROMPT_DATA_ATTRIBUTES_PROMPT_ID");
24+
25+
LLMObsCreatePromptVersionRequest body =
26+
new LLMObsCreatePromptVersionRequest()
27+
.data(
28+
new LLMObsCreatePromptVersionData()
29+
.attributes(
30+
new LLMObsCreatePromptVersionDataAttributes()
31+
.template(
32+
new LLMObsPromptTemplate(
33+
new LLMObsPromptChatTemplate(
34+
Arrays.asList(
35+
new LLMObsPromptChatMessage()
36+
.content(
37+
"You are a concise customer support assistant"
38+
+ " for {{company_name}}.")
39+
.role("system"),
40+
new LLMObsPromptChatMessage()
41+
.content(
42+
"Answer {{customer_name}}'s question:"
43+
+ " {{question}}")
44+
.role("user"))))))
45+
.type(LLMObsPromptVersionType.PROMPT_TEMPLATE_VERSIONS));
46+
47+
try {
48+
LLMObsPromptVersionResponse result =
49+
apiInstance.createLLMObsPromptVersion(PROMPT_DATA_ATTRIBUTES_PROMPT_ID, body);
50+
System.out.println(result);
51+
} catch (ApiException e) {
52+
System.err.println("Exception when calling LlmObservabilityApi#createLLMObsPromptVersion");
53+
System.err.println("Status code: " + e.getCode());
54+
System.err.println("Reason: " + e.getResponseBody());
55+
System.err.println("Response headers: " + e.getResponseHeaders());
56+
e.printStackTrace();
57+
}
58+
}
59+
}
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
// Delete an LLM Observability prompt returns "OK" response
2+
3+
import com.datadog.api.client.ApiClient;
4+
import com.datadog.api.client.ApiException;
5+
import com.datadog.api.client.v2.api.LlmObservabilityApi;
6+
import com.datadog.api.client.v2.model.LLMObsDeletedPromptResponse;
7+
8+
public class Example {
9+
public static void main(String[] args) {
10+
ApiClient defaultClient = ApiClient.getDefaultApiClient();
11+
defaultClient.setUnstableOperationEnabled("v2.deleteLLMObsPrompt", true);
12+
LlmObservabilityApi apiInstance = new LlmObservabilityApi(defaultClient);
13+
14+
// there is a valid "prompt" in the system
15+
String PROMPT_DATA_ATTRIBUTES_PROMPT_ID = System.getenv("PROMPT_DATA_ATTRIBUTES_PROMPT_ID");
16+
17+
try {
18+
LLMObsDeletedPromptResponse result =
19+
apiInstance.deleteLLMObsPrompt(PROMPT_DATA_ATTRIBUTES_PROMPT_ID);
20+
System.out.println(result);
21+
} catch (ApiException e) {
22+
System.err.println("Exception when calling LlmObservabilityApi#deleteLLMObsPrompt");
23+
System.err.println("Status code: " + e.getCode());
24+
System.err.println("Reason: " + e.getResponseBody());
25+
System.err.println("Response headers: " + e.getResponseHeaders());
26+
e.printStackTrace();
27+
}
28+
}
29+
}
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
// Get an LLM Observability prompt returns "OK" response
2+
3+
import com.datadog.api.client.ApiClient;
4+
import com.datadog.api.client.ApiException;
5+
import com.datadog.api.client.v2.api.LlmObservabilityApi;
6+
import com.datadog.api.client.v2.model.LLMObsPromptSDKResponse;
7+
8+
public class Example {
9+
public static void main(String[] args) {
10+
ApiClient defaultClient = ApiClient.getDefaultApiClient();
11+
defaultClient.setUnstableOperationEnabled("v2.getLLMObsPrompt", true);
12+
LlmObservabilityApi apiInstance = new LlmObservabilityApi(defaultClient);
13+
14+
// there is a valid "prompt" in the system
15+
String PROMPT_DATA_ATTRIBUTES_PROMPT_ID = System.getenv("PROMPT_DATA_ATTRIBUTES_PROMPT_ID");
16+
17+
try {
18+
LLMObsPromptSDKResponse result =
19+
apiInstance.getLLMObsPrompt(PROMPT_DATA_ATTRIBUTES_PROMPT_ID);
20+
System.out.println(result);
21+
} catch (ApiException e) {
22+
System.err.println("Exception when calling LlmObservabilityApi#getLLMObsPrompt");
23+
System.err.println("Status code: " + e.getCode());
24+
System.err.println("Reason: " + e.getResponseBody());
25+
System.err.println("Response headers: " + e.getResponseHeaders());
26+
e.printStackTrace();
27+
}
28+
}
29+
}
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
// Get a specific LLM Observability prompt version returns "OK" response
2+
3+
import com.datadog.api.client.ApiClient;
4+
import com.datadog.api.client.ApiException;
5+
import com.datadog.api.client.v2.api.LlmObservabilityApi;
6+
import com.datadog.api.client.v2.model.LLMObsPromptVersionResponse;
7+
8+
public class Example {
9+
public static void main(String[] args) {
10+
ApiClient defaultClient = ApiClient.getDefaultApiClient();
11+
defaultClient.setUnstableOperationEnabled("v2.getLLMObsPromptVersion", true);
12+
LlmObservabilityApi apiInstance = new LlmObservabilityApi(defaultClient);
13+
14+
// there is a valid "prompt" in the system
15+
String PROMPT_DATA_ATTRIBUTES_PROMPT_ID = System.getenv("PROMPT_DATA_ATTRIBUTES_PROMPT_ID");
16+
17+
// there is a valid "prompt_version" in the system
18+
Long PROMPT_VERSION_DATA_ATTRIBUTES_VERSION =
19+
Long.parseLong(System.getenv("PROMPT_VERSION_DATA_ATTRIBUTES_VERSION"));
20+
21+
try {
22+
LLMObsPromptVersionResponse result =
23+
apiInstance.getLLMObsPromptVersion(
24+
PROMPT_DATA_ATTRIBUTES_PROMPT_ID, PROMPT_VERSION_DATA_ATTRIBUTES_VERSION);
25+
System.out.println(result);
26+
} catch (ApiException e) {
27+
System.err.println("Exception when calling LlmObservabilityApi#getLLMObsPromptVersion");
28+
System.err.println("Status code: " + e.getCode());
29+
System.err.println("Reason: " + e.getResponseBody());
30+
System.err.println("Response headers: " + e.getResponseHeaders());
31+
e.printStackTrace();
32+
}
33+
}
34+
}
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
// List versions of an LLM Observability prompt returns "OK" response
2+
3+
import com.datadog.api.client.ApiClient;
4+
import com.datadog.api.client.ApiException;
5+
import com.datadog.api.client.v2.api.LlmObservabilityApi;
6+
import com.datadog.api.client.v2.model.LLMObsPromptVersionsResponse;
7+
8+
public class Example {
9+
public static void main(String[] args) {
10+
ApiClient defaultClient = ApiClient.getDefaultApiClient();
11+
defaultClient.setUnstableOperationEnabled("v2.listLLMObsPromptVersions", true);
12+
LlmObservabilityApi apiInstance = new LlmObservabilityApi(defaultClient);
13+
14+
// there is a valid "prompt" in the system
15+
String PROMPT_DATA_ATTRIBUTES_PROMPT_ID = System.getenv("PROMPT_DATA_ATTRIBUTES_PROMPT_ID");
16+
17+
try {
18+
LLMObsPromptVersionsResponse result =
19+
apiInstance.listLLMObsPromptVersions(PROMPT_DATA_ATTRIBUTES_PROMPT_ID);
20+
System.out.println(result);
21+
} catch (ApiException e) {
22+
System.err.println("Exception when calling LlmObservabilityApi#listLLMObsPromptVersions");
23+
System.err.println("Status code: " + e.getCode());
24+
System.err.println("Reason: " + e.getResponseBody());
25+
System.err.println("Response headers: " + e.getResponseHeaders());
26+
e.printStackTrace();
27+
}
28+
}
29+
}

0 commit comments

Comments
 (0)