feat: tests for stages output + testability refactoring

- add PollInterval, StagesWriter, RetryBaseDelay to UniversalClient
- 5 unit tests for waitForOperationFinish (mock API, 0.25s total)
- Sonnet/DeepSeek/Opus comparison answers archived
This commit is contained in:
“Naeel”
2026-08-09 20:01:43 +04:00
parent 5ce7853817
commit 90c5418bb1
6 changed files with 412 additions and 4 deletions
+23 -4
View File
@@ -35,6 +35,12 @@ type UniversalClient struct {
// LogLevel задаёт уровень вывода этапов операции: ""/"none" | "info" | "debug".
// Может быть переопределён на уровне ресурса через context (ключ ctxKeyLogLevel).
LogLevel string
// PollInterval — интервал поллинга. 0 = default 5s. Для тестов.
PollInterval time.Duration
// StagesWriter — writer для вывода этапов. nil = ttyOut(). Для тестов.
StagesWriter io.Writer
// RetryBaseDelay — базовая задержка retry в doRequest. 0 = default 2s. Для тестов.
RetryBaseDelay time.Duration
}
// instanceMutexes — глобальная карта мьютексов для сериализации операций на одном инстансе.
@@ -930,14 +936,24 @@ type operationStatusResponse struct {
func (c *UniversalClient) waitForOperationFinish(ctx context.Context, opUid string, timeout time.Duration) error {
deadline := time.Now().Add(timeout)
ticker := time.NewTicker(5 * time.Second)
interval := c.PollInterval
if interval <= 0 {
interval = 5 * time.Second
}
ticker := time.NewTicker(interval)
defer ticker.Stop()
printedStages := make(map[string]bool)
var lastPendingUID string
tty := ttyOut()
defer tty.Close()
var tty io.Writer
if c.StagesWriter != nil {
tty = c.StagesWriter
} else {
f := ttyOut()
defer f.Close()
tty = f
}
for {
select {
@@ -1033,7 +1049,10 @@ func (c *UniversalClient) doRequest(ctx context.Context, method, path string, pa
// User-Agent: браузерный, чтобы пройти DDoS-Guard (см. docs/ops/API_TOKENS.md).
// Go-http-client по умолчанию блокируется фильтром ddos-guard.
const maxRetries = 3
baseDelay := 2 * time.Second
baseDelay := c.RetryBaseDelay
if baseDelay <= 0 {
baseDelay = 2 * time.Second
}
var lastErr error
for attempt := 0; attempt <= maxRetries; attempt++ {