Consulta pré-resolvida
RÁPIDOSoluções de preflop e de mais de 5,8 milhões de flops. Retorna uma estratégia em milissegundos sem consultar o status da tarefa.
Começar com preflopUse MelaSolver GPU por meio de uma única API de autoatendimento. Comece com uma consulta pré-resolvida em milissegundos ou envie uma situação personalizada de flop, turn ou river ao pool de solvers em tempo real.
Baixe a coleção pública, importe-a para o Postman e defina a variável apiKey da coleção com sua chave de API antes de enviar uma solicitação. Ela usa Authorization: Bearer {{apiKey}} e a URL base pública https://pokerai.bet; os exemplos incluídos abrangem estratégia GTO de preflop e textura de board do PokerKit.
Coleção do Postman A fonte disponível para download não contém chave real, Cookie ou endpoint privado. Para o contrato público completo, consulte a Referência da API e o instantâneo OpenAPI.
Ambos usam a mesma chave de API e cota mensal.
Soluções de preflop e de mais de 5,8 milhões de flops. Retorna uma estratégia em milissegundos sem consultar o status da tarefa.
Começar com preflopÁrvores personalizadas de flop, turn e river. Envie uma vez, consulte pelo ID da tarefa e depois recupere a estratégia resolvida.
Enviar uma tarefa de resoluçãoInstale, autentique-se, faça a chamada. Nada mais para provisionar.
curl -s https://pokerai.bet/v1/gto/preflop \
-H "Authorization: Bearer $POKERAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{"hole_cards":"AhKh","positions":{"hero":"UTG"},"preflop_actions":[{"position":"SB","action":"small blind","amount":0.5},{"position":"BB","action":"big blind","amount":1}]}'
{
"hole_cards": "AhKh",
"situation": "RFI",
"strategy": [
{ "action": "raise", "frequency": 1, "amount_bb": 3, "sizing_pot": 0.8 }
],
"quota": { "used": 6, "limit": 100 }
}
Passe da primeira chamada para a produção sem procurar em uma única página longa.
Toda solicitação deve incluir uma chave da API. Obtenha uma chave em 60 segundos:
export POKERAI_API_KEY=gto_xxxxxxxx e você poderá executar o Início rápido abaixo.A partir daí, envie a mesma chave (a gto_xxx que você acabou de copiar — este é o “token Bearer”) em um cabeçalho em todas as solicitações. Escolha uma das formas abaixo — é uma chave, não duas:
Authorization: Bearer gto_xxxxxxxx # padrão (recomendado; corresponde ao esquema OpenAPI BearerApiKey)
# ou (totalmente equivalente; escolha um)
X-API-Key: gto_xxxxxxxx # equivalente (esquema OpenAPI XApiKey); útil para alguns gateways / SDKs / testes rápidos
Dois tipos de cota mensal, medidos separadamente e redefinidos no dia 1º de cada mês; o uso atual está no console:
/v1/gto/range e chamadas de range projetado consomem 1 cada./v1/gto/solver consome 1 cada vez que aciona uma nova resolução; reutilizar uma resolução em cache e obter a árvore/nó é grátis (a resposta tem o campo solve_quota quando há cobrança e não o tem quando não há).Todos os erros retornam um JSON uniforme: { "error": "<code>", "message": "<description>" }. Há algumas variações: alguns 502 usam reason em vez de message; o 429 quando todos os solvers estão ocupados é { "status": "busy", "message": ... }. Os valores de error específicos do endpoint estão na tabela “Possíveis erros” de cada endpoint; os códigos de status comuns estão abaixo:
| HTTP | error / significado | tentar novamente? |
|---|---|---|
| 400 | Entrada inválida ou campo ausente (consulte a tabela de cada endpoint para o error específico). | Não, corrija a entrada |
| 401 | missing_api_key / invalid_api_key: chave ausente ou inválida. | Não, verifique a chave |
| 403 | invalid_node_token / invalid_solve: token/handle inválido ou não é seu. | Não, obtenha novamente a árvore / reagende primeiro |
| 404 | no_solution: ainda não há dados GTO para esta situação. | Não, altere a situação |
| 429 | quota_exceeded (geral) / solve_quota_exceeded (resolução): cota mensal esgotada. | Não, é redefinida no dia 1º ou aumente sua cota |
| 429 | status: busy: todos os solvers estão ocupados (apenas /v1/gto/solver), sem cobrança. | Sim, aguarde e tente novamente |
| 502 | no_result (reason: timeout / no_worker_available) / auth_unavailable / solver_unreachable: backend temporariamente indisponível. | Sim, aguarde e tente novamente 2–3 vezes |
400 (entrada inválida):
{
"error": "invalid_board",
"message": "board must be 3 cards, e.g. \"2c2h2s\""
}
401 (Key ausente) / 404 (sem dados) / 429 (cota esgotada) — campo único ou mensagem curta:
{ "error": "missing_api_key" }
{ "error": "no_solution", "message": "no GTO data for this spot/board" }
{ "error": "quota_exceeded" }
502 (backend temporariamente indisponível, passível de nova tentativa):
{
"error": "no_result",
"reason": "timeout"
}
Tentar novamente: apenas 429 busy e 502 valem uma nova tentativa — use backoff exponencial (comece em ~1s, dobre, no máximo 2–3 vezes). Os demais (400/401/403/404/cota esgotada) são finais, e tentar novamente é inútil: corrija a entrada / altere a Key / busque a árvore de novo, ou espere a cota ser redefinida no dia 1º do mês. Não há limite de taxa por segundo, portanto não há cabeçalho Retry-After.
Quando tiver uma Key (veja acima), salve-a como POKERAI_API_KEY e copie este curl — a chamada bem-sucedida mais simples: Hero tem uma oportunidade de abertura em UTG (RFI), e a solução pré-resolvida de pré-flop retorna em milissegundos. Você também pode copiar o mesmo trecho inicial no dashboard.
curl -s https://pokerai.bet/v1/gto/preflop \
-H "Authorization: Bearer $POKERAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{"hole_cards":"AhKh","positions":{"hero":"UTG"},"preflop_actions":[{"position":"SB","action":"small blind","amount":0.5},{"position":"BB","action":"big blind","amount":1}]}'
Resposta real (UTG com AKs, oportunidade de abertura → abre 100% para 3BB):
{
"hole_cards": "AhKh",
"situation": "RFI",
"strategy": [
{ "action": "raise", "frequency": 1, "amount_bb": 3, "sizing_pot": 0.8 }
],
"quota": { "used": 6, "limit": 100 }
}
Enfrentando um raise? Basta adicionar a ação do oponente a preflop_actions (anexe {"position":"UTG","action":"raise","amount":3} e mude Hero para MP → isso se torna uma situação de 3bet, e situation retorna Raise). A frequência mista de cada ação é retornada (nenhuma ação recomendada; escolha você mesmo com base em frequency). As seções abaixo estão organizadas em três partes: Soluções pré-resolvidas (pré-flop / flop), cálculo do solver em tempo real e conversão de range.
Não quer escrever HTTP à mão? Os clientes oficiais são gerados automaticamente a partir da especificação OpenAPI e totalmente tipados, por isso sempre acompanham a API. A autenticação é apenas sua chave de API.
pip install pokerai-bet # nome da distribuição pokerai-bet, importe como pokerai
A mesma situação do Início rápido (abertura de Hero UTG), tipada:
from pokerai import AuthenticatedClient
from pokerai.api.lookup import preflop_strategy
from pokerai.models import (
PreflopRequest, PreflopRequestPositions, PreflopRequestPreflopActionsItem,
)
from pokerai.models.preflop_request_preflop_actions_item_action import (
PreflopRequestPreflopActionsItemAction as Act,
)
from pokerai.models.position import Position
client = AuthenticatedClient(base_url="https://pokerai.bet", token="gto_...")
resp = preflop_strategy.sync(client=client, body=PreflopRequest(
hole_cards="AhKh",
positions=PreflopRequestPositions(hero=Position.UTG),
preflop_actions=[
PreflopRequestPreflopActionsItem(position=Position.SB, action=Act.SMALL_BLIND, amount=0.5),
PreflopRequestPreflopActionsItem(position=Position.BB, action=Act.BIG_BLIND, amount=1.0),
],
))
print(resp.to_dict())
Saída real (mesma situação do Início rápido):
{"hole_cards": "AhKh", "situation": "RFI",
"strategy": [{"action": "raise", "frequency": 1, "sizing_pot": 0.8, "amount_bb": 3}],
"quota": {"used": 2702, "limit": 100000}}
npm install @pokerai/client
import { createPokeraiClient } from "@pokerai/client";
const client = createPokeraiClient({ apiKey: "gto_..." });
const { data, error } = await client.POST("/v1/gto/preflop", {
body: {
hole_cards: "AhKh",
positions: { hero: "UTG" },
preflop_actions: [
{ position: "SB", action: "small blind", amount: 0.5 },
{ position: "BB", action: "big blind", amount: 1 },
],
},
});
if (error) throw new Error(JSON.stringify(error));
console.log(data.situation, data.strategy);
// "RFI" [{ action: "raise", frequency: 1, amount_bb: 3, sizing_pot: 0.8 }]
Caminhos, corpos de requisição e campos de resposta são todos verificados por tipo — seu editor completa automaticamente toda a API. Os tipos são gerados a partir da especificação por openapi-typescript; o runtime é openapi-fetch.
Permita que Claude / Cursor e similares chamem a API Pokerai como ferramentas (@pokerai/mcp):
// mcp.json
{ "mcpServers": { "pokerai": {
"command": "npx", "args": ["-y", "@pokerai/mcp"],
"env": { "POKERAI_API_KEY": "gto_..." }
}}}
5 ferramentas de consulta pré-resolvida por padrão; adicione "POKERAI_ENABLE_SOLVE": "1" para habilitar as ferramentas do solver em tempo real (consome a cota de resolução).
O modelo mental geral — leia isto uma vez e as seções por endpoint abaixo serão mais fáceis de acompanhar.
Cada estratégia retorna a frequência mista de cada ação (0–1) e não escolhe a ação por você — você a implementa por conta própria a partir de frequency (use a maior probabilidade ou faça uma amostragem aleatória por frequência).
Cada bet/raise traz dois campos de tamanho: amount_bb (o valor absoluto, isto é, o BB para o qual você faz raise até) e sizing_pot (o valor relativo ao pote, a convenção padrão de % do pote):
Exemplo: 3bet para 9 enfrentando uma abertura de 3 — o pote é 4,5; após o call, 4,5+3=7,5; o raise excede em 9−3=6, então sizing_pot = 6/7,5 = 0,8. Quando é all-in, também inclui allin: true.
Tanto a árvore de decisão do flop quanto o solver em tempo real têm duas etapas: primeiro busque a árvore inteira (cada nó de decisão contém um token), depois use o token do nó de Hero para buscar a estratégia dessa etapa.
buscar árvore /flop/tree ou /solver (+ consultar repetidamente /solver/tree)
└─→ nodes[]: cada nó contém is_hero + token
└─→ escolha o nó com is_hero:true
buscar nó /flop/node ou /solver/node (o corpo contém o token desse nó)
└─→ a estratégia mista desta etapa
/flop/tree (cobra 1) → /flop/node (gratuito). O nó root = primeira decisão de Hero./solver retorna um identificador solve (cobra 1) → consultas repetidas a /solver/tree + /solver/node (ambos gratuitos). O range é informado apenas uma vez no agendamento, não é passado novamente.Notação do caminho do nó (duas convenções, dependendo da origem da árvore): a árvore de decisão do flop usa BET_8 (sublinhado, BB inteiro); a árvore do solver usa BET 8.000000 (espaço, 6 casas decimais). Ao passar node_id / navegar, ele deve corresponder aos rótulos daquela árvore (ou em solver_results) caractere por caractere.
Após agendar, consulte o spot_status de /solver/tree: available (não agendada) → computing (resolvendo, continue consultando) → queryable (é possível buscar nós) → expired (cache recuperado pelo TTL, é necessário reagendar). Quando terminar as consultas, você pode opcionalmente chamar /solver/release para devolver a porta ao pool imediatamente (caso contrário, ela é recuperada pelo TTL); após a liberação, outras consultas neste identificador de solve retornam expired.
preflop e flop usam soluções GTO pré-resolvidas, disponibilizadas instantaneamente, adequadas a casos de uso que precisam de uma resposta rápida. O stack efetivo é fixado em 100BB (pré-resolvido, não é uma entrada). Para calcular o flop ao vivo com o solucionador real, veja a próxima seção.
POST https://pokerai.bet/v1/gto/preflop cobra 1 geral
Esquema completo de parâmetros/resposta e teste ao vivo → referência interativa.
Você não precisa determinar "quantas apostas há no pote" — informe em ordem as ações preflop de todos os jogadores antes da ação do Hero, e o servidor deriva a situação automaticamente (sem abertura / enfrentando um raise / 3bet / 4bet…).
| campo | tipo | descrição |
|---|---|---|
hole_cards | string | As 2 cartas fechadas do Hero, por exemplo "AdKd". |
positions.hero | string | Posição do Hero, uma de SB BB UTG MP CO BTN (colocada em positions). |
preflop_actions | array | A sequência de ações completa e explícita do small blind até o jogador imediatamente antes do Hero (o Hero não está na sequência; a posição do Hero é informada por positions.hero, e a sequência termina no jogador anterior ao Hero). Cada item é { position, action, amount, allin? }; veja a tabela abaixo. |
preflop_version | string | Opcional. Qual conjunto de tabelas preflop 6max usar: 6max (padrão) / 6max_RC_100bb_200NL / 6max_RC_100bb_100NL / 6max_RC_40bb. Omita para o padrão da plataforma (6max); um valor desconhecido -> 400 unsupported_preflop_version. Versões diferentes fornecem frequências diferentes para a mesma situação. |
| campo | tipo | descrição |
|---|---|---|
position | string | A posição desta ação, uma de SB BB UTG MP CO BTN. |
action | string | ∈ "small blind" / "big blind" / "raise" / "call" / "fold" (observe que os blinds são strings de duas palavras). |
amount | number | O valor incremental recém-investido por esta ação (BB, não o total acumulado). Exemplos: small blind 0.5; big blind 1; um raise de abertura para 3 → amount 3 (a partir de 0); um jogador que já investiu 1 e aumenta novamente para 9 → amount 8. fold o omite (conta como 0). Pote = soma de todos os amount. |
allin | boolean | Opcional. Marca um all-in com stack curto (valor de aposta/call abaixo do raise mínimo); quando true, a verificação de raise mínimo é ignorada. |
Validação (violação → 400 invalid_actions): a sequência deve começar com small blind (0.5), depois big blind (1); cada raise/call precisa de um amount positivo; o total acumulado de um raise deve exceder a aposta atual e cumprir o raise mínimo (= aposta atual + o tamanho do raise anterior; portanto, abertura ≥ 2BB, e um 3bet sobre uma abertura para 3 deve ser ≥ 5BB) — exceto se allin:true; o total acumulado de um call deve ser exatamente igual à aposta atual — exceto se allin:true.
Os valores exatos afetam apenas o pote / sizing_pot, não as frequências: fornecer valores exatos de amount apenas torna o pote / sizing_pot exato; as frequências GTO são determinadas pela situação (RFI / 3bet / 4bet + posição) e não mudam com o tamanho da aposta.
curl -s https://pokerai.bet/v1/gto/preflop \
-H "Authorization: Bearer $POKERAI_API_KEY" -H "Content-Type: application/json" \
-d '{"hole_cards":"AhKh","positions":{"hero":"MP"},"preflop_version":"6max_RC_100bb_200NL",
"preflop_actions":[{"position":"SB","action":"small blind","amount":0.5},
{"position":"BB","action":"big blind","amount":1},
{"position":"UTG","action":"raise","amount":3}]}'
Omita preflop_version para o padrão (6max). As versões disponíveis estão listadas abaixo ou podem ser consultadas ao vivo com GET /v1/gto/preflop/versions.
{"hole_cards": "AhKh", "situation": "Raise", "strategy": [{"action": "raise", "frequency": 1, "amount_bb": 9, "sizing_pot": 0.8}], "quota": {"used": 7, "limit": 100}}
| campo | descrição |
|---|---|
hole_cards | A mão repetida na resposta. |
situation | O estado enfrentado pela mesa quando chega a vez do Hero: RFI (ninguém no pote, Hero tem uma oportunidade de abertura) / Limp (alguém deu limp, sem raise) / Raise (enfrentando um raise de abertura) / 3-Bet / 4-Bet / 5-Bet. Observação: BB sempre fica em Limp (alguém deve ter entrado no pote antes de ele agir). |
strategy[] | A estratégia mista de cada ação. raise inclui amount_bb (o valor absoluto para o qual se aumentou até, em BB) e sizing_pot (veja tamanho da aposta). O amount_bb preflop é definido pelo número de raises antes do Hero; veja a tabela abaixo. Nenhuma ação recomendada é retornada; escolha você mesmo com base em frequency. |
quota | Uso da cota geral deste mês (used / limit). |
amount_bb preflop (derivado do pote de flop pré-resolvido, valor aumentado até):
| número de raises antes do Hero | situação | amount_bb |
|---|---|---|
| 0 | abertura | 3 |
| 1 | 3bet | 9 |
| 2 | 4bet | 25 |
| ≥3 | 5bet+ | all-in 100 (allin: true) |
preflop_versionMesmo 6max, diferentes conjuntos de charts (as frequências diferem para o mesmo spot); omita para o padrão 6max. A lista oficial é o endpoint de descoberta GET /v1/gto/preflop/versions (gratuito; retorna id + label + default):
id (passe como preflop_version) | descrição |
|---|---|
6max (padrão) | 6 max 100bb Deepsolver |
6max_RC_100bb_200NL | 6 max 100bb GG 200NL 3b/f 2.2x - 2.5x |
6max_RC_100bb_100NL | 6 max 100bb GG 100NL 3b/f |
6max_RC_40bb | 6 max 40bb GG 100NL |
curl -s https://pokerai.bet/v1/gto/preflop/versions -H "Authorization: Bearer $POKERAI_API_KEY"
// {"versions": [{"id": "6max", "label": "6 max 100bb Deepsolver", "default": true}, …], "default": "6max"}
| HTTP | erro | gatilho / como corrigir |
|---|---|---|
| 400 | invalid_hole_cards | hole_cards não contém 2 cartas (por exemplo, "AdKd"). |
| 400 | unsupported_table_size / invalid_positions / invalid_actions | O tipo de mesa (atualmente apenas 6max), as posições de hero ou preflop_actions são inválidos. |
| 400 | unsupported_preflop_version | preflop_version não está no conjunto permitido (6max / 6max_RC_100bb_200NL / 6max_RC_100bb_100NL / 6max_RC_40bb). |
| 404 | no_solution | Não há solução pré-resolvida para este spot pré-flop; altere o spot. |
Baixar: request.jsonresponse.json
POST https://pokerai.bet/v1/gto/preflop/range · o Range completo 13×13 para um spot (posição + linha de ações), retornando fold/call/raise de todos os 169 tipos de mãos em uma chamada. Sem hole_cards (o spot vem de positions + preflop_actions). Consome 1 cota geral (uma chamada, não 169). Para renderizar uma grade de Range.
// Solicitação (sem hole_cards)
{"table_size": "6max", "positions": {"hero": "BTN"}, "preflop_actions": [{"position": "SB", "action": "small blind", "amount": 0.5}, {"position": "BB", "action": "big blind", "amount": 1}, {"position": "UTG", "action": "fold"}, {"position": "MP", "action": "fold"}, {"position": "CO", "action": "fold"}]}
// Resposta
{ "range": {"22": {"fold": 0.69, "call": 0, "raise": 0.31}, "33": {"fold": 0, "call": 0, "raise": 1}, "ATs": {"fold": 0, "call": 0, "raise": 1}, "AKs": {"fold": 0, "call": 0, "raise": 1}, "AKo": {"fold": 0, "call": 0, "raise": 1}, "KQs": {"fold": 0, "call": 0, "raise": 1}, "72o": {"fold": 1, "call": 0, "raise": 0}, "JJ": {"fold": 0, "call": 0, "raise": 1} , …169 mãos no total… },
"quota": {"used": 7, "limit": 100} }
Notação de mãos: par AA, suited AKs, offsuit AKo (carta alta primeiro); o fold+call+raise de cada entrada≈1. Esquema completo / experimente ao vivo → referência interativa.
A estratégia de flop é uma árvore de decisão: primeiro busque a árvore (obtendo todos os nós de decisão + o token de cada nó), seu sistema percorre o caminho na árvore pelas apostas reais e, no nó do Hero, busca a estratégia dessa etapa. Duas etapas, como no solver (tree → node).
POST https://pokerai.bet/v1/gto/flop/tree · entrada board + pot_type + positions (não é necessário hole_cards, a árvore é independente da mão).
Esquema completo de parâmetros / resposta e experimente ao vivo → referência interativa.
board | As 3 cartas do flop, por exemplo, "2c2h2s". |
pot_type | "SRP" com aumento único / "3BET" / "4BET" / "LIMP" com limp. |
positions | A posição de cada papel (SB BB UTG MP CO BTN), exigida por pot_type conforme abaixo. |
flop_version | Opcional. Qual conjunto de dados de flop (um resolvido por versão pré-flop): 6max (padrão) / 6max_RC_100bb_200NL / 6max_RC_100bb_100NL / 6max_RC_40bb. Omita para o padrão (6max); se essa versão não tiver dados para o spot, ela faz fallback de forma suave para 6max; um valor desconhecido -> 400 unsupported_flop_version. Independente de preflop_version. Os tokens dos nós carregam essa versão, portanto /v1/gto/flop/node permanece no mesmo conjunto de dados. |
| pot_type | posições obrigatórias | valor de Hero |
|---|---|---|
SRP | hero, raiser, caller | raiser ou caller |
3BET / 4BET | hero, raiser, three_bettor | raiser ou three_bettor |
LIMP | hero, limper | um de Hero ou limper deve ser BB |
// Solicitação (sem hole_cards)
{"board": "2c2h2s", "pot_type": "SRP", "positions": {"hero": "UTG", "raiser": "UTG", "caller": "BTN"}}
// Resposta (36 nós no total; primeiros 5 mostrados)
{"board": ["2c", "2h", "2s"], "pot_type": "SRP", "pot": 7.5, "effective_stack": 97, "oop_range": "AA:1,AKs:1,AQs:1,AJs:1,ATs:1,A9s:1,A8s:1,A7s:1,A6s:1,A5s:1,…", "ip_range": "AQs:0.05,AJs:0.86,ATs:0.436,A9s:0.356,A8s:0.36,A7s:0.196,…", "node_count": 36, "nodes": [{"node": "root", "is_hero": true, "token": "eyJ…"}, {"node": "root/BET_4", "is_hero": false, "token": "eyJ…"}, {"node": "root/BET_8", "is_hero": false, "token": "eyJ…"}, {"node": "root/BET_97", "is_hero": false, "token": "eyJ…"}, {"node": "root/CHECK", "is_hero": false, "token": "eyJ…"}, …], "quota": {"used": 7, "limit": 100}}
| campo | descrição |
|---|---|
oop_range / ip_range | O Range inicial deste spot (string de combos ponderados), usado como os pesos iniciais para conversão de Range. |
nodes[] | Todos os nós de decisão: node |
nodes[] | Todos os nós de decisão: node (caminho de ação, por exemplo, "root/CHECK/BET_8"), is_hero (se é um ponto de decisão do Hero), token (a credencial para buscar a estratégia desse nó, passada para a etapa 2; vinculada à conta + situação, não pode ser falsificada). |
pot / effective_stack / node_count | Pote, stack efetivo (BB) e número total de nós de decisão. |
quota | Uso da cota geral deste mês (used / limit). |
POST https://pokerai.bet/v1/gto/flop/node · recebe node (o token de algum nó da etapa 1). Com hole_cards → a estratégia mista para aquela mão; sem hole_cards → a estratégia para o range completo.
Esquema completo de parâmetros / resposta e teste ao vivo → referência interativa.
Toda decisão do Hero passa por aqui: a primeira ação do Hero = o nó root (OOP age primeiro, check/bet); quando o Hero está IP, enfrenta uma aposta ou age pela segunda vez, escolha o nó is_hero:true correspondente (por exemplo, root/CHECK/BET_8 = fiz check e agora enfrento uma aposta → fold/call/raise). A árvore do flop é de uma única street; para várias streets (turn/river), use /v1/gto/solver/*.
// Solicitação (nó do Hero, com hole_cards) -> estratégia do Hero
{"node": "eyJ…", "hole_cards": "AdKd"}
{"hole_cards": "AdKd", "node": "root", "is_hero": true, "strategy": [{"action": "check", "frequency": 0.7208}, {"action": "bet", "amount_bb": 4, "sizing_pot": 0.5333, "frequency": 0.0533}, {"action": "bet", "amount_bb": 8, "sizing_pot": 1.0667, "frequency": 0.2259}, {"action": "bet", "amount_bb": 97, "sizing_pot": 12.9333, "allin": true, "frequency": 0}]}
// Solicitação (sem hole_cards) -> estratégia para o range completo
{"node": "eyJ…"}
{"node": "root/BET_4", "is_hero": false, "actions": [{"action": "call"}, {"action": "raise", "amount_bb": 12, "sizing_pot": 0.5161}, {"action": "raise", "amount_bb": 20, "sizing_pot": 1.0323}, {"action": "raise", "amount_bb": 97, "sizing_pot": 6, "allin": true}, {"action": "fold"}], "range_strategy": {"3d3c": [0.93067, 4e-05, 0.06922, 1e-05, 7e-05], "3h3c": [0.92172, 6e-05, 0.07812, 1e-05, 0.0001], "3h3d": [0.94334, 4e-05, 0.05655, 1e-05, 7e-05], "…": "188 mãos no total"}, "range_hand_count": 188}
| campo | descrição |
|---|---|
is_hero | Se este nó é uma decisão do Hero. |
strategy[] | Nó do Hero (com hole_cards): a estratégia mista para esta mão. action ∈ check / bet / call / raise / fold (bet = primeira aposta, raise = um aumento diante de uma aposta); bet/raise trazem amount_bb e sizing_pot (veja tamanho da aposta), e all-in também traz allin: true; frequency é uma probabilidade de 0–1. Nenhuma ação recomendada é retornada; escolha você mesmo com base em frequency. |
actions[] + range_strategy | Nó do oponente (ou sem hole_cards): a estratégia para o range completo, com as frequências de cada mão alinhadas a actions; inclui range_hand_count. Pode ser usada para montar solver_results para "conversão de range". |
O BET_8 / RAISE_20 em um ID de nó é o valor absoluto da aposta (BB).
| HTTP | erro | gatilho / como corrigir |
|---|---|---|
| 400 | 1) invalid_board / invalid_positions; 2) missing_node / invalid_hole_cards | 1) o board não tem 3 cartas ou hero/posições são inválidos; 2) falta node ou hole_cards não tem 2 cartas. |
| 403 | invalid_node_token | (etapa 2) o token node é inválido ou não é seu — chame /v1/gto/flop/tree para buscar primeiro a árvore. |
| 404 | no_solution | Não há solução pré-resolvida para esta situação/board. |
Baixar: tree_request.jsontree_response.jsonnode_request.jsonnode_response.json
POST família https://pokerai.bet/v1/gto/solver. Solver puro de pós-flop, calculado em tempo real, usando uma cota de resolução separada. A essência é entrada para resolução: board + ranges oop/ip + pote + stack restante + quem é o Hero, sem necessidade de histórico, então você pode entrar de qualquer situação. Três etapas: agendar → consultar repetidamente a árvore até ela estar pronta → buscar a estratégia de um nó.
Esquema completo de parâmetros / resposta e teste ao vivo → referência interativa (inclui /solver/tree, /solver/node).
o tamanho do board define a street: 3=flop / 4=turn / 5=river. ⚠ A Resolução em tempo real começando no flop demora (flop SRP medido ~70 segundos) e não é adequada para casos de uso que precisam de uma resposta rápida — se quiser um flop rápido, use as "Soluções pré-resolvidas" acima (fornecidas instantaneamente em milissegundos); turn / river são mais rápidos (segundos a dezenas de segundos).
# 1) agendar (board 3/4/5 = flop/turn/river; flop ~70 segundos)
curl -s https://pokerai.bet/v1/gto/solver -H "Authorization: Bearer $POKERAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{"board":"2c2h2s","oop_range":"AA,KK,QQ,AKs","ip_range":"JJ,TT,AQs,KQs","pot":7.5,"effective_stack":97,"hero":"OOP","bet_sizes":{"flop":[33,75],"turn":[67],"river":[75]},"raise_sizes":{"flop":[50],"turn":[80],"river":[125]},"donk_sizes":{"turn":[55],"river":[90]},"raise_limit":3}'
# 2) consultar a árvore até spot_status=queryable; 3) buscar o nó
curl -s https://pokerai.bet/v1/gto/solver/tree -H "Authorization: Bearer $POKERAI_API_KEY" \
-H "Content-Type: application/json" -d '{"solve":"eyJ..."}'
board | 3=flop / 4=turn / 5=river, por exemplo, "2c2h2s9d" (turn). |
oop_range / ip_range | Obrigatório. Os Ranges dos dois jogadores que entram nesta street, strings de combos ponderados, por exemplo, "AsKs:1,QQ:0.75,...". |
pot / effective_stack | Obrigatório. O pote e o stack efetivo restante (BB) que entram nesta street; eles determinam os tamanhos de aposta e devem ser reais. |
hero | Obrigatório: "OOP" ou "IP". |
bet_sizes | Opcional: substitui os tamanhos de aposta de abertura por street, por exemplo, {"flop":[33,75],"turn":[67],"river":[75]} (% do pote); se flop for omitido, o padrão é 50%. |
raise_sizes | Opcional: substitui os tamanhos de aumento por street, por exemplo, {"flop":[50],"turn":[80],"river":[125]} (% do pote); streets omitidas reutilizam bet_sizes ou os padrões. |
donk_sizes | Opcional: substitui os tamanhos de donk-lead do OOP, por exemplo, {"turn":[55],"river":[90]} (% do pote); os padrões são 67% no turn e 100% no river. |
raise_limit | Opcional: limite de aumentos para toda a árvore, 1–4; o padrão é 3 para resoluções de flop/turn e 4 para resoluções somente de river. |
// Solicitação (flop, com tamanhos personalizados de aposta / aumento / donk)
{"board": "2c2h2s", "oop_range": "AA,KK,QQ,AKs", "ip_range": "JJ,TT,AQs,KQs", "pot": 7.5, "effective_stack": 97, "hero": "OOP", "bet_sizes": {"flop": [33,75], "turn": [67], "river": [75]}, "raise_sizes": {"flop": [50], "turn": [80], "river": [125]}, "donk_sizes": {"turn": [55], "river": [90]}, "raise_limit": 3}
// Resposta (primeiro acionamento, consome 1 resolução)
{"status": "computing", "solve": "eyJ0Ijoic2x2XzJmMjk2MWU3Y2Y0ODU3OGUiLCJ1IjoiYjk4Y2Y5NzAtZTVjMS00Njk5LTg4ODQtOGQzYzcwMGIyNGJlIiwidHMiOjE3ODIxMjkxMTUyMDJ9.rtmeNcZoBNWJRhkAGkTSSR58ZafpAh35mi510bgPU6c", "solve_quota": {"used": 1, "limit": 100}}
| campo / caso | descrição |
|---|---|
solve | O identificador da resolução, usado pelos /tree e /node subsequentes; o Range é fornecido apenas uma vez nesta etapa. |
status = computing | Uma nova resolução foi acionada, consome 1 cota de resolução (veja solve_quota). |
status = queryable | Já existe uma resolução em cache para este spot, sem cobrança (sem o campo solve_quota); consulte /tree diretamente. |
429 status = busy | Todos os solvers estão ocupados, sem cobrança; tente novamente mais tarde. |
Acerto de cache (sem nova cobrança): reagendar o mesmo spot (mesmo board/range/pot/stack/hero/bet_sizes/raise_sizes/donk_sizes/raise_limit) não consome mais cota de resolução — se a resposta não tiver o campo solve_quota, não houve cobrança; basta usar o identificador solve retornado para consultar /tree. Exemplos: solicitação / resposta.
POST https://pokerai.bet/v1/gto/solver/tree · leva o identificador solve; consulte até spot_status = queryable. Para acessar uma street posterior, informe as cartas distribuídas: turn_card (uma resolução de flop → um turn específico) e/ou river_card. Um spot de river de uma resolução de flop precisa de AMBOS turn_card + river_card (somente river não é único); uma resolução de turn precisa apenas de river_card; omita ambos para a street da própria resolução.
// (2) buscar a árvore desta street (flop)
{"solve": "eyJ…"}
{"street": "flop", "spot_status": "queryable", "pot": 7.5, "effective_stack": 97, "solve_seconds": 25.84, "node_count": 14, "nodes": [{"node": "root", "is_hero": true, "status": "queryable", "token": "eyJ…"}, {"node": "root/BET 4.000000", "is_hero": false, "status": "queryable", "token": "eyJ…"}, {"node": "root/BET 4.000000/RAISE 12.000000", "is_hero": true, "status": "queryable", "token": "eyJ…"}, …]}
// árvore de turn (resolução de flop + turn_card)
{"solve": "eyJ…", "turn_card": "9d"}
{"street": "turn", "spot_status": "queryable", "pot": 7.5, "effective_stack": 97, "solve_seconds": 25.84, "node_count": 104, "nodes": [{"node": "root/BET 4.000000/CALL/9d", "is_hero": false, "status": "queryable", "token": "eyJ…"}, {"node": "root/BET 4.000000/CALL/9d/BET 10.000000", "is_hero": true, "status": "queryable", "token": "eyJ…"}, {"node": "root/BET 4.000000/CALL/9d/BET 10.000000/RAISE 34.000000", "is_hero": false, "status": "queryable", "token": "eyJ…"}, …]}
// árvore de river (resolução de flop + turn_card + river_card)
{"solve": "eyJ…", "turn_card": "9d", "river_card": "Qh"}
{"street": "river", "spot_status": "queryable", "pot": 7.5, "effective_stack": 97, "solve_seconds": 25.84, "node_count": 308, "nodes": [{"node": "root/BET 4.000000/CALL/9d/BET 10.000000/CALL/Qh", "is_hero": true, "status": "queryable", "token": "eyJ…"}, {"node": "root/BET 4.000000/CALL/9d/BET 10.000000/CALL/Qh/BET 27.000000", "is_hero": false, "status": "queryable", "token": "eyJ…"}, {"node": "root/BET 4.000000/CALL/9d/BET 10.000000/CALL/Qh/BET 27.000000/RAISE 83.000000", "is_hero": true, "status": "queryable", "token": "eyJ…"}, …]}
| campo | descrição |
|---|---|
spot_status | Status da resolução: available (não agendada) / computing (em resolução, continue consultando) / queryable (disponível para busca) / expired (cache liberado, reagende na etapa 1) / no_nodes (a resolução convergiu, mas o runout/street consultado não tem nós de decisão na árvore — terminal, pare de consultar). |
nodes[] | Cada nó de decisão: node (caminho de ação), is_hero, status, token (a credencial para buscar a estratégia desse nó, passada à etapa 3). O runout de river é um nó de chance, navegado pela carta de river. |
street / pot / effective_stack / node_count | Street, pote, stack efetivo e número total de nós de decisão. |
solve_seconds | Tempo de relógio desta Resolução em tempo real, do agendamento à convergência (segundos). Retornado apenas quando queryable; todos os runouts da mesma resolução compartilham este valor. |
Esquema completo de parâmetros/resposta e experimente ao vivo → referência interativa.
POST https://pokerai.bet/v1/gto/solver/node · leva o token node. Um nó do Hero retorna a estratégia do Hero; um nó do oponente (ou sem hole_cards) retorna a estratégia de Range.
{"node": "eyJ…", "hole_cards": "AhKh"}
{"hole_cards": "AhKh", "node": "root", "is_hero": true, "strategy": [{"action": "check", "frequency": 0}, {"action": "bet", "amount_bb": 4, "sizing_pot": 0.5333, "frequency": 0.2666}, {"action": "bet", "amount_bb": 97, "sizing_pot": 12.9333, "allin": true, "frequency": 0.7334}]}
| campo | descrição |
|---|---|
is_hero | Se este nó é a decisão do Hero. |
strategy[] | Nó do Hero: estratégia mista do Hero para esta mão (action / amount_bb / sizing_pot (veja tamanho da aposta) / frequency), com allin: true adicionado quando está all-in. |
actions[] + range_strategy | Nó do oponente (ou sem hole_cards): em range_strategy, as frequências de cada mão se alinham à ordem de actions; também inclui range_hand_count. |
Esquema completo de parâmetros/resposta e experimente ao vivo → referência interativa.
Quando terminar, você pode opcionalmente chamar /v1/gto/solver/release para liberar a porta imediatamente (caso contrário, o sistema a recupera automaticamente por TTL). Quando o cache tiver sido recuperado ou substituído por uma resolução mais recente, esta etapa retornará { "node_status": "expired" }; basta reagendar na etapa 1. Um erro de resolução por nó retorna { "node_status": "error", "message": … } (terminal — pare de consultar). Esquema completo de parâmetros/resposta de /solver/release → referência interativa.
| HTTP | erro | causa / como corrigir |
|---|---|---|
| 400 | invalid_board / missing_range / invalid_pot / invalid_effective_stack / invalid_hero | (agendamento) o board, o Range oop/ip, o pote, o stack restante, o Hero ou outra entrada da resolução é inválida. |
| 400 | missing_solve / missing_node | (busca de tree/node) falta o identificador solve ou o token node. |
| 403 | invalid_solve / invalid_node_token | Identificador/token inválido ou não é seu — reagende / busque a tree novamente. |
| 429 | status: busy | Todos os solvers estão ocupados, não cobrado; aguarde e tente novamente. |
| 502 | solve_failed | O acionamento da resolução falhou; tente novamente mais tarde. |
| 503 | upstream_unavailable | (tree/node) o solver está inacessível após as próprias tentativas do serviço (erro de transporte / 5xx) — é possível tentar novamente. |
Baixar (turn, board=4): schedule_reqschedule_restree_reqtree_resnode_reqnode_res
Baixar (flop, board=3): schedule_reqschedule_restree_reqtree_resnode_reqnode_res
Baixar (river, board=5): schedule_reqschedule_restree_reqtree_resnode_reqnode_res
import requests, time
H = {"Authorization": "Bearer $POKERAI_API_KEY"}
BASE = "https://pokerai.bet/v1/gto"
# 1) agendar (consome 1 cota de resolução; grátis em acerto de cache)
solve = requests.post(f"{BASE}/solver", headers=H, json={
"board": "2c2h2s9d", "oop_range": "AA,KK,QQ,AKs", "ip_range": "JJ,TT,AQs,KQs",
"pot": 20, "effective_stack": 90, "hero": "OOP",
"bet_sizes": {"turn": [67], "river": [75]},
"raise_sizes": {"turn": [80], "river": [125]},
"donk_sizes": {"turn": [55], "river": [90]},
"raise_limit": 3}).json()["solve"]
# 2) consultar a tree até ficar queryable
while True:
tree = requests.post(f"{BASE}/solver/tree", headers=H, json={"solve": solve}).json()
if tree["spot_status"] == "queryable": break
time.sleep(2) # calculando -> aguarde e tente novamente
# 3) buscar a estratégia do nó raiz do Hero
root = next(n for n in tree["nodes"] if n["node"] == "root")
strat = requests.post(f"{BASE}/solver/node", headers=H,
json={"node": root["token"], "hole_cards": "AhKh"}).json()
print(strat["strategy"])
POST https://pokerai.bet/v1/gto/range consome 1 crédito geral
Esquema completo de parâmetros/resposta e experimente ao vivo → referência interativa.
Atualize os Ranges OOP/IP ao longo de uma linha de ações. É usado principalmente para obter o Range que entra na próxima street (flop→turn / turn→river) e, em seguida, fornecê-lo a /v1/gto/solver. Todo o cálculo de atualização de Ranges (incluindo normalização e desconto de blefe) é realizado pelo solver e é consistente com os resultados do solver.
Este é um proxy de passagem: você monta toda a entrada por conta própria, incluindo solver_results (a árvore de decisão). A árvore de decisão pode ser de uma das suas próprias resoluções ou montada a partir da árvore de decisão do flop desta plataforma: chame /v1/gto/flop/tree para o Range inicial e, em seguida, para cada nó, chame /v1/gto/flop/node sem hole_cards para obter a range_strategy completa, aninhada como {node_type,player,strategy,childrens}. Veja o script no final.
{
"range_oop": "AQs:1,AJs:0.48,...", // obrigatório, Range OOP inicial
"range_ip": "AA:1,AKs:1,...", // obrigatório, Range IP inicial
"solver_results": { /* obrigatório: a árvore de decisão */ },
"node_id": "root/CHECK", // obrigatório, a linha de ações
"board": "2c2h2s", // opcional, string sem separadores (igual aos outros endpoints)
"normalize": true, // opcional, padrão é true
"explain": false, // opcional, explicação da alteração por mão
"track_hands": ["AA"], // opcional, acompanhe apenas estas mãos
"bluff_discount_ratio": 0.8, // opcional, desconto de blefe
"hero_position": "oop", // opcional, "oop" / "ip" — qual jogador é o Hero (para bloqueio de cartas)
"hero_hand": "AsKs" // opcional, remove combinações que contêm as cartas do Hero (bloqueadores); retornado na resposta
}
Bloqueio de cartas (opcional): defina hero_position ("oop"/"ip") + hero_hand para remover dos Ranges todas as combinações que contêm uma das cartas do Hero — útil para análise de Range contra mão. Ambos são retornados na resposta. (Este par também é aceito pelos wrappers de projected-range; /v1/gto/flop/projected-range também aceita partner_hands.)
# solver_results é grande; coloque-o em um arquivo e use -d @
curl -s https://pokerai.bet/v1/gto/range -H "Authorization: Bearer $POKERAI_API_KEY" \
-H "Content-Type: application/json" -d @range_request.json
{"bluff_combos_ratio": 0.33, "bluff_discount_ratio": 1, "board": ["2c", "2h", "2s"], "hand_bottom_ranks_ip": "KsQh:2413,KsQd:2413,KsQc:2413,KhQs:2413,…", "hand_bottom_ranks_oop": "KcJh:2414,KcTs:2415,KsTs:2415,KsTh:2415,…", "hand_ranks_ip": "QcQh:313,QdQh:313,QdQs:313,QhQs:313,QcQs:313,…", "hand_ranks_oop": "Ad2d:155,AdAc:311,AhAc:311,AhAd:311,AsAc:311,…", "node_id": "root/CHECK", "path_length": 1, "range_ip_new": "33:0.193023,44:0.216279,54s:0.65814,…", "range_ip_new_raw": "3c3d:0.193023,3c3h:0.193023,3c3s:0.193023,…", "range_ip_new_raw_before_normalization": "3c3d:0.166,3c3h:0.166,3c3s:0.166,3d3h:0.166,…", "range_oop_new": "33:0.245724,44:0.272975,54s:0.420008,…", "range_oop_new_raw": "3d3c:0.245857,3h3c:0.245847,3h3d:0.24586,…", "range_oop_new_raw_before_normalization": "3d3c:0.245843,3h3c:0.245833,3h3d:0.245845,…", "quota": {"used": 7, "limit": 100}}
| campo | descrição |
|---|---|
range_oop_new / range_ip_new | O Range atualizado normalizado (notação de classe), usado diretamente como oop_range / ip_range da próxima street fornecido ao solver. |
range_oop_new_raw / range_ip_new_raw | O valor intermediário após o desconto de blefe, não normalizado (notação de combinação); use conforme necessário. |
range_oop_new_raw_before_normalization / range_ip_new_raw_before_normalization | O valor bruto limitado somente ao longo da linha de ações, sem desconto de blefe ou normalização. |
hand_ranks_oop / hand_ranks_ip | Classificação da força da mão (combo:rank, valores menores são mais fortes). |
hand_bottom_ranks_oop / hand_bottom_ranks_ip | Classificação da parte inferior do Range. |
node_id / board / path_length | A linha de ações, o board e o número de etapas da linha de ações retornados. |
bluff_discount_ratio / bluff_combos_ratio | Os parâmetros de desconto de blefe efetivamente usados desta vez. |
quota | O uso da cota geral deste mês (used / limit). |
| HTTP | erro | gatilho / como corrigir |
|---|---|---|
| 400 | missing_field | Falta um de range_oop / range_ip / solver_results / node_id. |
| 400 | bad_request | O lado do solver o rejeitou (por exemplo, o node_id não leva a lugar algum na árvore de decisão fornecida). |
Baixar: request.json (~1MB, inclui a árvore de decisão)response.jsonassemble_solver_results.py (script de ponta a ponta)
POST https://pokerai.bet/v1/gto/flop/projected-range cobra 1 geral
Esquema completo de parâmetros/resposta e teste ao vivo → referência interativa.
Restrinja os Ranges OOP/IP ao longo de uma linha de ações do flop para obter diretamente o Range inicial que entra no turn. Forneça o spot completo (board/pot_type/positions) e uma linha de ações (node_id), e a plataforma monta a árvore de decisão automaticamente no servidor e conclui a atualização do Range, retornando os mesmos campos da conversão de Range, além de pot_type retornado.
Este é um wrapper de conveniência sobre /v1/gto/range: ele poupa as etapas manuais de chamar /v1/gto/flop/tree + /v1/gto/flop/node por nó para montar solver_results. Ele se aplica apenas a linhas de ações do flop (a árvore de decisão é montada a partir dos resultados de flop pré-resolvidos desta plataforma); para turn→river etc., em que você deve trazer sua própria árvore de decisão, continue usando /v1/gto/range.
{
"board": "2c2h2s",
"pot_type": "SRP",
"positions": { "hero": "UTG", "raiser": "UTG", "caller": "BTN" },
"node_id": "root/BET_4",
"normalize": true,
"bluff_discount_ratio": 0.8,
"bluff_combos_ratio": 0.5,
"hero_position": "oop",
"hero_hand": "AsKs",
"partner_hands": ["Ac9c"]
}
| campo | descrição |
|---|---|
board | Obrigatório. O flop (string sem separadores, igual aos outros endpoints), por exemplo, "2c2h2s". |
pot_type | Obrigatório. O tipo de pote, por exemplo, "SRP". |
positions | Obrigatório. { hero, raiser, caller } (igual ao flop); spots de 3bet/limp podem incluir three_bettor / limper. |
node_id | Opcional; o padrão é "root". A linha de ações do flop, usando a notação de API retornada por /v1/gto/flop/tree (valor absoluto de aposta em BB), por exemplo, "root/BET_4", "root/CHECK/BET_8/CALL". |
normalize | Opcional; o padrão é true. Define se o Range atualizado será normalizado. |
bluff_discount_ratio / bluff_combos_ratio | Opcionais, cada um em [0,1] (fora do intervalo → 400). bluff_discount_ratio pondera os combos de blefe no fim do Range; bluff_combos_ratio é a fração do Range tratada como blefes. Omita para usar os padrões do servidor para turn/river. Ambos são retornados no eco da resposta. |
hero_position / hero_hand | Bloqueio de cartas opcional. Defina hero_position ("oop"/"ip") + hero_hand (por exemplo, "AsKs"): remove todo combo que contenha uma das cartas do Hero do Range atualizado do vilão (range_*_new_raw) e garante que a própria mão do Hero esteja presente em seu próprio Range. Ambos são retornados no eco da resposta. Apenas range_*_new_raw é afetado — hand_ranks / hand_bottom_ranks são filtrados somente pelo board. |
partner_hands | Array opcional de combos de 4 caracteres (por exemplo, ["Ac9c"]), requer hero_position. Remove todo combo que contenha uma dessas cartas de range_*_new_raw do vilão — modele cartas mortas conhecidas (mãos foldadas, cartas expostas). Somente entrada (não retornada no eco). Também é compatível com /v1/gto/turn/projected-range. |
flop_version | Opcional. Qual conjunto de dados de flop (um resolvido para cada versão de preflop): 6max (padrão) / 6max_RC_100bb_200NL / 6max_RC_100bb_100NL / 6max_RC_40bb. Omita para usar o padrão (6max); se essa versão não tiver dados para o spot, ela recorre automaticamente a 6max; um valor desconhecido -> 400 unsupported_flop_version. Independente de preflop_version. |
curl -s https://pokerai.bet/v1/gto/flop/projected-range -H "Authorization: Bearer $POKERAI_API_KEY" \
-H "Content-Type: application/json" -d @projected_range_request.json
{"board": ["2c", "2h", "2s"], "pot_type": "SRP", "node_id": "root/BET_4", "bluff_combos_ratio": 0.5, "bluff_discount_ratio": 0.8, "hero_position": "oop", "hero_hand": "AsKs", "hand_bottom_ranks_ip": "AhTh:2405,AsTs:2405,Ac9c:2406,Ad9d:2406,…", "hand_bottom_ranks_oop": "AhJs:2404,AsJc:2404,AsJd:2404,AsJh:2404,…", "hand_ranks_ip": "QcQd:313,QcQh:313,QcQs:313,QdQh:313,…", "hand_ranks_oop": "Ad2d:155,AdAc:311,AdAh:311,AdAs:311,…", "path_length": 1, "range_ip_new": "33:0.193023,44:0.216279,54s:0.65814,55:0.344186,…", "range_ip_new_raw": "3c3d:0.193023,3c3h:0.193023,3c3s:0.193023,3d3h:0.193023,…", "range_ip_new_raw_before_normalization": "3c3d:0.166,3c3h:0.166,3c3s:0.166,3d3h:0.166,…", "range_oop_new": "44:0.0120032,55:0.0422217,66:0.181192,77:0.327323,…", "range_oop_new_raw": "4s4c:0.0666554,4s4h:0.0666554,5d5c:0.005,5d5h:0.005,…", "range_oop_new_raw_before_normalization": "4s4c:0.011816,4s4h:0.011816,5s5c:0.0392591,5s5h:0.0392591,…", "quota": {"used": 7, "limit": 100}}
| campo | descrição |
|---|---|
range_oop_new / range_ip_new | O Range atualizado e normalizado (notação de classe), usado diretamente como oop_range / ip_range da próxima street fornecido ao solver. |
range_oop_new_raw / range_ip_new_raw | O valor intermediário após o desconto de blefe, sem normalização (notação de combo); use conforme necessário. |
range_oop_new_raw_before_normalization / range_ip_new_raw_before_normalization | O valor bruto restringido apenas ao longo da linha de ação, sem desconto de blefe ou normalização. |
hand_ranks_oop / hand_ranks_ip | Classificação da força da mão (combo:rank; valores menores são mais fortes). |
hand_bottom_ranks_oop / hand_bottom_ranks_ip | Classificação do fim do Range. |
node_id / board / pot_type / path_length | A linha de ação, o board, o tipo de pote e o número de etapas da linha de ação retornados no eco da resposta. |
bluff_discount_ratio / bluff_combos_ratio | Os parâmetros de desconto de blefe efetivamente usados desta vez. |
quota | Uso da cota geral deste mês (used / limit). |
| HTTP | erro | causa / como corrigir |
|---|---|---|
| 400 | invalid_board / invalid_positions | o board não tem 3 cartas, ou positions.hero é inválido. |
| 404 | no_solution (e um errorType do servidor, como no_ranges / no_root_node) | Não há árvore de flop pré-resolvida para este spot, ou a linha de ação node_id não leva a lugar algum. |
Baixar: request.jsonresponse.json
POST https://pokerai.bet/v1/gto/turn/projected-range grátis
Esquema completo de parâmetros/resposta e teste ao vivo → referência interativa.
A versão turn→river do Range projetado do flop, para uma Resolução em tempo real no turn. Restrinja os Ranges ao longo de uma linha de ação no turn (incluindo o CALL/CHECK que encerra a street) para obter diretamente o Range inicial que entra no river. Os Ranges OOP/IP que entram no turn são lidos da própria configuração da resolução (os Ranges com os quais ela foi agendada via /v1/gto/solver), portanto você só fornece o identificador da resolução solve + um node_id. Gratuito (a resolução já foi cobrada via /v1/gto/solver), assim como /v1/gto/solver/tree; retorna os mesmos campos da conversão de Range.
Primeiro, consulte /v1/gto/solver/tree até spot_status = queryable. Para turn→river, você não monta solver_results manualmente (a plataforma o lê da resolução e o monta).
{
"solve": "eyJ…",
"node_id": "root/CHECK/BET 6.000000/CALL",
"normalize": true,
"bluff_discount_ratio": 0.8,
"hero_position": "oop",
"hero_hand": "AsKs"
}
| campo | descrição |
|---|---|
solve | Obrigatório. O identificador da resolução retornado por /v1/gto/solver (uma resolução de turn). |
node_id | Obrigatório. Uma linha de ação no turn, pode terminar no CALL/CHECK que encerra a street. Notação de nó do solver (com espaços), por exemplo, "root/CHECK/BET 6.000000/CALL" (dos nós de /v1/gto/solver/tree). |
normalize | Opcional; o padrão é true. Define se o Range atualizado será normalizado. |
bluff_discount_ratio | Opcional. Desconto de blefe (0..1). |
hero_position / hero_hand | Bloqueio de cartas opcional: hero_position ("oop"/"ip") + hero_hand (por exemplo, "AsKs") remove todo combo que contenha uma das cartas do Hero do Range atualizado do vilão. |
partner_hands | Array opcional de combinações de 4 caracteres (por exemplo, ["Ac9c"]), requer hero_position. Remove todas as combinações que contêm uma dessas cartas do range_*_new_raw do vilão. Somente entrada. |
curl -s https://pokerai.bet/v1/gto/turn/projected-range -H "Authorization: Bearer $POKERAI_API_KEY" \
-H "Content-Type: application/json" -d @turn_projected_range_request.json
{"bluff_combos_ratio": 0.33, "bluff_discount_ratio": 1, "board": ["8d", "4h", "8s", "Qc"], "hand_bottom_ranks_ip": "TcTs:2943,TdTh:2943,TdTs:2943,9h9s:3020,…", "hand_bottom_ranks_oop": "AhKd:4646,AhKc:4646,AcKh:4646,JsTs:4746,…", "hand_ranks_ip": "Ac8c:2007,Ah8h:2007,KcKs:2645,KhKs:2645,…", "hand_ranks_oop": "8c8h:85,Ah8h:2007,Ac8c:2007,9c8c:2029,…", "node_id": "root/CHECK/BET 6.000000/CALL", "path_length": 3, "range_ip_new": "99:0.603064,A8s:0.5,AKs:0.70197,AQs:0.453337,…", "range_ip_new_raw": "9c9d:0.71487,9c9h:0.394271,9c9s:0.71487,…", "range_ip_new_raw_before_normalization": "9c9d:0.714699,9c9h:0.394176,9c9s:0.714699,…", "range_oop_new": "88:0.131148,98s:0.0902494,A8s:0.0344418,…", "range_oop_new_raw": "8c8h:0.777777,9c8c:0.185048,9h8h:0.17177,…", "range_oop_new_raw_before_normalization": "8c8h:0.418968,9c8c:0.0996806,9h8h:0.0925282,…"}
| campo | descrição |
|---|---|
range_oop_new / range_ip_new | O Range normalizado que entra no river (notação de classe), usado diretamente como oop_range / ip_range da resolução do river. |
range_*_raw / range_*_raw_before_normalization | Os valores intermediários não normalizados / antes do desconto (notação de combinações). |
hand_ranks_* / hand_bottom_ranks_* | Classificação da força da mão / classificação do fim do Range (combo:rank, menor é mais forte). |
node_id / board / path_length | A linha de ação, o board (4 cartas) e o número de etapas da linha de ação retornados. |
bluff_discount_ratio / bluff_combos_ratio | Os parâmetros de desconto de blefe realmente usados desta vez. |
Observação: gratuito; portanto, a resposta não tem o campo quota; e não tem pot_type (que é exclusivo do flop).
| HTTP | erro / estado | gatilho / como corrigir |
|---|---|---|
| 200 | { "spot_status": "computing" } | A resolução ainda não convergiu — continue consultando /v1/gto/solver/tree até ficar consultável. |
| 400 | missing_solve / missing_node_id | Falta o identificador solve ou node_id. |
| 410 | expired | A resolução expirou (TTL) — reagende via /v1/gto/solver. |
| 502 | no_solution etc. | Erro de resolução upstream. |
Baixar: request.jsonresponse.json
POST https://pokerai.bet/v1/gto/evs grátis
Esquema completo de parâmetros / resposta; teste ao vivo → referência interativa.
Valores esperados por mão e por ação em um nó de uma resolução concluída. Informe o identificador da resolução solve (de /v1/gto/solver) + um node_id (de /v1/gto/solver/tree); hand opcional filtra uma mão. Grátis (a resolução já foi cobrada). Primeiro, consulte /v1/gto/solver/tree até spot_status = queryable.
{
"solve": "eyJ0Ijoic2x2X3h4eXoi...(identificador de /v1/gto/solver)",
"node_id": "root",
"hand": "2c2d"
}
| campo | descrição |
|---|---|
solve | Obrigatório. O identificador da resolução de /v1/gto/solver. |
node_id | Obrigatório. Um nó de /v1/gto/solver/tree (notação do solver, por exemplo, "root", "root/CHECK/BET 6.000000"). |
hand | Opcional. Filtra os EVs de uma mão (por exemplo, "2c2d"); omita para todas as mãos. |
actions){"node_id": "root", "task_id": "slv_srp_…", "player": 1, "round": "FLOP", "actions": ["CHECK", "BET 4.000000", "BET 97.000000"], "evs": {"2c2d": [-0.826359, -0.792223, -1.643411], "2c2h": […], …}}
| campo | descrição |
|---|---|
actions | As ações do nó, em ordem; o array de EV de cada mão se alinha a elas. |
evs | Por mão → array de EV de cada ação (bb). Com hand fornecido, evs é um único array para essa mão. |
player / round / node_id / task_id | Qual jogador age, a rodada e o id de nó / resolução retornado. |
Observação: grátis, portanto sem campo quota. Retorna { "spot_status": "computing" } se a resolução não convergiu (consulte /v1/gto/solver/tree).
Combinando os endpoints: uma mão SRP (UTG abre, BTN paga), Hero = UTG. Os curls abaixo omitem o cabeçalho de autenticação (como no Início rápido).
POST /v1/gto/preflop
{ "hole_cards": "AdKd", "positions": { "hero": "UTG" },
"preflop_actions": [ { "position": "SB", "action": "small blind", "amount": 0.5 }, { "position": "BB", "action": "big blind", "amount": 1 } ] }
Apenas os posts de SB + BB (sem raises) = Hero é o primeiro a agir (uma situação de abertura). Retorna a frequência e o tamanho da abertura.
Flop 2c2h2s. O flop é uma árvore de decisão, em duas etapas: primeiro busque a árvore e depois use o token do nó do Hero para buscar a estratégia.
// 1) buscar a árvore (não são necessárias hole_cards)
POST /v1/gto/flop/tree
{ "board": "2c2h2s", "pot_type": "SRP",
"positions": { "hero": "UTG", "raiser": "UTG", "caller": "BTN" } }
// → em nodes[], root (is_hero:true) contém um token
// 2) usar o token de root para buscar a estratégia do Hero
POST /v1/gto/flop/node
{ "node": "<token de root>", "hole_cards": "AdKd" }
A primeira decisão do Hero = root; diante de uma aposta / agindo pela segunda vez → escolha o nó correspondente com is_hero:true. Consulte a árvore de decisão do flop.
O turn (por exemplo, 9d) precisa de uma Resolução em tempo real, que requer os Ranges de ambos os jogadores ao entrar no turn. Obtenha-os com a árvore de decisão do flop + conversão de Range:
/v1/gto/flop/tree para os oop_range / ip_range iniciais e os nós de decisão.root/CHECK/BET_8/CALL), chame /v1/gto/flop/node por nó (sem hole_cards) para buscar range_strategy e montar solver_results — consulte o script assemble_solver_results.py na seção de conversão de Range./v1/gto/range atualiza ao longo dessa linha → range_oop_new / range_ip_new são os Ranges que entram no turn.queryable e depois busque o nó:
POST /v1/gto/solver
{ "board": "2c2h2s9d", "oop_range": "<Range OOP entrando no turn>", "ip_range": "<Range IP entrando no turn>",
"pot": <pote no turn>, "effective_stack": <stack efetivo no turn>, "hero": "OOP" }
Já tem seu próprio range/spot? Na etapa 3, informe oop_range / ip_range diretamente e pule a derivação.
O river (board com 5 cartas) é igual ao turn: você pode resolvê-lo de forma independente (informe diretamente o Range que entra no river) ou usar a conversão de Ranges para atualizar mais uma vez a linha de ação do turn, obter o Range que entra no river e então enviá-lo ao solver.
Encapsula pokerkit-plus (um superconjunto de pokerkit 0.7.3): semântica de board/mão, Ranges & equidade, avaliação/equidade/ICM/notação e simulação de jogo. Reutiliza a mesma chave de API & cota — endpoints baratos cobram do bucket general, e endpoints de Monte Carlo, do bucket solve. Caminho base /v1/pokerkit/*; as entradas de cartas são strings sem separadores (AsKsQs), enums retornam {name,value}. Parâmetros/esquema completos por endpoint & teste ao vivo → referência interativa; especificação legível por máquina → /openapi.en.json (snapshot combinado de GTO + pokerkit).
Board (independente de Hero): /texture (umidade/conectividade/draws disponíveis), /nuts (nuts + combos que empatam), /category-combos, /board-report (texture+nuts). Hero: /hand-tier (nível de mão feita), /draws, /outs, /blockers, /hand-report (texture+tier+draws+outs em uma chamada).
| campo | descrição |
|---|---|
board | Obrigatório. 3/4/5 cartas comunitárias, sem separadores, por exemplo, "AsKsQs". |
hole | Obrigatório para endpoints de Hero (hand-tier / draws / outs / blockers / hand-report). 2 cartas fechadas, por exemplo, "JhTh"; endpoints de board (texture / nuts / category-combos / board-report) o omitem. |
hand_type | Opcional, o padrão é StandardHighHand (somente v1; outros tipos retornam 400). |
dead | Opcional. Cartas mortas / removidas (aceitas por todos os endpoints deste grupo). |
POST https://pokerai.bet/v1/pokerkit/texture — Estrutura do board: umidade/conectividade/faixa de ranks/disponibilidade de draws/formato de naipes. Parâmetros completos / testar ao vivo →
{"board": "AsKsQs"}
{"result": {"cards": ["As", "Ks", "Qs"], "wetness": {"name": "WET", "value": "Wet"}, "connectivity": {"name": "HIGH", "value": "High"}, "rank_band": {"name": "HIGH", "value": "High"}, "straight_draw": {"name": "OPEN_ENDED", "value": "Open-ended"}, "flush_draw": {"name": "LIVE", "value": "Live"}, "are_two_tone": false, "are_monotone": true, "are_rainbow": false}}
POST https://pokerai.bet/v1/pokerkit/nuts — Mão mais forte possível + todos os combos de duas cartas que empatam (com is_royal / board_is_nuts). Parâmetros completos / testar ao vivo →
{"board": "AsKsQs"}
{"result": {"hand": "TsJsKsQsAs", "combos": [{"cards": ["Ts", "Js"], "hand": "TsJsKsQsAs", "as_frozenset": ["Js", "Ts"]}], "candidate_count": 1176, "board_is_nuts": false, "is_royal": true, "label": {"name": "STRAIGHT_FLUSH", "value": "Straight flush"}}}
POST https://pokerai.bet/v1/pokerkit/category-combos — Cada combo ativo de duas cartas agrupado por categoria de mão feita. Parâmetros completos / testar ao vivo →
{"board": "AsKsQs"}
{"result": {"by_category": {"HIGH_CARD": [{"cards": ["2c", "3c"], "hand": "2c3cKsQsAs", "as_frozenset": ["2c", "3c"]}, {"cards": ["2c", "3d"], "hand": "2c3dKsQsAs", "as_frozenset": ["2c", "3d"]}], …}}}
POST https://pokerai.bet/v1/pokerkit/board-report — texture + nuts em uma chamada (visão geral do board). Parâmetros completos / testar ao vivo →
{"board": "AsKsQs"}
{"result": {"texture": {"cards": ["As", "Ks", "Qs"], "wetness": {"name": "WET", "value": "Wet"}, "connectivity": {"name": "HIGH", "value": "High"}, "rank_band": {"name": "HIGH", "value": "High"}, "straight_draw": {"name": "OPEN_ENDED", "value": "Open-ended"}, "flush_draw": {"name": "LIVE", "value": "Live"}, "are_two_tone": false, "are_monotone": true, "are_rainbow": false}, "nuts": {"hand": "TsJsKsQsAs", "combos": [{"cards": ["Ts", "Js"], "hand": "TsJsKsQsAs", "as_frozenset": ["Js", "Ts"]}], "candidate_count": 1176, "board_is_nuts": false, "is_royal": true, "label": {"name": "STRAIGHT_FLUSH", "value": "Straight flush"}}}}
POST https://pokerai.bet/v1/pokerkit/hand-tier — Nível de mão feita de Hero (pair / two-pair / trips / níveis de kicker, is_nut). Parâmetros completos / testar ao vivo →
{"hole": "JhTh", "board": "AsKsQs"}
{"result": {"category": {"name": "STRAIGHT", "value": "Straight"}, "is_nut": false, "pair_tier": null, "two_pair_tier": null, "three_of_a_kind_tier": null, "kicker_tier": null, "nut_rank": {"name": "NON_NUT", "value": "Non-nut"}}}
POST https://pokerai.bet/v1/pokerkit/draws — Draws de Hero (draw de sequência / flush draw, nut rank). Parâmetros completos / testar ao vivo →
{"hole": "Ah5h", "board": "Kh7h2c"}
{"result": {"straight_draw": null, "flush_draw": {"name": "LIVE", "value": "Live"}, "nut_rank": {"name": "NUT", "value": "Nut"}}}
POST https://pokerai.bet/v1/pokerkit/outs — Outs de Hero que melhoram a categoria de mão feita, agrupados + contagem. Parâmetros completos / testar ao vivo →
{"hole": "Ah5h", "board": "Kh7h2c"}
{"result": {"by_category": {"ONE_PAIR": ["2d", "2s", "5c", "5d", "5s", "7c", "7d", "7s", "Kc", "Kd", "Ks", "Ac", "Ad", "As"], "FLUSH": ["2h", "3h", "4h", "6h", "8h", "9h", "Th", "Jh", "Qh"]}, "count": 23}}
POST https://pokerai.bet/v1/pokerkit/blockers — Quantos combos de nuts Hero bloqueia (cartas bloqueadoras / fração). Parâmetros completos / testar ao vivo →
{"hole": "AhAd", "board": "AsKsQs"}
{"result": {"nut_combos_total": 1, "nut_combos_blocked": 0, "blocker_cards": [], "block_fraction": 0.0, "blocks_nuts": false}}
POST https://pokerai.bet/v1/pokerkit/hand-report — texture + tier + draws + outs em uma chamada (visão geral de Hero, principal). Parâmetros completos / testar ao vivo →
{"hole": "JhTh", "board": "AsKsQs"}
{"result": {"texture": {"cards": ["As", "Ks", "Qs"], "wetness": {"name": "WET", "value": "Wet"}, "connectivity": {"name": "HIGH", "value": "High"}, "rank_band": {"name": "HIGH", "value": "High"}, "straight_draw": {"name": "OPEN_ENDED", "value": "Open-ended"}, "flush_draw": {"name": "LIVE", "value": "Live"}, "are_two_tone": false, "are_monotone": true, "are_rainbow": false}, "tier": {"category": {"name": "STRAIGHT", "value": "Straight"}, "is_nut": false, "pair_tier": null, "two_pair_tier": null, "three_of_a_kind_tier": null, "kicker_tier": null, "nut_rank": {"name": "NON_NUT", "value": "Non-nut"}}, "draws": {"straight_draw": null, "flush_draw": null, "nut_rank": null}, "outs": {"by_category": {}, "count": 0}}}
/range/expand (notação → combos concretos), /range/value (Range de valor pelo piso da categoria de mão feita; aggression ∈ NO_BET/SINGLE_BET/RAISED), /range/nut-advantage (participação exata de nuts, sem amostragem).
| campo | descrição |
|---|---|
notation | (expand) array de notação de Ranges, por exemplo. ["AA","KQs","QQ+"]. |
hero / villain | (nut-advantage) um array de notação de Ranges para cada um. |
board | Cartas comunitárias (obrigatórias para value / nut-advantage; expand a omite). |
aggression | (valor) NO_BET / SINGLE_BET / RAISED define o piso da categoria; ou floor para defini-lo explicitamente. |
POST https://pokerai.bet/v1/pokerkit/range/expand — Expanda a notação de Range em combinações concretas de duas cartas. Parâmetros completos / experimente ao vivo →
{"notation": ["AA", "KQs"]}
{"result": [["Ac", "Ad"], ["Ac", "Ah"], ["Ac", "As"], ["Ad", "Ah"], ["Ad", "As"], ["Ah", "As"], ["Kc", "Qc"], ["Kd", "Qd"], ["Kh", "Qh"], ["Ks", "Qs"]]}
POST https://pokerai.bet/v1/pokerkit/range/value — Crie uma Range de valor pelo piso de categoria formada (aggression). Parâmetros completos / experimente ao vivo →
{"board": "AsKsQs", "aggression": "SINGLE_BET"}
{"result": [["2s", "3s"], ["2s", "4s"], ["2s", "5s"], ["2s", "6s"], ["2s", "7s"], ["2s", "8s"], …]}
POST https://pokerai.bet/v1/pokerkit/range/nut-advantage — Divisão exata da parcela de nuts por contagem de combos (sem amostragem, determinística). Parâmetros completos / experimente ao vivo →
{"hero": ["AA", "KK"], "villain": ["QQ", "JJ"], "board": "AsKsQs"}
{"result": {"hero_share": 0.5, "villain_share": 0.5, "basis": {"name": "NUT_SHARE", "value": "Nut share"}}}
cobra 1 general /eval/hand, /eval/compare (classificação + empates), /icm (determinístico), /notation/parse (.phh → estruturado). cobra 1 solve Monte-Carlo: /equity, /hand-strength, /range/equity-advantage — com sample_count (limitado) e seed (reproduzível, ~2s@10k).
Os endpoints Monte-Carlo (equity / hand-strength / range/equity-advantage) cobram do saldo de solve; os demais cobram de general.
| campo | descrição |
|---|---|
hole / holdings / board | Entradas de avaliação: hole + board (eval/hand), ou holdings (2+) + board (eval/compare). |
ranges / hole_range / hero / villain | Notação de Range (equity / hand-strength / range/equity-advantage). |
sample_count / seed | Monte-Carlo: contagem de amostras (limitada; acima do limite é restringida) / seed de RNG (reproduzível). |
payouts / chips | (icm) estrutura de premiação / fichas por jogador. |
text | (notation/parse) uma string de histórico de mão .phh. |
POST https://pokerai.bet/v1/pokerkit/eval/hand — Avalie hole + board em uma mão formada (5 cartas + rótulo de categoria). Parâmetros completos / experimente ao vivo →
{"hole": "JhTh", "board": "AsKsQs"}
{"result": {"hand": "JhThAsKsQs", "label": {"name": "STRAIGHT", "value": "Straight"}}}
POST https://pokerai.bet/v1/pokerkit/eval/compare — Classifique 2+ holdings em um board (com empates). Parâmetros completos / experimente ao vivo →
{"holdings": ["AcAd", "KsKh", "JhTh"], "board": "AsKsQs"}
{"result": [{"index": 2, "hole": "JhTh", "hand": "JhThAsKsQs", "rank": 1, "label": {"name": "STRAIGHT", "value": "Straight"}}, {"index": 0, "hole": "AcAd", "hand": "AcAdAsKsQs", "rank": 2, "label": {"name": "THREE_OF_A_KIND", "value": "Three of a kind"}}, {"index": 1, "hole": "KsKh", "hand": "KsKhAsKsQs", "rank": 3, "label": {"name": "THREE_OF_A_KIND", "value": "Three of a kind"}}]}
POST https://pokerai.bet/v1/pokerkit/equity — Equity de várias Ranges em um board (Monte-Carlo). Parâmetros completos / experimente ao vivo →
{"ranges": [["AA"], ["KK"]], "board": "", "sample_count": 2000, "seed": 7}
{"result": {"equities": [0.8235, 0.1765], "sample_count": 2000}}
POST https://pokerai.bet/v1/pokerkit/hand-strength — Fração de vitórias do hero contra N jogadores (Monte-Carlo). Parâmetros completos / experimente ao vivo →
{"hole_range": ["AhKh"], "board": "Qh7c2d", "player_count": 3, "sample_count": 2000, "seed": 7}
{"result": {"hand_strength": 0.3945, "player_count": 3, "sample_count": 2000}}
POST https://pokerai.bet/v1/pokerkit/icm — divisão de equidade ICM a partir de fichas / premiações (determinístico). Parâmetros completos / experimente ao vivo →
{"payouts": [50, 30, 20], "chips": [5000, 3000, 2000]}
{"result": {"icm": [38.392857142857146, 32.75, 28.857142857142854]}}
POST https://pokerai.bet/v1/pokerkit/range/equity-advantage — Divisão da parcela de equity entre duas Ranges (Monte-Carlo). Parâmetros completos / experimente ao vivo →
{"hero": ["AA", "KK"], "villain": ["QQ", "JJ"], "board": "AsKsQs", "sample_count": 2000, "seed": 7}
{"result": {"hero_share": 0.80325, "villain_share": 0.19675, "basis": {"name": "EQUITY", "value": "Equity"}, "sample_count": 2000}}
POST https://pokerai.bet/v1/pokerkit/notation/parse — Analise um histórico de mão .phh em uma configuração estruturada (variant / blinds / stacks / actions…). Parâmetros completos / experimente ao vivo →
{"text": "variant = \"NT\"\nante_trimming_status = true\nantes = [0, 0]\nblinds_or_straddles = [1, 2]\nmin_bet = 2\nstarting_stacks = [200, 200]\nactions = [\"d dh p1 AhKh\", \"d dh p2 QsQd\", \"p1 cbr 6\", \"p2 cc\", \"d db Qh7c2d\"]\n"}
{"result": {"variant": "NT", "ante_trimming_status": true, "antes": [0, 0], "blinds_or_straddles": [1, 2], "bring_in": null, "small_bet": null, "big_bet": null, "min_bet": 2, "starting_stacks": [200, 200], "actions": ["d dh p1 AhKh", "d dh p2 QsQd", "p1 cbr 6", "p2 cc", "d db Qh7c2d"], "automations": [{"name": "ANTE_POSTING", "value": "Ante posting"}, …], "author": null, "event": null, "day": null, "month": null, "year": null, "hand": null, "currency": null}}
Reprodução sem estado, com informação completa: o cliente carrega a lista de ações, e o servidor reconstrói o estado com pokerkit (zero estado no servidor). /games/state (instantâneo da situação atual), /games/step (aplique next_action; expected_action_count é um token de concorrência otimista, divergência → 409), /notation/replay (configuração ou texto .phh → instantâneos por etapa), /cards/normalize (validar/normalizar uma string de carta).
| campo | descrição |
|---|---|
variant | Obrigatório. Código da variante, por exemplo, "NT" (no-limit hold'em); lista completa em /v1/pokerkit/meta. |
antes / starting_stacks | Obrigatório. Antes / stacks iniciais por jogador (arrays de inteiros). |
blinds_or_straddles / min_bet | Blinds / straddles; min_bet obrigatório para no-limit / pot-limit (fixed-limit / stud usam small_bet / big_bet / bring_in). |
actions | Lista de ações até agora (notação pokerkit: d dh p1 AhKh distribui hole, p2 cbr 6 aumenta para 6, p1 cc check/call, p1 f fold). |
next_action / expected_action_count | (etapa) ação a aplicar / token de simultaneidade (= tamanho da lista que você estende; divergência → 409). |
text / index | (reprodução) use um texto .phh em vez disso; index retorna apenas essa etapa. cards/normalize aceita apenas cards (uma string de cartas). |
POST https://pokerai.bet/v1/pokerkit/games/state — Lista de ações → instantâneo da situação atual (todas as cartas fechadas exibidas). Parâmetros completos / experimente ao vivo →
{"variant": "NT", "antes": [0, 0], "blinds_or_straddles": [1, 2], "min_bet": 2, "starting_stacks": [200, 200], "actions": ["d dh p1 AhKh", "d dh p2 QsQd", "p2 cbr 6"]}
{"result": {"snapshot": {"terminal": false, "street_index": 0, "actor_index": 0, "pot": 8, "bets": [2, 6], "stacks": [198, 194], "board": [], "hole_cards": [{"player": 0, "cards": ["Ah", "Kh"]}, {"player": 1, "cards": ["Qs", "Qd"]}], "legal_actions": [{"action": "fold"}, {"action": "check_or_call", "amount": 4}, {"action": "complete_bet_or_raise_to", "min": 10, "max": 200}]}, "actions": ["d dh p1 AhKh", "d dh p2 QsQd", "p2 cbr 6"]}}
POST https://pokerai.bet/v1/pokerkit/games/step — Aplique next_action → novo instantâneo (token de simultaneidade; 409 em caso de divergência). Parâmetros completos / experimente ao vivo →
{"variant": "NT", "antes": [0, 0], "blinds_or_straddles": [1, 2], "min_bet": 2, "starting_stacks": [200, 200], "actions": ["d dh p1 AhKh", "d dh p2 QsQd", "p2 cbr 6"], "next_action": "p1 cc", "expected_action_count": 3}
{"result": {"snapshot": {"terminal": false, "street_index": 1, "actor_index": null, "pot": 12, "bets": [0, 0], "stacks": [194, 194], "board": [], "hole_cards": [{"player": 0, "cards": ["Ah", "Kh"]}, {"player": 1, "cards": ["Qs", "Qd"]}], "legal_actions": [{"action": "deal_board"}]}, "actions": ["d dh p1 AhKh", "d dh p2 QsQd", "p2 cbr 6", "p1 cc"]}}
POST https://pokerai.bet/v1/pokerkit/notation/replay — config ou .phh → instantâneos por etapa (index opcional para uma única etapa). Parâmetros completos / experimente ao vivo →
{"variant": "NT", "antes": [0, 0], "blinds_or_straddles": [1, 2], "min_bet": 2, "starting_stacks": [200, 200], "actions": ["d dh p1 AhKh", "d dh p2 QsQd", "p2 cbr 6", "p1 f"], "index": 2}
{"result": {"snapshot": {"terminal": false, "street_index": 0, "actor_index": 1, "pot": 3, "bets": [2, 1], "stacks": [198, 199], "board": [], "hole_cards": [{"player": 0, "cards": ["Ah", "Kh"]}, {"player": 1, "cards": ["Qs", "Qd"]}], "legal_actions": [{"action": "fold"}, {"action": "check_or_call", "amount": 1}, {"action": "complete_bet_or_raise_to", "min": 4, "max": 200}]}, "step_count": 5}}
POST https://pokerai.bet/v1/pokerkit/cards/normalize — Valide / normalize uma string de cartas para cartas padrão de 2 caracteres. Parâmetros completos / experimente ao vivo →
{"cards": "Ah Ks Qs"}
{"result": ["Ah", "Ks", "Qs"]}
Também GET /v1/pokerkit/meta (versões / códigos de variante / tipos de mão / vocabulários de enum). Esquema completo de parâmetros e experimente ao vivo para cada endpoint → referência interativa (navegue pelas duas APIs a partir do topo).
Um resumo da solicitação/resposta completa de cada endpoint (dados reais, nenhum campo omitido) está no "Download" de cada seção acima, ou: preflop · árvore do flop · nó do flop · solver · range · range projetado · resposta de range projetado · script de montagem.
/v1 no caminho é a versão principal. Alterações incompatíveis (remover/alterar campos, mudar a semântica) vão para uma nova versão principal /v2, e /v1 permanece disponível./v1 sem aviso separado — faça o parsing "ignorando campos desconhecidos" e não valide estritamente os campos de resposta por lista de permissões.| data | alteração |
|---|---|
| 2026-07-22 | /v1/gto/solver agora aceita campos independentes raise_sizes, donk_sizes e raise_limit, além de bet_sizes. |
| 2026-07-12 | Adicionado POST /v1/gto/solver/release — libera antecipadamente a porta do pool de uma resolução para que ela retorne ao pool imediatamente, em vez de aguardar o TTL do cache (opcional, gratuito; chame após seu último /solver/tree / /solver/node para essa resolução). |
| 2026-07-04 | Adicionado /v1/gto/evs (EVs de nó por mão e por ação de uma resolução concluída); /v1/gto/turn/projected-range agora também oferece suporte a partner_hands. |
| 2026-07-04 | /v1/gto/flop/projected-range agora respeita bluff_discount_ratio / bluff_combos_ratio da solicitação, injeta a própria mão do Hero no range do Hero e adiciona partner_hands (bloqueia as cartas mortas do parceiro do range do vilão). |
| 2026-06-22 | Adicionada a API de mecanismo / semântica de poker /v1/pokerkit/* (semântica de board/mão, ranges/equity, eval/equity/ICM/notação, simulação de jogo; mesma chave e cota). Veja abaixo. |
| 2026-06-22 | Adicionado /v1/gto/preflop/range (todo o range preflop 13×13, 169 mãos em uma chamada). |
| 2026-06-18 | Divisão do flop: removida a consulta única /v1/gto/flop, substituída por /v1/gto/flop/tree (buscar árvore) + /v1/gto/flop/node (buscar nó, gratuito), alinhada à árvore/nó do solver. |
| 2026-06-17 | Adicionado /v1/gto/flop/projected-range (um wrapper de conveniência sobre /v1/gto/range: forneça a situação completa do flop + linha de ações, o servidor monta a árvore de decisão automaticamente e retorna o range do turn diretamente). |
| 2026-06-17 | Formato unificado de board / mão: a entrada é uma string sem separadores, e o board de resposta é sempre retornado como um array. |
| 2026-06-17 | Adicionada a especificação OpenAPI 3.0; adicionada documentação de tutorial de notação de ranges / conceitos / fluxo completo. |
| 2026-06-17 | /v1/gto/solver agora oferece suporte a Resolução em tempo real no flop (board=3); bet_sizes.flop pode personalizar os tamanhos de aposta do flop. |
| 2026-06-17 | Correção: amount_bb do raise na consulta de flop era incorretamente 0 (agora retorna o BB absoluto correto). |
| 2026-06-17 | Adicionada a conversão de range /v1/gto/range; /flop/tree expõe os oop_range / ip_range iniciais; /flop e /solver/node retornam a estratégia de range completa quando hole_cards não é informado. |
| 2026-06-16 | Adicionada a família de solucionador em tempo real turn / river /v1/gto/solver (cota de resolução separada); adicionada a árvore de decisões do flop /v1/gto/flop/tree. |
| 2026-06-15 | Removido o campo recommendation de todas as respostas — escolha as ações você mesmo com base em frequency. |
pokerai.bet · GTO API v1