{
  "openapi": "3.0.1",
  "info": {
    "title": "SBA Loan Portfolio Explorer API — 7(a) & 504 Rollups",
    "description": "SBA loan data API over the 7(a) and 504 FOIA loan-level files. Look up loans by state, NAICS industry, lender, fiscal year and amount; roll up by lender / industry / geography; and flag risk outliers (amount-per-job, charge-offs, lender concentration). Keyless.",
    "version": "1.0",
    "x-build-id": "wAEnJK7t1zUYMxxKO"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/malonestar~sba-loan-portfolio-explorer/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-malonestar-sba-loan-portfolio-explorer",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    },
    "/acts/malonestar~sba-loan-portfolio-explorer/runs": {
      "post": {
        "operationId": "runs-sync-malonestar-sba-loan-portfolio-explorer",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor and returns information about the initiated run in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/runsResponseSchema"
                }
              }
            }
          }
        }
      }
    },
    "/acts/malonestar~sba-loan-portfolio-explorer/run-sync": {
      "post": {
        "operationId": "run-sync-malonestar-sba-loan-portfolio-explorer",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "inputSchema": {
        "type": "object",
        "properties": {
          "program": {
            "title": "Loan program",
            "enum": [
              "all",
              "7a",
              "504"
            ],
            "type": "string",
            "description": "Which SBA loan program to query: '7a' (7(a) guaranteed loans), '504' (504/CDC loans), or 'all' for both. PPP is not included in v1 (PPP ships only as a multi-GB bulk file).",
            "default": "all"
          },
          "fiscalYear": {
            "title": "Approval fiscal year",
            "minimum": 1990,
            "maximum": 2100,
            "type": "integer",
            "description": "Restrict to loans approved in this SBA fiscal year (Oct 1-Sep 30). Also routes the query to only the FOIA file that covers this year. Leave empty for all years the selected files cover."
          },
          "state": {
            "title": "State (2-letter)",
            "type": "string",
            "description": "Filter to loans whose borrower OR project state equals this 2-letter code, e.g. 'CA', 'TX'. Empty = all states."
          },
          "naicsPrefix": {
            "title": "NAICS industry prefix",
            "type": "string",
            "description": "Keep only loans whose NAICS code starts with this prefix, e.g. '72' (accommodation & food services), '23' (construction). Empty = all industries."
          },
          "lenderName": {
            "title": "Lender name contains",
            "type": "string",
            "description": "Substring match (case-insensitive) on the funding bank / lender name (7(a) BankName or 504 third-party lender). Empty = all lenders."
          },
          "query": {
            "title": "Free-text search (borrower or lender name)",
            "type": "string",
            "description": "Case-insensitive substring match over the borrower name AND the lender name, e.g. 'acme diner' or 'wells fargo'. A row is kept if EITHER name contains the text. data.sba.gov has no query API, so this is applied while the published CSVs are streamed - it narrows the answer, it does not speed up the scan. Combined with the other filters using AND. Empty = no free-text filter. Every emitted row reports query_applied so you can see it was honoured."
          },
          "sinceDate": {
            "title": "Approved on/after (YYYY-MM-DD)",
            "pattern": "^$|^\\d{4}-\\d{1,2}-\\d{1,2}$",
            "type": "string",
            "description": "Only return loans with approval_date on or after this date. MUST be YYYY-MM-DD (e.g. 2023-01-15) - any other format is rejected and the run FAILS without billing, rather than silently returning the whole portfolio or none of it. It is string-compared against ISO approval dates, so a wrong format is invisible in the output: '01/15/2023' returned every loan and 'Jan 2023' returned none, both labelled as a successful filtered answer. Slash forms are rejected on purpose - 05/06/2025 is ambiguous between US and EU order. Empty = no lower bound."
          },
          "untilDate": {
            "title": "Approved on/before (YYYY-MM-DD)",
            "pattern": "^$|^\\d{4}-\\d{1,2}-\\d{1,2}$",
            "type": "string",
            "description": "Only return loans with approval_date on or before this date. MUST be YYYY-MM-DD (e.g. 2023-12-31) - any other format is rejected and the run FAILS without billing. It is string-compared against ISO approval dates, so a wrong format here returned ZERO rows ('01/15/2023') or the entire portfolio ('Jan 2023') with no sign in the output; a buyer reads that empty as a fact about SBA lending rather than as a rejected input. Must be on or after sinceDate - an inverted window also fails rather than returning a confident empty. Empty = no upper bound."
          },
          "minAmount": {
            "title": "Minimum gross approval ($)",
            "minimum": 0,
            "type": "integer",
            "description": "Only return loans whose gross approval amount is at least this many dollars. Empty = no minimum."
          },
          "order": {
            "title": "File read order (newest or oldest first)",
            "pattern": "^$|^(newest|oldest)$",
            "type": "string",
            "description": "Which SBA FOIA file the run reads FIRST: 'newest' (default) starts with the file covering the most recent fiscal years, 'oldest' starts with FY1991. Empty means newest. Any other value is rejected and the run FAILS without billing, rather than quietly giving you the opposite of what you asked for. This matters because results are the first N matches in read order: before this existed, files were read in SBA's own catalog order, which is oldest-first, so a bare {program:'7a', state:'CA'} returned loans approved in 1990. IMPORTANT - this orders FILES, not ROWS. SBA publishes each file ascending by ApprovalDate (measured 2026-08-25), and this Actor does not re-sort rows, so 'newest' returns the OLDEST rows of the NEWEST file. Use sinceDate / untilDate / fiscalYear to place a recent window. Every row reports file_order and row_order_note."
          },
          "mode": {
            "title": "Output mode",
            "enum": [
              "loans",
              "rollup-by-lender",
              "rollup-by-naics",
              "rollup-by-state"
            ],
            "type": "string",
            "description": "'loans' emits one normalized loan row per result (with risk flags). 'rollup-by-lender', 'rollup-by-naics', and 'rollup-by-state' instead emit one aggregate row per lender / NAICS industry / state (loan count, total & avg approved $, charge-off/default proxy rate, jobs supported).",
            "default": "loans"
          },
          "flagRisk": {
            "title": "Add risk flags (loans mode)",
            "type": "boolean",
            "description": "In 'loans' mode, compute per-loan risk_flags and risk_score over the result set: high loan-amount-per-job outliers, charged-off/default loans, and single-lender concentration. Ignored in rollup modes.",
            "default": true
          },
          "maxResults": {
            "title": "Max results",
            "minimum": 1,
            "maximum": 200000,
            "type": "integer",
            "description": "Hard cap on the number of rows EMITTED, and therefore on what the run can bill: one emitted row is one billable result. Applies to loan rows and rollup rows alike. Bounds emission only - use maxScanRows to bound how much of the (large) source files is read. In rollup modes, rollups are computed over the loans fetched under this cap. WHICH rows you get is decided by the read order: results are the first N matches in read order, which the `order` input controls (newest-first by default).",
            "default": 1000
          },
          "maxScanRows": {
            "title": "Max rows to scan per file",
            "minimum": 1000,
            "maximum": 5000000,
            "type": "integer",
            "description": "Upper bound on how many CSV rows are scanned per FOIA file before the scan of that file stops. This bounds READING, not emission, and it is not a cost cap - only maxResults bounds what a run can charge for. The read order (the `order` input) decides which file this budget lands on first: with the default newest-first it is spent on the most recent fiscal-year file. Raise for exhaustive rollups over the full loan history; lower for faster sampling. Only matters when filters match few rows.",
            "default": 500000
          }
        }
      },
      "runsResponseSchema": {
        "type": "object",
        "properties": {
          "data": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "actId": {
                "type": "string"
              },
              "userId": {
                "type": "string"
              },
              "startedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "finishedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "status": {
                "type": "string",
                "example": "READY"
              },
              "meta": {
                "type": "object",
                "properties": {
                  "origin": {
                    "type": "string",
                    "example": "API"
                  },
                  "userAgent": {
                    "type": "string"
                  }
                }
              },
              "stats": {
                "type": "object",
                "properties": {
                  "inputBodyLen": {
                    "type": "integer",
                    "example": 2000
                  },
                  "rebootCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "restartCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "resurrectCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "computeUnits": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "options": {
                "type": "object",
                "properties": {
                  "build": {
                    "type": "string",
                    "example": "latest"
                  },
                  "timeoutSecs": {
                    "type": "integer",
                    "example": 300
                  },
                  "memoryMbytes": {
                    "type": "integer",
                    "example": 1024
                  },
                  "diskMbytes": {
                    "type": "integer",
                    "example": 2048
                  }
                }
              },
              "buildId": {
                "type": "string"
              },
              "defaultKeyValueStoreId": {
                "type": "string"
              },
              "defaultDatasetId": {
                "type": "string"
              },
              "defaultRequestQueueId": {
                "type": "string"
              },
              "buildNumber": {
                "type": "string",
                "example": "1.0.0"
              },
              "containerUrl": {
                "type": "string"
              },
              "usage": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "integer",
                    "example": 1
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "usageTotalUsd": {
                "type": "number",
                "example": 0.00005
              },
              "usageUsd": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "number",
                    "example": 0.00005
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}