Skip to content

Commit 9c3c285

Browse files
feat: [DevOps] Update orchestration specification (#669)
* Update orchestration based on rel-0.108.12 * Fixed error classes * Formatting --------- Co-authored-by: I538344 <charles.dubois@sap.com>
1 parent 247143f commit 9c3c285

31 files changed

+627
-73
lines changed

orchestration/pom.xml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -38,8 +38,8 @@
3838
<project.rootdir>${project.basedir}/../</project.rootdir>
3939
<coverage.complexity>80%</coverage.complexity>
4040
<coverage.line>94%</coverage.line>
41-
<coverage.instruction>94%</coverage.instruction>
42-
<coverage.branch>75%</coverage.branch>
41+
<coverage.instruction>93%</coverage.instruction>
42+
<coverage.branch>74%</coverage.branch>
4343
<coverage.method>93%</coverage.method>
4444
<coverage.class>100%</coverage.class>
4545
</properties>

orchestration/src/main/java/com/sap/ai/sdk/orchestration/ConfigToRequestTransformer.java

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
11
package com.sap.ai.sdk.orchestration;
22

3-
import com.sap.ai.sdk.orchestration.model.ChatMessage;
43
import com.sap.ai.sdk.orchestration.model.CompletionRequestConfiguration;
54
import com.sap.ai.sdk.orchestration.model.ModuleConfigs;
65
import com.sap.ai.sdk.orchestration.model.OrchestrationConfig;
6+
import com.sap.ai.sdk.orchestration.model.OrchestrationConfigModules;
7+
import com.sap.ai.sdk.orchestration.model.OrchestrationConfigModules.InnerModuleConfigs;
78
import com.sap.ai.sdk.orchestration.model.PromptTemplatingModuleConfig;
89
import com.sap.ai.sdk.orchestration.model.PromptTemplatingModuleConfigPrompt;
910
import com.sap.ai.sdk.orchestration.model.Template;
@@ -31,10 +32,7 @@ static CompletionRequestConfiguration toCompletionPostRequest(
3132
val configCopy = config.withTemplateConfig(template);
3233

3334
val messageHistory =
34-
prompt.getMessagesHistory().stream()
35-
.map(Message::createChatMessage)
36-
.map(ChatMessage.class::cast)
37-
.toList();
35+
prompt.getMessagesHistory().stream().map(Message::createChatMessage).toList();
3836

3937
val moduleConfigs = toModuleConfigs(configCopy);
4038

@@ -81,13 +79,13 @@ static PromptTemplatingModuleConfigPrompt toTemplateModuleConfig(
8179
.responseFormat(template.getResponseFormat());
8280

8381
for (val customFieldName : template.getCustomFieldNames()) {
84-
result.setCustomField(customFieldName, template.getCustomField(customFieldName));
82+
result.setCustomField(customFieldName, template.toMap().get(customFieldName));
8583
}
8684
return result;
8785
}
8886

8987
@Nonnull
90-
static ModuleConfigs toModuleConfigs(@Nonnull final OrchestrationModuleConfig config) {
88+
static InnerModuleConfigs toModuleConfigs(@Nonnull final OrchestrationModuleConfig config) {
9189
val llmConfig =
9290
Option.of(config.getLlmConfig())
9391
.getOrElseThrow(() -> new IllegalStateException("LLM config is required."));
@@ -113,6 +111,6 @@ static ModuleConfigs toModuleConfigs(@Nonnull final OrchestrationModuleConfig co
113111
outputTranslation.forEach(moduleConfig.getTranslation()::output);
114112
}
115113

116-
return moduleConfig;
114+
return OrchestrationConfigModules.createInnerModuleConfigs(moduleConfig);
117115
}
118116
}

orchestration/src/main/java/com/sap/ai/sdk/orchestration/OrchestrationAiModel.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ public class OrchestrationAiModel {
2929
*
3030
* <pre>{@code
3131
* Map.of(
32-
* "max_tokens", 50,
32+
* "max_completion_tokens", 50,
3333
* "temperature", 0.1,
3434
* "frequency_penalty", 0,
3535
* "presence_penalty", 0)
@@ -375,7 +375,7 @@ public <ValueT> OrchestrationAiModel withParam(
375375
@FunctionalInterface
376376
public interface Parameter<ValueT> {
377377
/** The maximum number of tokens to generate. */
378-
Parameter<Integer> MAX_TOKENS = () -> "max_tokens";
378+
Parameter<Integer> MAX_TOKENS = () -> "max_completion_tokens";
379379

380380
/** The sampling temperature. */
381381
Parameter<Number> TEMPERATURE = () -> "temperature";

orchestration/src/main/java/com/sap/ai/sdk/orchestration/OrchestrationClientException.java

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,9 @@
66
import com.sap.ai.sdk.orchestration.OrchestrationFilterException.Input;
77
import com.sap.ai.sdk.orchestration.model.Error;
88
import com.sap.ai.sdk.orchestration.model.ErrorResponse;
9+
import com.sap.ai.sdk.orchestration.model.ErrorResponseError;
910
import com.sap.ai.sdk.orchestration.model.ErrorResponseStreaming;
11+
import com.sap.ai.sdk.orchestration.model.ErrorResponseStreamingError;
1012
import com.sap.ai.sdk.orchestration.model.ErrorStreaming;
1113
import com.sap.ai.sdk.orchestration.model.GenericModuleResult;
1214
import com.sap.ai.sdk.orchestration.model.ModuleResults;
@@ -17,6 +19,7 @@
1719
import javax.annotation.Nonnull;
1820
import javax.annotation.Nullable;
1921
import lombok.experimental.StandardException;
22+
import lombok.val;
2023

2124
/** Exception thrown by the {@link OrchestrationClient} in case of an error. */
2225
@StandardException
@@ -37,6 +40,7 @@ static Map<String, Object> extractInputFilterDetails(@Nullable final Orchestrati
3740
if (error instanceof OrchestrationError.Synchronous synchronousError) {
3841
return Optional.of(synchronousError.getErrorResponse())
3942
.map(ErrorResponse::getError)
43+
.flatMap(OrchestrationClientException::lastError)
4044
.map(Error::getIntermediateResults)
4145
.map(ModuleResults::getInputFiltering)
4246
.filter(filter -> !filter.getMessage().equals("Input Filter passed successfully."))
@@ -46,6 +50,7 @@ static Map<String, Object> extractInputFilterDetails(@Nullable final Orchestrati
4650
} else if (error instanceof OrchestrationError.Streaming streamingError) {
4751
return Optional.of(streamingError.getErrorResponse())
4852
.map(ErrorResponseStreaming::getError)
53+
.flatMap(OrchestrationClientException::lastErrorStreaming)
4954
.map(ErrorStreaming::getIntermediateResults)
5055
.map(ModuleResultsStreaming::getInputFiltering)
5156
.filter(filter -> !filter.getMessage().equals("Input Filter passed successfully."))
@@ -57,6 +62,29 @@ static Map<String, Object> extractInputFilterDetails(@Nullable final Orchestrati
5762
return Collections.emptyMap();
5863
}
5964

65+
static Optional<Error> lastError(final ErrorResponseError responseError) {
66+
if (responseError instanceof ErrorResponseError.InnerError innerError) {
67+
return Optional.of(innerError.value());
68+
}
69+
if (responseError instanceof ErrorResponseError.ListOfErrors listOfErrors) {
70+
val list = listOfErrors.values();
71+
return list.isEmpty() ? Optional.empty() : Optional.of(list.get(list.size() - 1));
72+
}
73+
return Optional.empty();
74+
}
75+
76+
static Optional<ErrorStreaming> lastErrorStreaming(
77+
final ErrorResponseStreamingError responseError) {
78+
if (responseError instanceof ErrorResponseStreamingError.InnerErrorStreaming innerError) {
79+
return Optional.of(innerError.value());
80+
}
81+
if (responseError instanceof ErrorResponseStreamingError.ListOfErrorStreamings listOfErrors) {
82+
val list = listOfErrors.values();
83+
return list.isEmpty() ? Optional.empty() : Optional.of(list.get(list.size() - 1));
84+
}
85+
return Optional.empty();
86+
}
87+
6088
@Override
6189
@Nullable
6290
public OrchestrationError getClientError() {
@@ -104,6 +132,7 @@ public ErrorResponseStreaming getErrorResponseStreaming() {
104132
public Integer getStatusCode() {
105133
return Optional.ofNullable(getErrorResponse())
106134
.map(ErrorResponse::getError)
135+
.flatMap(OrchestrationClientException::lastError)
107136
.map(Error::getCode)
108137
.orElse(null);
109138
}

orchestration/src/main/java/com/sap/ai/sdk/orchestration/OrchestrationError.java

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
package com.sap.ai.sdk.orchestration;
22

3+
import static com.sap.ai.sdk.orchestration.OrchestrationClientException.lastError;
4+
import static com.sap.ai.sdk.orchestration.OrchestrationClientException.lastErrorStreaming;
5+
36
import com.fasterxml.jackson.annotation.JsonCreator;
47
import com.google.common.annotations.Beta;
58
import com.sap.ai.sdk.core.common.ClientError;
@@ -27,12 +30,14 @@ public interface OrchestrationError extends ClientError {
2730
@AllArgsConstructor(onConstructor = @__({@JsonCreator}), access = AccessLevel.PROTECTED)
2831
@Value
2932
class Synchronous implements OrchestrationError {
33+
private static Error NOT_FOUND =
34+
Error.create().requestId("").code(-1).message("Error not found.").location("");
3035
ErrorResponse errorResponse;
3136

3237
@Override
3338
@Nonnull
3439
public String getMessage() {
35-
final Error e = errorResponse.getError();
40+
final Error e = lastError(errorResponse.getError()).orElse(NOT_FOUND);
3641
final String message = e.getMessage();
3742
return e.getCode() == 500 ? "%s located in %s".formatted(message, e.getLocation()) : message;
3843
}
@@ -46,12 +51,14 @@ public String getMessage() {
4651
@AllArgsConstructor(onConstructor = @__({@JsonCreator}), access = AccessLevel.PROTECTED)
4752
@Value
4853
class Streaming implements OrchestrationError {
54+
private static ErrorStreaming NOT_FOUND =
55+
ErrorStreaming.create().requestId("").code(-1).message("Error not found.").location("");
4956
ErrorResponseStreaming errorResponse;
5057

5158
@Override
5259
@Nonnull
5360
public String getMessage() {
54-
final ErrorStreaming e = errorResponse.getError();
61+
final ErrorStreaming e = lastErrorStreaming(errorResponse.getError()).orElse(NOT_FOUND);
5562
final String message = e.getMessage();
5663
return e.getCode() == 500 ? "%s located in %s".formatted(message, e.getLocation()) : message;
5764
}

orchestration/src/main/java/com/sap/ai/sdk/orchestration/model/AzureContentSafetyInput.java

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -177,7 +177,8 @@ public void setViolence(@Nullable final AzureThreshold violence) {
177177
* Set the promptShield of this {@link AzureContentSafetyInput} instance and return the same
178178
* instance.
179179
*
180-
* @param promptShield A flag to use prompt shield
180+
* @param promptShield Filter prompts for harmful content such as jailbreaks and prompt
181+
* injections.
181182
* @return The same instance of this {@link AzureContentSafetyInput} class
182183
*/
183184
@Nonnull
@@ -187,7 +188,7 @@ public AzureContentSafetyInput promptShield(@Nullable final Boolean promptShield
187188
}
188189

189190
/**
190-
* A flag to use prompt shield
191+
* Filter prompts for harmful content such as jailbreaks and prompt injections.
191192
*
192193
* @return promptShield The promptShield of this {@link AzureContentSafetyInput} instance.
193194
*/
@@ -199,7 +200,8 @@ public Boolean isPromptShield() {
199200
/**
200201
* Set the promptShield of this {@link AzureContentSafetyInput} instance.
201202
*
202-
* @param promptShield A flag to use prompt shield
203+
* @param promptShield Filter prompts for harmful content such as jailbreaks and prompt
204+
* injections.
203205
*/
204206
public void setPromptShield(@Nullable final Boolean promptShield) {
205207
this.promptShield = promptShield;

orchestration/src/main/java/com/sap/ai/sdk/orchestration/model/AzureContentSafetyOutput.java

Lines changed: 52 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,9 @@ public class AzureContentSafetyOutput
4040
@JsonProperty("violence")
4141
private AzureThreshold violence;
4242

43+
@JsonProperty("protected_material_code")
44+
private Boolean protectedMaterialCode = false;
45+
4346
@JsonAnySetter @JsonAnyGetter
4447
private final Map<String, Object> cloudSdkCustomFields = new LinkedHashMap<>();
4548

@@ -172,6 +175,45 @@ public void setViolence(@Nullable final AzureThreshold violence) {
172175
this.violence = violence;
173176
}
174177

178+
/**
179+
* Set the protectedMaterialCode of this {@link AzureContentSafetyOutput} instance and return the
180+
* same instance.
181+
*
182+
* @param protectedMaterialCode Detect protected code content from known GitHub repositories. The
183+
* scan includes software libraries, source code, algorithms, and other proprietary
184+
* programming content.
185+
* @return The same instance of this {@link AzureContentSafetyOutput} class
186+
*/
187+
@Nonnull
188+
public AzureContentSafetyOutput protectedMaterialCode(
189+
@Nullable final Boolean protectedMaterialCode) {
190+
this.protectedMaterialCode = protectedMaterialCode;
191+
return this;
192+
}
193+
194+
/**
195+
* Detect protected code content from known GitHub repositories. The scan includes software
196+
* libraries, source code, algorithms, and other proprietary programming content.
197+
*
198+
* @return protectedMaterialCode The protectedMaterialCode of this {@link
199+
* AzureContentSafetyOutput} instance.
200+
*/
201+
@Nonnull
202+
public Boolean isProtectedMaterialCode() {
203+
return protectedMaterialCode;
204+
}
205+
206+
/**
207+
* Set the protectedMaterialCode of this {@link AzureContentSafetyOutput} instance.
208+
*
209+
* @param protectedMaterialCode Detect protected code content from known GitHub repositories. The
210+
* scan includes software libraries, source code, algorithms, and other proprietary
211+
* programming content.
212+
*/
213+
public void setProtectedMaterialCode(@Nullable final Boolean protectedMaterialCode) {
214+
this.protectedMaterialCode = protectedMaterialCode;
215+
}
216+
175217
/**
176218
* Get the names of the unrecognizable properties of the {@link AzureContentSafetyOutput}.
177219
*
@@ -215,6 +257,8 @@ public Map<String, Object> toMap() {
215257
if (selfHarm != null) declaredFields.put("selfHarm", selfHarm);
216258
if (sexual != null) declaredFields.put("sexual", sexual);
217259
if (violence != null) declaredFields.put("violence", violence);
260+
if (protectedMaterialCode != null)
261+
declaredFields.put("protectedMaterialCode", protectedMaterialCode);
218262
return declaredFields;
219263
}
220264

@@ -243,12 +287,15 @@ public boolean equals(@Nullable final java.lang.Object o) {
243287
&& Objects.equals(this.hate, azureContentSafetyOutput.hate)
244288
&& Objects.equals(this.selfHarm, azureContentSafetyOutput.selfHarm)
245289
&& Objects.equals(this.sexual, azureContentSafetyOutput.sexual)
246-
&& Objects.equals(this.violence, azureContentSafetyOutput.violence);
290+
&& Objects.equals(this.violence, azureContentSafetyOutput.violence)
291+
&& Objects.equals(
292+
this.protectedMaterialCode, azureContentSafetyOutput.protectedMaterialCode);
247293
}
248294

249295
@Override
250296
public int hashCode() {
251-
return Objects.hash(hate, selfHarm, sexual, violence, cloudSdkCustomFields);
297+
return Objects.hash(
298+
hate, selfHarm, sexual, violence, protectedMaterialCode, cloudSdkCustomFields);
252299
}
253300

254301
@Override
@@ -260,6 +307,9 @@ public String toString() {
260307
sb.append(" selfHarm: ").append(toIndentedString(selfHarm)).append("\n");
261308
sb.append(" sexual: ").append(toIndentedString(sexual)).append("\n");
262309
sb.append(" violence: ").append(toIndentedString(violence)).append("\n");
310+
sb.append(" protectedMaterialCode: ")
311+
.append(toIndentedString(protectedMaterialCode))
312+
.append("\n");
263313
cloudSdkCustomFields.forEach(
264314
(k, v) ->
265315
sb.append(" ").append(k).append(": ").append(toIndentedString(v)).append("\n"));

0 commit comments

Comments
 (0)