Skip to content

Distribute notes

fact Every call on this page exists on NoteCore and RollPolicy as deployed on Robinhood Chain testnet (deployment 11). The full developer reference is under Developers; this page is the shortest path for a distribution surface such as a wallet stock page.

A note appears where the user already is: the stock page. Three screens, four contract calls.

ScreenCallWhat it shows
Discoverroll.openSeriesOf(underlying)The live series for the stock on screen, with coupon and barrier
Termscore.getSeries(seriesId)Barrier, coupon, observations, fees, exactly as enforced
Subscribecore.depositCoupon(seriesId, amount)One signature after the USDG approval. The wallet holds the ERC-1155 leg
Holdcore.accruedCoupon(seriesId, owner)Coupons paid so far; claim any time, redeem at maturity

The Build on Note page renders this pattern as a wallet design study.

// series in subscription for one stock
uint256[] memory ids = roll.openSeriesOf(underlying);
INoteCore.SeriesView memory v = core.getSeries(ids[0]);
// v.barrierBps, v.autocallBps, v.couponFloorBps, v.couponCapBps, v.refBps,
// v.observations, v.subscriptionEnd,
// v.minTicket, v.status; after strike also v.s0, v.couponBps, v.lastPrice,
// v.couponIndex, v.breached

A series is worth surfacing when status is subscription and subscriptionEnd is in the future. Before strike the coupon is a range: couponFloorBps to couponCapBps, with refBps as the reference the desk quotes around. At strike couponBps is discovered and s0 is set; from then on show those. Everything shown is what the contract enforces, not a projection.

The subscription is at par: one USDG of deposit is one unit of COUPON notional. What the user needs to see before signing:

FieldSource
Coupon per observationv.couponFloorBps to v.couponCapBps before strike (v.refBps reference); v.couponBps after
Barrierv.barrierBps of s0; the strike price v.s0 is set at strike from the feed
Observation datesv.observations, an array of timestamps
Autocall levelv.autocallBps of s0
Feesv.couponFeeBps on coupons, v.notionalFeeBps on matched notional
If breached at maturityStock delivered at s0: amount × 1e20 ÷ s0 in 18-decimal stock units

Minimum ticket (v.minTicket) and the deadline (v.subscriptionEnd) come from the series; a deposit after the deadline or below the minimum reverts.

usdg.approve(address(core), amount);
core.depositCoupon(seriesId, amount);

The deposit sits in escrow until strike. If the series is under-matched the unmatched part is refunded (core.refund(seriesId)); the matched part becomes COUPON units in NoteLegs, id (seriesId << 1) | 0. A wallet that wants the user to hold the leg directly simply lets the user’s address be the depositor.

// claimable now
uint256 owed = core.accruedCoupon(seriesId, owner);
// pays coupons to the caller
core.claim(seriesId);
// principal at autocall or maturity, USDG or stock
core.redeem(seriesId, units);

claim and redeem settle the caller’s position first if strike has happened but settlement has not run for them. Between observations the position needs no action; coupons accrue to the holder of the leg and follow the leg on transfer.

For a position card, the three numbers users care about are accruedCoupon, the next observation date and the distance to the barrier (lastPrice ÷ barrierPrice − 1).

The other side of every note is the SHIELD leg: stock plus a small prefund, earning the coupons the COUPON side pays. A broker can offer it to holders of the underlying. See Subscribe SHIELD for requiredPrefund and depositShield.

Events for every step are listed under Events. A stock page needs none of them: the reads above are enough and are bounded per stock.