fix/resetdata-provider-beta-compat #18
@@ -30,8 +30,10 @@ type ResetDataRequest struct {
|
||||
|
||||
// ResetDataMessage represents a message in the ResetData format
|
||||
type ResetDataMessage struct {
|
||||
Role string `json:"role"` // system, user, assistant
|
||||
Content string `json:"content"`
|
||||
Role string `json:"role"` // system, user, assistant
|
||||
Content string `json:"content"`
|
||||
Reasoning string `json:"reasoning,omitempty"` // reasoning chain (GLM-4.7, GPT-OSS, Nemotron 3 Nano)
|
||||
ReasoningContent string `json:"reasoning_content,omitempty"` // alternate reasoning field (GPT-OSS)
|
||||
}
|
||||
|
||||
// ResetDataResponse represents a response from ResetData LaaS API
|
||||
@@ -107,7 +109,7 @@ func (p *ResetDataProvider) ExecuteTask(ctx context.Context, request *TaskReques
|
||||
}
|
||||
|
||||
// Execute the request
|
||||
response, err := p.makeRequest(ctx, "/v1/chat/completions", resetDataReq)
|
||||
response, err := p.makeRequest(ctx, "/chat/completions", resetDataReq)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
@@ -122,6 +124,12 @@ func (p *ResetDataProvider) ExecuteTask(ctx context.Context, request *TaskReques
|
||||
choice := response.Choices[0]
|
||||
responseText := choice.Message.Content
|
||||
|
||||
// Extract reasoning chain - prefer Reasoning field, fall back to ReasoningContent
|
||||
reasoning := choice.Message.Reasoning
|
||||
if reasoning == "" {
|
||||
reasoning = choice.Message.ReasoningContent
|
||||
}
|
||||
|
||||
// Parse response for actions and artifacts
|
||||
actions, artifacts := p.parseResponseForActions(responseText, request)
|
||||
|
||||
@@ -132,6 +140,7 @@ func (p *ResetDataProvider) ExecuteTask(ctx context.Context, request *TaskReques
|
||||
ModelUsed: response.Model,
|
||||
Provider: "resetdata",
|
||||
Response: responseText,
|
||||
Reasoning: reasoning,
|
||||
Actions: actions,
|
||||
Artifacts: artifacts,
|
||||
StartTime: startTime,
|
||||
@@ -405,7 +414,7 @@ func (p *ResetDataProvider) makeRequest(ctx context.Context, endpoint string, re
|
||||
|
||||
// testConnection tests the connection to ResetData API
|
||||
func (p *ResetDataProvider) testConnection(ctx context.Context) error {
|
||||
url := strings.TrimSuffix(p.config.Endpoint, "/") + "/v1/models"
|
||||
url := strings.TrimSuffix(p.config.Endpoint, "/") + "/models"
|
||||
req, err := http.NewRequestWithContext(ctx, "GET", url, nil)
|
||||
if err != nil {
|
||||
return err
|
||||
@@ -429,52 +438,92 @@ func (p *ResetDataProvider) testConnection(ctx context.Context) error {
|
||||
|
||||
// getSupportedModels returns a list of supported ResetData models
|
||||
func (p *ResetDataProvider) getSupportedModels() []string {
|
||||
// Common models available through ResetData LaaS
|
||||
// Models available through ResetData beta (as of 2026-02)
|
||||
return []string{
|
||||
"llama3.1:8b", "llama3.1:70b",
|
||||
"mistral:7b", "mixtral:8x7b",
|
||||
"qwen2:7b", "qwen2:72b",
|
||||
"gemma:7b", "gemma2:9b",
|
||||
"codellama:7b", "codellama:13b",
|
||||
"zai-org/glm-4.7-fp8",
|
||||
"openai/gpt-oss-120b",
|
||||
"google/gemma-3-27b-it",
|
||||
"meta/llama-3.1-8b-instruct",
|
||||
"nvidia/nemotron-3-nano-30b-a3b",
|
||||
"nvidia/cosmos-reason2-8b",
|
||||
"nvidia/nemotron-nano-2-vl",
|
||||
}
|
||||
}
|
||||
|
||||
// handleHTTPError converts HTTP errors to provider errors
|
||||
func (p *ResetDataProvider) handleHTTPError(statusCode int, body []byte) *ProviderError {
|
||||
bodyStr := string(body)
|
||||
// Extract a human-readable error message from the response body.
|
||||
// ResetData returns two formats:
|
||||
// Format 1 (auth): {"success":false,"error":"Invalid or expired token"}
|
||||
// Format 2 (model/validation): {"error":{"message":"...","type":"...","code":"..."}}
|
||||
errMsg := p.extractErrorMessage(body)
|
||||
|
||||
switch statusCode {
|
||||
case http.StatusUnauthorized:
|
||||
return &ProviderError{
|
||||
Code: "UNAUTHORIZED",
|
||||
Message: "Invalid ResetData API key",
|
||||
Details: bodyStr,
|
||||
Message: fmt.Sprintf("ResetData auth failed: %s", errMsg),
|
||||
Details: string(body),
|
||||
Retryable: false,
|
||||
}
|
||||
case http.StatusTooManyRequests:
|
||||
return &ProviderError{
|
||||
Code: "RATE_LIMIT_EXCEEDED",
|
||||
Message: "ResetData API rate limit exceeded",
|
||||
Details: bodyStr,
|
||||
Message: fmt.Sprintf("ResetData rate limit: %s", errMsg),
|
||||
Details: string(body),
|
||||
Retryable: true,
|
||||
}
|
||||
case http.StatusInternalServerError, http.StatusBadGateway, http.StatusServiceUnavailable:
|
||||
return &ProviderError{
|
||||
Code: "SERVICE_UNAVAILABLE",
|
||||
Message: "ResetData API service unavailable",
|
||||
Details: bodyStr,
|
||||
Message: fmt.Sprintf("ResetData unavailable: %s", errMsg),
|
||||
Details: string(body),
|
||||
Retryable: true,
|
||||
}
|
||||
default:
|
||||
return &ProviderError{
|
||||
Code: "API_ERROR",
|
||||
Message: fmt.Sprintf("ResetData API error (status %d)", statusCode),
|
||||
Details: bodyStr,
|
||||
Message: fmt.Sprintf("ResetData error (status %d): %s", statusCode, errMsg),
|
||||
Details: string(body),
|
||||
Retryable: true,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// extractErrorMessage parses error details from ResetData API response bodies.
|
||||
func (p *ResetDataProvider) extractErrorMessage(body []byte) string {
|
||||
// Try Format 2: {"error":{"message":"...","type":"...","code":"..."}}
|
||||
var nestedErr struct {
|
||||
Error struct {
|
||||
Message string `json:"message"`
|
||||
Type string `json:"type"`
|
||||
Code string `json:"code"`
|
||||
} `json:"error"`
|
||||
}
|
||||
if err := json.Unmarshal(body, &nestedErr); err == nil && nestedErr.Error.Message != "" {
|
||||
if nestedErr.Error.Type != "" {
|
||||
return fmt.Sprintf("%s (%s)", nestedErr.Error.Message, nestedErr.Error.Type)
|
||||
}
|
||||
return nestedErr.Error.Message
|
||||
}
|
||||
|
||||
// Try Format 1: {"success":false,"error":"string message"}
|
||||
var flatErr struct {
|
||||
Success bool `json:"success"`
|
||||
Error string `json:"error"`
|
||||
}
|
||||
if err := json.Unmarshal(body, &flatErr); err == nil && flatErr.Error != "" {
|
||||
return flatErr.Error
|
||||
}
|
||||
|
||||
// Fallback: return raw body truncated
|
||||
s := string(body)
|
||||
if len(s) > 200 {
|
||||
s = s[:200] + "..."
|
||||
}
|
||||
return s
|
||||
}
|
||||
|
||||
// parseResponseForActions extracts actions from the response text
|
||||
func (p *ResetDataProvider) parseResponseForActions(response string, request *TaskRequest) ([]TaskAction, []Artifact) {
|
||||
var actions []TaskAction
|
||||
|
||||
Reference in New Issue
Block a user