openapi: 3.0.3
info:
  title: Leads Module (RPC)
  version: v0.1.0

servers:
  - url: /

tags:
  - name: Leads

paths:

  /adm/api/Leads/ping:
    post:
      tags:
        - Leads
      summary: Ping
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              additionalProperties: true
      responses:
        "200":
          description: OK
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcOk"

  /adm/api/Leads/summary:
    post:
      tags:
        - Leads
      summary: Summary cards (by_status, next_actions, top_src)
      requestBody:
        required: false
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsSummaryRequest"
      responses:
        "200":
          description: Summary
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadsSummaryResponse"

  /adm/api/Leads/list:
    post:
      tags:
        - Leads
      summary: List leads (paginated)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsListRequest"
      responses:
        "200":
          description: Rows + total
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadsListResponse"

  /adm/api/Leads/get:
    post:
      tags:
        - Leads
      summary: Get lead by id
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id
              properties:
                id:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: Lead
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadGetResponse"

  /adm/api/Leads/save:
    post:
      tags:
        - Leads
      summary: Create/update lead
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadUpsertRequest"
      responses:
        "200":
          description: Saved
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadUpsertResponse"

  /adm/api/Leads/delete:
    post:
      tags:
        - Leads
      summary: Delete lead
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id
              properties:
                id:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: Deleted
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/DeleteResponse"

  /adm/api/Leads/status:
    post:
      tags:
        - Leads
      summary: Update lead status
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadStatusRequest"
      responses:
        "200":
          description: Updated
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadStatusResponse"

  /adm/api/Leads/notes_list:
    post:
      tags:
        - Leads
      summary: List notes for lead
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id
              properties:
                id:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: Notes
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadNotesListResponse"

  /adm/api/Leads/notes_add:
    post:
      tags:
        - Leads
      summary: Add note to lead
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadNotesAddRequest"
      responses:
        "200":
          description: Added
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/prefs_save:
    post:
      tags:
        - Leads
      summary: Save preferences for lead (leads_prefs)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadPrefsSaveRequest"
      responses:
        "200":
          description: Saved
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/origens:
    post:
      tags:
        - Leads
      summary: Select2 - origens (src) usadas
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              properties:
                contrato:
                  type: integer
                  minimum: 1
                  nullable: true
      responses:
        "200":
          description: Options
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/Select2OptionsResponse"

  /adm/api/Leads/divulgadores:
    post:
      tags:
        - Leads
      summary: Select2 - divulgadores
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              properties:
                contrato:
                  type: integer
                  minimum: 1
                  nullable: true
      responses:
        "200":
          description: Options
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/Select2OptionsResponse"

  /adm/api/Leads/atendentes:
    post:
      tags:
        - Leads
      summary: Select2 - atendentes
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              properties:
                contrato:
                  type: integer
                  minimum: 1
                  nullable: true
      responses:
        "200":
          description: Options
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/Select2OptionsResponse"

  /adm/api/Leads/equipes_list:
    post:
      tags:
        - Leads
      summary: Select2 - equipes por contrato
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - contrato
              properties:
                contrato:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: Options
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/Select2OptionsResponse"

  /adm/api/Leads/vendedores_por_equipes:
    post:
      tags:
        - Leads
      summary: Retorna vendedores por equipes
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - equipes
              properties:
                equipes:
                  type: array
                  items:
                    type: integer
                    minimum: 1
      responses:
        "200":
          description: Options
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/Select2OptionsResponse"

  /adm/api/Leads/equipes_vendedores:
    post:
      tags:
        - Leads
      summary: Alias compat da rota vendedores_por_equipes
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - equipes
              properties:
                equipes:
                  type: array
                  items:
                    type: integer
                    minimum: 1
      responses:
        "200":
          description: Options
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/Select2OptionsResponse"

  /adm/api/Leads/relatorio:
    post:
      tags:
        - Leads
      summary: Relatório (compat legado)
      requestBody:
        required: false
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsRelatorioRequest"
      responses:
        "200":
          description: Relatório
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadsRelatorioResponse"

  /adm/api/Leads/evolucaoOrigemTempo:
    post:
      tags:
        - Leads
      summary: Evolução por origem ao longo do tempo
      requestBody:
        required: false
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsGraficoRequest"
      responses:
        "200":
          description: Gráfico
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadsEvolucaoOrigemTempoResponse"

  /adm/api/Leads/distribuicaoOrigens:
    post:
      tags:
        - Leads
      summary: Distribuição por origens
      requestBody:
        required: false
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsGraficoRequest"
      responses:
        "200":
          description: Gráfico
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadsDistribuicaoOrigensResponse"

  /adm/api/Leads/graficoPizzaPorDivulgador:
    post:
      tags:
        - Leads
      summary: Pizza por divulgador
      requestBody:
        required: false
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsGraficoRequest"
      responses:
        "200":
          description: Gráfico
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadsDistribuicaoOrigensResponse"

  /adm/api/Leads/acaoMassa:
    post:
      tags:
        - Leads
      summary: Ação em massa
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsMassActionRequest"
      responses:
        "200":
          description: Result
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/mass_action:
    post:
      tags:
        - Leads
      summary: Alias compat de acaoMassa
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsMassActionRequest"
      responses:
        "200":
          description: Result
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/atribuirLeads:
    post:
      tags:
        - Leads
      summary: Atribuir leads para vendedores (round-robin)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsAtribuirRequest"
      responses:
        "200":
          description: Result
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/assign_bulk:
    post:
      tags:
        - Leads
      summary: Alias compat de atribuirLeads
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/LeadsAtribuirRequest"
      responses:
        "200":
          description: Result
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/verificarLead:
    post:
      tags:
        - Leads
      summary: Verifica lead (atendente atual)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id
              properties:
                id:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: Data
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/LeadVerificarResponse"

  /adm/api/Leads/iniciarAtendimento:
    post:
      tags:
        - Leads
      summary: Inicia atendimento (set atendimento_inicio + status)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id
              properties:
                id:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: Result
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/encerrarAtendimento:
    post:
      tags:
        - Leads
      summary: Encerra atendimento (set atendimento_fim + status final)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id
                - atendimento
              properties:
                id:
                  type: integer
                  minimum: 1
                atendimento:
                  type: string
                  enum:
                    - ganho
                    - perdido
                    - sem_interesse
                    - invalido
      responses:
        "200":
          description: Result
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/take:
    post:
      tags:
        - Leads
      summary: Alias compat para assumir um lead
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id
              properties:
                id:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: Result
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/TakeResponse"

  /adm/api/Leads/take_bulk:
    post:
      tags:
        - Leads
      summary: Alias compat para assumir múltiplos leads
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/TakeBulkRequest"
      responses:
        "200":
          description: Result
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/TakeBulkResponse"

  /adm/api/Leads/convite_criar:
    post:
      tags:
        - Leads
      summary: Criar convite para lead (token)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id_lead
              properties:
                id_lead:
                  type: integer
                  minimum: 1
                expires_at:
                  type: string
                  format: date-time
                  nullable: true
      responses:
        "200":
          description: Token
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/ConviteCriarResponse"

  /adm/api/Leads/convite_marcar_enviado:
    post:
      tags:
        - Leads
      summary: Marcar convite como enviado
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - token
              properties:
                token:
                  type: string
                  minLength: 16
      responses:
        "200":
          description: OK
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/convite_aceitar:
    post:
      tags:
        - Leads
      summary: Aceitar convite (marca aceito)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - token
              properties:
                token:
                  type: string
                  minLength: 16
      responses:
        "200":
          description: OK
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/ConviteAceitarResponse"

  /adm/api/Leads/convites_expirar_vencidos:
    post:
      tags:
        - Leads
      summary: Expira convites vencidos (job/manual)
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              additionalProperties: true
      responses:
        "200":
          description: OK
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/invite_create:
    post:
      tags:
        - Leads
      summary: Alias compat para criar convite
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              properties:
                id:
                  type: integer
                  minimum: 1
                id_lead:
                  type: integer
                  minimum: 1
                days:
                  type: integer
                  minimum: 1
                  nullable: true
      responses:
        "200":
          description: Convite
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/InviteCreateAliasResponse"

  /adm/api/Leads/invite_list:
    post:
      tags:
        - Leads
      summary: Alias compat para listar convites de um lead
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id
              properties:
                id:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: Lista de convites
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/InviteListResponse"

  /adm/api/Leads/invite_cancel:
    post:
      tags:
        - Leads
      summary: Alias compat para cancelar convite
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - invite_id
              properties:
                invite_id:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: Convite cancelado
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/import_criar:
    post:
      tags:
        - Leads
      summary: Criar lote de importação
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - id_profissional
                - nome_lote
              properties:
                id_profissional:
                  type: integer
                  minimum: 1
                nome_lote:
                  type: string
                  minLength: 2
                  maxLength: 120
                arquivo:
                  type: string
                  nullable: true
      responses:
        "200":
          description: OK
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/ImportCriarResponse"

  /adm/api/Leads/import_add_item:
    post:
      tags:
        - Leads
      summary: Adiciona item (raw_row) ao lote
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - import_id
                - raw_row
              properties:
                import_id:
                  type: integer
                  minimum: 1
                raw_row:
                  type: object
                  additionalProperties: true
                status:
                  type: string
                  enum:
                    - novo
                    - vincular
                    - ignorar
                    - erro
                  default: novo
                motivo:
                  type: string
                  nullable: true
      responses:
        "200":
          description: OK
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/import_aprovar:
    post:
      tags:
        - Leads
      summary: Aprova lote (status=aprovado)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - import_id
              properties:
                import_id:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: OK
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/RpcMsgOkResponse"

  /adm/api/Leads/import_processar:
    post:
      tags:
        - Leads
      summary: Processa lote (cria/vincula/ignora)
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - import_id
                - contrato
              properties:
                import_id:
                  type: integer
                  minimum: 1
                contrato:
                  type: integer
                  minimum: 1
      responses:
        "200":
          description: OK
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/ImportProcessarResponse"

  /adm/api/Leads/import_preview:
    post:
      tags:
        - Leads
      summary: Alias compat para preview de CSV
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/ImportPreviewRequest"
      responses:
        "200":
          description: Preview
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/ImportPreviewResponse"

  /adm/api/Leads/import_commit:
    post:
      tags:
        - Leads
      summary: Alias compat para processar importação
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: "#/components/schemas/ImportCommitRequest"
      responses:
        "200":
          description: Commit
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/ImportProcessarResponse"

components:
  schemas:

    RpcOk:
      type: object
      properties:
        __status:
          type: integer
          example: 200
        ok:
          type: integer
          enum:
            - 0
            - 1
          example: 1
        msg:
          type: string
          nullable: true
        data:
          type: object
          nullable: true
          additionalProperties: true

    RpcMsgOkResponse:
      type: object
      properties:
        __status:
          type: integer
          example: 200
        ok:
          type: integer
          enum:
            - 0
            - 1
          example: 1
        data:
          type: object
          nullable: true
          additionalProperties: true
        msg:
          type: string
          nullable: true

    DeleteResponse:
      type: object
      properties:
        __status:
          type: integer
          example: 200
        ok:
          type: integer
          enum:
            - 0
            - 1
          example: 1
        data:
          type: object
          properties:
            deleted:
              type: integer
              example: 1
        msg:
          type: string
          nullable: true

    Select2Option:
      type: object
      properties:
        id:
          oneOf:
            - type: integer
            - type: string
        text:
          type: string

    Select2OptionsResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: array
          items:
            $ref: "#/components/schemas/Select2Option"
        msg:
          type: string
          nullable: true

    LeadsSummaryRequest:
      type: object
      properties:
        id_contrato:
          type: integer
          minimum: 1
          nullable: true
        contrato:
          type: integer
          minimum: 1
          nullable: true
        status:
          type: string
          nullable: true
        src:
          type: string
          nullable: true
        q:
          type: string
          nullable: true
        next_due:
          type: string
          nullable: true
          enum:
            - ""
            - "overdue"
            - "today"
            - "7d"
        scope:
          type: string
          nullable: true
          enum:
            - ""
            - "mine"

    LeadsSummaryResponse:
      type: object
      properties:
        __status:
          type: integer
          example: 200
        ok:
          type: integer
          enum:
            - 0
            - 1
          example: 1
        data:
          type: object
          properties:
            by_status:
              type: object
              additionalProperties:
                type: integer
            next_actions:
              type: object
              properties:
                overdue:
                  type: integer
                today:
                  type: integer
                next_7d:
                  type: integer
            extra:
              type: object
              properties:
                top_src:
                  type: array
                  items:
                    type: object
                    properties:
                      src:
                        type: string
                      qtd:
                        type: integer

    LeadsListRequest:
      type: object
      properties:
        limit:
          type: integer
          minimum: 1
          maximum: 500
          default: 30
        offset:
          type: integer
          minimum: 0
          default: 0
        order:
          type: string
          enum:
            - "recent"
            - "score"
            - "next_action"
            - "activity"
          default: "recent"
        id_contrato:
          type: integer
          minimum: 1
          nullable: true
        contrato:
          type: integer
          minimum: 1
          nullable: true
        status:
          type: string
          nullable: true
        atendimento:
          type: string
          nullable: true
        src:
          type: string
          nullable: true
        origem:
          type: string
          nullable: true
        q:
          type: string
          nullable: true
        nome:
          type: string
          nullable: true
        email:
          type: string
          nullable: true
        whatsapp:
          type: string
          nullable: true
        cpf:
          type: string
          nullable: true
        divulgador:
          type: integer
          minimum: 1
          nullable: true
        atendente:
          type: integer
          minimum: 1
          nullable: true
        cliente:
          type: integer
          nullable: true
        visita:
          type: integer
          nullable: true
        equipe:
          type: integer
          minimum: 1
          nullable: true
        dataini:
          type: string
          format: date
          nullable: true
        datafim:
          type: string
          format: date
          nullable: true
        next_due:
          type: string
          nullable: true
          enum:
            - ""
            - "overdue"
            - "today"
            - "7d"
        scope:
          type: string
          nullable: true
          enum:
            - ""
            - "mine"

    LeadsListResponse:
      type: object
      properties:
        __status:
          type: integer
          example: 200
        ok:
          type: integer
          enum:
            - 0
            - 1
          example: 1
        data:
          type: object
          properties:
            total:
              type: integer
            rows:
              type: array
              items:
                $ref: "#/components/schemas/LeadRow"

    LeadRow:
      type: object
      properties:
        id:
          type: integer
        nome:
          type: string
          nullable: true
        email:
          type: string
          nullable: true
        whatsapp:
          type: string
          nullable: true
        cpf:
          type: string
          nullable: true
        divulgador:
          type: integer
          nullable: true
        src:
          type: string
          nullable: true
        atendimento:
          type: string
          nullable: true
        score:
          type: integer
          nullable: true
        next_action_at:
          type: string
          format: date-time
          nullable: true
        last_activity_at:
          type: string
          format: date-time
          nullable: true
        atendimento_inicio:
          type: string
          format: date-time
          nullable: true
        atendimento_fim:
          type: string
          format: date-time
          nullable: true
        cliente:
          type: integer
          nullable: true
        atendente:
          type: integer
          nullable: true
        visita:
          type: integer
          nullable: true
        contrato:
          type: integer
          nullable: true
        data_cadastro:
          type: string
          format: date-time
          nullable: true
        nome_contrato:
          type: string
          nullable: true
        nome_divulgador:
          type: string
          nullable: true
        nome_atendente:
          type: string
          nullable: true
        nome_equipe:
          type: string
          nullable: true

    LeadGetResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          $ref: "#/components/schemas/LeadRow"
        msg:
          type: string
          nullable: true

    LeadUpsertRequest:
      type: object
      properties:
        id:
          type: integer
          minimum: 1
          nullable: true
        nome:
          type: string
          nullable: true
        email:
          type: string
          nullable: true
        whatsapp:
          type: string
          nullable: true
        cpf:
          type: string
          nullable: true
        divulgador:
          type: integer
          minimum: 1
          nullable: true
        src:
          type: string
          nullable: true
        atendimento:
          type: string
          nullable: true
          enum:
            - em_espera
            - novo
            - em_andamento
            - aguardando
            - agendado
            - ganho
            - perdido
            - sem_interesse
            - invalido
        status:
          type: string
          nullable: true
          enum:
            - em_espera
            - novo
            - em_andamento
            - aguardando
            - agendado
            - ganho
            - perdido
            - sem_interesse
            - invalido
        score:
          type: integer
          minimum: 0
          maximum: 100
          nullable: true
        next_action_at:
          type: string
          format: date-time
          nullable: true
        contrato:
          type: integer
          minimum: 1
          nullable: true
        id_contrato:
          type: integer
          minimum: 1
          nullable: true
        atendente:
          type: integer
          minimum: 1
          nullable: true

    LeadUpsertResponse:
      type: object
      properties:
        __status:
          type: integer
          example: 200
        ok:
          type: integer
          enum:
            - 0
            - 1
          example: 1
        data:
          type: object
          properties:
            id:
              type: integer
        msg:
          type: string
          nullable: true

    LeadStatusRequest:
      type: object
      required:
        - id
        - status
      properties:
        id:
          type: integer
          minimum: 1
        status:
          type: string
          enum:
            - em_espera
            - novo
            - em_andamento
            - aguardando
            - agendado
            - ganho
            - perdido
            - sem_interesse
            - invalido

    LeadStatusResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            updated:
              type: integer
              example: 1
        msg:
          type: string
          nullable: true

    LeadNotesListResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            rows:
              type: array
              items:
                $ref: "#/components/schemas/LeadNoteRow"

    LeadNoteRow:
      type: object
      properties:
        id:
          type: integer
        id_lead:
          type: integer
        author_id:
          type: integer
          nullable: true
        tipo:
          type: string
        conteudo:
          type: string
        created_at:
          type: string
          format: date-time

    LeadNotesAddRequest:
      type: object
      required:
        - id
        - conteudo
      properties:
        id:
          type: integer
          minimum: 1
        tipo:
          type: string
          enum:
            - nota
            - ligacao
            - whatsapp
            - email
            - reuniao
            - outro
          default: nota
        conteudo:
          type: string
          minLength: 1

    LeadPrefsSaveRequest:
      type: object
      required:
        - id
      properties:
        id:
          type: integer
          minimum: 1
        modalidade:
          type: string
          enum:
            - presencial
            - domicilio
            - online
          nullable: true
        endereco_id:
          type: integer
          minimum: 1
          nullable: true
        servico_id:
          type: integer
          minimum: 1
          nullable: true
        procedimento_id:
          type: integer
          minimum: 1
          nullable: true
        obs:
          type: string
          nullable: true
          maxLength: 255

    LeadsRelatorioRequest:
      type: object
      properties:
        contrato:
          type: integer
          minimum: 1
          nullable: true
        status:
          type: string
          nullable: true
          enum:
            - em_espera
            - novo
            - em_andamento
            - aguardando
            - agendado
            - ganho
            - perdido
            - sem_interesse
            - invalido
        origem:
          type: string
          nullable: true
        divulgador:
          type: integer
          minimum: 1
          nullable: true
        atendente:
          type: integer
          minimum: 1
          nullable: true
        dataini:
          type: string
          format: date
          nullable: true
        datafim:
          type: string
          format: date
          nullable: true

    LeadsRelatorioResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        dados:
          type: array
          items:
            type: object
            additionalProperties: true

    LeadsGraficoRequest:
      type: object
      properties:
        contrato:
          type: integer
          minimum: 1
          nullable: true
        status:
          type: string
          nullable: true
          enum:
            - em_espera
            - novo
            - em_andamento
            - aguardando
            - agendado
            - ganho
            - perdido
            - sem_interesse
            - invalido
        origem:
          type: string
          nullable: true
        divulgador:
          type: integer
          minimum: 1
          nullable: true
        atendente:
          type: integer
          minimum: 1
          nullable: true
        dataini:
          type: string
          format: date
          nullable: true
        datafim:
          type: string
          format: date
          nullable: true

    LeadsEvolucaoOrigemTempoResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        erro:
          type: integer
          enum:
            - 0
            - 1
          nullable: true
        dados:
          type: object
          properties:
            datas:
              type: array
              items:
                type: string
                format: date
            series:
              type: object
              additionalProperties:
                type: array
                items:
                  type: integer

    LeadsDistribuicaoOrigensResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        erro:
          type: integer
          enum:
            - 0
            - 1
          nullable: true
        grafico:
          type: object
          properties:
            labels:
              type: array
              items:
                type: string
            values:
              type: array
              items:
                type: integer

    LeadsMassActionRequest:
      type: object
      required:
        - acao
        - ids
      properties:
        acao:
          type: string
          enum:
            - remover
            - sem_interesse
            - liberar_novo
            - invalido
        ids:
          type: array
          minItems: 1
          items:
            type: integer
            minimum: 1

    LeadsAtribuirRequest:
      type: object
      required:
        - ids
        - vendedores
      properties:
        ids:
          type: array
          minItems: 1
          items:
            type: integer
            minimum: 1
        vendedores:
          type: array
          minItems: 1
          items:
            type: integer
            minimum: 1
        equipes:
          type: array
          nullable: true
          items:
            type: integer
            minimum: 1

    LeadVerificarResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            id:
              type: integer
            atendente:
              type: integer
              nullable: true
            atendimento:
              type: string
              nullable: true
        msg:
          type: string
          nullable: true

    TakeResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            taken:
              type: array
              items:
                type: integer
            skipped:
              type: array
              items:
                type: object
                additionalProperties: true
            msg:
              type: string
              nullable: true
        msg:
          type: string
          nullable: true

    TakeBulkRequest:
      type: object
      required:
        - ids
      properties:
        ids:
          type: array
          minItems: 1
          items:
            type: integer
            minimum: 1
        max:
          type: integer
          minimum: 1
          nullable: true

    TakeBulkResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            taken:
              type: array
              items:
                type: integer
            skipped:
              type: array
              items:
                type: object
                additionalProperties: true
        msg:
          type: string
          nullable: true

    ConviteCriarResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            token:
              type: string
        msg:
          type: string
          nullable: true

    ConviteAceitarResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            id_lead:
              type: integer
        msg:
          type: string
          nullable: true

    InviteCreateAliasResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            token:
              type: string
            url:
              type: string
        msg:
          type: string
          nullable: true

    InviteListResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            rows:
              type: array
              items:
                $ref: "#/components/schemas/InviteRow"
        msg:
          type: string
          nullable: true

    InviteRow:
      type: object
      properties:
        id:
          type: integer
        id_lead:
          type: integer
        token:
          type: string
        status:
          type: string
        sent_at:
          type: string
          format: date-time
          nullable: true
        accepted_at:
          type: string
          format: date-time
          nullable: true
        expires_at:
          type: string
          format: date-time
          nullable: true
        created_at:
          type: string
          format: date-time
          nullable: true

    ImportCriarResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            import_id:
              type: integer
        msg:
          type: string
          nullable: true

    ImportProcessarResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            criados:
              type: integer
            vinculados:
              type: integer
            ignorados:
              type: integer
            erros:
              type: integer
        msg:
          type: string
          nullable: true

    ImportPreviewRequest:
      type: object
      required:
        - contrato
        - nome_lote
        - csv_text
      properties:
        contrato:
          type: integer
          minimum: 1
        nome_lote:
          type: string
          minLength: 2
          maxLength: 120
        csv_text:
          type: string
          minLength: 1

    ImportPreviewResponse:
      type: object
      properties:
        __status:
          type: integer
        ok:
          type: integer
          enum:
            - 0
            - 1
        data:
          type: object
          properties:
            import_id:
              type: integer
            stats:
              type: object
              properties:
                novo:
                  type: integer
                vincular:
                  type: integer
                erro:
                  type: integer
            preview:
              type: array
              items:
                type: object
                properties:
                  row:
                    type: object
                    additionalProperties: true
                  status:
                    type: string
                  motivo:
                    type: string
                    nullable: true
        msg:
          type: string
          nullable: true

    ImportCommitRequest:
      type: object
      required:
        - import_id
        - contrato
      properties:
        import_id:
          type: integer
          minimum: 1
        contrato:
          type: integer
          minimum: 1
        default_status:
          type: string
          nullable: true
          enum:
            - em_espera
            - novo
            - aguardando