feat: expand speech provider support with new client types and config… (#389)

* feat: expand speech provider support with new client types and configuration schema

* feat: add icon support for speech providers and update related configurations

* feat: add SVG support for Deepgram and Elevenlabs with Vue components

* feat: except *-speech client type in llm provider

* feat: enhance speech provider functionality with advanced settings and model import capabilities

* chore: remove go.mod replace

* feat: enhance speech provider functionality with advanced settings and model import capabilities

* chore: update go module dependencies

---------

Co-authored-by: Acbox <acbox0328@gmail.com>
This commit is contained in:
Yiming Qi
2026-04-19 22:58:16 +09:00
committed by GitHub
parent 8e013ad1ad
commit 8d78925a23
46 changed files with 2808 additions and 565 deletions
+3
View File
@@ -0,0 +1,3 @@
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="none">
<path fill="currentColor" d="M11.203 24H1.517a.364.364 0 0 1-.258-.62l6.239-6.275a.37.37 0 0 1 .259-.108h3.52c2.723 0 5.025-2.127 5.107-4.845a5.004 5.004 0 0 0-4.999-5.148H7.613v4.646c0 .2-.164.364-.365.364H.968a.365.365 0 0 1-.363-.364V.364C.605.164.768 0 .969 0h10.416c6.684 0 12.111 5.485 12.01 12.187C23.293 18.77 17.794 24 11.202 24z"/>
</svg>

After

Width:  |  Height:  |  Size: 424 B

+4
View File
@@ -0,0 +1,4 @@
<svg xmlns="http://www.w3.org/2000/svg" viewBox="172 129 156 242" fill="none">
<path d="M314 355H271V145H314V355Z" fill="currentColor"/>
<path d="M229 355H186V145H229V355Z" fill="currentColor"/>
</svg>

After

Width:  |  Height:  |  Size: 206 B

+2
View File
@@ -18,6 +18,8 @@ const llmProviders: string[] = [
...withVariants('anthropic', []),
...withVariants('google', ['color', 'brand-color']),
...withVariants('deepseek', ['color']),
...withVariants('deepgram', []),
...withVariants('elevenlabs', []),
...withVariants('groq', []),
...withVariants('huggingface', ['color']),
...withVariants('lmstudio', []),
+17
View File
@@ -0,0 +1,17 @@
<template>
<svg
xmlns="http://www.w3.org/2000/svg"
:width="size"
:height="size"
viewBox="0 0 24 24"
v-bind="$attrs"
><path
fill="currentColor"
d="M11.203 24H1.517a.364.364 0 0 1-.258-.62l6.239-6.275a.37.37 0 0 1 .259-.108h3.52c2.723 0 5.025-2.127 5.107-4.845a5.004 5.004 0 0 0-4.999-5.148H7.613v4.646c0 .2-.164.364-.365.364H.968a.365.365 0 0 1-.363-.364V.364C.605.164.768 0 .969 0h10.416c6.684 0 12.111 5.485 12.01 12.187C23.293 18.77 17.794 24 11.202 24z"
/></svg>
</template>
<script setup lang="ts">
withDefaults(defineProps<{ size?: string | number }>(), { size: '1em' })
defineOptions({ inheritAttrs: false })
</script>
+21
View File
@@ -0,0 +1,21 @@
<template>
<svg
xmlns="http://www.w3.org/2000/svg"
:width="size"
:height="size"
viewBox="172 129 156 242"
v-bind="$attrs"
><path
d="M314 355H271V145H314V355Z"
fill="currentColor"
/>
<path
d="M229 355H186V145H229V355Z"
fill="currentColor"
/></svg>
</template>
<script setup lang="ts">
withDefaults(defineProps<{ size?: string | number }>(), { size: '1em' })
defineOptions({ inheritAttrs: false })
</script>
+2
View File
@@ -15,6 +15,7 @@ export { default as Claude } from './icons/Claude.vue'
export { default as ClaudeColor } from './icons/ClaudeColor.vue'
export { default as Cohere } from './icons/Cohere.vue'
export { default as CohereColor } from './icons/CohereColor.vue'
export { default as Deepgram } from './icons/Deepgram.vue'
export { default as Deepseek } from './icons/Deepseek.vue'
export { default as DeepseekColor } from './icons/DeepseekColor.vue'
export { default as Dingtalk } from './icons/Dingtalk.vue'
@@ -22,6 +23,7 @@ export { default as Discord } from './icons/Discord.vue'
export { default as Doubao } from './icons/Doubao.vue'
export { default as DoubaoColor } from './icons/DoubaoColor.vue'
export { default as Duckduckgo } from './icons/Duckduckgo.vue'
export { default as Elevenlabs } from './icons/Elevenlabs.vue'
export { default as Exa } from './icons/Exa.vue'
export { default as ExaColor } from './icons/ExaColor.vue'
export { default as Feishu } from './icons/Feishu.vue'
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
+138
View File
@@ -1642,8 +1642,34 @@ export type SettingsUpsertRequest = {
tts_model_id?: string;
};
export type TtsConfigSchema = {
fields?: Array<TtsFieldSchema>;
};
export type TtsFieldSchema = {
advanced?: boolean;
description?: string;
enum?: Array<string>;
example?: unknown;
key?: string;
order?: number;
required?: boolean;
title?: string;
type?: string;
};
export type TtsImportModelsResponse = {
created?: number;
models?: Array<string>;
skipped?: number;
};
export type TtsModelCapabilities = {
config_schema?: TtsConfigSchema;
formats?: Array<string>;
metadata?: {
[key: string]: string;
};
pitch?: TtsParamConstraint;
speed?: TtsParamConstraint;
voices?: Array<TtsVoiceInfo>;
@@ -1651,6 +1677,7 @@ export type TtsModelCapabilities = {
export type TtsModelInfo = {
capabilities?: TtsModelCapabilities;
config_schema?: TtsConfigSchema;
description?: string;
id?: string;
name?: string;
@@ -1664,6 +1691,7 @@ export type TtsParamConstraint = {
};
export type TtsProviderMetaResponse = {
config_schema?: TtsConfigSchema;
default_model?: string;
description?: string;
display_name?: string;
@@ -1686,8 +1714,12 @@ export type TtsSpeechModelResponse = {
export type TtsSpeechProviderResponse = {
client_type?: string;
config?: {
[key: string]: unknown;
};
created_at?: string;
enable?: boolean;
icon?: string;
id?: string;
name?: string;
updated_at?: string;
@@ -8331,6 +8363,112 @@ export type GetSpeechProvidersMetaResponses = {
export type GetSpeechProvidersMetaResponse = GetSpeechProvidersMetaResponses[keyof GetSpeechProvidersMetaResponses];
export type GetSpeechProvidersByIdData = {
body?: never;
path: {
/**
* Provider ID (UUID)
*/
id: string;
};
query?: never;
url: '/speech-providers/{id}';
};
export type GetSpeechProvidersByIdErrors = {
/**
* Bad Request
*/
400: HandlersErrorResponse;
/**
* Not Found
*/
404: HandlersErrorResponse;
};
export type GetSpeechProvidersByIdError = GetSpeechProvidersByIdErrors[keyof GetSpeechProvidersByIdErrors];
export type GetSpeechProvidersByIdResponses = {
/**
* OK
*/
200: TtsSpeechProviderResponse;
};
export type GetSpeechProvidersByIdResponse = GetSpeechProvidersByIdResponses[keyof GetSpeechProvidersByIdResponses];
export type PostSpeechProvidersByIdImportModelsData = {
body?: never;
path: {
/**
* Provider ID (UUID)
*/
id: string;
};
query?: never;
url: '/speech-providers/{id}/import-models';
};
export type PostSpeechProvidersByIdImportModelsErrors = {
/**
* Bad Request
*/
400: HandlersErrorResponse;
/**
* Not Found
*/
404: HandlersErrorResponse;
/**
* Internal Server Error
*/
500: HandlersErrorResponse;
};
export type PostSpeechProvidersByIdImportModelsError = PostSpeechProvidersByIdImportModelsErrors[keyof PostSpeechProvidersByIdImportModelsErrors];
export type PostSpeechProvidersByIdImportModelsResponses = {
/**
* OK
*/
200: TtsImportModelsResponse;
};
export type PostSpeechProvidersByIdImportModelsResponse = PostSpeechProvidersByIdImportModelsResponses[keyof PostSpeechProvidersByIdImportModelsResponses];
export type GetSpeechProvidersByIdModelsData = {
body?: never;
path: {
/**
* Provider ID (UUID)
*/
id: string;
};
query?: never;
url: '/speech-providers/{id}/models';
};
export type GetSpeechProvidersByIdModelsErrors = {
/**
* Bad Request
*/
400: HandlersErrorResponse;
/**
* Internal Server Error
*/
500: HandlersErrorResponse;
};
export type GetSpeechProvidersByIdModelsError = GetSpeechProvidersByIdModelsErrors[keyof GetSpeechProvidersByIdModelsErrors];
export type GetSpeechProvidersByIdModelsResponses = {
/**
* OK
*/
200: Array<TtsSpeechModelResponse>;
};
export type GetSpeechProvidersByIdModelsResponse = GetSpeechProvidersByIdModelsResponses[keyof GetSpeechProvidersByIdModelsResponses];
export type GetSupermarketMcpsData = {
body?: never;
path?: never;