openapi: 3.1.0
info:
  title: Revorian — Insider Trading Intelligence API
  description: |
    Real-time and historical SEC Form 4 insider trading data for US public companies.
    Track insider buys, sells, and signals. 1.3M+ transactions, 7,000+ companies,
    75,000+ insiders. Updated in real-time as filings hit SEC EDGAR.

    Free tier: 100 requests/day, 7 days of history.
    Paid plans from $49/mo for full historical access.

    ## Quick Start
    The feed endpoints are free and require no authentication:
    ```
    curl https://api.revorian.com/v1/feed
    ```

    For authenticated endpoints, include your API key:
    ```
    curl -H "Authorization: Bearer rev_live_sk_..." https://api.revorian.com/v1/transactions?ticker=TSLA
    ```
  version: 1.0.0
  contact:
    name: Revorian
    url: https://revorian.com
    email: api@revorian.com
servers:
  - url: https://api.revorian.com/v1
    description: Production

paths:
  # ── Public Endpoints (no auth required) ──

  /feed:
    get:
      operationId: getInsiderTradingFeed
      summary: Get real-time insider trading feed
      description: |
        Returns recent SEC Form 4 insider transactions — open market buys and sells
        by corporate officers, directors, and 10% owners. Free, rate-limited to 60 req/min per IP.
      tags: [Feed]
      parameters:
        - name: type
          in: query
          description: Filter by transaction direction
          schema:
            type: string
            enum: [buy, sell]
        - name: min_value
          in: query
          description: Minimum transaction dollar value
          schema:
            type: integer
        - name: include_grants
          in: query
          description: Include grant/award transactions (default false, shows only open-market P/S)
          schema:
            type: boolean
            default: false
        - name: sort
          in: query
          description: Sort field
          schema:
            type: string
            enum: [date, value, significance]
            default: date
        - name: order
          in: query
          schema:
            type: string
            enum: [asc, desc]
            default: desc
        - name: sector
          in: query
          description: Filter by company sector (e.g., Technology, Healthcare)
          schema:
            type: string
        - name: ceo_cfo
          in: query
          description: Only show CEO/CFO transactions
          schema:
            type: boolean
        - name: today_only
          in: query
          description: Only show filings from today
          schema:
            type: boolean
        - name: limit
          in: query
          schema:
            type: integer
            default: 30
            maximum: 100
        - name: offset
          in: query
          schema:
            type: integer
            default: 0
      responses:
        "200":
          description: Paginated list of insider transactions
          content:
            application/json:
              schema:
                $ref: "#/components/schemas/FeedResponse"

  /feed/top-today:
    get:
      operationId: getTopTradesToday
      summary: Get top 5 insider trades by value today
      description: Returns the 5 largest open-market insider transactions filed today. Free, 60 req/min.
      tags: [Feed]
      responses:
        "200":
          description: Top transactions today
          content:
            application/json:
              schema:
                type: object
                properties:
                  success:
                    type: boolean
                  data:
                    type: object
                    properties:
                      transactions:
                        type: array
                        items:
                          $ref: "#/components/schemas/FeedTransaction"

  /feed/sectors:
    get:
      operationId: getSectorList
      summary: Get list of company sectors
      description: Returns distinct sector names for filtering. Cached 1 hour.
      tags: [Feed]
      responses:
        "200":
          description: Sector list
          content:
            application/json:
              schema:
                type: object
                properties:
                  success:
                    type: boolean
                  data:
                    type: object
                    properties:
                      sectors:
                        type: array
                        items:
                          type: string

  /feed/signals:
    get:
      operationId: getRecentSignals
      summary: Get recent insider trading signals
      description: |
        Returns AI-detected patterns: cluster buying/selling, unusual trade sizes,
        large liquidations, CEO/CFO sales. Free, 30 req/min.
      tags: [Feed]
      parameters:
        - name: type
          in: query
          schema:
            type: string
            enum: [cluster_sell, cluster_buy, unusual_size, large_liquidation, ceo_sell, cfo_sell, first_time_buy, first_time_sell]
        - name: severity
          in: query
          schema:
            type: string
            enum: [critical, high, medium]
        - name: limit
          in: query
          schema:
            type: integer
            default: 10
      responses:
        "200":
          description: Recent signals
          content:
            application/json:
              schema:
                type: object
                properties:
                  success:
                    type: boolean
                  data:
                    type: object
                    properties:
                      signals:
                        type: array
                        items:
                          $ref: "#/components/schemas/Signal"

  /feed/companies/{ticker}:
    get:
      operationId: getPublicCompanyProfile
      summary: Get company insider trading profile
      description: Returns company info and last 30 days of open-market insider transactions. Free, 60 req/min.
      tags: [Feed]
      parameters:
        - name: ticker
          in: path
          required: true
          schema:
            type: string
          example: TSLA
      responses:
        "200":
          description: Company profile with recent transactions
          content:
            application/json:
              schema:
                type: object
                properties:
                  success:
                    type: boolean
                  data:
                    type: object
                    properties:
                      company:
                        $ref: "#/components/schemas/Company"
                      transactions:
                        type: array
                        items:
                          $ref: "#/components/schemas/CompanyTransaction"

  /feed/transaction/{id}:
    get:
      operationId: getPublicTransactionDetail
      summary: Get single transaction detail
      description: Returns full detail for one insider transaction including signals, filing URLs, and ownership info. Free, 60 req/min.
      tags: [Feed]
      parameters:
        - name: id
          in: path
          required: true
          schema:
            type: integer
      responses:
        "200":
          description: Transaction detail
          content:
            application/json:
              schema:
                type: object
                properties:
                  success:
                    type: boolean
                  data:
                    $ref: "#/components/schemas/TransactionDetail"

  /feed/insiders/{cik}:
    get:
      operationId: getPublicInsiderProfile
      summary: Get insider profile and recent trades
      description: Returns insider info and their most recent transactions across all companies. Free, 60 req/min.
      tags: [Feed]
      parameters:
        - name: cik
          in: path
          required: true
          schema:
            type: string
        - name: limit
          in: query
          schema:
            type: integer
            default: 10
            maximum: 50
      responses:
        "200":
          description: Insider profile with transactions

  /feed/search:
    get:
      operationId: searchTickers
      summary: Ticker/company autocomplete search
      description: Search companies by ticker or name. Returns up to 8 matches. Free, 120 req/min.
      tags: [Feed]
      parameters:
        - name: q
          in: query
          required: true
          description: Search query (ticker or company name)
          schema:
            type: string
      responses:
        "200":
          description: Matching companies

  # ── Authenticated Endpoints ──

  /transactions:
    get:
      operationId: searchInsiderTransactions
      summary: Search insider transactions with full filters
      description: |
        Full search across 1.3M+ insider transactions. Filter by ticker, insider name,
        transaction type, date range, value range, significance level. 1 credit per request.
      tags: [Transactions]
      security:
        - apiKey: []
      parameters:
        - name: ticker
          in: query
          description: Company ticker symbol (e.g., TSLA, AAPL)
          schema:
            type: string
        - name: insider_name
          in: query
          description: Insider name (partial match)
          schema:
            type: string
        - name: transaction_code
          in: query
          description: "P=Purchase, S=Sale, A=Grant, M=Option exercise"
          schema:
            type: string
            enum: [P, S, A, M, F, D, G]
        - name: min_value
          in: query
          schema:
            type: integer
        - name: max_value
          in: query
          schema:
            type: integer
        - name: from_date
          in: query
          schema:
            type: string
            format: date
        - name: to_date
          in: query
          schema:
            type: string
            format: date
        - name: is_officer
          in: query
          schema:
            type: boolean
        - name: significance
          in: query
          schema:
            type: string
            enum: [critical, high, medium]
        - name: signals
          in: query
          description: Filter by signal type
          schema:
            type: string
        - name: sort
          in: query
          schema:
            type: string
            enum: [date, value, significance]
            default: date
        - name: limit
          in: query
          schema:
            type: integer
            default: 20
            maximum: 100
        - name: offset
          in: query
          schema:
            type: integer
            default: 0
      responses:
        "200":
          description: Paginated transactions

  /transactions/{id}:
    get:
      operationId: getTransactionById
      summary: Get transaction by ID
      tags: [Transactions]
      security:
        - apiKey: []
      parameters:
        - name: id
          in: path
          required: true
          schema:
            type: integer
      responses:
        "200":
          description: Transaction detail

  /companies/{ticker}/transactions:
    get:
      operationId: getCompanyTransactions
      summary: Get all insider transactions for a company
      description: Returns filtered insider transactions for a specific company. 1 credit per request.
      tags: [Companies]
      security:
        - apiKey: []
      parameters:
        - name: ticker
          in: path
          required: true
          schema:
            type: string
        - name: transaction_code
          in: query
          schema:
            type: string
            enum: [P, S, A, M, F, D, G]
        - name: from_date
          in: query
          schema:
            type: string
            format: date
        - name: to_date
          in: query
          schema:
            type: string
            format: date
        - name: min_value
          in: query
          schema:
            type: integer
        - name: limit
          in: query
          schema:
            type: integer
            default: 20
        - name: offset
          in: query
          schema:
            type: integer
            default: 0
      responses:
        "200":
          description: Company transactions

  /companies/{ticker}/summary:
    get:
      operationId: getCompanyInsiderSummary
      summary: Get insider trading summary for a company
      description: |
        Returns 30-day, 90-day, and 365-day insider trading summaries: total buys,
        total sells, net position, active insiders, and top traders. 1 credit per request.
      tags: [Companies]
      security:
        - apiKey: []
      parameters:
        - name: ticker
          in: path
          required: true
          schema:
            type: string
          example: AAPL
      responses:
        "200":
          description: Company insider summary

  /insiders/{cik}/transactions:
    get:
      operationId: getInsiderTransactions
      summary: Get insider's full trading history
      description: Returns all transactions by a specific insider across all companies. 1 credit per request.
      tags: [Insiders]
      security:
        - apiKey: []
      parameters:
        - name: cik
          in: path
          required: true
          schema:
            type: string
        - name: from_date
          in: query
          schema:
            type: string
            format: date
        - name: to_date
          in: query
          schema:
            type: string
            format: date
        - name: limit
          in: query
          schema:
            type: integer
            default: 20
        - name: offset
          in: query
          schema:
            type: integer
            default: 0
      responses:
        "200":
          description: Insider transactions

  /signals:
    get:
      operationId: searchSignals
      summary: Search trading signals
      description: Search detected insider trading signals with filters. 1 credit per request.
      tags: [Signals]
      security:
        - apiKey: []
      parameters:
        - name: type
          in: query
          schema:
            type: string
            enum: [cluster_sell, cluster_buy, unusual_size, large_liquidation, ceo_sell, cfo_sell, first_time_buy, first_time_sell]
        - name: severity
          in: query
          schema:
            type: string
            enum: [critical, high, medium]
        - name: ticker
          in: query
          schema:
            type: string
        - name: from_date
          in: query
          schema:
            type: string
            format: date
        - name: to_date
          in: query
          schema:
            type: string
            format: date
        - name: limit
          in: query
          schema:
            type: integer
            default: 20
        - name: offset
          in: query
          schema:
            type: integer
            default: 0
      responses:
        "200":
          description: Signals list

  /signals/clusters:
    get:
      operationId: getClusterSignals
      summary: Get cluster buy/sell signals
      description: |
        Detects when 3+ insiders at the same company trade within a short window.
        One of the strongest insider trading signals. 2 credits per request.
      tags: [Signals]
      security:
        - apiKey: []
      parameters:
        - name: direction
          in: query
          description: Filter by buy or sell clusters
          schema:
            type: string
            enum: [buy, sell]
        - name: min_insiders
          in: query
          description: Minimum number of insiders (default 3)
          schema:
            type: integer
            default: 3
        - name: days
          in: query
          description: Lookback window in days (default 7)
          schema:
            type: integer
            default: 7
        - name: limit
          in: query
          schema:
            type: integer
            default: 20
      responses:
        "200":
          description: Cluster signals

  /stats/sector-sentiment:
    get:
      operationId: getSectorSentiment
      summary: Get insider sentiment by sector
      description: Aggregate insider buy/sell ratios across sectors. 2 credits per request.
      tags: [Stats]
      security:
        - apiKey: []
      parameters:
        - name: days
          in: query
          description: Lookback window in days (default 30)
          schema:
            type: integer
            default: 30
      responses:
        "200":
          description: Sector sentiment data

  /stats/top-buys:
    get:
      operationId: getTopBuys
      summary: Get largest insider purchases
      description: Ranked list of the largest insider purchases by dollar value. 1 credit per request.
      tags: [Stats]
      security:
        - apiKey: []
      parameters:
        - name: days
          in: query
          schema:
            type: integer
            default: 7
        - name: limit
          in: query
          schema:
            type: integer
            default: 10
      responses:
        "200":
          description: Top buys

  /stats/top-sells:
    get:
      operationId: getTopSells
      summary: Get largest insider sales
      description: Ranked list of the largest insider sales by dollar value. 1 credit per request.
      tags: [Stats]
      security:
        - apiKey: []
      parameters:
        - name: days
          in: query
          schema:
            type: integer
            default: 7
        - name: limit
          in: query
          schema:
            type: integer
            default: 10
      responses:
        "200":
          description: Top sells

  /watchlists:
    get:
      operationId: listWatchlists
      summary: List watchlist entries
      description: Get all tickers on your watchlist with alert settings.
      tags: [Watchlists]
      security:
        - apiKey: []
      responses:
        "200":
          description: Watchlist entries
    post:
      operationId: addToWatchlist
      summary: Add a company to your watchlist
      description: Track a company and receive webhook/email alerts when insiders trade.
      tags: [Watchlists]
      security:
        - apiKey: []
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [ticker]
              properties:
                ticker:
                  type: string
                  example: TSLA
                webhook_url:
                  type: string
                  format: uri
                webhook_secret:
                  type: string
                notify_email:
                  type: boolean
                min_significance:
                  type: string
                  enum: [critical, high, medium, normal]
      responses:
        "201":
          description: Watchlist entry created

  /watchlists/{id}:
    delete:
      operationId: removeFromWatchlist
      summary: Remove a company from your watchlist
      tags: [Watchlists]
      security:
        - apiKey: []
      parameters:
        - name: id
          in: path
          required: true
          schema:
            type: integer
      responses:
        "200":
          description: Watchlist entry removed

components:
  securitySchemes:
    apiKey:
      type: http
      scheme: bearer
      description: "API key with prefix rev_live_sk_. Get one at https://revorian.com/signup"

  schemas:
    FeedResponse:
      type: object
      properties:
        success:
          type: boolean
        data:
          type: object
          properties:
            transactions:
              type: array
              items:
                $ref: "#/components/schemas/FeedTransaction"
            total:
              type: integer

    FeedTransaction:
      type: object
      properties:
        id:
          type: integer
        accessionNumber:
          type: string
        filingDate:
          type: string
          format: date-time
        transactionDate:
          type: string
          format: date
        transactionCode:
          type: string
          description: "P=Purchase, S=Sale, A=Grant, M=Option exercise, F=Tax withholding"
          example: P
        acquiredDisposed:
          type: string
          enum: [A, D]
        shares:
          type: string
          example: "10000"
        pricePerShare:
          type: string
          example: "248.30"
        totalValue:
          type: string
          example: "2483000"
        significance:
          type: string
          enum: [critical, high, medium, normal, low]
        isOfficer:
          type: boolean
        officerTitle:
          type: string
          example: CEO
        filingUrl:
          type: string
          format: uri
        companyTicker:
          type: string
          example: TSLA
        companyName:
          type: string
          example: "Tesla, Inc."
        companyExchange:
          type: string
          example: NASDAQ
        insiderName:
          type: string
          example: "Musk Elon"
        insiderCik:
          type: string

    TransactionDetail:
      allOf:
        - $ref: "#/components/schemas/FeedTransaction"
        - type: object
          properties:
            sharesOwnedAfter:
              type: string
            ownershipType:
              type: string
            signals:
              type: array
              items:
                type: string
              example: ["cluster_sell", "unusual_size"]
            isDirector:
              type: boolean
            isTenPercentOwner:
              type: boolean
            rawXmlUrl:
              type: string
              format: uri
            companyCik:
              type: string
            companySector:
              type: string

    Company:
      type: object
      properties:
        id:
          type: integer
        ticker:
          type: string
        name:
          type: string
        cik:
          type: string
        exchange:
          type: string
        sector:
          type: string

    CompanyTransaction:
      type: object
      properties:
        id:
          type: integer
        filingDate:
          type: string
          format: date-time
        transactionDate:
          type: string
          format: date
        transactionCode:
          type: string
        acquiredDisposed:
          type: string
        shares:
          type: string
        pricePerShare:
          type: string
        totalValue:
          type: string
        significance:
          type: string
        isOfficer:
          type: boolean
        officerTitle:
          type: string
        insiderName:
          type: string
        insiderCik:
          type: string

    Signal:
      type: object
      properties:
        id:
          type: integer
        signalType:
          type: string
          enum: [cluster_sell, cluster_buy, unusual_size, large_liquidation, ceo_sell, cfo_sell, first_time_buy, first_time_sell]
        description:
          type: string
        severity:
          type: string
          enum: [critical, high, medium]
        transactionIds:
          type: array
          items:
            type: integer
        metadata:
          type: object
        detectedAt:
          type: string
          format: date-time
        companyTicker:
          type: string
        companyName:
          type: string
