Pular para conteúdo

Scheduler — atividades e reconciliação

Owner: Scheduler. Os documentos de aplicação usam MONGODB_DATABASE, default default; JobRunr usa sua database própria, JOBRUNR_DATABASE, default scheduler_jobrunr_v2. Esses defaults de código não definem os bancos corporativos. O modelo abaixo corresponde ao checkout atual, não à antiga análise de uma feature.

Modelos visuais

Atividades e checkpoints

afterId é cursor por domínio, não FK. Jobs internos pertencem ao JobRunr.

Atividades e checkpoints; visão simplificada. Detalhes no visualizador abaixo. Atividades e checkpoints; visão simplificada em tema escuro.

Explorar diagramas detalhados com zoom

Legenda e convenções dos modelos. Os dicionários e evidências desta página permanecem a referência dos campos.

%%{init: {"theme":"base","themeVariables":{"fontFamily":"Arial, sans-serif","fontSize":"16px","lineColor":"#64748b","primaryTextColor":"#172b4d"},"flowchart":{"htmlLabels":true,"useMaxWidth":true,"nodeSpacing":28,"rankSpacing":38,"padding":14,"curve":"linear","subGraphTitleMargin":{"top":12,"bottom":16}},"sequence":{"useMaxWidth":true,"actorMargin":28,"width":145,"height":45,"diagramMarginX":32,"diagramMarginY":12,"messageMargin":24,"wrap":true,"mirrorActors":false},"themeCSS":".edgeLabel, .edgeLabel p {background-color:var(--diagram-surface)!important;color:var(--diagram-text)!important}\n.cluster rect {fill:var(--diagram-group)!important;stroke:var(--diagram-line)!important}\n.cluster-label span, .cluster-label text {color:var(--diagram-text)!important;fill:var(--diagram-text)!important}\n.flowchart-link, .actor-line {stroke:var(--diagram-line)!important}\nmarker path {fill:var(--diagram-line)!important;stroke:var(--diagram-line)!important}\n.actor {fill:var(--diagram-domain)!important;stroke:var(--diagram-domain-border)!important}\ntext.actor, .messageText, .loopText, .labelText {fill:var(--diagram-text)!important}\n.messageLine0, .messageLine1, .loopLine {stroke:var(--diagram-line)!important}\n.labelBox {fill:var(--diagram-surface)!important;stroke:var(--diagram-line)!important}\n.note {fill:var(--diagram-async)!important;stroke:var(--diagram-async-border)!important}\n.noteText {fill:var(--diagram-text)!important}\n.nodeLabel, .nodeLabel p, .nodeLabel span {color:var(--diagram-text)!important}\n.node .nodeLabel, .node .nodeLabel p {font-size:17px;font-weight:600;line-height:1.4;text-align:center}\n.nodeLabel small {display:inline-block;margin-top:4px;font-size:15px;font-weight:400;line-height:1.4;color:var(--diagram-description)!important}\ntext.actor, text.actor tspan {font-size:17px;font-weight:600}\n.node.entry rect, .node.entry polygon, .node.entry path, .node.entry circle {fill:var(--diagram-entry)!important;stroke:var(--diagram-entry-border)!important}\n.node.domain rect, .node.domain polygon, .node.domain path, .node.domain circle {fill:var(--diagram-domain)!important;stroke:var(--diagram-domain-border)!important}\n.node.security rect, .node.security polygon, .node.security path, .node.security circle {fill:var(--diagram-security)!important;stroke:var(--diagram-security-border)!important}\n.node.store rect, .node.store polygon, .node.store path, .node.store circle {fill:var(--diagram-store)!important;stroke:var(--diagram-store-border)!important}\n.node.async rect, .node.async polygon, .node.async path, .node.async circle {fill:var(--diagram-async)!important;stroke:var(--diagram-async-border)!important}\n.node.external rect, .node.external polygon, .node.external path, .node.external circle {fill:var(--diagram-external)!important;stroke:var(--diagram-external-border)!important}\n text.actor tspan, .loopText tspan, .labelText tspan, .messageText tspan, .noteText tspan {fill:var(--diagram-text)!important}\n\n"}}%%
flowchart TB
    http["http_calls_activities<br/><small>Request, trigger e execução</small>"]:::store
    rate["rate_limit_activities<br/><small>Reposição de quotas por tenant</small>"]:::store
    checkpoint["scheduler_reconciliation_checkpoints<br/><small>Cursor por domínio</small>"]:::store
    jobrunr["JobRunr<br/><small>Jobs em database própria</small>"]:::async
    http -->|executionJobId / agendamento| jobrunr
    rate -->|Agendamento| jobrunr
    checkpoint -->|afterId: varredura, não FK| http
    classDef store stroke-width:1.5px;
    classDef async stroke-width:1.5px;

O checkpoint também atende Rate Limit. afterId é um cursor para paginação por _id, não uma referência física com exclusão em cascata.

Collection Modelo, estados e operações
rate_limit_activities _id string, tenant, intervalo, máximo, estado e último resultado. REGISTERING/ACTIVE/ERROR/DELETING; ação pendente INITIALIZE_IF_ABSENT/RESET. CRUD e reconciliação por estado/cursor; atualiza snapshot lastExecution
http_calls_activities Request embutido (url, method, headers, body), trigger, política e resultado. Estados REGISTERING/ACTIVE/SCHEDULED/PAUSED/COMPLETED/CANCELLED/ERROR/DELETING; execução condicionada por executionJobId protege resultado de tentativa substituída
scheduler_reconciliation_checkpoints _id é o domínio reconciliado; replace/upsert de afterId e updatedAt

trigger.type declara CRON, AT, AFTER; criação normaliza disparos conforme o serviço. policy inclui timeout, retries e overlap SKIP. O documento HTTP não tem tenantId próprio: contexto pode existir nos headers do callback. createdBy não é uma restrição de tenant. Política de autorização deve ser analisada independentemente dessa estrutura.

Repositories usam insert, replace, delete e updates condicionais; busca HTTP filtra nome, status, tipo e criador com paginação. A criação inicia REGISTERING. O job reconciliador recupera atividades a partir do estado persistido. Não há índices secundários nem TTL Mongo declarados nas três collections de aplicação. Retenção JobRunr usa configurações de jobs concluídos/excluídos (defaults 24 h / 7 dias), não TTL dessas atividades.

As collections internas e o schema de jobs são geridos pela biblioteca JobRunr; não se inventa sua modelagem a partir dos documentos de aplicação. Redis fornece contador de quotas e lock de overlap, detalhados no inventário de caches.

Fontes: repositories HTTP, quotas, checkpoint, modelo HTTP, serviços HTTP, configuração.

O teste HttpCallActivityRepositoryImplTest especifica CRUD, resultados condicionados à execução atual, rejeição de execução substituída e paginação por cursor na reconciliação.

Dicionário de documentos

Os nomes BSON abaixo respeitam @BsonId/@BsonProperty. A nulabilidade descreve o tipo Java, não uma validação de schema Mongo. Valores iniciais Java precedem os construtores e serviços; os defaults de criação e invariantes estão descritos acima. Referências anuláveis não significam que a API aceite omiti-las em todas as operações. Campos de mapas/documentos livres não possuem schema fechado no modelo.

Propriedades calculadas expostas por getters públicos são identificadas separadamente: fazem parte da superfície do codec POJO, não do estado independente da entidade. @BsonIgnore é respeitado. A representação UUID depende da configuração do codec; os tipos de transporte JSON não substituem os tipos BSON.

Collection / documento raiz Modelo
scheduler_reconciliation_checkpoints ReconciliationCheckpointEntity
rate_limit_activities RateLimitActivityEntity
http_calls_activities ScheduledHttpCallEntity

scheduler_reconciliation_checkpoints — ReconciliationCheckpointEntity

ReconciliationCheckpointEntity.

Campo BSON Tipo Java / estrutura Representação Nulabilidade / valor inicial
_id String string Identificador BSON; tipo e geração conforme o ciclo de criação
afterId String string Referência anulável; inicial Java: null
updatedAt Instant data/hora Referência anulável; inicial Java: null

Exemplo de estrutura

Fragmento derivado dos campos do modelo vinculado acima, com valores substituídos por identificadores/textos sintéticos e data fixa. Não é um payload de criação nem um documento completo. ObjectId/data usam notação Extended JSON; nenhum dado de ambiente foi copiado.

{
  "_id": "exemplo-id",
  "afterId": "exemplo-id",
  "updatedAt": {
    "$date": "2026-10-13T00:00:00Z"
  }
}

rate_limit_activities — RateLimitActivityEntity

RateLimitActivityEntity.

Campo BSON Tipo Java / estrutura Representação Nulabilidade / valor inicial
_id String string Identificador BSON; tipo e geração conforme o ciclo de criação
tenantId String string Referência anulável; inicial Java: null
interval long int64 Primitivo não nulo; inicial Java: 0
maxRequests int int32 Primitivo não nulo; inicial Java: 0
status RateLimitStatus enum string Referência anulável; inicial Java: null
createdAt Instant data/hora Referência anulável; inicial Java: null
updatedAt Instant data/hora Referência anulável; inicial Java: null
lastExecution LastExecution documento embutido Referência anulável; inicial Java: null
pendingCounterAction RateLimitCounterAction enum string Referência anulável; inicial Java: null

Exemplo de estrutura

Fragmento derivado dos campos do modelo vinculado acima, com valores substituídos por identificadores/textos sintéticos e data fixa. Não é um payload de criação nem um documento completo. ObjectId/data usam notação Extended JSON; nenhum dado de ambiente foi copiado.

{
  "_id": "exemplo-id",
  "tenantId": "exemplo-id",
  "status": "REGISTERING",
  "createdAt": {
    "$date": "2026-10-13T00:00:00Z"
  }
}

http_calls_activities — ScheduledHttpCallEntity

ScheduledHttpCallEntity.

Campo BSON Tipo Java / estrutura Representação Nulabilidade / valor inicial
_id String string Identificador BSON; tipo e geração conforme o ciclo de criação
name String string Referência anulável; inicial Java: null
request HttpRequestDefinition documento embutido Referência anulável; inicial Java: null
trigger TriggerDefinition documento embutido Referência anulável; inicial Java: null
policy ExecutionPolicy documento embutido Referência anulável; inicial Java: null
status ScheduledCallStatus enum string Referência anulável; inicial Java: null
lastExecution LastExecution documento embutido Referência anulável; inicial Java: null
createdAt Instant data/hora Referência anulável; inicial Java: null
updatedAt Instant data/hora Referência anulável; inicial Java: null
createdBy String string Referência anulável; inicial Java: null
executionJobId String string Referência anulável; inicial Java: null
executionId String string Referência anulável; inicial Java: null
executionAttempt int int32 Primitivo não nulo; inicial Java: 0
errorPhase ScheduledCallErrorPhase enum string Referência anulável; inicial Java: null
executable boolean boolean Calculado por isExecutable(); propriedade derivada
oneTime boolean boolean Calculado por isOneTime(); propriedade derivada
cron boolean boolean Calculado por isCron(); propriedade derivada

Exemplo de estrutura

Fragmento derivado dos campos do modelo vinculado acima, com valores substituídos por identificadores/textos sintéticos e data fixa. Não é um payload de criação nem um documento completo. ObjectId/data usam notação Extended JSON; nenhum dado de ambiente foi copiado.

{
  "_id": "exemplo-id",
  "name": "exemplo-sanitizado",
  "status": "REGISTERING",
  "createdAt": {
    "$date": "2026-10-13T00:00:00Z"
  }
}

Estruturas embutidas, herança e enums

Estes tipos não criam collections próprias. Quando uma entidade raiz aparece dentro de um snapshot, a mesma estrutura é embutida naquele caminho. Tipos de elementos de arrays e valores de mapas estão vinculados nas tabelas.

ExecutionPolicy

src/main/java/app/totvs/gateway/scheduler/httpcall/model/ExecutionPolicy.java.

Campo BSON Tipo Java / estrutura Representação Nulabilidade / valor inicial
timeoutSeconds int int32 Primitivo não nulo; inicial Java: 0
maxRetries int int32 Primitivo não nulo; inicial Java: 0
overlap OverlapPolicy enum string Referência anulável; inicial Java: null

ExecutionResult

src/main/java/app/totvs/gateway/scheduler/httpcall/model/ExecutionResult.java.

Valores: SUCCESS, TRANSIENT_ERROR, PERMANENT_ERROR, SKIPPED.

HttpRequestDefinition

src/main/java/app/totvs/gateway/scheduler/httpcall/model/HttpRequestDefinition.java.

Campo BSON Tipo Java / estrutura Representação Nulabilidade / valor inicial
url String string Referência anulável; inicial Java: null
method String string Referência anulável; inicial Java: null
headers Map<String, String> documento / mapa Referência anulável; inicial Java: new LinkedHashMap<>()
body Map<String, Object> documento / mapa Referência anulável; inicial Java: null

LastExecution

src/main/java/app/totvs/gateway/scheduler/httpcall/model/LastExecution.java.

Campo BSON Tipo Java / estrutura Representação Nulabilidade / valor inicial
occurredAt Instant data/hora Referência anulável; inicial Java: null
result ExecutionResult enum string Referência anulável; inicial Java: null
httpStatus Integer int32 Referência anulável; inicial Java: null
durationMs long int64 Primitivo não nulo; inicial Java: 0
errorCode String string Referência anulável; inicial Java: null

OverlapPolicy

src/main/java/app/totvs/gateway/scheduler/httpcall/model/OverlapPolicy.java.

Valores: SKIP.

ScheduledCallErrorPhase

src/main/java/app/totvs/gateway/scheduler/httpcall/model/ScheduledCallErrorPhase.java.

Valores: SCHEDULING, EXECUTION.

ScheduledCallStatus

src/main/java/app/totvs/gateway/scheduler/httpcall/model/ScheduledCallStatus.java.

Valores: REGISTERING, ACTIVE, SCHEDULED, PAUSED, COMPLETED, CANCELLED, ERROR, DELETING.

TriggerDefinition

src/main/java/app/totvs/gateway/scheduler/httpcall/model/TriggerDefinition.java.

Campo BSON Tipo Java / estrutura Representação Nulabilidade / valor inicial
type TriggerType enum string Referência anulável; inicial Java: null
cronExpression String string Referência anulável; inicial Java: null
timeZone String string Referência anulável; inicial Java: null
executeAt Instant data/hora Referência anulável; inicial Java: null

TriggerType

src/main/java/app/totvs/gateway/scheduler/httpcall/model/TriggerType.java.

Valores: CRON, AT, AFTER.

LastExecution

src/main/java/app/totvs/gateway/scheduler/ratelimit/model/LastExecution.java.

Campo BSON Tipo Java / estrutura Representação Nulabilidade / valor inicial
occurredAt Instant data/hora Referência anulável; inicial Java: null
result RateLimitResetResult enum string Referência anulável; inicial Java: null
errorCode String string Referência anulável; inicial Java: null

RateLimitCounterAction

src/main/java/app/totvs/gateway/scheduler/ratelimit/model/RateLimitCounterAction.java.

Valores: INITIALIZE_IF_ABSENT, RESET.

RateLimitResetResult

src/main/java/app/totvs/gateway/scheduler/ratelimit/model/RateLimitResetResult.java.

Valores: SUCCESS, ERROR.

RateLimitStatus

src/main/java/app/totvs/gateway/scheduler/ratelimit/model/RateLimitStatus.java.

Valores: REGISTERING, ACTIVE, ERROR, DELETING.