Skip to content

Go Server SDK ​

Официальный серверный SDK на Go — github.com/Captcha-La/captchala-go.

Три задачи, которые SDK берёт на себя:

  1. Validate — проверка pt_ pass Token из браузерного SDK.
  2. Issue — выпуск одноразового sct_ server Token для привязки предстоящего запроса к конкретному action / IP / UID.
  3. Moderate — мультимодальная (текст + изображение) модерация контента через тот же OpenAI-совместимый pipeline, что использует панель управления.

Установка ​

bash
go get github.com/Captcha-La/captchala-go

Только стандартная библиотека. Никаких внешних зависимостей.

Validate (pt_ Token) ​

go
import captchala "github.com/Captcha-La/captchala-go"

client := captchala.NewClient(appKey, appSecret)

result, err := client.ValidateWithClientIP(token, false, clientIP(r))
if err != nil || !result.Valid {
    http.Error(w, result.Error, http.StatusBadRequest)
    return
}
// proceed with the request

// Real end-user IP behind a CDN / proxy
func clientIP(r *http.Request) string {
    if ip := r.Header.Get("CF-Connecting-IP"); ip != "" {
        return ip
    }
    if xff := r.Header.Get("X-Forwarded-For"); xff != "" {
        return strings.TrimSpace(strings.Split(xff, ",")[0])
    }
    host, _, _ := net.SplitHostPort(r.RemoteAddr)
    return host
}

Если исходный server_token был выпущен с bind_uid, сравните:

go
if result.UID != expectedUserID {
    http.Error(w, "user mismatch", http.StatusBadRequest)
    return
}

IP-аргумент ValidateWithClientIP необязателен, но рекомендуется — передайте IP конечного пользователя из вашего входящего запроса; он используется для дополнительных проверок риска. Можно безопасно опустить (тогда используйте Validate / ValidateWithOptions). Контекст на момент решения также возвращается в result.CaptchaArgs для справки:

go
ip := result.CaptchaArgs.UserIP   // visitor IP recorded at solve time

Токены только клиента (резерв при сбое) ​

Если API CaptchaLa недоступен, клиентский SDK всё равно может завершить проверку и вернуть токен только клиента (префикс client_ или co_). Он принимается, только если API недоступен и с вашего сервера; иначе он отклоняется с Error="client_only_rejected_api_reachable". Принятый токен помечается ClientOnly=true.

Результат проверки доступности кэшируется (30 с, если доступен, 5 с — если нет), поэтому сбой не замедляет каждый запрос. Параллельные проверки токенов используют одну проверку доступности.

Для чувствительных действий (вход, оплата) можно отклонять токены только клиента даже во время сбоя:

go
client.RejectClientOnly = true
// client_ / co_ -> Valid=false, Error=captchala.ErrClientOnlyPolicy ("client_only_rejected_by_policy")

Выпуск server Token ​

Рекомендуется для ответственных потоков (вход, регистрация, оплата): backend выпускает одноразовый sct_ Token, передаёт его в браузер, браузер использует его как prop serverToken. Одноразовый, привязан к action, опционально к IP/UID.

go
issue, err := client.IssueServerTokenWithOptions("login", captchala.IssueOptions{
    BindingIP: userIP,    // backend rejects token if a different IP redeems it
    TTL:       300,       // seconds
    MaxUses:   5,         // SDK retry budget
    BindUID:   userID,    // pair with ValidateResult.UID on verify
})
if err != nil || !issue.OK {
    http.Error(w, issue.Error, http.StatusBadRequest)
    return
}
// hand issue.Token to the browser

Сокращённый вариант с настройками по умолчанию:

go
issue, err := client.IssueServerToken("login")

Модерация контента ​

Мультимодальная — принимает срез ModerationItem (текст и/или image_url в формате, совместимом с OpenAI):

go
result, err := client.ModerationCheck([]captchala.ModerationItem{
    captchala.TextItem(userComment),
    captchala.ImageURLItem(uploadedImageURL),
}, userID)

if err != nil || !result.OK {
    http.Error(w, result.Error, http.StatusBadRequest)
    return
}

if result.Flagged {
    if result.HasCategory("violence", "csam") {
        // hard block
    }
}

Сокращённый вариант для plain-text:

go
result, err := client.ModerationText("user comment here", userID)

Категории определяются моделью; итерируйте result.Categories защитно, а не зашивайте фиксированный набор.

Типы ​

ТипПоля
ValidateResultValid, Error, UID, ChallengeID, Action, Offline, ClientOnly, Warning, CaptchaArgs
CaptchaArgsPlatform, UserIP, Referer, Pkg, SolvedAt, RiskScore (только для информации)
IssueResultOK, Token, ExpiresIn, IssuedAt, Error, Message
IssueOptionsBindingIP, TTL, MaxUses, BindUID
ModerationItemType, Text, ImageURL (используйте helper-ы TextItem() / ImageURLItem())
ModerationResultOK, Flagged, Categories, ContentType, Raw, Error, Message; метод HasCategory(...names)

Ссылки ​

MIT-licensed examples · CaptchaLa is operated independently