fix(prices): stop rescaling an ADS market cap onto the issuer's ordinary share count - #4417
Merged
Conversation
…ary share count
A company whose US listing is an American Depositary Share has an SEC cover
page counting ORDINARY shares while its price is quoted per receipt. The Yahoo
key-stats sync rescales the feed's market cap onto the EDGAR share base, so for
these issuers it multiplied a correct figure by the deposit ratio: BeOne
Medicines (ONC, 13 ordinary per ADS) stored $557.0B against a true ~$42.9B.
Neither existing guard sees it. The foreign-private-issuer check is form-based
and ONC files 10-K, and the same-unit ratio check draws its line at 300x, far
above any real deposit ratio (ONC 13x, SNY and AZN 2x). The damage is also
invisible downstream, because the stored pair stays self-consistent: cap over
shares still equals the real ADS close, so nothing that inspects the pair can
tell it apart from a correctly priced company.
Ask the issuer's own registered 12(b) title instead. It is already materialized
on the stock for its own ticker, and it states the listed unit outright. Both
writers of CommonStock.SharesOutStanding consult it, or the facts importer
would put the count back on the ordinary base every cycle while the price lane
kept the cap on the ADS base. The ratio is never read out of the title, only
the fact that the listing is a receipt, so the repair is to stop rescaling
rather than to divide: the feed's figure is already on the listed unit and now
stands verbatim, exactly as it does for a 20-F filer.
The pattern accepts the "Depository" misspelling that four filers registered,
and requires "American" so the far commoner preferred form ("Depositary Shares,
each representing a 1/1,000th interest in ... Preferred Stock") cannot match.
Self-heals on the next enrichment rotation; no data fix needed.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
A company whose US listing is an American Depositary Share has an SEC cover page counting ordinary shares, while its price is quoted per receipt.
YahooPriceImportServicerescales the feed's market cap onto the EDGAR share base, so for these issuers it multiplied a correct figure by the deposit ratio.BeOne Medicines (
ONC, 13 ordinary per ADS) in production:557,045,957,486.84~42.85e91,478,124,405(ordinary)113,701,877(ADS)557,045,957,486.84 / 1,478,124,405 = 376.86, which is the real ADS close that session. That is what makes it dangerous: the stored pair is internally consistent, so nothing that inspects the pair can tell it apart from a correctly priced company, and the inflated cap flows into every surface that ranks on market capitalization.Neither existing guard sees it:
IsForeignPrivateIssueris form-based, and ONC files 10-K/10-Q.ShareBasisPlausibility.MaxPlausibleSameUnitRatiois 300x, far above any real deposit ratio (ONC 13x, SNY and AZN 2x), so the figures alone can never expose it.Fix
Ask the issuer's own registered 12(b) title, which states the listed unit outright and is already materialized on
CommonStock.ListedSecurityTitlebyXbrlFactExtractionServicefor the stock's own ticker.ListedSecurityClassifier.IsAmericanDepositary(title), a separate question fromClassify(an ADS over ordinary shares is still common equity and still classifies as such). Matched against the raw title, because a filer can bury the phrase in a parenthetical thatClassifystrips.CommonStock.SharesOutStanding. Only guarding the price lane would leave the facts importer putting the count back on the ordinary base every cycle while the price lane kept the cap on the ADS base, and the two would undo each other forever.The pattern accepts the
Depositorymisspelling four filers actually registered (ARBK,IX,ALAR,NICM), and requiresAmericanso the far commoner preferred form (Depositary Shares, each representing a 1/1,000th interest in ... Preferred Stock) cannot match. Global Depositary Shares are deliberately out of scope and documented as such: the one GDS issuer on record files as an FPI, so the form-based guard answers for it.Tests
+27tests, all values read from the production store rather than invented:ListedSecurityClassifierDepositaryTests(26) works realdei:Security12bTitlestrings, both spellings, singular/plural, receipts, parenthetical-embedded, and the negatives that must not fire.YahooPriceImportServiceAdsMarketCapTests(3) pins the defect in ONC's own numbers (reproducing the$557.0Bto within a rounding error of the close), pins that withholding the count leaves the feed's cap verbatim, and pins that13xsits far inside the same-unit tolerance, which is why the title has to be asked first.dotnet csharpier check .clean,dotnet build Equibles.sln -c Release0 errors, full unit suite 4,466 passed / 0 failed.Rollout
Additive, no migration. Self-heals on the next enrichment rotation for each affected stock, so no manual data fix.
Blast radius in production: 332 stocks carry an ADS title and a non-zero market cap.
A.L.V.I.S.