feat: Add stock market endpoints (EOD, IEX, News)

Add OpenAPI specifications for stock market data:
- End-of-day prices with metadata
- IEX real-time prices, quotes, and historical data
- News articles with tags and sources

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
Cameron Yick
2025-12-13 23:30:11 -05:00
parent 2ab8cdb0b8
commit 5a42e329cb
6 changed files with 1125 additions and 0 deletions

View File

@@ -0,0 +1,119 @@
# End-of-Day Stock Price API Schemas
# Reference: https://www.tiingo.com/documentation/end-of-day
PriceData: &PriceData
type: array
description: Array of End-of-Day price data objects with OHLCV (Open, High, Low, Close, Volume) data
items:
type: object
properties:
date:
$ref: '../schemas/common.yaml#/Date'
description: The date this data pertains to
open:
type: number
format: float
description: The opening price for the asset on the given date
example: 150.25
high:
type: number
format: float
description: The high price for the asset on the given date
example: 152.50
low:
type: number
format: float
description: The low price for the asset on the given date
example: 149.75
close:
type: number
format: float
description: The closing price for the asset on the given date
example: 151.80
volume:
type: integer
format: int64
description: The number of shares traded for the asset
example: 50000000
adjOpen:
type: number
format: float
description: The adjusted opening price for the asset on the given date (includes splits and dividends)
example: 150.25
adjHigh:
type: number
format: float
description: The adjusted high price for the asset on the given date (includes splits and dividends)
example: 152.50
adjLow:
type: number
format: float
description: The adjusted low price for the asset on the given date (includes splits and dividends)
example: 149.75
adjClose:
type: number
format: float
description: The adjusted closing price for the asset on the given date (includes splits and dividends)
example: 151.80
adjVolume:
type: integer
format: int64
description: The number of shares traded for the asset (adjusted for splits)
example: 50000000
divCash:
type: number
format: float
description: The dividend paid out on the given date (note that date will be the exDate for the dividend)
example: 0.0
splitFactor:
type: number
format: float
description: The factor used to adjust prices when a company splits, reverse splits, or pays a distribution
example: 1.0
required:
- date
- close
- volume
TickerMetadata: &TickerMetadata
type: object
description: Metadata information about a stock ticker
properties:
ticker:
$ref: '../schemas/common.yaml#/Ticker'
description: Ticker related to the asset
name:
type: string
description: Full-length name of the asset
example: "Apple Inc"
exchangeCode:
type: string
description: An identifier that maps which Exchange this asset is listed on
enum:
- NASDAQ
- NYSE
- AMEX
- OTC
- BATS
- IEX
example: "NASDAQ"
description:
type: string
description: Long-form description of the asset
example: "Apple Inc is an American multinational technology company that specializes in consumer electronics, software and online services."
startDate:
type: string
format: date
nullable: true
description: The earliest date we have price data available for the asset. When null, no price data is available
example: "1990-01-01"
endDate:
type: string
format: date
nullable: true
description: The latest date we have price data available for the asset. When null, no price data is available
example: "2024-01-01"
required:
- ticker
- name
- exchangeCode

View File

@@ -0,0 +1,220 @@
# IEX Exchange API Response Schemas
# Reference: https://api.tiingo.com/documentation/iex
IEXTopOfBook: &IEXTopOfBook
type: object
description: |
Top-of-book and last price data for a stock on IEX Exchange.
Note: Fields marked with "*IEX entitlement required*" will return null unless you are
registered with the IEX Exchange and have a market data policy in place. These fields
provide full TOPS feed data including direct bid/ask/last data from IEX.
Tiingo-enriched fields (tngoLast, mid, open, high, low) are calculated by Tiingo
and do not require IEX entitlement.
properties:
ticker:
$ref: '../schemas/common.yaml#/Ticker'
description: Ticker symbol for the asset
timestamp:
$ref: '../schemas/common.yaml#/DateTime'
description: Timestamp when the data was last refreshed
quoteTimestamp:
type: string
format: date-time
nullable: true
description: |
Timestamp when the last quote (bid/ask) data was received from IEX.
Requires IEX entitlement. Null if not entitled.
lastSaleTimeStamp:
type: string
format: date-time
nullable: true
description: |
Timestamp when the last trade (last/lastSize) data was received from IEX.
Requires IEX entitlement. Null if not entitled.
last:
type: number
format: double
nullable: true
description: |
Last trade price executed on IEX.
Requires IEX entitlement. Null if not entitled.
example: 162.37
lastSize:
type: integer
format: int32
nullable: true
description: |
Number of shares traded at the last price on IEX.
Requires IEX entitlement. Null if not entitled.
example: 100
tngoLast:
type: number
format: double
description: |
Tiingo-calculated last price. Either the last trade price or mid price.
The mid price is only used if the spread is not considered too wide by Tiingo's algorithm.
After the official exchange print comes in, this value changes to that value.
This is a Tiingo-enriched field and does not require IEX entitlement.
example: 162.33
prevClose:
type: number
format: double
description: |
Previous day's closing price of the security.
Can be from any exchange (NYSE, NASDAQ, IEX, etc.)
example: 154.68
open:
type: number
format: double
nullable: true
description: |
Opening price of the asset on the current day.
Tiingo-calculated field, does not require IEX entitlement.
example: 161.83
high:
type: number
format: double
nullable: true
description: |
High price of the asset on the current day.
Tiingo-calculated field, does not require IEX entitlement.
example: 163.25
low:
type: number
format: double
nullable: true
description: |
Low price of the asset on the current day.
Tiingo-calculated field, does not require IEX entitlement.
example: 160.38
mid:
type: number
format: double
nullable: true
description: |
Mid price at current timestamp when both bidPrice and askPrice are not null.
Formula: mid = (bidPrice + askPrice) / 2.0
Tiingo-calculated field, does not require IEX entitlement.
example: 162.67
volume:
type: integer
format: int64
description: |
Volume data. IEX volume throughout the trading day.
Once the official closing price is received, reflects total volume across all exchanges.
This field is provided for convenience.
example: 0
bidSize:
type: number
format: double
nullable: true
description: |
Number of shares available at the bid price.
Requires IEX entitlement. Null if not entitled.
example: 100
bidPrice:
type: number
format: double
nullable: true
description: |
Current bid price.
Requires IEX entitlement. Null if not entitled.
example: 162.34
askSize:
type: number
format: double
nullable: true
description: |
Number of shares available at the ask price.
Requires IEX entitlement. Null if not entitled.
example: 100
askPrice:
type: number
format: double
nullable: true
description: |
Current ask price.
Requires IEX entitlement. Null if not entitled.
example: 163.0
required:
- ticker
- timestamp
- tngoLast
- prevClose
- volume
example:
ticker: 'AAPL'
timestamp: '2019-01-30T10:33:38.186520297-05:00'
quoteTimestamp: '2019-01-30T10:33:38.186520297-05:00'
lastSaleTimeStamp: '2019-01-30T10:33:34.176037579-05:00'
last: 162.37
lastSize: 100
tngoLast: 162.33
prevClose: 154.68
open: 161.83
high: 163.25
low: 160.38
mid: 162.67
volume: 0
bidSize: 100
bidPrice: 162.34
askSize: 100
askPrice: 163.0
IEXPrice: &IEXPrice
type: object
description: |
Historical intraday price data in OHLC format from IEX Exchange.
The time period covered by each bar is determined by the resampleFreq parameter.
Volume data is IEX-only and must be explicitly requested using the columns parameter.
properties:
date:
$ref: '../schemas/common.yaml#/DateTime'
description: |
Timestamp for this OHLC bar. Marks the beginning of the time period.
Format: ISO 8601 (RFC 3339)
open:
type: number
format: double
description: Opening price for the time period
example: 154.74
high:
type: number
format: double
description: Highest price during the time period
example: 155.52
low:
type: number
format: double
description: Lowest price during the time period
example: 154.58
close:
type: number
format: double
description: Closing price for the time period
example: 154.76
volume:
type: integer
format: int64
nullable: true
description: |
Number of shares traded on IEX only during the time period.
This field is only included if explicitly requested via the columns parameter
(e.g., ?columns=open,high,low,close,volume)
example: 16102
required:
- date
- open
- high
- low
- close
example:
date: '2019-01-02T14:30:00.000Z'
open: 154.74
high: 155.52
low: 154.58
close: 154.76
volume: 16102

View File

@@ -0,0 +1,114 @@
# News API Schema Definitions
# Reference these using: $ref: '../schemas/news-schemas.yaml#/SchemaName'
NewsArticle: &NewsArticle
type: object
description: A news article with ticker and tag associations
properties:
id:
type: integer
format: int32
description: Unique identifier specific to the news article
example: 28515261
title:
type: string
description: Title of the news article
example: "Apple's CEO sees optimism as trade tension between U.S. and China lessens"
url:
type: string
format: uri
description: URL of the news article
example: "https://www.cnbc.com/2019/01/29/apples-ceo-sees-optimism-as-trade-tension-between-us-and-china-lessens.html"
description:
type: string
description: Long-form description of the news story
example: "Apple CEO Tim Cook told CNBC that trade tensions between the U.S. and China have improved since late December."
publishedDate:
type: string
format: date-time
description: The datetime the news story was published in UTC. Usually reported by the news source, or the time discovered by Tiingo's crawler if not declared.
example: "2019-01-29T22:17:00Z"
crawlDate:
type: string
format: date-time
description: The datetime the news story was added to the database in UTC. Always recorded by Tiingo. Large gaps between crawlDate and publishedDate indicate backfilled articles.
example: "2019-01-29T22:20:01.696871Z"
source:
type: string
description: The domain the news source is from
example: "cnbc.com"
tickers:
type: array
items:
type: string
pattern: '^[A-Z0-9]+$'
description: Tickers mentioned in the news story using Tiingo's proprietary tagging algorithm
example: ["AAPL"]
tags:
type: array
items:
type: string
description: Tags mapped and discovered by Tiingo using Tiingo's proprietary tagging algorithm
example: ["China", "Economic Measures", "Economics", "Markets", "Stock", "Technology"]
required:
- id
- title
- url
- publishedDate
- crawlDate
- source
BulkDownloadFile: &BulkDownloadFile
type: object
description: Metadata for a bulk news download file (institutional clients only)
properties:
id:
type: integer
format: int32
description: Unique identifier specific to the bulk download file. Used to select which file to download.
example: 755
filename:
type: string
description: The filename of the batch file
example: "bulkfile_2019-01-28_2019-01-29.tar.gz"
batchType:
type: string
enum:
- base
- incremental
description: "Describes what kind of batch file this is: 'base' is an entire dump of the data, 'incremental' is a partial dump of the data"
example: "incremental"
startDate:
type: string
format: date-time
description: The start date used to select the News objects to generate the batch file. This is inclusive (publishedDate >= startDate).
example: "2019-01-28T05:00:00Z"
endDate:
type: string
format: date-time
description: The end date used to select the News objects to generate the batch file. This is not inclusive (publishedDate < endDate).
example: "2019-01-29T05:00:00Z"
url:
type: string
format: uri
description: A url to directly download the batch file. NOTE - This url contains your Auth Token and is meant to be a copy/paste url for convenience.
example: "https://api.tiingo.com/tiingo/news/bulk_download/755?token=YOUR_API_TOKEN"
fileSizeUncompressed:
type: integer
format: int64
description: The size of the file in bytes uncompressed
example: 10385878
fileSizeCompressed:
type: integer
format: int64
description: The size of the file in bytes compressed using gzip
example: 3018550
required:
- id
- filename
- batchType
- startDate
- endDate
- url
- fileSizeUncompressed
- fileSizeCompressed