AlphaEdge
An Intraday Workspace That Was Built to Refuse
At a Glance
- 141
- commits across three and a half months
- 1,348
- tests passing across two Python interpreters
- 103
- candlestick patterns in the recognition subsystem
- 257
- Sensex sessions in the chase-and-hold empirical test
- ~12%
- of sessions that are trend days — the only ones worth trading
- HTTP 410
- returned by every mutation path, enforcing monitoring-only structurally
- 13
- scheduled jobs, of which nothing read the newest one's log for 16 consecutive failures
- +0.990
- correlation between job overlap and slowdown, in a defect nothing reported
The brief
A trading day produces a verdict by 3:30 PM whether or not the trader deserves one. AlphaEdge was built to put a second, better-founded verdict next to it: what the market regime actually is, whether a structure has confirmed, and whether today is a day to act at all.
The single most consequential design decision was made first and never revisited: the system advises and tracks. It cannot execute. No auto-trading, no order placement, no exception. It is a deliberate guard against a weakness its own operator had already diagnosed in himself — and it is enforced in the architecture rather than in the documentation, with every mutation path in the API returning HTTP 410 Gone.
Stack: Python / FastAPI, React / Vite / TypeScript, SQLite, Angel One SmartAPI.
What It Actually Answers
Regime. Trend or range, read live. This is the product's most valuable output and it came from a test rather than an opinion.
Structure. Structure-aware coil triggers with OR logic for BankNifty, so a move-in-progress is not mistaken for a fresh, structure-confirmed entry.
Sanity. Risk-reward ceilings as guardrails: any setup showing better than roughly 8:1 is flagged red, on the reasoning that an implausibly good ratio is more likely a measurement error than an opportunity.
Pattern. A 103-pattern candlestick recognition subsystem, built against a single licensed source text, with seven distinct PDF-extraction defects found and fixed during ingestion — and an explicit two-namespace rule keeping the book's published statistics permanently separate from locally-measured ones, so a printed claim can never quietly become an observed result.
Breadth. A C5 emerging-cap scanner running a nightly pipeline against BSE sources, designed to survive data-source outages without losing data.
Timeline
| Date | Milestone | What landed |
|---|---|---|
| 31 May | Project start | Backend, tracking-only invariant established. |
| 9 Jun | Signal logic | BankNifty OR logic; structure-aware coil trigger; RR sanity bounds. Built in the repository, deliberately not in chat. |
| 11 Aug | Live session | Regime-flip alert binding; coil trigger fixes; RR ceiling guardrails; the Gann null result. 561 tests on the main dashboard, 656 on Signal Lab, four known defects held open and named rather than quietly closed. |
| 11 Aug | A real handoff failure, named | Two distinct surfaces (dashboard and Signal Lab) were treated as one across three handoff documents, each executed exactly where it pointed without ever flagging that the operator's actual daily-use dashboard was not the one being changed. |
| 28 Aug | Build record | Three months compiled. 134 commits, 1,323 tests. Python 3.12 migration. First unattended overnight run. |
| 28 Aug – 7 Sep | Unattended operation | Nine consecutive days of real running, with real network weather. |
| 7 Sep | Revision 2 | The 21:15 scheduling defect surfaced, fully understood, correct fix identified. Disk-growth risk flagged before outage. |
Two Empirical Results, Both Negative, Both Kept
The most valuable output of this project is not a feature. It is two findings that closed off avenues rather than opening them.
The Gann null. Tested directly, came back null, recorded as null. No partial rescue, no "needs more tuning," no quiet retention in a corner of the interface.
The chase-and-hold test across 257 Sensex sessions. Trend days — roughly 12% of all sessions — return positively. Non-trend days produce negative expectancy. The conclusion was not a feature but a behavioural commitment: sit out chop days. A dashboard that tells its operator to do nothing on 88% of days is an unusual product, and it is the correct one.
This is the strongest single argument for the whole system's existence: it converted a felt intuition into a measured rule with a number attached, and the rule points away from activity.
The Failures That Taught the Most
The logzero catch — the sharpest finding in three months. A dependency (smartapi-python) imported a logging library at module scope without declaring it. In the new Python 3.12 environment that library was silently absent, meaning the live market adapter would have gone on reporting healthy while actually broken. The profound part: MOCK-mode testing, chosen deliberately to make testing safe — no real broker calls, no accidental alerts — was structurally incapable of catching this failure, because MOCK never touches the SDK that was broken. The safety measure and the blind spot were the same decision.
The C5 locked-database incident — a nested bug. A SQLite lock-contention failure during an unusually long overnight run caused an unguarded pipeline stage to crash before it could record why it crashed. The first guard attempt was itself wrong: the session.rollback() needed to recover the session also expires and discards every attribute just written. Solved by accumulating values into a local dict inside the guarded block and applying them with setattr only after the guard succeeded.
The segfault investigation. Seven SIGSEGV crashes in a single day. Threading ruled out, the crash report's own memory summary read correctly, and the true cause identified as self-inflicted memory exhaustion from an over-aggressive 30-agent parallel workflow on an 8GB machine — rather than assumed to be disk or a code defect. Zero Python crashes in the nine days after migration. The migration is validated by nine days of nothing going wrong, which is a different and stronger kind of evidence than a passing smoke test.
The tool cascade. Ten backend files, five test files and a frontend module destroyed outright by a tooling failure. Entirely reconstructed.
Two unexplained files. Files appeared in a session scratchpad with names no instruction had chosen. The scratchpad was cleared before they were inspected, so their contents will never be known. Recorded permanently as unexplained rather than given an invented explanation.
The 21:15 Defect
A pattern-radar refresh job was scheduled at a fixed 21:15, on the assumption the 20:30 C5 pipeline would have finished by then. Across nine days of unattended running it overlapped with C5 on every single scheduled night — never once landing in the assumed gap.
| Measure | Value |
|---|---|
| Overlap range | 2.2 – 102.6 minutes |
| Refresh duration, uncontended | 1.1 minutes |
| Refresh duration, maximum contention | 152.4 minutes |
| Variation | 137× |
| Correlation, overlap against slowdown | +0.990 |
The root-cause honesty is the substance here. The fixed 45-minute offset was chosen from a duration distribution that had already been observed violating that same assumption — runs of over 1,000, 2,000 and 4,000 seconds were on record before the schedule was written. Not bad luck discovered later. Evidence that existed at the time and was not acted on.
It never failed, which is the more unsettling part. It survived every night purely because an earlier, unrelated fix — a 60-second busy timeout introduced during the lock incident — happened to absorb contention it was never designed to address. A real defect ran for nine consecutive nights, costing real time every night, completely invisible in the system's own success/failure output because something else caught the fall.
The fix landed, and the honest result is that it only half worked. Sequencing on the actual C5 completion record — polling for a terminal-status run row instead of assuming a fixed offset would be late enough — shipped as c616df1. Overlap-driven failures are gone and the best case went from 152 minutes to 62 seconds.
But the duration still ranges 62 seconds to 8 hours, and the cause of the rest is unknown. An 8-hour run on 9 September and a 2-hour run on 15 September both happened with C5 not running. So contention was a major cause and demonstrably not the only one. The measured correlation of +0.990 was real and the fix derived from it was correct; it simply was not the whole story. Still open.
The principle it produced: verification proves a change works; only operation proves it was the right change. The second half of that sentence is doing the work here: the fix verified, operated, and revealed a second cause underneath the first.
And the same shape appeared again, on a newer job. A flow-capture task failed identically sixteen times with no signal, because nothing read its log. The healthcheck now checks scheduled-job outcomes — but it was added only after the cost was paid, and it covers three of the thirteen jobs. A defect that never fails is invisible; so is one that fails every time where nobody is looking.
Risk Held Openly
Disk space fell from 12GB free to 5GB free — 98% used — across nine days, with c5.sqlite alone growing from 583MB to 624MB. The operating system refused a software update for lack of space. It bottomed at 2.9GB, 99% used.
It has since recovered to 14GB free, 93% — and the distinction matters more than the number. That came from a one-off cleanup and newly-added log rotation, which reclaimed 39MB of archives. It did not come from any mechanism that throttles or prunes the warehouse, because none exists. c5.sqlite is 684.6MB now, up from 583MB in three weeks, and bars_cache.sqlite is 1.4GB. Nothing prunes either.
So the outage was deferred, not prevented, and the trend resumes from a higher floor. Flagged in the record before it became an outage, and still flagged after it did not.
Security posture, separately audited: no credentials leaked; Telegram bot token rotated; Angel API key confirmed inert without login secrets.
Standing Rules the Project Produced
- Advise, never execute. Enforce the invariant in the architecture, not the documentation.
- Distinguish "we could not measure" from "the measurement is zero."
- Keep two namespaces: published statistics and locally-measured statistics never mix.
- A risk-reward ratio that looks too good is a measurement error until proven otherwise.
- A safety measure and a blind spot can be the same decision. Ask what your test mode structurally cannot see.
- Verification proves a change works; only operation proves it was the right change.
- A defect that never fails is still a defect. Success/failure output is not a performance record.
- Name the four known defects. Do not close them quietly.
What It Demonstrates
Three months of solitary systems engineering with no team, no user besides its author, and no tolerance for a comfortable answer. The product's most valuable output is a rule that instructs its own operator to stay out of the market on nine days in ten — a finding derived from 257 sessions of real data, and one that no dashboard built to encourage engagement would ever have surfaced.
Assets to attach: regime-tinted topology field, the liquid-glass interface at 3200 × 2000, Signal Lab, the C5 scanner, the pattern subsystem. Demo data must be labelled as such; live figures must not be implied.
Materials not yet approved for publication. Interface captures show demo data and are labelled as such. Live figures are not implied.