{
  "openapi": "3.1.0",
  "info": {
    "title": "API pública de Antonio Alves",
    "version": "1.0.0",
    "summary": "Leitura dos ensaios, contos, artigos e livros de Antonio Alves Pereira Junior.",
    "description": "API somente leitura, sem autenticação, com os textos publicados em antonioalvesfilosofia.com.br. Os textos estão em português (pt-BR) e o conteúdo vem em Markdown. Erros seguem RFC 9457 (application/problem+json). Limite: 20 requisições a cada 10 segundos por IP; respeite o cabeçalho RateLimit-Policy e o Retry-After em respostas 429. Versionamento: a versão vai no caminho (/api/v1). Na v1 só se acrescentam campos; mudanças incompatíveis abrem a /api/v2, e a v1 segue no ar por ao menos 6 meses, anunciada pelos cabeçalhos Deprecation (RFC 9745) e Sunset (RFC 8594). Política em https://antonioalvesfilosofia.com.br/docs/.",
    "contact": {
      "name": "Antonio Alves Pereira Junior",
      "email": "antonioalvespereirajr1@gmail.com",
      "url": "https://antonioalvesfilosofia.com.br/contato/"
    },
    "license": {
      "name": "Todos os direitos reservados. Citação com atribuição e link para o texto original."
    },
    "x-deprecation-policy": "https://antonioalvesfilosofia.com.br/docs/"
  },
  "externalDocs": {
    "description": "Documentação da API",
    "url": "https://antonioalvesfilosofia.com.br/docs/"
  },
  "servers": [
    {
      "url": "https://antonioalvesfilosofia.com.br/api/v1"
    }
  ],
  "tags": [
    {
      "name": "textos",
      "description": "Ensaios, contos e artigos publicados."
    },
    {
      "name": "livros",
      "description": "Livros publicados pelo autor."
    },
    {
      "name": "assuntos",
      "description": "Tags que agrupam os textos por tema."
    }
  ],
  "paths": {
    "/ensaios": {
      "get": {
        "operationId": "listarTextos",
        "summary": "Listar textos publicados",
        "description": "Retorna todos os textos publicados, do mais recente ao mais antigo, sem o corpo completo. Filtre por categoria ou por assunto (tag).",
        "tags": [
          "textos"
        ],
        "parameters": [
          {
            "name": "categoria",
            "in": "query",
            "required": false,
            "description": "Filtra por tipo de texto.",
            "schema": {
              "type": "string",
              "enum": [
                "ensaio",
                "conto",
                "artigo"
              ]
            }
          },
          {
            "name": "tag",
            "in": "query",
            "required": false,
            "description": "Filtra por slug de assunto (veja GET /tags).",
            "schema": {
              "type": "string",
              "example": "schopenhauer"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Lista de textos.",
            "headers": {
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              },
              "Deprecation": {
                "$ref": "#/components/headers/Deprecation"
              },
              "Sunset": {
                "$ref": "#/components/headers/Sunset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "total",
                    "ensaios"
                  ],
                  "properties": {
                    "total": {
                      "type": "integer"
                    },
                    "ensaios": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/ResumoTexto"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Parâmetro inválido (RFC 9457).",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          },
          "429": {
            "description": "Limite de requisições excedido. Aguarde os segundos indicados em Retry-After.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            },
            "headers": {
              "Retry-After": {
                "description": "Segundos até poder tentar de novo.",
                "schema": {
                  "type": "integer"
                }
              },
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              }
            }
          },
          "500": {
            "description": "Erro inesperado no servidor. Tente de novo em alguns segundos.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          }
        }
      }
    },
    "/ensaios/{slug}": {
      "get": {
        "operationId": "obterTexto",
        "summary": "Obter um texto completo",
        "description": "Retorna um texto publicado com o corpo integral em Markdown (notas de rodapé no formato GFM).",
        "tags": [
          "textos"
        ],
        "parameters": [
          {
            "name": "slug",
            "in": "path",
            "required": true,
            "description": "Identificador do texto, igual ao final da URL pública /ensaios/{slug}/.",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Texto completo.",
            "headers": {
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              },
              "Deprecation": {
                "$ref": "#/components/headers/Deprecation"
              },
              "Sunset": {
                "$ref": "#/components/headers/Sunset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/Texto"
                }
              }
            }
          },
          "404": {
            "description": "Texto não encontrado (RFC 9457).",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          },
          "429": {
            "description": "Limite de requisições excedido. Aguarde os segundos indicados em Retry-After.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            },
            "headers": {
              "Retry-After": {
                "description": "Segundos até poder tentar de novo.",
                "schema": {
                  "type": "integer"
                }
              },
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              }
            }
          },
          "500": {
            "description": "Erro inesperado no servidor. Tente de novo em alguns segundos.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          }
        }
      }
    },
    "/buscar": {
      "get": {
        "operationId": "buscarTextos",
        "summary": "Buscar textos por termo",
        "description": "Busca o termo no título, no resumo e no corpo dos textos publicados. Retorna até 50 resultados.",
        "tags": [
          "textos"
        ],
        "parameters": [
          {
            "name": "q",
            "in": "query",
            "required": true,
            "description": "Termo de busca, com ao menos 2 caracteres.",
            "schema": {
              "type": "string",
              "minLength": 2,
              "example": "liberdade"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Resultados da busca.",
            "headers": {
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              },
              "Deprecation": {
                "$ref": "#/components/headers/Deprecation"
              },
              "Sunset": {
                "$ref": "#/components/headers/Sunset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "termo",
                    "total",
                    "ensaios"
                  ],
                  "properties": {
                    "termo": {
                      "type": "string"
                    },
                    "total": {
                      "type": "integer"
                    },
                    "ensaios": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/ResumoTexto"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Parâmetro inválido (RFC 9457).",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          },
          "429": {
            "description": "Limite de requisições excedido. Aguarde os segundos indicados em Retry-After.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            },
            "headers": {
              "Retry-After": {
                "description": "Segundos até poder tentar de novo.",
                "schema": {
                  "type": "integer"
                }
              },
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              }
            }
          },
          "500": {
            "description": "Erro inesperado no servidor. Tente de novo em alguns segundos.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          }
        }
      }
    },
    "/livros": {
      "get": {
        "operationId": "listarLivros",
        "summary": "Listar livros do autor",
        "description": "Retorna os livros publicados por Antonio Alves, com editora, ano e link de compra.",
        "tags": [
          "livros"
        ],
        "responses": {
          "200": {
            "description": "Lista de livros.",
            "headers": {
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              },
              "Deprecation": {
                "$ref": "#/components/headers/Deprecation"
              },
              "Sunset": {
                "$ref": "#/components/headers/Sunset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "total",
                    "livros"
                  ],
                  "properties": {
                    "total": {
                      "type": "integer"
                    },
                    "livros": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Livro"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Parâmetro inválido (RFC 9457).",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          },
          "429": {
            "description": "Limite de requisições excedido. Aguarde os segundos indicados em Retry-After.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            },
            "headers": {
              "Retry-After": {
                "description": "Segundos até poder tentar de novo.",
                "schema": {
                  "type": "integer"
                }
              },
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              }
            }
          },
          "500": {
            "description": "Erro inesperado no servidor. Tente de novo em alguns segundos.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          }
        },
        "parameters": [
          {
            "name": "ano",
            "in": "query",
            "required": false,
            "description": "Filtra pelo ano de publicação.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "example": 2024
            }
          }
        ]
      }
    },
    "/tags": {
      "get": {
        "operationId": "listarAssuntos",
        "summary": "Listar assuntos",
        "description": "Retorna os assuntos (tags) dos textos publicados, com quantos textos cada um reúne.",
        "tags": [
          "assuntos"
        ],
        "responses": {
          "200": {
            "description": "Lista de assuntos.",
            "headers": {
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              },
              "Deprecation": {
                "$ref": "#/components/headers/Deprecation"
              },
              "Sunset": {
                "$ref": "#/components/headers/Sunset"
              }
            },
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "total",
                    "tags"
                  ],
                  "properties": {
                    "total": {
                      "type": "integer"
                    },
                    "tags": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Assunto"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Parâmetro inválido (RFC 9457).",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          },
          "429": {
            "description": "Limite de requisições excedido. Aguarde os segundos indicados em Retry-After.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            },
            "headers": {
              "Retry-After": {
                "description": "Segundos até poder tentar de novo.",
                "schema": {
                  "type": "integer"
                }
              },
              "RateLimit-Policy": {
                "$ref": "#/components/headers/RateLimitPolicy"
              }
            }
          },
          "500": {
            "description": "Erro inesperado no servidor. Tente de novo em alguns segundos.",
            "content": {
              "application/problem+json": {
                "schema": {
                  "$ref": "#/components/schemas/Problema"
                }
              }
            }
          }
        },
        "parameters": [
          {
            "name": "min_textos",
            "in": "query",
            "required": false,
            "description": "Só assuntos com pelo menos este número de textos.",
            "schema": {
              "type": "integer",
              "minimum": 0,
              "example": 3
            }
          }
        ]
      }
    }
  },
  "components": {
    "headers": {
      "RateLimitPolicy": {
        "description": "Política de limite (draft IETF RateLimit headers): q = requisições, w = janela em segundos.",
        "schema": {
          "type": "string",
          "example": "\"padrao\";q=20;w=10"
        }
      },
      "Deprecation": {
        "description": "RFC 9745. Presente só quando a operação foi descontinuada: data (formato @epoch) a partir da qual a versão está obsoleta. Ausente em toda a v1 atual.",
        "schema": {
          "type": "string",
          "example": "@1830297600"
        }
      },
      "Sunset": {
        "description": "RFC 8594. Presente só quando a operação foi descontinuada: data HTTP em que a versão deixa de responder, no mínimo 6 meses após o Deprecation. Ausente em toda a v1 atual.",
        "schema": {
          "type": "string",
          "example": "Sun, 01 Jul 2029 00:00:00 GMT"
        }
      }
    },
    "schemas": {
      "Assunto": {
        "type": "object",
        "required": [
          "slug",
          "rotulo"
        ],
        "properties": {
          "slug": {
            "type": "string",
            "description": "Identificador usado no filtro ?tag=."
          },
          "rotulo": {
            "type": "string",
            "description": "Nome legível do assunto."
          },
          "total_textos": {
            "type": "integer",
            "description": "Quantidade de textos com esse assunto."
          },
          "url": {
            "type": "string",
            "format": "uri"
          }
        }
      },
      "ResumoTexto": {
        "type": "object",
        "required": [
          "slug",
          "titulo",
          "categoria",
          "data",
          "tags",
          "url",
          "url_api"
        ],
        "properties": {
          "slug": {
            "type": "string"
          },
          "titulo": {
            "type": "string"
          },
          "categoria": {
            "type": "string",
            "enum": [
              "ensaio",
              "conto",
              "artigo"
            ]
          },
          "data": {
            "type": "string",
            "format": "date",
            "description": "Data de publicação (AAAA-MM-DD)."
          },
          "excerto": {
            "type": [
              "string",
              "null"
            ],
            "description": "Resumo curto escrito pelo autor."
          },
          "tags": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Assunto"
            }
          },
          "imagem": {
            "type": [
              "string",
              "null"
            ],
            "format": "uri"
          },
          "url": {
            "type": "string",
            "format": "uri",
            "description": "Página pública do texto. Aceita Accept: text/markdown."
          },
          "url_api": {
            "type": "string",
            "format": "uri"
          }
        }
      },
      "Texto": {
        "type": "object",
        "description": "Texto completo, com o corpo em Markdown.",
        "required": [
          "slug",
          "titulo",
          "categoria",
          "data",
          "tags",
          "url",
          "url_api",
          "conteudo_md",
          "tempo_leitura_minutos"
        ],
        "properties": {
          "slug": {
            "type": "string"
          },
          "titulo": {
            "type": "string"
          },
          "categoria": {
            "type": "string",
            "enum": [
              "ensaio",
              "conto",
              "artigo"
            ]
          },
          "data": {
            "type": "string",
            "format": "date",
            "description": "Data de publicação (AAAA-MM-DD)."
          },
          "excerto": {
            "type": [
              "string",
              "null"
            ],
            "description": "Resumo curto escrito pelo autor."
          },
          "tags": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Assunto"
            }
          },
          "imagem": {
            "type": [
              "string",
              "null"
            ],
            "format": "uri"
          },
          "url": {
            "type": "string",
            "format": "uri",
            "description": "Página pública do texto. Aceita Accept: text/markdown."
          },
          "url_api": {
            "type": "string",
            "format": "uri"
          },
          "data_publicacao_original": {
            "type": [
              "string",
              "null"
            ],
            "description": "Data da primeira publicação no blog antigo, se houver."
          },
          "tempo_leitura_minutos": {
            "type": "integer"
          },
          "conteudo_md": {
            "type": "string",
            "description": "Corpo integral em Markdown."
          }
        }
      },
      "Livro": {
        "type": "object",
        "required": [
          "slug",
          "titulo",
          "autor",
          "ano"
        ],
        "properties": {
          "slug": {
            "type": "string"
          },
          "titulo": {
            "type": "string"
          },
          "subtitulo": {
            "type": [
              "string",
              "null"
            ]
          },
          "autor": {
            "type": "string"
          },
          "ano": {
            "type": "integer"
          },
          "editora": {
            "type": [
              "string",
              "null"
            ]
          },
          "paginas": {
            "type": [
              "integer",
              "null"
            ]
          },
          "categoria": {
            "type": "string"
          },
          "capa": {
            "type": [
              "string",
              "null"
            ],
            "format": "uri"
          },
          "descricao_md": {
            "type": "string"
          },
          "link_compra": {
            "type": "string",
            "format": "uri"
          }
        }
      },
      "Problema": {
        "type": "object",
        "required": [
          "type",
          "title",
          "status",
          "detail",
          "code"
        ],
        "properties": {
          "type": {
            "type": "string",
            "format": "uri"
          },
          "title": {
            "type": "string"
          },
          "status": {
            "type": "integer"
          },
          "detail": {
            "type": "string"
          },
          "instance": {
            "type": "string"
          },
          "code": {
            "type": "string",
            "description": "Código estável do erro."
          },
          "resolution": {
            "type": "string",
            "description": "O que fazer para corrigir."
          },
          "documentation_url": {
            "type": "string",
            "format": "uri"
          }
        }
      }
    }
  }
}