Alphanume

Insights

FDA Complete Response Letter Database for Biotech Research

Alphanume Team · August 20, 2026

An FDA complete response letter database should answer when a US-listed company first disclosed a CRL, which drug program it affected, what reasons the issuer attributed to the FDA, and whether a later filing reported a resolution. It should not pretend that the full FDA letter is public when the source record is the company's Form 8-K disclosure.

Alphanume's FDA Response Events dataset structures those issuer disclosures alongside full and partial clinical holds and Refuse-to-File letters. The dataset begins on January 2, 2024 and is updated from SEC EDGAR after the filing day closes. A CRL study must filter the broader response-event feed rather than treating every row as the same regulatory action.

Define the CRL cohort precisely

Each dataset row is one filing, not one unique FDA event. One drug program can produce an initial_disclosure, one or more follow_up_update filings, and a later resolution. For a de-duplicated first-disclosure cohort, use event_type=crl together with filing_role=initial_disclosure. Use (cik, asset_key) when grouping the later filing chain for one issuer and drug program.

Field

Research role

Caveat

disclosed_date

Primary event-study date from the EDGAR filing

It can differ from the date the FDA acted

filing_timestamp

Full timestamp with timezone offset

Use it to distinguish before-close from after-close disclosure

event_letter_date

Date of the FDA action extracted from filing prose

Read it with event_letter_date_precision

event_type

CRL, clinical hold, Refuse-to-File, or another classified action

Filter to crl for a CRL-only cohort

filing_role

Initial disclosure, follow-up, or resolution

Unfiltered row counts overstate unique events

filing_url

Primary issuer disclosure in EDGAR

It is not necessarily the full FDA letter

The distinction between disclosed_date and event_letter_date is load-bearing. A company can receive a letter before it files the 8-K. If the research question concerns market reaction to public information, the filing timestamp is usually the defensible anchor. If it concerns disclosure latency, use days_letter_to_disclosure only on initial disclosures with day-level letter-date precision.

Pull CRLs for a fixed historical window

The documented REST route is GET /v1/biotech/fda-response-events. The example below requests initial CRL disclosures from 2024 through 2025 and reads the API key from the process environment. That window requires access to historical data beyond the Free rolling window.

import os
import requests

response = requests.get(
    "https://api.alphanume.com/v1/biotech/fda-response-events",
    headers={"X-API-Key": os.environ["ALPHANUME_API_KEY"]},
    params={
        "event_type": "crl",
        "filing_role": "initial_disclosure",
        "date_gte": "2024-01-01",
        "date_lte": "2025-12-31",
    },
    timeout=30,
)
response.raise_for_status()
payload = response.json()
crls = payload["data"]

The response can include has_more and next_cursor. If has_more is true, send both cursor_date and cursor_accession from the returned cursor. Stopping after the first page creates an undocumented sample. The complete parameter and field list is in the FDA Response Events documentation.

Keep the issuer's evidence and the unknowns

The structured row includes fda_stated_reasons, a one-sentence event_description, and evidence flags for a required new trial, manufacturing issues, a stated resubmission path, and a lifted hold. Those flags are three-state integers. One means the filing said yes, zero means it said no, and null means the filing was silent. Null cannot be converted to zero without changing the evidence.

The severity field follows an explicit grading precedence. Its numeric severity_rank is not a predicted stock impact and is not an ordering of investment outcomes. A manufacturing-only CRL can have a lower rank number than a safety signal with no stated path even when the commercial consequences differ sharply. Preserve the named category and underlying evidence flags in any analysis.

required = {
    "disclosed_date",
    "filing_timestamp",
    "cik",
    "asset_key",
    "event_type",
    "filing_role",
    "filing_url",
}

assert all(required.issubset(row) for row in crls)
assert all(row["event_type"] == "crl" for row in crls)
assert all(row["filing_role"] == "initial_disclosure" for row in crls)

cohort = sorted(crls, key=lambda row: row["filing_timestamp"])
null_reasons = sum(row["fda_stated_reasons"] is None for row in cohort)
Measure resolution without leaking it backward

Initial rows can later gain resolved_flag, resolution_accession_number, resolution_disclosed_date, and days_to_resolution. Those linkage fields are updated after later filings arrive. They are valid for a retrospective duration study, but they were not known on the original event date. Save the first-observed row separately if the backtest asks what was knowable at disclosure.

A null resolved_flag has a specific meaning: the row is itself a resolution filing. It does not mean unknown. On an initial-disclosure cohort, zero means no linked resolution is present and one means a later resolution was linked. An incremental data job should use updated_since because a date-only sync can miss later linkage changes to older disclosures.

Account for coverage and event-study limits
  • Coverage is based on adverse FDA actions disclosed by US-listed issuers in Form 8-K or 8-K/A filings.
  • An action disclosed only in a 10-Q, only in a press release without an 8-K, or never disclosed is outside this corpus.
  • Real events are sparse, so a short Free window can correctly return very few rows or none.
  • Market cap at filing is context, not proof that small issuers have a universal post-CRL return.
  • A CRL means the application was not approved in its current form. It does not predict the outcome of a resubmission.

The database supports a reproducible event cohort, not an approval model or a guaranteed short signal. Results also depend on how returns are timestamped around before-close and after-close filings, how delistings are retained, and whether overlapping events for one issuer are treated separately.

Save one auditable CRL sample

Run the fixed-window query, save every raw page, and export one row per initial CRL disclosure with issuer, program, both date roles, precision, severity evidence, filing URL, and market cap at filing. Report missing reasons and low-precision letter dates rather than dropping them. Then inspect five source filings before attaching prices. The next useful comparison is a separate clinical-hold cohort built with the same disclosure-time rules, not a blended FDA setback average.