openapi: 3.0.3
info:
  title: FinanceGPT Enterprise API
  version: 2.0.0
  description: >-
    Workspace-scoped FinanceGPT and EquityGPT intelligence API. Production and sandbox
    credentials are separate. Sandbox requests return deterministic fixtures and never read
    production workspace records.
servers:
  - url: https://financegpt.tools/api/v2
    description: FinanceGPT deployment
security:
  - bearerAuth: []
paths:
  /oauth/token:
    post:
      security: []
      summary: Issue an OAuth 2.0 client-credentials service token
      requestBody:
        required: true
        content:
          application/x-www-form-urlencoded:
            schema:
              type: object
              required: [grant_type, client_id, client_secret]
              properties:
                grant_type: {type: string, enum: [client_credentials]}
                client_id: {type: string}
                client_secret: {type: string, format: password}
                scope: {type: string, description: Space-delimited subset of the client's scopes.}
      responses:
        '200': {description: Access token issued}
        '400': {description: Invalid grant or scope}
        '401': {description: Invalid client}
        '403': {description: API entitlement unavailable}
  /workspace:
    get:
      summary: Get the credential's FinanceGPT workspace
      x-financegpt-scope: workspace:read
      responses: {'200': {description: Workspace}}
  /agents/tools:
    get:
      summary: List FinanceGPT MCP tools and credential grant state
      x-financegpt-scope: agents:mcp:read
      responses: {'200': {description: Agent tool catalogue}}
  /agents/invocations:
    get:
      summary: List hash-only MCP invocation audit metadata for this agent credential
      x-financegpt-scope: agents:mcp:read
      parameters:
        - {in: query, name: limit, schema: {type: integer, minimum: 1, maximum: 100, default: 25}}
      responses: {'200': {description: Agent invocation audit rows}}
  /financial/snapshots:
    get:
      summary: List normalized connected financial snapshots
      x-financegpt-scope: financial:read
      parameters:
        - {in: query, name: provider, schema: {type: string}}
        - {in: query, name: from, schema: {type: string, format: date}}
        - {in: query, name: to, schema: {type: string, format: date}}
        - {in: query, name: after_id, schema: {type: integer}}
        - {in: query, name: limit, schema: {type: integer, minimum: 1, maximum: 100, default: 50}}
      responses: {'200': {description: Financial snapshots}}
  /financial/transactions:
    get:
      summary: List normalized connected financial transactions
      x-financegpt-scope: financial:read
      parameters:
        - {in: query, name: provider, schema: {type: string}}
        - {in: query, name: direction, schema: {type: string}}
        - {in: query, name: status, schema: {type: string}}
        - {in: query, name: from, schema: {type: string, format: date}}
        - {in: query, name: to, schema: {type: string, format: date}}
        - {in: query, name: after_id, schema: {type: integer}}
        - {in: query, name: limit, schema: {type: integer, minimum: 1, maximum: 200, default: 100}}
      responses: {'200': {description: Financial transactions}}
  /planning/forecasts:
    get:
      summary: List governed FinanceGPT forecasts
      x-financegpt-scope: planning:read
      responses: {'200': {description: Forecasts}}
    post:
      summary: Generate and persist a backtest-selected forecast
      x-financegpt-scope: planning:forecast:create
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [metric]
              properties:
                metric: {type: string}
                company_id: {type: integer, nullable: true}
                horizon: {type: integer, minimum: 1, maximum: 24, default: 6}
                reason: {type: string, maxLength: 191}
      responses:
        '201': {description: Forecast generated}
        '422': {description: Insufficient history or invalid input}
  /workflows/runs:
    get:
      summary: List finance workflow runs, task status and reporting-pack status
      x-financegpt-scope: workflow:read
      responses: {'200': {description: Workflow runs}}
  /investment/companies/{symbol}:
    get:
      summary: Read governed Company 360 investment evidence
      x-financegpt-scope: investment:read
      parameters: [{in: path, name: symbol, required: true, schema: {type: string}}]
      responses: {'200': {description: Company profile and evidence available to the workspace}}
  /investment/portfolios/{portfolio}/construct:
    post:
      summary: Run governed quantitative portfolio construction
      x-financegpt-scope: investment:run
      parameters: [{in: path, name: portfolio, required: true, schema: {type: string}}]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [symbols]
              properties:
                symbols: {type: array, minItems: 2, maxItems: 30, items: {type: string}}
                restricted_symbols: {type: array, maxItems: 30, items: {type: string}}
                objective: {type: string, enum: [balanced, min_volatility, max_expected_return]}
                max_position_pct: {type: number, minimum: 1, maximum: 100}
                risk_aversion: {type: number, minimum: 0.01, maximum: 100}
                history_months: {type: integer, minimum: 12, maximum: 120}
                create_model_portfolio: {type: boolean}
                model_name: {type: string, maxLength: 191}
                benchmark_symbol: {type: string, maxLength: 32}
      responses:
        '201': {description: Construction evidence created; no order placed}
        '422': {description: Invalid input or insufficient governed market evidence}
  /investment/portfolios/{portfolio}/scenarios:
    post:
      summary: Run a deterministic governed portfolio stress scenario
      x-financegpt-scope: investment:run
      parameters: [{in: path, name: portfolio, required: true, schema: {type: string}}]
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              properties:
                global_price_pct: {type: number, minimum: -100, maximum: 1000}
                symbols: {type: object, additionalProperties: {type: number}}
                factors: {type: object, additionalProperties: {type: number}}
      responses: {'201': {description: Scenario run with source and result hashes}}
  /investment/portfolios/{portfolio}/tax-lots:
    get:
      summary: List governed tax-lot records for an adopted portfolio
      x-financegpt-scope: investment:read
      parameters: [{in: path, name: portfolio, required: true, schema: {type: string}}]
      responses: {'200': {description: Tax lots and verification provenance}}
  /investment/portfolios/{portfolio}/tax-harvest:
    post:
      summary: Create a tax-harvest proposal without executing a trade
      x-financegpt-scope: investment:run
      parameters: [{in: path, name: portfolio, required: true, schema: {type: string}}]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [tax_regime]
              properties:
                tax_regime: {type: string, maxLength: 80}
                jurisdiction: {type: string, maxLength: 80}
                tax_rate_pct: {type: number, minimum: 0, maximum: 100}
                minimum_loss_usd: {type: number, minimum: 0}
                restriction_window_days: {type: integer, minimum: 0, maximum: 366}
                replacement_symbols: {type: array, items: {type: string}}
      responses: {'201': {description: Draft tax-harvest proposal; financial_action_executed is false}}
  /investment/execution/batches:
    get:
      summary: List governed investment execution batches
      x-financegpt-scope: investment:read
      responses: {'200': {description: Workspace execution batches and reconciliation state}}
    post:
      summary: Create an execution batch from an approved rebalance proposal
      x-financegpt-scope: investment:execute
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [rebalance_proposal_id, connector_id]
              properties:
                rebalance_proposal_id: {type: integer}
                connector_id: {type: integer}
                autonomy_mandate_uid: {type: string, format: uuid}
      responses: {'201': {description: Execution batch created; approval or mandate boundaries still apply}}
  /investment/execution/batches/{uid}/submit:
    post:
      summary: Submit an investment order batch for approval
      x-financegpt-scope: investment:execute
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Batch submitted for approval}}
  /investment/execution/batches/{uid}/execute:
    post:
      summary: Execute an approved governed investment order batch
      x-financegpt-scope: investment:execute
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses:
        '200': {description: Provider submission result or sandbox simulation}
        '422': {description: Rejected or uncertain execution outcome}
  /investment/execution/batches/{uid}/reconcile:
    post:
      summary: Reconcile an investment execution batch with broker/custodian evidence
      x-financegpt-scope: investment:execute
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Reconciled execution state}}
  /investment/risk:
    get:
      summary: List EquityGPT Professional risk snapshots
      x-financegpt-scope: investment:read
      parameters:
        - {in: query, name: portfolio_id, schema: {type: string}}
        - {in: query, name: limit, schema: {type: integer, minimum: 1, maximum: 100, default: 20}}
      responses: {'200': {description: Investment risk snapshots}}
  /investment/reports:
    get:
      summary: List approved/finalized investment client reports
      x-financegpt-scope: investment:read
      responses: {'200': {description: Approved client reports}}
  /benchmarking/comparisons:
    get:
      summary: List published privacy-safe benchmark comparisons
      x-financegpt-scope: benchmark:read
      parameters:
        - {in: query, name: period_key, schema: {type: string}}
        - {in: query, name: metric_key, schema: {type: string}}
      responses: {'200': {description: Published comparisons only}}
  /intelligence/summary:
    get:
      summary: Retrieve an embedded cross-domain FinanceGPT intelligence summary
      x-financegpt-scope: intelligence:read
      responses: {'200': {description: Workspace intelligence summary}}
  /ml/models:
    get:
      summary: List approved active FinanceGPT ML model cards available to the workspace
      x-financegpt-scope: ml:read
      responses: {'200': {description: Active model registry}}
  /ml/anomaly:
    post:
      summary: Run approved financial anomaly inference on the latest synchronized derived feature vector
      x-financegpt-scope: ml:inference
      responses:
        '201': {description: Anomaly inference result}
        '409': {description: Approved model or synchronized features unavailable}
  /ml/scenarios:
    post:
      summary: Generate model-sampled financial stress scenarios from an approved VAE
      x-financegpt-scope: ml:inference
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              properties:
                samples: {type: integer, minimum: 1, maximum: 20, default: 5}
                stress: {type: object, additionalProperties: {type: number}}
      responses:
        '201': {description: Generated scenario samples; not forecasts or probabilities}
        '409': {description: Approved model or synchronized features unavailable}
  /data/datasets:
    get:
      summary: List datasets currently licensed for FinanceGPT API redistribution
      x-financegpt-scope: data:reference:read
      responses: {'200': {description: Redistributable dataset catalogue}}
  /data/instruments:
    get:
      summary: Search the canonical FinanceGPT securities master
      x-financegpt-scope: data:reference:read
      responses: {'200': {description: Canonical instruments}}
  /data/instruments/{uid}:
    get:
      summary: Get a canonical instrument, issuer, venue and identifiers
      x-financegpt-scope: data:reference:read
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Instrument profile}}
  /data/instruments/{uid}/prices:
    get:
      summary: Get licence-governed normalized price history
      x-financegpt-scope: data:market:read
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Price bars with provenance}}
  /data/instruments/{uid}/fundamentals:
    get:
      summary: Get standardized fundamental facts
      x-financegpt-scope: data:fundamentals:read
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Fundamental facts with provenance}}
  /data/instruments/{uid}/corporate-actions:
    get:
      summary: Get normalized corporate actions
      x-financegpt-scope: data:market:read
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Corporate actions}}
  /data/economics/series:
    get:
      summary: Search licence-governed economic series
      x-financegpt-scope: data:economics:read
      responses: {'200': {description: Economic series}}
  /data/economics/series/{key}:
    get:
      summary: Get an economic series profile
      x-financegpt-scope: data:economics:read
      parameters: [{in: path, name: key, required: true, schema: {type: string}}]
      responses: {'200': {description: Economic series profile}}
  /data/economics/series/{key}/observations:
    get:
      summary: Get economic observations and vintages
      x-financegpt-scope: data:economics:read
      parameters: [{in: path, name: key, required: true, schema: {type: string}}]
      responses: {'200': {description: Economic observations with vintages}}
  /quant/features:
    get:
      summary: List governed FinanceGPT point-in-time feature definitions
      x-financegpt-scope: quant:features:read
      responses: {'200': {description: Feature catalogue}}
  /quant/features/{key}:
    get:
      summary: Get one governed financial feature definition
      x-financegpt-scope: quant:features:read
      parameters: [{in: path, name: key, required: true, schema: {type: string}}]
      responses: {'200': {description: Feature definition and methodology}}
  /quant/features/{key}/values:
    get:
      summary: Get look-ahead-safe API-releasable feature values for a canonical instrument
      x-financegpt-scope: quant:features:read
      parameters:
        - {in: path, name: key, required: true, schema: {type: string}}
        - {in: query, name: instrument_uid, required: true, schema: {type: string, format: uuid}}
      responses: {'200': {description: Point-in-time feature values with lineage}}
  /quant/projects:
    get:
      summary: List workspace quantitative research projects
      x-financegpt-scope: quant:research:read
      responses: {'200': {description: Workspace research projects}}
  /quant/research/snapshots:
    post:
      summary: Generate a sealed point-in-time research feature matrix
      x-financegpt-scope: quant:research:run
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [project_id, as_of_date]
              properties:
                project_id: {type: integer}
                as_of_date: {type: string, format: date}
      responses: {'201': {description: Sealed research snapshot}}
  /quant/research/snapshots/{uid}:
    get:
      summary: Retrieve a sealed research snapshot and its point-in-time feature rows
      x-financegpt-scope: quant:research:read
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Sealed snapshot and feature matrix}}
  /quant/research/runs:
    post:
      summary: Run a governed feature-quality experiment against a sealed snapshot
      x-financegpt-scope: quant:research:run
      responses: {'201': {description: Reproducible experiment result}}
  /quant/models:
    get:
      summary: List validated deterministic FinanceGPT quantitative models
      x-financegpt-scope: quant:models:read
      responses: {'200': {description: Quantitative model registry and active model cards}}
  /quant/models/{key}:
    get:
      summary: Get one quantitative model card, schema, methodology and validation evidence
      x-financegpt-scope: quant:models:read
      parameters: [{in: path, name: key, required: true, schema: {type: string}}]
      responses: {'200': {description: Quantitative model card}}
  /quant/models/{key}/run:
    post:
      summary: Execute a validated deterministic quantitative model
      x-financegpt-scope: quant:models:run
      parameters: [{in: path, name: key, required: true, schema: {type: string}}]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [input]
              properties:
                input: {type: object, additionalProperties: true}
      responses:
        '201': {description: Versioned model output with reproducibility hashes}
        '422': {description: Invalid model input}
  /quant/model-runs:
    get:
      summary: Read workspace quantitative-model execution history
      x-financegpt-scope: quant:models:read
      parameters: [{in: query, name: limit, schema: {type: integer, minimum: 1, maximum: 100, default: 25}}]
      responses: {'200': {description: Workspace model execution history without decrypted model inputs}}
  /quant/statistical-models:
    get:
      summary: List FinanceGPT forecasting, econometrics, volatility, factor and statistical-risk models
      x-financegpt-scope: quant:models:read
      responses: {'200': {description: M19 statistical model registry cards}}
  /quant/model-tournaments:
    get:
      summary: List workspace forecast-model tournaments
      x-financegpt-scope: quant:models:read
      parameters: [{in: query, name: limit, schema: {type: integer, minimum: 1, maximum: 100, default: 25}}]
      responses: {'200': {description: Workspace tournament history}}
    post:
      summary: Run a governed holdout forecast-model tournament
      x-financegpt-scope: quant:models:run
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [series]
              properties:
                series: {type: array, minItems: 12, maxItems: 5000, items: {type: number}}
                name: {type: string}
                holdout: {type: integer, minimum: 2, maximum: 120}
                forecast_horizon: {type: integer, minimum: 1, maximum: 60}
                metric: {type: string, enum: [mae, rmse, mape]}
                candidate_models: {type: array, minItems: 2, maxItems: 6, items: {type: string}}
      responses:
        '201': {description: Completed tournament with candidate errors and selected forecast}
        '422': {description: Invalid tournament input or no successful candidates}
  /quant/model-tournaments/{uid}:
    get:
      summary: Retrieve one governed forecast-model tournament
      x-financegpt-scope: quant:models:read
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Tournament result and candidate evaluation metrics}}
  /generative/models:
    get:
      summary: List approved FinanceGPT generative financial models
      x-financegpt-scope: generative:models:read
      responses: {'200': {description: Approved model cards, algorithms, artifact hashes and evaluation evidence}}
  /generative/scenarios:
    post:
      summary: Generate reproducible regime-conditioned financial scenarios
      x-financegpt-scope: generative:inference
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [regime]
              properties:
                regime: {type: string, enum: [contraction, neutral, expansion]}
                samples: {type: integer, minimum: 1, maximum: 20, default: 5}
                seed: {type: integer, minimum: 0, maximum: 2147483647, default: 42}
                stress: {type: object, additionalProperties: {type: number}}
      responses:
        '201': {description: Seeded conditional scenario run with reproducibility hashes}
        '409': {description: Approved model or synchronized feature context unavailable}
  /generative/paths:
    post:
      summary: Generate reproducible multi-period synthetic financial stress paths
      x-financegpt-scope: generative:inference
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [regime]
              properties:
                regime: {type: string, enum: [contraction, neutral, expansion]}
                samples: {type: integer, minimum: 1, maximum: 20, default: 3}
                horizon: {type: integer, minimum: 1, maximum: 12, default: 6}
                seed: {type: integer, minimum: 0, maximum: 2147483647, default: 42}
                stress: {type: object, additionalProperties: {type: number}}
      responses:
        '201': {description: Seeded multi-period path run with model/version/source hashes}
        '409': {description: Approved time-series model or synchronized feature context unavailable}
  /generative/runs:
    get:
      summary: Read workspace generative-model run history
      x-financegpt-scope: generative:models:read
      parameters:
        - {in: query, name: limit, schema: {type: integer, minimum: 1, maximum: 100, default: 25}}
        - {in: query, name: type, schema: {type: string, enum: [conditional_scenario, time_series_path]}}
      responses: {'200': {description: Workspace-scoped run history with seeds and reproducibility hashes}}
  /generative/runs/{uid}:
    get:
      summary: Retrieve one reproducible generative finance run
      x-financegpt-scope: generative:models:read
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Generative run result, conditions, seed and hashes}}
  /quant/compute/jobs:
    get:
      summary: List workspace Quant Compute Cloud jobs
      x-financegpt-scope: quant:compute:read
      parameters:
        - {in: query, name: limit, schema: {type: integer, minimum: 1, maximum: 100, default: 25}}
        - {in: query, name: type, schema: {type: string, enum: [backtest, simulation, optimization]}}
      responses: {'200': {description: Durable compute job history without decrypted submission inputs}}
  /quant/compute/jobs/{uid}:
    get:
      summary: Retrieve one Quant Compute Cloud job and completed result
      x-financegpt-scope: quant:compute:read
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Workspace-scoped job status, hashes and completed result payload}}
  /quant/compute/backtests:
    post:
      summary: Queue a governed historical backtest
      x-financegpt-scope: quant:compute:run
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [input]
              properties:
                input: {type: object, additionalProperties: true}
                service_class: {type: string, nullable: true}
                region: {type: string, nullable: true}
      responses:
        '202': {description: Durable queued backtest job; poll the returned job URL}
        '422': {description: Invalid or oversized compute input}
  /quant/compute/simulations:
    post:
      summary: Queue a seeded Monte Carlo simulation
      x-financegpt-scope: quant:compute:run
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [input]
              properties:
                input: {type: object, additionalProperties: true}
                service_class: {type: string, nullable: true}
                region: {type: string, nullable: true}
      responses:
        '202': {description: Durable queued simulation job; poll the returned job URL}
        '422': {description: Invalid or oversized compute input}
  /quant/compute/optimizations:
    post:
      summary: Queue a bounded parameter-grid optimization over an approved FinanceGPT model
      x-financegpt-scope: quant:compute:run
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [input]
              properties:
                input: {type: object, additionalProperties: true}
                service_class: {type: string, nullable: true}
                region: {type: string, nullable: true}
      responses:
        '202': {description: Durable queued optimization job; poll the returned job URL}
        '422': {description: Invalid model, objective or parameter grid}
  /quant/compute/jobs/{uid}/cancel:
    post:
      summary: Cancel a queued Quant Compute Cloud job
      x-financegpt-scope: quant:compute:run
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses:
        '200': {description: Queued job cancelled}
        '409': {description: Running or terminal jobs cannot be cancelled}
  /infrastructure/posture:
    get:
      summary: Read workspace institutional compute and licensing posture
      x-financegpt-scope: infrastructure:read
      responses: {'200': {description: Service class, region policy, data grants and deployment-truth claims}}
  /infrastructure/service-classes:
    get:
      summary: List FinanceGPT compute service classes
      x-financegpt-scope: infrastructure:read
      responses: {'200': {description: Compute service classes and service-target metadata}}
  /infrastructure/regions:
    get:
      summary: List configured compute regions and explicit deployment state
      x-financegpt-scope: infrastructure:read
      responses: {'200': {description: Provisioned and planned region metadata}}
  /infrastructure/usage:
    get:
      summary: Read 30-day institutional compute telemetry
      x-financegpt-scope: infrastructure:read
      responses: {'200': {description: Queue, compute, unit and estimated-cost telemetry}}
  /infrastructure/data-entitlements:
    get:
      summary: Read workspace contractual data-entitlement overlays
      x-financegpt-scope: infrastructure:read
      responses: {'200': {description: Dataset use, region and jurisdiction grants}}
  /infrastructure/lineage-exports:
    post:
      summary: Create a sealed FinanceGPT lineage manifest
      x-financegpt-scope: infrastructure:lineage
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required: [scope_type]
              properties:
                scope_type: {type: string, enum: [workspace, compute_job, quant_model_run, ml_inference]}
                scope_id: {type: string, nullable: true}
      responses:
        '201': {description: SHA-256 sealed lineage export created}
        '422': {description: Unsupported scope or unknown governed record}
  /infrastructure/lineage-exports/{uid}:
    get:
      summary: Retrieve a sealed lineage manifest
      x-financegpt-scope: infrastructure:lineage
      parameters: [{in: path, name: uid, required: true, schema: {type: string, format: uuid}}]
      responses: {'200': {description: Lineage manifest without secrets or raw ML training data}}
  /marketplace/listings:
    get:
      summary: Discover verified marketplace APIs, models and datasets
      x-financegpt-scope: marketplace:read
      parameters:
        - {in: query, name: category, schema: {type: string}}
      responses:
        '200': {description: Platform-reviewed publisher listings and active commercial offers}
  /marketplace/{slug}/invoke:
    post:
      summary: Invoke an actively subscribed verified marketplace listing
      x-financegpt-scope: marketplace:invoke
      parameters:
        - {in: path, name: slug, required: true, schema: {type: string}}
      requestBody:
        required: false
        content:
          application/json:
            schema: {type: object, additionalProperties: true}
      responses:
        '200': {description: Publisher JSON response wrapped by the FinanceGPT gateway}
        '403': {description: Active marketplace subscription required}
        '429': {description: FinanceGPT or marketplace subscription request limit exceeded}
        '502': {description: Publisher upstream failed security or invocation checks}
  /companies:
    get:
      summary: List company-finance workspaces
      x-financegpt-scope: financial:analysis:read
      responses: {'200': {description: Companies with source and coverage metadata}}
  /companies/{company}:
    get:
      summary: Read company finance profile and data coverage
      x-financegpt-scope: financial:analysis:read
      parameters: [{in: path, name: company, required: true, schema: {type: integer}}]
      responses: {'200': {description: Company finance profile}}
  /companies/{company}/financials:
    get:
      summary: Read normalized financial periods with source provenance
      x-financegpt-scope: financial:analysis:read
      parameters: [{in: path, name: company, required: true, schema: {type: integer}}]
      responses: {'200': {description: Financial periods; unavailable values remain null}}
  /companies/{company}/ratios:
    get:
      summary: Read deterministic financial ratios
      x-financegpt-scope: financial:analysis:read
      parameters: [{in: path, name: company, required: true, schema: {type: integer}}]
      responses: {'200': {description: Liquidity, leverage, profitability, coverage and cash-flow ratios}}
  /companies/{company}/analysis:
    get:
      summary: Read company analysis, financial resilience, DCF and linked forecast
      x-financegpt-scope: financial:analysis:read
      parameters: [{in: path, name: company, required: true, schema: {type: integer}}]
      responses: {'200': {description: Deterministic analysis with methodology disclosures}}
  /companies/{company}/valuations:
    post:
      summary: Run free-cash-flow DCF valuation
      x-financegpt-scope: financial:analysis:run
      parameters: [{in: path, name: company, required: true, schema: {type: integer}}]
      requestBody:
        required: false
        content:
          application/json:
            schema:
              type: object
              properties:
                wacc: {type: number}
                terminal_growth: {type: number}
      responses:
        '201': {description: DCF result with explicit assumptions and sensitivity evidence}
        '422': {description: Insufficient free-cash-flow evidence or invalid assumptions}
  /companies/{company}/scenarios:
    post:
      summary: Run deterministic company revenue and expense scenarios
      x-financegpt-scope: financial:analysis:run
      parameters: [{in: path, name: company, required: true, schema: {type: integer}}]
      responses: {'201': {description: Scenario comparison against the latest recorded period}}
components:
  securitySchemes:
    bearerAuth:
      type: http
      scheme: bearer
      bearerFormat: FinanceGPT API key or OAuth service token
