# New Issue Bond Feed — SEC EDGAR (CUSIP & Terms) (`integrative_tangent/new-issue-bond-feed`) Actor

Daily feed of new US corporate bond issues from SEC EDGAR 424B2, 424B5 and FWP filings: CUSIP/ISIN validation, coupon, maturity, size, call terms, guarantor, field-level sources. onlyChanges for daily runs.

- **URL**: https://apify.com/integrative_tangent/new-issue-bond-feed.md
- **Developed by:** [Luis Segura](https://apify.com/integrative_tangent) (community)
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $10.00 / 1,000 new bond issues

This Actor is paid per event and usage. You are charged both the fixed price for specific events and for Apify platform usage.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## New Issue Bond Feed — SEC EDGAR

**Status: v1.0 beta.** Covers US-registered corporate bond issues from SEC EDGAR only.

A daily feed of **new US-registered corporate bond issues** from SEC EDGAR. Every 424B2, 424B5 and FWP filed in your date range is triaged. Bank structured notes, equity offerings, ABS and shelf/program supplements are dropped. The Actor is designed to return **one row per tranche** with its CUSIP/ISIN and terms; `tranche_index` and `tranches_in_document` identify each tranche of a multi-tranche document. Key values come with the sentence they were taken from.

Built for pipelines that run on a schedule: a stable natural key, an incremental `onlyChanges` mode, a versioned schema, and runs that **fail loudly** instead of finishing green with an empty dataset.

### Who it's for

- Fixed-income desks and analysts who check EDGAR by hand for new deals.
- Data teams that feed a database, alert or pricing tool each evening with the day's new issues.

### What you get

| Field group | Fields |
|---|---|
| Identifiers | `cusip`, `isin`, `cusip_check_digit_valid`, `isin_check_digit_valid`, `identifier_crosscheck` |
| Issuer | `issuer_legal_name`, `cik`, `sic`, `sic_description`, `guarantor` |
| Instrument | `instrument_name`, `series`, `instrument_kind`, `tranche_index`, `tranches_in_document` |
| Coupon | `coupon_rate`, `coupon_type` (`fixed`, `floating`, `fixed_to_floating`, `fixed_reset`, `step_up`, `zero`), `reference_rate`, `spread_bps` |
| Dates | `pricing_date`, `original_issue_date`, `maturity_date` |
| Size & price | `original_issue_amount`, `issue_price` (% of par), `denomination_min`, `denomination_increment`, `currency` |
| Structure | `seniority`, `secured_status`, `is_callable`, `first_call_date`, `par_call_date`, `make_whole_provision`, `make_whole_spread_bps`, `is_convertible` |
| Provenance | `source_url`, `accession_number`, `form`, `filing_date`, `supporting_documents[]`, `provenance{...}` (source and quoted text for each key value) |
| Quality | `needs_review`, `review_reasons[]`, `term_changes[]`, `classification_reasons[]` |
| Feed | `schema_version`, `record_status` (`new` / `final_update` / `seen`), `natural_key`, `issue_id`, `observed_at` |

#### Example row (shape only, placeholder values)

```json
{
  "cusip": "<9-character CUSIP from the filing>",
  "isin": "<ISIN, check digit validated>",
  "issuer_legal_name": "<Issuer legal name>",
  "form": "424B5",
  "accession_number": "<EDGAR accession number>",
  "coupon_type": "fixed",
  "coupon_rate": 0.0,
  "maturity_date": "YYYY-MM-DD",
  "original_issue_amount": 0,
  "is_callable": true,
  "first_call_date": "YYYY-MM-DD",
  "needs_review": false,
  "record_status": "new",
  "natural_key": "<cusip>|<accession_number>"
}
```

### Why the FWP ↔ 424B join matters

For benchmark deals the final prospectus supplement often prints no CUSIP. The CUSIP is in the issuer's FWP *Pricing Term Sheet*, filed a day or two earlier. The Actor links the two documents by issuer, maturity and coupon, then applies these rules:

- **The final 424B wins** for every term both documents state. Each disagreement is kept in `term_changes` (`field`, `term_sheet_value`, `final_value`).
- **The FWP fills only what the 424B leaves blank**, typically `cusip`, `isin` and `issue_price`. `provenance.cusip.source_url` then points at the FWP.
- If a term sheet was filed before your date range, the Actor looks back `termSheetLookbackDays` in that issuer's filings.
- If a term sheet has no final yet, it is emitted with `document_status = "term_sheet"`. When the final arrives, the issue comes back once more with `record_status = "final_update"`.

### Data rules

- **Identifiers are not invented.** A CUSIP/ISIN is taken only from text that labels it as one, and its check digit must validate. A valid check digit proves the string is well-formed, not that it belongs to the bond. `provenance.cusip.supporting_text` shows the exact line.
- **Tri-state booleans.** `is_callable`, `make_whole_provision` and `is_convertible` are `true`, `false` or `null`. `null` means the document does not say.
- **Original ≠ outstanding.** `original_issue_amount` is what was offered. `amount_outstanding` is always `null`, because a prospectus cannot know about later reopenings or buybacks.
- **Preliminary vs final.** Preliminary pricing supplements are skipped unless `includePreliminary` is on.
- **Unattributed values stay null.** If one redemption section covers several tranches, call dates and make-whole spreads are left `null` with a warning instead of being assigned to the wrong tranche.

### Natural key, dedupe and schema

- **`natural_key`** = `cusip|accession_number` (or `NO-CUSIP|accession#tranche` when no CUSIP is printed). Upsert on it to make re-ingestion idempotent.
- **`issue_id`** = `CUSIP:<cusip>` when known: the same bond across documents. Use it to collapse the FWP-first row and the later `final_update` row.
- **`schema_version`** = `"1.0"`. Fields are only added within 1.x. A rename or meaning change bumps the major version.

### Daily use (incremental mode)

Run it on weekday evenings with `onlyChanges: true`. A run then returns only issues it has not seen before, plus `final_update` rows. Seen issues are remembered in a named key-value store (`stateStoreName`, default `new-issue-bond-feed-state`), which survives across runs. Overlapping daily windows and re-runs do not duplicate rows.

**Timing:** EDGAR publishes the full daily index in the evening. Run after 18:30 America/New_York. A run earlier in the day only sees filings made until that moment. The default range (previous business day → today) means a Monday run still covers Friday.

**Webhook on completion:** add an Actor webhook for `ACTOR.RUN.SUCCEEDED` (and `ACTOR.RUN.FAILED`, to get alerted), then fetch the run's dataset:

```
GET https://api.apify.com/v2/datasets/{datasetId}/items?format=json&clean=1
```

**Flattening arrays for CSV:** `supporting_documents`, `term_changes` and `review_reasons` are arrays. Use the dataset API's `unwind` parameter for one row per element:

```
GET /v2/datasets/{id}/items?format=csv&unwind=term_changes
GET /v2/datasets/{id}/items?format=csv&flatten=provenance
```

**Run summary:** every run writes `RUN_SUMMARY` to its default key-value store, with per-day sources, classification breakdown, failures by cause, rows emitted and needing review, and HTTP stats.

### Input

| Field | Default | Notes |
|---|---|---|
| `startDate`, `endDate` | previous business day → today (NY) | max 31 days per run |
| `onlyChanges` | `false` | use `true` for daily runs |
| `issuerContains`, `ciks`, `currencies` | — | filters |
| `includeStructuredNotes` | `false` | emits bank structured notes with `instrument_kind = structured_note` |
| `includePreliminary` | `false` | |
| `termSheetLookbackDays` | `7` | |
| `requestsPerSecond` | `8` | SEC fair access caps at 10 |
| `userAgent` | Actor default | SEC asks for a name and contact email |

### Failure behaviour

A run **fails** (status `FAILED`, with the cause in the status message) when:

- no filings exist for the range (weekend or holiday, or EDGAR has not published yet), or
- every filing failed to download or parse. Causes are counted (`rate-limited`, `blocked`, `timeout`, `not-found`, …).

A business day where every debt filing was a structured note or a preliminary is a valid empty result. The run succeeds, and `RUN_SUMMARY.classification` shows why.

### Quality and known limits

- **Coverage:** SEC-registered deals only (424B2, 424B5, FWP). 144A and Reg S deals are not filed on EDGAR and are not included. Non-US markets (e.g. FIRDS/Europe) are not included.
- **Review flags:** on some days a large share of rows is flagged `needs_review`, mostly multi-tranche deals with term changes between the term sheet and the final. Check `review_reasons` and `term_changes` before using a row for trading decisions.
- **Shared redemption sections:** call dates and make-whole spreads covering several tranches are left `null` unless a term sheet supplies them.
- **Step-up coupons** report no single `coupon_rate`.
- **Structured notes**, when included, are identified but their payoff terms are not modelled.
- **Volume:** daily volume depends on what is filed that day and has not yet been measured over several days. Multi-tranche documents are under QA, so no tranche count is published yet.

### Source and compliance

The only source is public SEC EDGAR data (daily form indices, the live filings feed and the filing archives). Every request is identified with a User-Agent and throttled below SEC's 10 requests/second. No third-party data providers are used.

### Pricing

Pay per event plus usage. Event: `new-issue`, charged once per bond row that passes validation (validated CUSIP, coupon and maturity). Rows flagged `needs_review` are not charged. Bonds already in your state store are not charged again.

**Price: US$0.01 per `new-issue` event.**

# Actor input Schema

## `mode` (type: `string`):

feed = every new issue filed in the date range (default). lookup = find specific bonds from a list of issuers / maturities / coupons.

## `startDate` (type: `string`):

First EDGAR filing date to scan. Default: the previous business day (America/New_York).

## `endDate` (type: `string`):

Last EDGAR filing date to scan (inclusive). Default: today (America/New_York). Today's filings come from EDGAR's live feed until the daily index is published in the evening. Maximum span: 31 days per run.

## `onlyChanges` (type: `boolean`):

Return only issues not seen in previous runs (state is kept in a named key-value store), plus final_update rows when a final 424B arrives for an issue first seen in an FWP term sheet.

## `issuerContains` (type: `array`):

Optional. Keep only filings whose filer or co-registrant name contains any of these strings (case-insensitive), e.g. "Goldman", "Lennar".

## `ciks` (type: `array`):

Optional. Keep only filings by these SEC CIKs (leading zeros optional).

## `currencies` (type: `array`):

Optional. Keep only issues denominated in these ISO currencies, e.g. USD, EUR.

## `includeStructuredNotes` (type: `boolean`):

Structured notes (autocallables, buffered/digital/index-linked notes, range accruals, CPI-linked) are ~90% of 424B2 volume. They are excluded by default; when included they are emitted with instrument_kind = structured_note and coupon fields describe only what the document states.

## `includePreliminary` (type: `boolean`):

Preliminary pricing supplements ('subject to completion', blank pricing date or amount) are not issues yet. Off by default.

## `termSheetLookbackDays` (type: `integer`):

When a final 424B in the range prints no CUSIP, look back this many days in the issuer's own filings for the FWP pricing term sheet that does.

## `maxFilings` (type: `integer`):

Testing aid. 0 = all filings in the range.

## `requestsPerSecond` (type: `integer`):

Throttle toward sec.gov. SEC fair-access policy caps clients at 10 requests/second.

## `userAgent` (type: `string`):

SEC requires a User-Agent identifying you (name and email). Leave empty to use the Actor's default.

## `stateStoreName` (type: `string`):

Named key-value store that remembers seen issues for onlyChanges. Use a different name per independent feed.

## `lookups` (type: `array`):

Lookup mode only. Each item: {"issuer_name"|"ticker"|"cik", "maturity" (YYYY-MM-DD or YYYY), "coupon" (e.g. 5.95), "cusip", "row_id"}. All fields optional, but one of issuer_name / ticker / cik is needed to find the issuer.

## `lookupsCsv` (type: `string`):

Lookup mode only. CSV with a header row: issuer_name,ticker,cik,maturity,coupon,cusip,row_id (any subset). Up to 500 rows per run, together with the JSON rows.

## `maxDocsPerIssuer` (type: `integer`):

Lookup mode only. How many of the issuer's most recent 424B2/424B5/FWP filings to read. Banks file hundreds of structured notes, so an older bond may need more.

## `maxCandidates` (type: `integer`):

Lookup mode only. Ambiguous rows return several ranked candidates, never an arbitrary pick.

## Actor input object example

```json
{
  "mode": "feed",
  "onlyChanges": false,
  "includeStructuredNotes": false,
  "includePreliminary": false,
  "termSheetLookbackDays": 7,
  "maxFilings": 0,
  "requestsPerSecond": 8,
  "stateStoreName": "new-issue-bond-feed-state",
  "lookups": [
    {
      "row_id": "1",
      "ticker": "LEN",
      "maturity": "2032",
      "coupon": 5.95
    }
  ],
  "maxDocsPerIssuer": 60,
  "maxCandidates": 5
}
```

# Actor output Schema

## `results` (type: `string`):

One row per validated new bond tranche: filing date, issuer, CUSIP, ISIN, coupon, maturity, size, call terms and needs_review flag.

## `terms` (type: `string`):

One row per tranche with all terms: coupon, reference rate, spread, dates, denominations, seniority, guarantor, call and make-whole provisions.

## `provenance` (type: `string`):

Field-level evidence: supporting text and source URL for CUSIP, coupon, maturity and size, plus review reasons.

## `pricing` (type: `string`):

Pricing data per tranche when the filing discloses it: benchmark, spread, reoffer yield, ratings, bookrunners and co-managers.

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "lookups": [
        {
            "row_id": "1",
            "ticker": "LEN",
            "maturity": "2032",
            "coupon": 5.95
        }
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("integrative_tangent/new-issue-bond-feed").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = { "lookups": [{
            "row_id": "1",
            "ticker": "LEN",
            "maturity": "2032",
            "coupon": 5.95,
        }] }

# Run the Actor and wait for it to finish
run = client.actor("integrative_tangent/new-issue-bond-feed").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "lookups": [
    {
      "row_id": "1",
      "ticker": "LEN",
      "maturity": "2032",
      "coupon": 5.95
    }
  ]
}' |
apify call integrative_tangent/new-issue-bond-feed --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,integrative_tangent/new-issue-bond-feed"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/Zsjyio5OU9BfWHRzM/builds/SDG7Ou4kxJ9XdDWNk/openapi.json
