> ## Documentation Index
> Fetch the complete documentation index at: https://developers.googa.com.br/llms.txt
> Use this file to discover all available pages before exploring further.

# Progresso de leitura consolidado de um assinante

> Uma linha por novela que o assinante já abriu — em andamento ou concluída. Nomeado no singular (`subscriber`, não `subscribers`) para seguir a mesma convenção de `GET /subscriber-status/{id}` na Platform API.

`active_novel_count` nunca passa de `active_novel_limit` (hoje fixo em 3): é o limite de novelas simultâneas não finalizadas, aplicado no servidor por `enforce_reading_rules()` — o assinante precisa terminar (ou remover) uma novela em andamento antes de abrir uma quarta. Um parceiro que queira, por exemplo, avisar "sua base já está no limite" numa tela própria tem esse dado aqui sem precisar hardcodar o número 3.



## OpenAPI

````yaml /novelai/openapi.yaml get /subscriber/{id}/reading-progress
openapi: 3.1.0
info:
  title: Googa NovelAI API
  version: 1.0.0
  summary: >-
    API específica de produto para NovelAI — catálogo de novelas seriadas,
    capítulos liberados pelo drip diário, progresso de leitura por assinante e
    os finais disponíveis. Não repete Entitlements, Billing ou SSO — isso é
    resolvido uma única vez pela Platform API (ver aba API Platform); esta
    especificação cobre apenas o que é específico de conteúdo/leitura do
    NovelAI.
  description: >-
    Hoje o catálogo, os capítulos e o progresso de leitura são consumidos
    diretamente pelo app oficial (Web/PWA — não há apps nativos) contra o
    Supabase do projeto "Novel", via Row Level Security. Esta especificação é um
    **contrato proposto, ainda não implementado**: descreve como um sistema
    terceiro (como o app da operadora) leria esses mesmos dados sem acesso
    direto ao banco. Ver [Modelo de autenticação sobre
    Supabase](/architecture/supabase-auth-model) para o desenho de autenticação
    completo.


    Esta é uma API **somente leitura** do ponto de vista do parceiro: nenhum
    endpoint aqui escreve em `reading_progress`, `subscriptions` ou qualquer
    outra tabela de domínio do leitor — isso continua sendo decisão do app
    oficial e, para os aspectos de assinatura/plano, da Platform API (`POST
    /entitlements`). O parceiro lê catálogo, capítulos liberados e progresso;
    não empurra leitura.


    NovelAI e NovelAudio compartilham o mesmo projeto Supabase ("Novel") e o
    mesmo domínio `api.novelai.com.br` — os recursos de streaming e player de
    áudio (voz, posição de reprodução, download offline) são documentados na aba
    NovelAudio, não aqui, ainda que fisicamente sejam a mesma API.
  contact:
    name: Googa — Suporte a parceiros
    email: developers@googa.com.br
  license:
    name: Uso restrito — ver Política de Uso da API
    url: https://developers.googa.com.br/security/api-usage-policy
servers:
  - url: https://api.novelai.com.br/v1
    description: Produção (proposto)
  - url: https://sandbox.novelai.com.br/v1
    description: Sandbox (proposto) — catálogo fictício, sem impacto em billing real
security:
  - partnerOAuth2: []
tags:
  - name: Catalog
    description: Catálogo público de categorias e novelas — metadados, sem gate de drip.
  - name: Chapters
    description: Capítulos de uma novela e seu estado de liberação (drip) por assinante.
  - name: Progress
    description: Progresso de leitura consolidado por assinante, entre novelas.
  - name: Choices
    description: >-
      Finais disponíveis de uma novela — só aparecem quando o drip libera o
      último capítulo.
  - name: Analytics
    description: >-
      Métricas agregadas de engajamento por parceiro — nunca por leitor
      identificável.
paths:
  /subscriber/{id}/reading-progress:
    get:
      tags:
        - Progress
      summary: Progresso de leitura consolidado de um assinante
      description: >-
        Uma linha por novela que o assinante já abriu — em andamento ou
        concluída. Nomeado no singular (`subscriber`, não `subscribers`) para
        seguir a mesma convenção de `GET /subscriber-status/{id}` na Platform
        API.


        `active_novel_count` nunca passa de `active_novel_limit` (hoje fixo em
        3): é o limite de novelas simultâneas não finalizadas, aplicado no
        servidor por `enforce_reading_rules()` — o assinante precisa terminar
        (ou remover) uma novela em andamento antes de abrir uma quarta. Um
        parceiro que queira, por exemplo, avisar "sua base já está no limite"
        numa tela própria tem esse dado aqui sem precisar hardcodar o número 3.
      operationId: getSubscriberReadingProgress
      parameters:
        - name: id
          in: path
          required: true
          schema:
            type: string
          description: Identificador do assinante no sistema do parceiro.
      responses:
        '200':
          description: Progresso consolidado.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SubscriberReadingProgress'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '404':
          description: >-
            Assinante nunca visto por este parceiro (nenhum entitlement
            emitido).
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
components:
  schemas:
    SubscriberReadingProgress:
      type: object
      properties:
        subscriber_id:
          type: string
        active_novel_count:
          type: integer
          description: Novelas em andamento (`finished_at` nulo) agora.
        active_novel_limit:
          type: integer
          description: >-
            Limite de novelas simultâneas não finalizadas — hoje fixo em 3,
            aplicado no servidor.
          example: 3
        novels:
          type: array
          items:
            $ref: '#/components/schemas/ReadingProgressEntry'
          description: Toda novela que o assinante já abriu, em andamento ou concluída.
    Error:
      type: object
      description: >-
        Mesmo formato de erro (estilo OAuth2, RFC 6749 §5.2) usado pela Platform
        API.
      properties:
        error:
          type: string
          example: invalid_request
        error_description:
          type: string
          example: Novela inexistente ou removida do catálogo
    ReadingProgressEntry:
      type: object
      properties:
        novel_id:
          type: string
        title:
          type: string
        started_at:
          type: string
          format: date-time
        current_chapter:
          type: integer
          description: >-
            Último capítulo em que o assinante salvou a posição de leitura
            (`reading_progress.current_page`).
        unlocked_chapters:
          type: integer
          description: Capítulos já liberados para este assinante nesta novela agora.
        total_chapters:
          type: integer
        finished_at:
          type: string
          format: date-time
          nullable: true
        chosen_choice_id:
          type: string
          nullable: true
  responses:
    Unauthorized:
      description: Credenciais ausentes, inválidas ou expiradas.
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
  securitySchemes:
    partnerOAuth2:
      type: oauth2
      description: >-
        Client credentials — emitido **uma única vez**, de forma centralizada,
        pela Platform API (`POST https://api.googa.com.br/v1/oauth2/token`, ver
        aba API Platform). Este domínio (`api.novelai.com.br`) só *valida* o
        token — via a chave pública do projeto Supabase "Platform" — nunca emite
        um token próprio. Isso evita duplicar a verificação de
        `client_id`/`client_secret` em três projetos Supabase diferentes: o
        parceiro autentica uma vez, e o mesmo token (com os escopos certos)
        funciona em qualquer domínio de produto. Ver "Roteamento cross-projeto"
        em [Modelo de autenticação sobre
        Supabase](/architecture/supabase-auth-model#partner-gateway-a-camada-que-conecta-as-duas-pontas).
      flows:
        clientCredentials:
          tokenUrl: https://api.googa.com.br/v1/oauth2/token
          scopes:
            novelai:catalog:read: Ler catálogo (novelas e categorias)
            novelai:chapters:read: Ler capítulos e estado de liberação por assinante
            novelai:progress:read: Ler progresso de leitura consolidado por assinante
            novelai:choices:read: Ler finais disponíveis por assinante
            novelai:analytics:read: Ler métricas agregadas de engajamento

````