API Reference

Every number on this site over plain HTTPS: JSON or CSV, no key, no account. The endpoint and dataset sections below are rendered from the server's own schema and dataset cards, so they describe exactly what this server is running.

Quick Start

The base URL is:

https://ploveranalytics.com

Three requests that show the shape of the whole API. Each opens in the browser.

  1. /api/v1/catalog/datasets what is on the server
  2. /api/v1/cpi-jp/series?q=electricity find a series code by name, in English or Japanese
  3. /api/v1/cpi-jp/observations?series=0001,0161&measure=yoy&start=2020-01 headline and core inflation, year over year, since 2020

Add &format=csv to any /observations URL for a file that pandas, R and Excel read directly, and &as_of=YYYY-MM-DD to freeze it as the data stood on that date. Code samples are below; the machine-readable schema is at /api/openapi.json and a try-it-out console at /api/swagger.

Conventions

Base URL and versioning

All data endpoints sit under /api/v1. Within v1, response fields are added but never removed or renamed, and a dataset's endpoints never change shape once published. Anything that would break a client goes to a new version prefix. There is no authentication and every endpoint is read-only.

Response shape

Every response says where its numbers came from. A dataset response carries a release block naming the source document, the file that was downloaded, its SHA-256 and when it was retrieved, and a trust field: official for values exactly as published, derived for a rate this platform calculated, in which case calc states the formula. A trimmed /observations response:

{
  "dataset": "cpi-jp",
  "measure": "yoy",
  "unit": "%",
  "trust": "derived",
  "calc": "(index[t] / index[t−12 months] − 1) × 100, from published index values.",
  "release": {
    "release_id": 342,
    "label": "Data through September 2026",
    "latest_period": "2026-09-01",
    "ingested_at": "2026-10-23T13:00:15Z",
    "sha256": "29b63b7aa5cba598…",
    "download_url": "https://www.e-stat.go.jp/stat-search/file-download?statInfId=000040482943&fileKind=1",
    "source_name": "CPI Japan, national, Table 1: middle-class indices (Jan 1970 – latest month), 2025 base",
    "source_id": "e-stat:000040482943",
    "base": "2025=100",
    "frequency": "monthly",
    "known_at": "2026-10-23T13:00:15Z",
    "known_at_basis": "our fetch"
  },
  "series": [
    { "code": "0001", "name_en": "All items", "name_ja": "総合",
      "points": [["2026-08-01", 1.894317], ["2026-09-01", 2.097902]] }
  ]
}

Points are [period, value] pairs. Values are unrounded: round at display time to the precision the dataset's page uses. Company-disclosure endpoints, /api/v1/equity for Japan and /api/v1/us for the United States, carry the filing each row came from (the EDINET doc_id or the SEC accession number, the fiscal year and the filed date) instead of a release block.

Datasets, series and measures

A dataset is one official table: cpi-jp, boj-assets, jgb-yields and so on. The full list, with each dataset's series-code scheme, is in Datasets. A series is one line in that table, addressed by its code; find codes with /{dataset}/series?q=, which searches English and Japanese names as well as codes. A measure is how the series is read: index is the published value; yoy, mom and the rest are calculated, and each dataset card lists the measures it offers with their formulas. Price changes, price levels, stocks and flows are different kinds of number, and the API refuses a calculation that does not apply, for example a percentage change on a flow that crosses zero, rather than serving nonsense.

Dates and periods

Monthly periods are the first of the month (2026-07-01); start and end accept YYYY-MM. Daily series such as JGB yields use full dates. Annual datasets use the reference date the publisher states, and the dataset card says which. Fiscal-year data from company filings is keyed by fiscal year end. Customs and visitor flows can be re-summed into a company's own fiscal quarters or years with period=fiscal_quarter and fy_end=; only complete periods are returned.

Missing values

A value the publisher did not release is null in JSON and an empty cell in CSV, never zero. Gaps stay gaps: nothing is interpolated, smoothed or seasonally adjusted. A maturity not yet issued, an item not yet priced, a prefecture the survey suppressed, are all null.

Point-in-time data

Publishers revise. Every accepted download is kept as a release, and the vintage history is append-only. as_of=YYYY-MM-DD on /observations returns the numbers as they stood on that date, before any later revision, and the release block describes the vintage that was live then. The same URL returns the same numbers next year, which is what makes a chart citable and a backtest honest. /revisions shows how one figure moved release by release, and /releases lists every vintage held.

CSV downloads

format=csv on /observations returns one wide table: a period column and one column per series, under a # metadata block that states the source, the release, the formula, the vintage and the URL it was retrieved from. The block is what makes a saved file citable on its own. Readers skip it with comment="#" in pandas and comment.char="#" in R.

Errors

Errors are JSON with a detail field and the usual status codes: 400 for a bad parameter value (the message lists the valid ones), 404 for an unknown dataset, series or company, 422 for a missing required parameter, and 503 when a dataset has no published release yet.

GET /api/v1/cpi-jp/observations?series=0001&measure=bogus
400  {"detail": "Unknown measure 'bogus'; one of ['ann3m', 'index', 'mom', 'yoy']"}

Caching and limits

Responses carry an ETag and Cache-Control: max-age=60. Data changes only when a new release is published, so send If-None-Match on repeat requests and an unchanged answer costs a bodiless 304. Responses are gzip-compressed when the client accepts it. There is no per-key quota because there are no keys; a scheduled job that pulls what it needs once a day is the intended use, and /api/v1/catalog/health says whether anything has changed.

Attribution

Every source is public and free. Each dataset card carries the publisher's credit line and its reuse terms; the credit line is also in every CSV header. Bank of Japan data must display the Bank's credit line wherever it appears. The platform adds nothing proprietary to an official value and asks for a link back when a calculated figure is republished.

Endpoints

Grouped by product area. Each entry shows what the endpoint returns, its parameters and one working example. For the shared dataset endpoints, the datasets that offer them are listed.

Loading the schema…

Datasets

One card per dataset: its source and coverage, every measure with its formula, the endpoints it offers, and the caveats that apply. Open a card for detail.

Loading dataset cards…

Code Samples

Python

import pandas as pd
import requests

BASE = "https://ploveranalytics.com"

# CSV: one column per series, metadata in the '#' header block
url = f"{BASE}/api/v1/cpi-jp/observations?series=0001,0161&measure=yoy&start=2015-01&format=csv"
cpi = pd.read_csv(url, comment="#", index_col="period", parse_dates=True)

# JSON, frozen as of a date so the backtest sees what was known then
r = requests.get(f"{BASE}/api/v1/cpi-jp/observations",
                 params={"series": "0001", "measure": "yoy", "as_of": "2026-08-20"})
r.raise_for_status()
body = r.json()
points = pd.DataFrame(body["series"][0]["points"], columns=["period", "value"])
print(body["trust"], body["calc"])           # derived, and the formula it was derived by

# Company disclosures: calculated ratios for one filer, in Japan and in the US
fin = requests.get(f"{BASE}/api/v1/equity/financials/metrics/7203").json()
us_fin = requests.get(f"{BASE}/api/v1/us/financials/metrics/AAPL").json()

# US CPI, all items, year over year
us_cpi = pd.read_csv(f"{BASE}/api/v1/cpi-us/observations?series=CUUR0000SA0&measure=yoy&start=2015-01&format=csv",
                     comment="#", index_col="period", parse_dates=True)

R

base <- "https://ploveranalytics.com"

cpi <- read.csv(paste0(base, "/api/v1/cpi-jp/observations?series=0001,0161&measure=yoy&start=2015-01&format=csv"),
                comment.char = "#")

library(jsonlite)
curve <- fromJSON(paste0(base, "/api/v1/jgb-yields/curve"))
us_curve <- fromJSON(paste0(base, "/api/v1/ust-yields/curve"))

Shell

BASE=https://ploveranalytics.com

# the last three readings of headline inflation
curl -s "$BASE/api/v1/cpi-jp/observations?series=0001&measure=yoy" | jq '.series[0].points[-3:]'

# is every dataset current?
curl -s "$BASE/api/v1/catalog/health" | jq '.datasets[] | select(.stale or .unpublished_artifact)'

# revalidate cheaply on a schedule
curl -s -H 'If-None-Match: "fe631f52bc1f28710ebef0e51d047799"' -o /dev/null -w '%{http_code}\n' "$BASE/api/v1/cpi-jp/overview"

Excel and other tools

Any tool that opens a CSV from a URL can use a format=csv link directly; in Excel, Data → From Web with the URL. Skip the leading # lines or keep them as the file's provenance. AI assistants use the same numbers over the MCP connector.