From 47e96ee909cd559696c96ff5df91fbf36b07f8ee Mon Sep 17 00:00:00 2001 From: seymourtang Date: Wed, 4 Jun 2025 16:01:40 +0800 Subject: [PATCH] feat: Enhance JoinConvoAIReq and UpdateConvoAIReq with new LLM parameters and turn detection configuration - Added support for LLM parameters in UpdateConvoAIReq, allowing for system messages and additional parameters. - Introduced turn detection configuration in JoinConvoAIReq, enabling more control over agent interactions. - Updated InterruptConvoAIAPI to use an empty map for request body. - Enhanced JoinConvoAIReq with new fields for vendor, style, and additional TTS settings, improving customization options. --- .../convoai/api/InterruptConvoAIAPI.java | 7 +- .../services/convoai/req/JoinConvoAIReq.java | 799 +++++++++++++++++- .../convoai/req/UpdateConvoAIReq.java | 101 ++- .../examples/convoai/service/Service.java | 86 +- 4 files changed, 956 insertions(+), 37 deletions(-) diff --git a/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/api/InterruptConvoAIAPI.java b/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/api/InterruptConvoAIAPI.java index 4a94e66..1cd6326 100644 --- a/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/api/InterruptConvoAIAPI.java +++ b/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/api/InterruptConvoAIAPI.java @@ -1,5 +1,8 @@ package io.agora.rest.services.convoai.api; +import java.util.HashMap; +import java.util.Map; + import io.agora.rest.core.Context; import io.agora.rest.exception.AgoraNeedRetryException; import io.agora.rest.services.convoai.res.InterruptConvoAIRes; @@ -14,7 +17,9 @@ public InterruptConvoAIAPI(Context context, String pathPrefix, Integer maxAttemp public Mono handle(String agentId) { String path = String.format("%s/agents/%s/interrupt", pathPrefix, agentId); - return this.context.sendRequest(path, HttpMethod.POST, null, InterruptConvoAIRes.class) + // use empty map as body + Map body = new HashMap<>(); + return this.context.sendRequest(path, HttpMethod.POST, body, InterruptConvoAIRes.class) .retryWhen(customRetry(e -> e instanceof AgoraNeedRetryException)); } } diff --git a/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/req/JoinConvoAIReq.java b/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/req/JoinConvoAIReq.java index 220a2d6..ff5cde5 100644 --- a/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/req/JoinConvoAIReq.java +++ b/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/req/JoinConvoAIReq.java @@ -1,7 +1,10 @@ package io.agora.rest.services.convoai.req; +import com.fasterxml.jackson.annotation.JsonAnyGetter; +import com.fasterxml.jackson.annotation.JsonIgnore; import com.fasterxml.jackson.annotation.JsonProperty; import com.fasterxml.jackson.annotation.JsonValue; +import com.fasterxml.jackson.databind.ObjectMapper; import java.util.HashMap; import java.util.List; @@ -123,7 +126,10 @@ public static class Properties { *

* Only valid when advanced_features.enable_rtm is true. *

+ * + * @deprecated This field is deprecated since v0.6.0, use agent_rtc_uid instead. */ + @Deprecated @JsonProperty("agent_rtm_uid") private String agentRtmUId; @@ -162,8 +168,15 @@ public static class Properties { @JsonProperty("asr") private ASRPayload asrPayload; + /** + * Turn detection configuration (optional), see {@link TurnDetectionPayload} for + * details + */ + @JsonProperty("turn_detection") + private TurnDetectionPayload turnDetectionPayload; + @JsonProperty("parameters") - private Map parameters; + private Parameters parameters; public static Builder builder() { return new Builder(); @@ -182,6 +195,7 @@ private Properties(Builder builder) { setTts(builder.ttsPayload); setVad(builder.vadPayload); setAsr(builder.asrPayload); + setTurnDetectionPayload(builder.turnDetectionPayload); setParameters(builder.parameters); } @@ -281,14 +295,22 @@ public void setAsr(ASRPayload ASRPayload) { this.asrPayload = ASRPayload; } - public Map getParameters() { + public Parameters getParameters() { return parameters; } - public void setParameters(Map parameters) { + public void setParameters(Parameters parameters) { this.parameters = parameters; } + public TurnDetectionPayload getTurnDetectionPayload() { + return turnDetectionPayload; + } + + public void setTurnDetectionPayload(TurnDetectionPayload turnDetectionPayload) { + this.turnDetectionPayload = turnDetectionPayload; + } + public static final class Builder { private String token; private String channel; @@ -302,7 +324,8 @@ public static final class Builder { private TTSPayload ttsPayload; private VADPayload vadPayload; private ASRPayload asrPayload; - private Map parameters; + private Parameters parameters; + private TurnDetectionPayload turnDetectionPayload; private Builder() { } @@ -337,6 +360,7 @@ public Builder idleTimeout(Integer val) { return this; } + @Deprecated public Builder agentRtmUId(String val) { agentRtmUId = val; return this; @@ -367,7 +391,12 @@ public Builder asrPayload(ASRPayload val) { return this; } - public Builder parameters(Map val) { + public Builder turnDetectionPayload(TurnDetectionPayload val) { + turnDetectionPayload = val; + return this; + } + + public Builder parameters(Parameters val) { parameters = val; return this; } @@ -558,6 +587,53 @@ public static class LLMPayload { @JsonProperty("failure_message") private String failureMessage; + /** + * LLM provider(Optional), supports the following settings: + *

+ * - "custom": Custom LLM provider. + *

+ * When you set this option, the agent includes the following fields, in + * addition + * to role and content when making requests to the custom LLM. + *

+ * - turn_id: A unique identifier for each conversation turn. It starts from 0 + * and increments with each turn. One user-agent interaction corresponds to + * one turn_id. + *

+ * - timestamp: The request timestamp, in milliseconds. + *

+ * - "aliyun": Aliyun LLM provider.(Only available in China Mainland service + * region) + *

+ * - "bytedance": Bytedance LLM provider.(Only available in China Mainland + * service region) + *

+ * - "deepseek": DeepSeek LLM provider.(Only available in China Mainland service + * region) + *

+ * - "tencent": Tencent LLM provider.(Only available in China Mainland service + * region) + * + * @since v0.6.0 + */ + @JsonProperty("vendor") + private String vendor; + + /** + * The request style for chat completion.(Optional)(Only available in global + * service region) + *

+ * - "openai": OpenAI style.(Default) + *

+ * - "gemini": Gemini style. + *

+ * - "anthropic": Anthropic style. + * + * @since v0.6.0 + */ + @JsonProperty("style") + private String style; + public static Builder builder() { return new Builder(); } @@ -572,6 +648,8 @@ private LLMPayload(Builder builder) { setInputModalities(builder.inputModalities); setOutputModalities(builder.outputModalities); setFailureMessage(builder.failureMessage); + setVendor(builder.vendor); + setStyle(builder.style); } public String getUrl() { @@ -646,6 +724,22 @@ public void setFailureMessage(String failureMessage) { this.failureMessage = failureMessage; } + public String getVendor() { + return this.vendor; + } + + public void setVendor(String vendor) { + this.vendor = vendor; + } + + public String getStyle() { + return this.style; + } + + public void setStyle(String style) { + this.style = style; + } + public static final class Builder { private String url; private String apiKey; @@ -656,6 +750,8 @@ public static final class Builder { private List inputModalities; private List outputModalities; private String failureMessage; + private String vendor; + private String style; private Builder() { } @@ -705,6 +801,16 @@ public Builder failureMessage(String val) { return this; } + public Builder vendor(String val) { + vendor = val; + return this; + } + + public Builder style(String val) { + style = val; + return this; + } + public LLMPayload build() { return new LLMPayload(this); } @@ -876,6 +982,30 @@ public static class MinimaxTTSVendorParams implements TTSVendorParams { @JsonProperty("voice_setting") private MinimaxTTSVendorVoiceSettingParam voiceSetting; + /** + * Pronunciation dictionary + * + * @since v0.6.0 + */ + @JsonProperty("pronunciation_dict") + private PronunciationDictParam pronunciationDict; + + /** + * Timber weight + * + * @since v0.6.0 + */ + @JsonProperty("timber_weights") + private List timberWeights; + + /** + * Language boost + * + * @since v0.6.0 + */ + @JsonProperty("language_boost") + private String languageBoost; + public static Builder builder() { return new Builder(); } @@ -886,6 +1016,9 @@ private MinimaxTTSVendorParams(Builder builder) { setModel(builder.model); setAudioSetting(builder.audioSetting); setVoiceSetting(builder.voiceSetting); + setPronunciationDict(builder.pronunciationDict); + setTimberWeights(builder.timberWeights); + setLanguageBoost(builder.languageBoost); } public MinimaxTTSVendorVoiceSettingParam getVoiceSetting() { @@ -928,6 +1061,30 @@ public void setGroupId(String groupId) { this.groupId = groupId; } + public List getTimberWeights() { + return timberWeights; + } + + public void setTimberWeights(List timberWeights) { + this.timberWeights = timberWeights; + } + + public String getLanguageBoost() { + return languageBoost; + } + + public void setLanguageBoost(String languageBoost) { + this.languageBoost = languageBoost; + } + + public PronunciationDictParam getPronunciationDict() { + return pronunciationDict; + } + + public void setPronunciationDict(PronunciationDictParam pronunciationDict) { + this.pronunciationDict = pronunciationDict; + } + public static final class Builder { private String groupId; @@ -940,6 +1097,12 @@ public static final class Builder { private MinimaxTTSVendorVoiceSettingParam voiceSetting; + private List timberWeights; + + private PronunciationDictParam pronunciationDict; + + private String languageBoost; + private Builder() { } @@ -969,6 +1132,21 @@ public Builder voiceSetting(MinimaxTTSVendorVoiceSettingParam voiceSetting) { return this; } + public Builder timberWeights(List timberWeights) { + this.timberWeights = timberWeights; + return this; + } + + public Builder pronunciationDict(PronunciationDictParam pronunciationDict) { + this.pronunciationDict = pronunciationDict; + return this; + } + + public Builder languageBoost(String languageBoost) { + this.languageBoost = languageBoost; + return this; + } + public MinimaxTTSVendorParams build() { return new MinimaxTTSVendorParams(this); } @@ -1056,6 +1234,22 @@ public static class MinimaxTTSVendorVoiceSettingParam { @JsonProperty("emotion") private String emotion; + /** + * Whether to read the latex content + * + * @since v0.6.0 + */ + @JsonProperty("latex_read") + private Boolean latexRead; + + /** + * Whether to normalize the english content + * + * @since v0.6.0 + */ + @JsonProperty("english_normalization") + private Boolean englishNormalization; + public static Builder builder() { return new Builder(); } @@ -1066,6 +1260,8 @@ private MinimaxTTSVendorVoiceSettingParam(Builder builder) { setVol(builder.vol); setPitch(builder.pitch); setEmotion(builder.emotion); + setLatexRead(builder.latexRead); + setEnglishNormalization(builder.englishNormalization); } public String getEmotion() { @@ -1108,12 +1304,30 @@ public void setVoiceId(String voiceId) { this.voiceId = voiceId; } + public Boolean getLatexRead() { + return latexRead; + } + + public void setLatexRead(Boolean latexRead) { + this.latexRead = latexRead; + } + + public Boolean getEnglishNormalization() { + return englishNormalization; + } + + public void setEnglishNormalization(Boolean englishNormalization) { + this.englishNormalization = englishNormalization; + } + public static final class Builder { private String voiceId; private Float speed; private Float vol; private Integer pitch; private String emotion; + private Boolean latexRead; + private Boolean englishNormalization; private Builder() { } @@ -1143,12 +1357,124 @@ public Builder emotion(String val) { return this; } + public Builder latexRead(Boolean val) { + latexRead = val; + return this; + } + + public Builder englishNormalization(Boolean val) { + englishNormalization = val; + return this; + } + public MinimaxTTSVendorVoiceSettingParam build() { return new MinimaxTTSVendorVoiceSettingParam(this); } } } + /** + * @brief Define Minimax TTS vendor pronunciation dictionary parameter + * @since v0.6.0 + */ + public static class PronunciationDictParam { + + @JsonProperty("tones") + private List tones; + + public static Builder builder() { + return new Builder(); + } + + private PronunciationDictParam(Builder builder) { + setTones(builder.tones); + } + + public List getTones() { + return tones; + } + + public void setTones(List tones) { + this.tones = tones; + } + + public static final class Builder { + private List tones; + + private Builder() { + } + + public Builder tones(List tones) { + this.tones = tones; + return this; + } + + public PronunciationDictParam build() { + return new PronunciationDictParam(this); + } + } + } + + /** + * @brief Define Minimax TTS vendor timber weight parameter + * @since v0.6.0 + */ + public static class MinimaxTTSVendorTimberWeightParam { + + @JsonProperty("voice_id") + private String voiceId; + + @JsonProperty("weight") + private Float weight; + + public static Builder builder() { + return new Builder(); + } + + private MinimaxTTSVendorTimberWeightParam(Builder builder) { + setVoiceId(builder.voiceId); + setWeight(builder.weight); + } + + public String getVoiceId() { + return voiceId; + } + + public void setVoiceId(String voiceId) { + this.voiceId = voiceId; + } + + public Float getWeight() { + return weight; + } + + public void setWeight(Float weight) { + this.weight = weight; + } + + public static final class Builder { + private String voiceId; + private Float weight; + + private Builder() { + } + + public Builder voiceId(String val) { + voiceId = val; + return this; + } + + public Builder weight(Float val) { + weight = val; + return this; + } + + public MinimaxTTSVendorTimberWeightParam build() { + return new MinimaxTTSVendorTimberWeightParam(this); + } + } + } + /** * @brief Define Tencent TTS module parameters, see * + * - "interrupt"(Default): Interrupt mode, human voice immediately interrupts + * the agent's interaction. + *

+ * The agent will terminate the current interaction and directly process the + * human voice input. + *

+ * - "append": Append mode, human voice does not interrupt the agent. (Default) + *

+ * The agent will process the human voice request after the current interaction + * ends. + *

+ * - "ignore": Ignore mode, the agent ignores the human voice request. + *

+ * If the agent is speaking or thinking and receives human voice during the + * process, + * the agent will directly ignore and discard the human voice request, not + * storing it in the context. + * + * @since v0.6.0 + */ + @JsonProperty("interrupt_mode") + private String interruptMode; + + public static TurnDetectionPayload.Builder builder() { + return new TurnDetectionPayload.Builder(); + } + + private TurnDetectionPayload(Builder builder) { + setInterruptMode(builder.interruptMode); + } + + public static final class Builder { + private String interruptMode; + + private Builder() { + } + + public Builder interruptMode(String val) { + interruptMode = val; + return this; + } + + public TurnDetectionPayload build() { + return new TurnDetectionPayload(this); + } + } + + } + + /** + * @brief Defines the parameters for the agent,the same key in the fixedParams + * and extraParams will be merged + * @since v0.6.0 + */ + public static class Parameters { + + /** + * Fixed parameters for the agent + */ + @JsonIgnore + private FixedParams fixedParams; + + /** + * Extra parameters for the agent + */ + @JsonIgnore + private Map extraParams = new HashMap<>(); + + public FixedParams getFixedParams() { + return fixedParams; + } + + public Map getExtraParams() { + return extraParams; + } + + @JsonAnyGetter + public Map getParameters() throws IllegalArgumentException { + Map merged = new HashMap<>(); + + if (fixedParams != null) { + try { + ObjectMapper objectMapper = new ObjectMapper(); + Map fixedParamsMap = objectMapper.convertValue(fixedParams, Map.class); + merged.putAll(fixedParamsMap); + } catch (Exception e) { + throw new IllegalArgumentException("Failed to convert fixed params to map", e); + } + } + + if (extraParams != null) { + merged.putAll(extraParams); + } + return merged; + } + + private void setFixedParams(FixedParams fixedParams) { + this.fixedParams = fixedParams; + } + + private void setExtraParams(Map extraParams) { + this.extraParams = extraParams; + } + + public static Builder builder() { + return new Builder(); + } + + private Parameters(Builder builder) { + setFixedParams(builder.fixedParams); + setExtraParams(builder.extraParams); + } + + public static final class Builder { + private FixedParams fixedParams; + private Map extraParams; + + private Builder() { + } + + public Builder fixedParams(FixedParams val) { + fixedParams = val; + return this; + } + + public Builder extraParams(Map val) { + extraParams = val; + return this; + } + + public Parameters build() { + return new Parameters(this); + } + } + } + + /** + * @brief Defines the fixed parameters for the agent + * @since v0.6.0 + */ + public static class FixedParams { + + @JsonProperty("silence_config") + private SilenceConfig silenceConfig; + + public SilenceConfig getSilenceConfig() { + return silenceConfig; + } + + public void setSilenceConfig(SilenceConfig silenceConfig) { + this.silenceConfig = silenceConfig; + } + + public static Builder builder() { + return new Builder(); + } + + private FixedParams(Builder builder) { + setSilenceConfig(builder.silenceConfig); + } + + public static final class Builder { + private SilenceConfig silenceConfig; + + private Builder() { + } + + public Builder silenceConfig(SilenceConfig val) { + silenceConfig = val; + return this; + } + + public FixedParams build() { + return new FixedParams(this); + } + } + } + + /** + * @brief Defines the silence config for the agent + * @since v0.6.0 + */ + public static class SilenceConfig { + + /** + * Agent maximum silence time (ms).(Optional) + *

+ * After the agent is created and a user joins the channel, + * the duration of the agent's non-listening, thinking, or speaking state is + * called the agent's silence time. + *

+ * When the silence time reaches the set value, the agent will report the + * silence prompt message. + *

+ * This feature can be used to let the agent remind users when users are + * inactive. + *

+ * Set 0: Do not enable this feature. + *

+ * Set to (0,60000]: Must also set content to enable normal reporting of + * silence prompts, otherwise the setting is invalid. + */ + @JsonProperty("timeout_ms") + private Integer timeoutMs; + + /** + * When the silence time reaches the set value, the agent will take the + * following actions(Optional): + *

+ * - "speak": Use TTS module to report the silence message(Default) + *

+ * - "think": Append the silence message to the end of the context and + * pass it to LLM + */ + @JsonProperty("action") + private String action; + + /** + * Content of the silence message (Optional) + *

+ * The content will be used in different ways according to the settings in + * the action. + */ + @JsonProperty("content") + private String content; + + public Integer getTimeoutMs() { + return timeoutMs; + } + + public String getAction() { + return action; + } + + public String getContent() { + return content; + } + + public void setTimeoutMs(Integer timeoutMs) { + this.timeoutMs = timeoutMs; + } + + public void setAction(String action) { + this.action = action; + } + + public void setContent(String content) { + this.content = content; + } + + public static Builder builder() { + return new Builder(); + } + + private SilenceConfig(Builder builder) { + setAction(builder.action); + setContent(builder.content); + setTimeoutMs(builder.timeoutMs); + } + + public static final class Builder { + private Integer timeoutMs; + private String action; + private String content; + + private Builder() { + } + + public Builder timeoutMs(Integer val) { + timeoutMs = val; + return this; + } + + public Builder action(String val) { + action = val; + return this; + } + + public Builder content(String val) { + content = val; + return this; + } + + public SilenceConfig build() { + return new SilenceConfig(this); + } + } + } } diff --git a/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/req/UpdateConvoAIReq.java b/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/req/UpdateConvoAIReq.java index fe1ac12..3500772 100644 --- a/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/req/UpdateConvoAIReq.java +++ b/agora-rest-client-core/src/main/java/io/agora/rest/services/convoai/req/UpdateConvoAIReq.java @@ -1,5 +1,8 @@ package io.agora.rest.services.convoai.req; +import java.util.List; +import java.util.Map; + import com.fasterxml.jackson.annotation.JsonProperty; /** @@ -9,17 +12,25 @@ public class UpdateConvoAIReq { /** - * Dynamic key (Token) used for authentication. If your project has enabled the App Certificate, you must pass the dynamic key in this field. + * Dynamic key (Token) used for authentication. If your project has enabled the + * App Certificate, you must pass the dynamic key in this field. */ @JsonProperty("token") private String token; + /** + * LLM parameters + */ + @JsonProperty("llm") + private UpdateLLMParams llm; + public static Builder builder() { return new Builder(); } private UpdateConvoAIReq(Builder builder) { setToken(builder.token); + setLlm(builder.llm); } public String getToken() { @@ -30,9 +41,19 @@ public void setToken(String token) { this.token = token; } + public UpdateLLMParams getLlm() { + return llm; + } + + public void setLlm(UpdateLLMParams llm) { + this.llm = llm; + } + public static final class Builder { private String token; + private UpdateLLMParams llm; + private Builder() { } @@ -41,8 +62,86 @@ public Builder token(String val) { return this; } + public Builder llm(UpdateLLMParams val) { + llm = val; + return this; + } + public UpdateConvoAIReq build() { return new UpdateConvoAIReq(this); } } + + /** + * @brief Define LLM parameters + * @since v0.6.0 + */ + public static class UpdateLLMParams { + /** + * A set of predefined information attached at the beginning of each LLM call, + * used to control LLM output (optional) + *

+ * Can be role settings, prompts, and answer examples, must be compatible with + * OpenAI protocol + */ + @JsonProperty("system_messages") + private List> systemMessages; + + /** + * Additional information transmitted in the LLM message body, such as the model + * used, maximum token limit, etc. (optional) + *

+ * Different LLM providers support different configurations, see their + * respective LLM documentation for details. + */ + @JsonProperty("params") + private Map params; + + public static Builder builder() { + return new Builder(); + } + + private UpdateLLMParams(Builder builder) { + setSystemMessages(builder.systemMessages); + setParams(builder.params); + } + + public List> getSystemMessages() { + return systemMessages; + } + + public void setSystemMessages(List> systemMessages) { + this.systemMessages = systemMessages; + } + + public Map getParams() { + return params; + } + + public void setParams(Map params) { + this.params = params; + } + + public static final class Builder { + private List> systemMessages; + private Map params; + + private Builder() { + } + + public Builder systemMessages(List> val) { + systemMessages = val; + return this; + } + + public Builder params(Map val) { + params = val; + return this; + } + + public UpdateLLMParams build() { + return new UpdateLLMParams(this); + } + } + } } diff --git a/examples/convoai/src/main/java/io/agora/rest/examples/convoai/service/Service.java b/examples/convoai/src/main/java/io/agora/rest/examples/convoai/service/Service.java index 8bc6def..9aa51b4 100644 --- a/examples/convoai/src/main/java/io/agora/rest/examples/convoai/service/Service.java +++ b/examples/convoai/src/main/java/io/agora/rest/examples/convoai/service/Service.java @@ -118,6 +118,15 @@ public void runCustomTTS(JoinConvoAIReq.TTSVendorEnum ttsVendor, JoinConvoAIReq. .asrPayload(JoinConvoAIReq.ASRPayload.builder() .language("zh-CN") .build()) + .parameters(JoinConvoAIReq.Parameters.builder() + .fixedParams(JoinConvoAIReq.FixedParams.builder() + .silenceConfig(JoinConvoAIReq.SilenceConfig.builder() + .timeoutMs(1000) + .action("speak") + .content("Hello,how can I help you?") + .build()) + .build()) + .build()) .build()) .build()).block(); } catch (AgoraException e) { @@ -254,7 +263,27 @@ public void runCustomTTS(JoinConvoAIReq.TTSVendorEnum ttsVendor, JoinConvoAIReq. try { updateConvoAIRes = this.convoAIClient.update(agentId, UpdateConvoAIReq.builder() - .token(updateToken).build()).block(); + .llm(UpdateConvoAIReq.UpdateLLMParams.builder() + .params(new HashMap() { + { + put("model", llmModel); + put("max_tokens", 2048); + put("username", "Tom"); + } + }) + .systemMessages(new ArrayList>() { + { + add(new HashMap() { + { + put("content", "You are a helpful chatbot, and you are a new assistant."); + put("role", "system"); + } + }); + } + }) + .build()) + .token(updateToken) + .build()).block(); } catch (AgoraException e) { logger.error("Failed to update the agent,err:{}", e.getMessage()); return; @@ -298,8 +327,15 @@ public void runBytedanceTTS() { } JoinConvoAIReq.BytedanceTTSVendorParams ttsVendorParams = JoinConvoAIReq.BytedanceTTSVendorParams.builder() - .token(ttsToken).cluster(ttsCluster).voiceType(ttsVoiceType).appId(ttsAppId).speedRatio(1.0F) - .volumeRatio(1.0F).pitchRatio(1.0F).emotion("happy").build(); + .token(ttsToken) + .cluster(ttsCluster) + .voiceType(ttsVoiceType) + .appId(ttsAppId) + .speedRatio(1.0F) + .volumeRatio(1.0F) + .pitchRatio(1.0F) + .emotion("happy") + .build(); runCustomTTS(JoinConvoAIReq.TTSVendorEnum.BYTEDANCE, ttsVendorParams); } @@ -322,8 +358,15 @@ public void runTencentTTS() { } JoinConvoAIReq.TencentTTSVendorParams ttsVendorParams = JoinConvoAIReq.TencentTTSVendorParams.builder() - .appId(ttsAppId).secretId(ttsSecretId).secretKey(ttsSecretKey).voiceType(601005).volume(0).speed(0) - .emotionCategory("happy").emotionIntensity(100).build(); + .appId(ttsAppId) + .secretId(ttsSecretId) + .secretKey(ttsSecretKey) + .voiceType(601005) + .volume(0) + .speed(0) + .emotionCategory("happy") + .emotionIntensity(100) + .build(); runCustomTTS(JoinConvoAIReq.TTSVendorEnum.TENCENT, ttsVendorParams); @@ -347,9 +390,22 @@ public void runMinimaxTTS() { } JoinConvoAIReq.MinimaxTTSVendorParams ttsVendorParams = JoinConvoAIReq.MinimaxTTSVendorParams.builder() - .groupId(ttsGroupId).key(ttsGroupKey).model(ttsGroupModel) - .voiceSetting(JoinConvoAIReq.MinimaxTTSVendorVoiceSettingParam.builder().voiceId("female-shaonv") - .speed(1F).vol(1F).pitch(0).emotion("happy").build()) + .groupId(ttsGroupId) + .key(ttsGroupKey) + .model(ttsGroupModel) + .voiceSetting(JoinConvoAIReq.MinimaxTTSVendorVoiceSettingParam.builder() + .voiceId("female-shaonv") + .speed(1F) + .vol(1F) + .pitch(0) + .emotion("happy") + .latexRead(true) + .englishNormalization(true) + .build()) + .audioSetting(JoinConvoAIReq.MinimaxTTSVendorAudioSettingParam.builder() + .sampleRate(24000) + .build()) + .languageBoost("auto") .build(); runCustomTTS(JoinConvoAIReq.TTSVendorEnum.MINIMAX, ttsVendorParams); @@ -374,7 +430,13 @@ public void runMicrosoftTTS() { } JoinConvoAIReq.MicrosoftTTSVendorParams ttsVendorParams = JoinConvoAIReq.MicrosoftTTSVendorParams.builder() - .key(ttsKey).region(ttsRegion).voiceName(ttsVoiceName).rate(1.8F).volume(70F).build(); + .key(ttsKey) + .region(ttsRegion) + .voiceName(ttsVoiceName) + .speed(1.8F) + .sampleRate(24000) + .volume(70F) + .build(); runCustomTTS(JoinConvoAIReq.TTSVendorEnum.MICROSOFT, ttsVendorParams); } @@ -397,7 +459,11 @@ public void runElevenlabsTTS() { } JoinConvoAIReq.ElevenLabsTTSVendorParams ttsVendorParams = JoinConvoAIReq.ElevenLabsTTSVendorParams.builder() - .apiKey(ttsApiKey).modelId(ttsModelId).voiceId(ttsVoiceId).build(); + .key(ttsApiKey) + .modelId(ttsModelId) + .voiceId(ttsVoiceId) + .sampleRate(24000) + .build(); runCustomTTS(JoinConvoAIReq.TTSVendorEnum.ELEVENLABS, ttsVendorParams); }