mirror of
https://github.com/openclaw/openclaw.git
synced 2026-03-13 11:00:50 +00:00
105 lines
4.4 KiB
Swift
105 lines
4.4 KiB
Swift
import Foundation
|
|
import OpenClawKit
|
|
|
|
struct TalkModeGatewayConfigState {
|
|
let activeProvider: String
|
|
let normalizedPayload: Bool
|
|
let missingResolvedPayload: Bool
|
|
let voiceId: String?
|
|
let voiceAliases: [String: String]
|
|
let modelId: String?
|
|
let outputFormat: String?
|
|
let interruptOnSpeech: Bool
|
|
let silenceTimeoutMs: Int
|
|
let apiKey: String?
|
|
let seamColorHex: String?
|
|
}
|
|
|
|
enum TalkModeGatewayConfigParser {
|
|
static func parse(
|
|
snapshot: ConfigSnapshot,
|
|
defaultProvider: String,
|
|
defaultModelIdFallback: String,
|
|
defaultSilenceTimeoutMs: Int,
|
|
envVoice: String?,
|
|
sagVoice: String?,
|
|
envApiKey: String?
|
|
) -> TalkModeGatewayConfigState {
|
|
let talk = snapshot.config?["talk"]?.dictionaryValue
|
|
let selection = TalkConfigParsing.selectProviderConfig(talk, defaultProvider: defaultProvider)
|
|
let activeProvider = selection?.provider ?? defaultProvider
|
|
let activeConfig = selection?.config
|
|
let silenceTimeoutMs = TalkConfigParsing.resolvedSilenceTimeoutMs(
|
|
talk,
|
|
fallback: defaultSilenceTimeoutMs)
|
|
let ui = snapshot.config?["ui"]?.dictionaryValue
|
|
let rawSeam = ui?["seamColor"]?.stringValue?.trimmingCharacters(in: .whitespacesAndNewlines) ?? ""
|
|
let voice = activeConfig?["voiceId"]?.stringValue
|
|
let rawAliases = activeConfig?["voiceAliases"]?.dictionaryValue
|
|
let resolvedAliases: [String: String] =
|
|
rawAliases?.reduce(into: [:]) { acc, entry in
|
|
let key = entry.key.trimmingCharacters(in: .whitespacesAndNewlines).lowercased()
|
|
let value = entry.value.stringValue?.trimmingCharacters(in: .whitespacesAndNewlines) ?? ""
|
|
guard !key.isEmpty, !value.isEmpty else { return }
|
|
acc[key] = value
|
|
} ?? [:]
|
|
let model = activeConfig?["modelId"]?.stringValue?.trimmingCharacters(in: .whitespacesAndNewlines)
|
|
let resolvedModel = (model?.isEmpty == false) ? model! : defaultModelIdFallback
|
|
let outputFormat = activeConfig?["outputFormat"]?.stringValue
|
|
let interrupt = talk?["interruptOnSpeech"]?.boolValue
|
|
let apiKey = activeConfig?["apiKey"]?.stringValue
|
|
let resolvedVoice: String? = if activeProvider == defaultProvider {
|
|
(voice?.trimmingCharacters(in: .whitespacesAndNewlines).isEmpty == false ? voice : nil) ??
|
|
(envVoice?.isEmpty == false ? envVoice : nil) ??
|
|
(sagVoice?.isEmpty == false ? sagVoice : nil)
|
|
} else {
|
|
(voice?.trimmingCharacters(in: .whitespacesAndNewlines).isEmpty == false ? voice : nil)
|
|
}
|
|
let resolvedApiKey: String? = if activeProvider == defaultProvider {
|
|
(envApiKey?.isEmpty == false ? envApiKey : nil) ??
|
|
(apiKey?.trimmingCharacters(in: .whitespacesAndNewlines).isEmpty == false ? apiKey : nil)
|
|
} else {
|
|
nil
|
|
}
|
|
|
|
return TalkModeGatewayConfigState(
|
|
activeProvider: activeProvider,
|
|
normalizedPayload: selection?.normalizedPayload == true,
|
|
missingResolvedPayload: talk != nil && selection == nil,
|
|
voiceId: resolvedVoice,
|
|
voiceAliases: resolvedAliases,
|
|
modelId: resolvedModel,
|
|
outputFormat: outputFormat,
|
|
interruptOnSpeech: interrupt ?? true,
|
|
silenceTimeoutMs: silenceTimeoutMs,
|
|
apiKey: resolvedApiKey,
|
|
seamColorHex: rawSeam.isEmpty ? nil : rawSeam)
|
|
}
|
|
|
|
static func fallback(
|
|
defaultModelIdFallback: String,
|
|
defaultSilenceTimeoutMs: Int,
|
|
envVoice: String?,
|
|
sagVoice: String?,
|
|
envApiKey: String?
|
|
) -> TalkModeGatewayConfigState {
|
|
let resolvedVoice =
|
|
(envVoice?.isEmpty == false ? envVoice : nil) ??
|
|
(sagVoice?.isEmpty == false ? sagVoice : nil)
|
|
let resolvedApiKey = envApiKey?.isEmpty == false ? envApiKey : nil
|
|
|
|
return TalkModeGatewayConfigState(
|
|
activeProvider: "elevenlabs",
|
|
normalizedPayload: false,
|
|
missingResolvedPayload: false,
|
|
voiceId: resolvedVoice,
|
|
voiceAliases: [:],
|
|
modelId: defaultModelIdFallback,
|
|
outputFormat: nil,
|
|
interruptOnSpeech: true,
|
|
silenceTimeoutMs: defaultSilenceTimeoutMs,
|
|
apiKey: resolvedApiKey,
|
|
seamColorHex: nil)
|
|
}
|
|
}
|