cyan-eclipse-book 0.1.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- cyan_eclipse_book-0.1.0/.github/workflows/ci.yml +37 -0
- cyan_eclipse_book-0.1.0/.github/workflows/publish-mcp-registry.yml +30 -0
- cyan_eclipse_book-0.1.0/.github/workflows/publish-pypi.yml +64 -0
- cyan_eclipse_book-0.1.0/.github/workflows/release.yml +33 -0
- cyan_eclipse_book-0.1.0/.gitignore +18 -0
- cyan_eclipse_book-0.1.0/BENCH-VERITY.md +156 -0
- cyan_eclipse_book-0.1.0/LICENSE +21 -0
- cyan_eclipse_book-0.1.0/OWNER-HANDS.md +33 -0
- cyan_eclipse_book-0.1.0/PKG-INFO +50 -0
- cyan_eclipse_book-0.1.0/PYPI_README.md +31 -0
- cyan_eclipse_book-0.1.0/README.md +43 -0
- cyan_eclipse_book-0.1.0/VERSION +1 -0
- cyan_eclipse_book-0.1.0/bazaar-manifest.json +66 -0
- cyan_eclipse_book-0.1.0/book_engine.py +619 -0
- cyan_eclipse_book-0.1.0/fixtures.json +1 -0
- cyan_eclipse_book-0.1.0/glama.json +6 -0
- cyan_eclipse_book-0.1.0/icon-512.png +0 -0
- cyan_eclipse_book-0.1.0/make_icon.py +51 -0
- cyan_eclipse_book-0.1.0/pyproject.toml +47 -0
- cyan_eclipse_book-0.1.0/server.json +32 -0
- cyan_eclipse_book-0.1.0/server.py +428 -0
- cyan_eclipse_book-0.1.0/smoke.py +118 -0
- cyan_eclipse_book-0.1.0/tests/test_book.py +414 -0
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
branches: [main]
|
|
6
|
+
pull_request:
|
|
7
|
+
|
|
8
|
+
permissions:
|
|
9
|
+
contents: read
|
|
10
|
+
|
|
11
|
+
concurrency:
|
|
12
|
+
group: ci-${{ github.ref }}
|
|
13
|
+
cancel-in-progress: true
|
|
14
|
+
|
|
15
|
+
jobs:
|
|
16
|
+
test:
|
|
17
|
+
runs-on: ubuntu-latest
|
|
18
|
+
steps:
|
|
19
|
+
- uses: actions/checkout@v4
|
|
20
|
+
|
|
21
|
+
- uses: actions/setup-python@v5
|
|
22
|
+
with:
|
|
23
|
+
python-version: "3.12"
|
|
24
|
+
|
|
25
|
+
- name: Byte-compile all Python sources
|
|
26
|
+
run: python -m compileall -q .
|
|
27
|
+
|
|
28
|
+
- name: Validate JSON files
|
|
29
|
+
run: |
|
|
30
|
+
for f in *.json; do
|
|
31
|
+
[ -e "$f" ] || continue
|
|
32
|
+
python -m json.tool "$f" > /dev/null && echo "OK $f"
|
|
33
|
+
done
|
|
34
|
+
|
|
35
|
+
- name: MCP initialize handshake smoke
|
|
36
|
+
run: |
|
|
37
|
+
printf '%s\n' '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2024-11-05","capabilities":{},"clientInfo":{"name":"ci","version":"0"}}}' | timeout 30 python server.py | grep -q '"result"'
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
name: Publish to Official MCP Registry
|
|
2
|
+
|
|
3
|
+
# Publishes server.json to registry.modelcontextprotocol.io using GitHub OIDC
|
|
4
|
+
# (no stored secrets). Run manually after changing server.json - each publish
|
|
5
|
+
# needs a new unique "version" in server.json.
|
|
6
|
+
on:
|
|
7
|
+
workflow_dispatch:
|
|
8
|
+
|
|
9
|
+
permissions:
|
|
10
|
+
id-token: write
|
|
11
|
+
contents: read
|
|
12
|
+
|
|
13
|
+
jobs:
|
|
14
|
+
publish:
|
|
15
|
+
runs-on: ubuntu-latest
|
|
16
|
+
steps:
|
|
17
|
+
- uses: actions/checkout@v4
|
|
18
|
+
|
|
19
|
+
- name: Install mcp-publisher
|
|
20
|
+
run: |
|
|
21
|
+
curl -L "https://github.com/modelcontextprotocol/registry/releases/download/v1.8.4/mcp-publisher_linux_amd64.tar.gz" | tar xz mcp-publisher
|
|
22
|
+
|
|
23
|
+
- name: Validate server.json
|
|
24
|
+
run: ./mcp-publisher validate
|
|
25
|
+
|
|
26
|
+
- name: Login with GitHub OIDC
|
|
27
|
+
run: ./mcp-publisher login github-oidc
|
|
28
|
+
|
|
29
|
+
- name: Publish
|
|
30
|
+
run: ./mcp-publisher publish
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
name: Publish to PyPI
|
|
2
|
+
|
|
3
|
+
# Gate S5 (applies to every artifact in the PyPI slate): releases
|
|
4
|
+
# build ONLY here, from a tagged commit, and publish via Trusted
|
|
5
|
+
# Publishing (OIDC) - no long-lived PyPI tokens anywhere, no laptop
|
|
6
|
+
# uploads. PEP 740 attestations are generated by the publish action.
|
|
7
|
+
on:
|
|
8
|
+
push:
|
|
9
|
+
tags: ["v*"]
|
|
10
|
+
workflow_dispatch:
|
|
11
|
+
|
|
12
|
+
permissions:
|
|
13
|
+
contents: read
|
|
14
|
+
|
|
15
|
+
concurrency:
|
|
16
|
+
group: publish-pypi-${{ github.ref }}
|
|
17
|
+
cancel-in-progress: false
|
|
18
|
+
|
|
19
|
+
jobs:
|
|
20
|
+
build:
|
|
21
|
+
runs-on: ubuntu-latest
|
|
22
|
+
steps:
|
|
23
|
+
- uses: actions/checkout@v4
|
|
24
|
+
|
|
25
|
+
- uses: actions/setup-python@v5
|
|
26
|
+
with:
|
|
27
|
+
python-version: "3.12"
|
|
28
|
+
|
|
29
|
+
- name: Run the test suite
|
|
30
|
+
run: python -m unittest discover -s tests
|
|
31
|
+
|
|
32
|
+
- name: Build wheel + sdist
|
|
33
|
+
run: |
|
|
34
|
+
pip install build
|
|
35
|
+
python -m build
|
|
36
|
+
|
|
37
|
+
- name: twine check
|
|
38
|
+
run: |
|
|
39
|
+
pip install twine
|
|
40
|
+
twine check dist/*
|
|
41
|
+
|
|
42
|
+
- uses: actions/upload-artifact@v4
|
|
43
|
+
with:
|
|
44
|
+
name: dist
|
|
45
|
+
path: dist/
|
|
46
|
+
|
|
47
|
+
publish:
|
|
48
|
+
needs: build
|
|
49
|
+
runs-on: ubuntu-latest
|
|
50
|
+
environment:
|
|
51
|
+
name: pypi
|
|
52
|
+
url: https://pypi.org/project/cyan-eclipse-book/
|
|
53
|
+
permissions:
|
|
54
|
+
id-token: write
|
|
55
|
+
steps:
|
|
56
|
+
- uses: actions/download-artifact@v4
|
|
57
|
+
with:
|
|
58
|
+
name: dist
|
|
59
|
+
path: dist/
|
|
60
|
+
|
|
61
|
+
- name: Publish to PyPI (Trusted Publishing, PEP 740 attestations)
|
|
62
|
+
uses: pypa/gh-action-pypi-publish@release/v1
|
|
63
|
+
with:
|
|
64
|
+
attestations: true
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
name: Release
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
tags: ["v*"]
|
|
6
|
+
|
|
7
|
+
permissions:
|
|
8
|
+
contents: write
|
|
9
|
+
|
|
10
|
+
concurrency:
|
|
11
|
+
group: release-${{ github.ref }}
|
|
12
|
+
cancel-in-progress: false
|
|
13
|
+
|
|
14
|
+
jobs:
|
|
15
|
+
release:
|
|
16
|
+
runs-on: ubuntu-latest
|
|
17
|
+
steps:
|
|
18
|
+
- uses: actions/checkout@v4
|
|
19
|
+
|
|
20
|
+
- name: Build distributable (git archive of the tag)
|
|
21
|
+
run: |
|
|
22
|
+
name="eclipse-book-mcp-${GITHUB_REF_NAME}"
|
|
23
|
+
git archive --format=zip --prefix="${name}/" -o "${name}.zip" HEAD
|
|
24
|
+
ls -la "${name}.zip"
|
|
25
|
+
|
|
26
|
+
- name: Publish GitHub Release with artifact
|
|
27
|
+
env:
|
|
28
|
+
GH_TOKEN: ${{ github.token }}
|
|
29
|
+
run: |
|
|
30
|
+
gh release create "${GITHUB_REF_NAME}" \
|
|
31
|
+
--title "${GITHUB_REF_NAME}" \
|
|
32
|
+
--generate-notes \
|
|
33
|
+
"eclipse-book-mcp-${GITHUB_REF_NAME}.zip"
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
data/
|
|
2
|
+
__pycache__/
|
|
3
|
+
keys/
|
|
4
|
+
*.key
|
|
5
|
+
*.pem
|
|
6
|
+
.env
|
|
7
|
+
.env.*
|
|
8
|
+
*.pyc
|
|
9
|
+
state/
|
|
10
|
+
|
|
11
|
+
# --- probe-mirror standard protections (2026-11-02) ---
|
|
12
|
+
id_rsa*
|
|
13
|
+
.git-credentials
|
|
14
|
+
credentials*.json
|
|
15
|
+
*secret*
|
|
16
|
+
*.tfstate
|
|
17
|
+
*.tfstate.*
|
|
18
|
+
.mcp.json
|
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
# BENCH-VERITY — Cyan Eclipse Book MCP v0.1.0
|
|
2
|
+
|
|
3
|
+
**Verdict: PASS-WITH-CONDITIONS**
|
|
4
|
+
**Scope: local stdio build (working tree of `eclipse-book-mcp`,
|
|
5
|
+
v0.1.0, as run from this network seat (VM egress,
|
|
6
|
+
America/Los_Angeles host) on 2026-11-02/03.** Bench:
|
|
7
|
+
`/tmp/bench-evidence/bench_book.py` — 28 independent checks,
|
|
8
|
+
black-box over stdio JSON-RPC; the bench never imports
|
|
9
|
+
`book_engine` — fee math, quote fields, criteria hashes and the
|
|
10
|
+
receipt chain were recomputed by the bench's own Decimal/sha256
|
|
11
|
+
code from raw inputs. Builder's own suites re-run green from a
|
|
12
|
+
clean sibling checkout (19/19 unittest + stdio smoke) — baseline
|
|
13
|
+
only, not bench evidence. Live venue payloads were fetched by
|
|
14
|
+
the bench seat itself from the venues' public APIs (direct
|
|
15
|
+
egress, no auth, no accounts, no keys) and fed through the
|
|
16
|
+
server's transport seam (`instrument_ingest` / `book_ingest`) —
|
|
17
|
+
M0 contains no network code path of its own (verified at source:
|
|
18
|
+
no socket/urllib/http code in `server.py` / `book_engine.py`).
|
|
19
|
+
|
|
20
|
+
## What was verified
|
|
21
|
+
|
|
22
|
+
- **Handshake + surface (B1–B2).** `initialize` returns
|
|
23
|
+
`eclipse-book` / `0.1.0`; `tools/list` is exactly the 17 M0
|
|
24
|
+
tools the manifest claims — no more, no fewer.
|
|
25
|
+
- **Denylist (B3).** 17 forbidden/variant names — `order_place`,
|
|
26
|
+
`withdraw`, `recommend`, `probability_get`, `signal_get`,
|
|
27
|
+
`buy`, `sell`, `account_get`, plus case variants
|
|
28
|
+
(`Order_Place`, `ORDER_SUBMIT`), a separator variant and a
|
|
29
|
+
Cyrillic-confusable `probаbility_get` — all refused with
|
|
30
|
+
JSON-RPC `-32602` by name.
|
|
31
|
+
- **Malformed args (B4).** Missing required fields refuse with
|
|
32
|
+
named `ToolError`s (`INSTRUMENT_FIELD_REQUIRED`,
|
|
33
|
+
`RESOLUTION_CRITERIA_REQUIRED`); a missing `size` on
|
|
34
|
+
`quote_get` surfaces a JSON-RPC error and the process stays
|
|
35
|
+
alive and correct afterwards (no crash).
|
|
36
|
+
- **Live Kalshi read (B5–B6).** Market `KXFEDDECISION-28JAN-H26`
|
|
37
|
+
fetched live: verbatim `rules_primary` ingested as the
|
|
38
|
+
resolution criteria; the bench's independent sha256 of the
|
|
39
|
+
criteria text matches the stored criteria hash. Kalshi's
|
|
40
|
+
native status `active` — not in the core vocabulary —
|
|
41
|
+
surfaced as `UNMAPPED` with the native string preserved,
|
|
42
|
+
never coerced. The live order book (YES bids as published;
|
|
43
|
+
YES asks derived from NO bids as `1 − price`, the venue's own
|
|
44
|
+
book construction) produced a quote whose bid / ask / mid /
|
|
45
|
+
spread_bps / liquidity flag matched the bench's independent
|
|
46
|
+
recomputation exactly (0.08 / 0.14 / 0.11 / 5454.54… bps /
|
|
47
|
+
THIN — $14.42 notional at best ask). With no Kalshi fee
|
|
48
|
+
schedule registered, the quote carried
|
|
49
|
+
`fee_status: NO_SCHEDULE` and both all-in fields degraded to
|
|
50
|
+
`FEE_UNVERIFIED` — no wrong number quoted. The verbatim
|
|
51
|
+
criteria + its hash ride on the quote.
|
|
52
|
+
- **Live Polymarket read (B7).** Gamma market
|
|
53
|
+
`will-gavin-newsom-win-the-2028-democratic-presidential-nomination-568`
|
|
54
|
+
+ its live CLOB book (46 levels, returned unsorted by the
|
|
55
|
+
venue) fed raw through `book_ingest`: the core sorted to the
|
|
56
|
+
bench's independently computed best bid 0.157 / best ask
|
|
57
|
+
0.158.
|
|
58
|
+
- **Fee truth (B8–B9).** On the bench's own numbers (25 bps,
|
|
59
|
+
100.00/100.50 book, size 40): all-in buy 4030.05 (fee 10.05),
|
|
60
|
+
all-in sell 3990 (fee 10), per-unit figures exact to the
|
|
61
|
+
string; liquidity DEEP at $50,250 notional. A schedule 72 h
|
|
62
|
+
old against a 24 h freshness window → `fee_status: STALE`,
|
|
63
|
+
all-in fields `FEE_UNVERIFIED`. A 0-bps FRESH schedule on the
|
|
64
|
+
live Kalshi book: all-in buy total exactly 1.4 (0.14 × 10,
|
|
65
|
+
fee 0).
|
|
66
|
+
- **Probability law (B10, B15).** An ingest carrying
|
|
67
|
+
`provenance.probability_of_yes` was refused
|
|
68
|
+
`PROBABILITY_FIELD_FORBIDDEN` **pre-commit** — no instrument
|
|
69
|
+
persisted, receipt count unchanged (the 2026-10-25 Test Bench
|
|
70
|
+
post-commit observation is closed in this build). A nested,
|
|
71
|
+
capitalized `trading_window.window.Probability` key was
|
|
72
|
+
likewise refused. A scan of all 31 outputs produced during
|
|
73
|
+
the bench found no probability-, recommendation-, signal-,
|
|
74
|
+
advice- or rating-shaped key anywhere.
|
|
75
|
+
- **Criteria pinning (B11).** Position opened on the live
|
|
76
|
+
Kalshi instrument; a one-word criteria edit on re-ingest
|
|
77
|
+
produced a `CRITERIA_CHANGED` event (old hash = the live
|
|
78
|
+
rules hash), and the position still carries the as-of-entry
|
|
79
|
+
criteria + hash with `criteria_changed_since_entry: true`.
|
|
80
|
+
- **Resolution fences (B12).** `resolution_verify` against a
|
|
81
|
+
wrong source was refused by name
|
|
82
|
+
(`RESOLUTION_SOURCE_MISMATCH`, naming 'Federal Reserve'); an
|
|
83
|
+
open dispute blocked verification (`RESOLUTION_DISPUTED`);
|
|
84
|
+
after `dispute_cleared`, verification against the criteria's
|
|
85
|
+
own named source → `VERIFIED`.
|
|
86
|
+
- **Order fence (B13).** `ICEBERG` refused
|
|
87
|
+
(`ORDER_TYPE_NOT_IN_V1_ALLOWLIST`); a LIMIT draft records
|
|
88
|
+
`status: DRAFT`, `mandate_pre_eval:
|
|
89
|
+
NOT_EVALUATED_M0_DATA_ONLY`, with a receipt ref. No
|
|
90
|
+
submission path exists.
|
|
91
|
+
- **Ledger (B14).** The bench recomputed the full receipt
|
|
92
|
+
hash chain from the state file with its own implementation —
|
|
93
|
+
12 receipts, chain valid, matching the server's own
|
|
94
|
+
`chain_valid: true`.
|
|
95
|
+
- **Venue status (B16).** `capability: M0_DATA_ONLY`,
|
|
96
|
+
`order_tools: ABSENT`, `account_tools: ABSENT`.
|
|
97
|
+
|
|
98
|
+
## Conditions
|
|
99
|
+
|
|
100
|
+
- **C-B1 (minor, non-blocking).** `max_payout_for_size` — a
|
|
101
|
+
fee-independent figure (size × $1) — is attached to an
|
|
102
|
+
event-contract quote only when the fee schedule is FRESH;
|
|
103
|
+
under `NO_SCHEDULE` / `STALE` it is omitted along with the
|
|
104
|
+
all-in fields. Absence, never a wrong number — but the
|
|
105
|
+
payout does not depend on the fee schedule and the spec's
|
|
106
|
+
quote shape implies it attaches. Queued as an M1 fix.
|
|
107
|
+
- **C-B2 (publish hygiene, non-blocking for use).** Version
|
|
108
|
+
drift: `server.json` reads 0.1.1 while `VERSION`,
|
|
109
|
+
`pyproject.toml` and the server's own version string read
|
|
110
|
+
0.1.0. OWNER-HANDS ship-day step 1 requires agreement before
|
|
111
|
+
tagging; reconcile before the PyPI/MCP-Registry publish.
|
|
112
|
+
|
|
113
|
+
## Scope fences on this verdict
|
|
114
|
+
|
|
115
|
+
- PASS-WITH-CONDITIONS covers the M0 data core above: local
|
|
116
|
+
stdio build + live **public reads** from Kalshi and
|
|
117
|
+
Polymarket as ingested through the transport seam from this
|
|
118
|
+
seat on 2026-11-03. Book itself makes no network calls; the
|
|
119
|
+
live step verified is the seam + normalization + law against
|
|
120
|
+
real venue payloads, not a shipped venue adapter.
|
|
121
|
+
- NOT_RUN / out of scope, unchanged from the manifest: order
|
|
122
|
+
placement, account reads, the Wallet mandate gate (M2/M1,
|
|
123
|
+
owner-gated, spec §18 D3); fee schedules as live venue data
|
|
124
|
+
(Kalshi's published fee formula is not bps-shaped; no live
|
|
125
|
+
schedule was registered for a venue — venue quotes honestly
|
|
126
|
+
degrade to `FEE_UNVERIFIED`); Polymarket US / Kraken /
|
|
127
|
+
Binance.US / Alpaca chapters (specced, not built).
|
|
128
|
+
- The market-data gate fences were probed, not assumed: no
|
|
129
|
+
tool emits a recommendation, signal, ranking or probability
|
|
130
|
+
(B3/B10/B15); copy in README + manifest carries no
|
|
131
|
+
advice-shaped claims.
|
|
132
|
+
|
|
133
|
+
— Verity bench, 2026-11-02
|
|
134
|
+
|
|
135
|
+
**Postscript (2026-11-02, ship-day execution).** C-B2
|
|
136
|
+
reconciled to 0.1.0 across VERSION / pyproject / server.json
|
|
137
|
+
(the MCP Registry already held book@0.1.0, so the registry
|
|
138
|
+
snapshot and the package now describe the same build); tree
|
|
139
|
+
committed (371b61e) and tag v0.1.0 pushed. The Publish-to-PyPI
|
|
140
|
+
run (gh 41557921209) FAILED in the build job's test step —
|
|
141
|
+
the test loader assumed the suite's sibling layout, which a
|
|
142
|
+
standalone checkout doesn't have — and the publish job never
|
|
143
|
+
ran: nothing reached PyPI (verified after the fact via the
|
|
144
|
+
JSON API, the simple index, and pip; an interim "uploaded"
|
|
145
|
+
reading from this VM's egress was a false signal and is
|
|
146
|
+
withdrawn). Loader fixed with an in-repo fallback + the
|
|
147
|
+
cross-adapter parity test now skips with a stated reason
|
|
148
|
+
when siblings are absent (commit c60ba0d; standalone suite
|
|
149
|
+
green: 18 pass + 1 skip; sibling layout 19/19 + smoke).
|
|
150
|
+
OWNER-HANDS' Trusted Publisher table also named the wrong
|
|
151
|
+
repo (`eclipse-book-mcp`; actual: `cyan-eclipse-book-mcp`) —
|
|
152
|
+
corrected in the same commit. Re-run is HELD pending the
|
|
153
|
+
owner's delete + re-add of the pending publisher under the
|
|
154
|
+
corrected repo name; on his confirmation the v0.1.0 tag
|
|
155
|
+
re-points to c60ba0d and the workflow re-runs by dispatch on
|
|
156
|
+
that ref.
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Cyan Eclipse Technologies LLC
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# OWNER-HANDS - cyan-eclipse-book PyPI launch (renamed from eclipse-book, 2026-10-28)
|
|
2
|
+
|
|
3
|
+
Everything in this file is done **by the owner, in the owner's
|
|
4
|
+
browser**. The package is built and locally proven (wheel + sdist,
|
|
5
|
+
clean-venv install, MCP handshake against the installed entry point);
|
|
6
|
+
it is **not yet published** - no Trusted Publisher exists for this
|
|
7
|
+
project yet.
|
|
8
|
+
|
|
9
|
+
> **Stop rule:** no step below creates or hands over an API token.
|
|
10
|
+
> Publishing runs on Trusted Publishing (OIDC) only.
|
|
11
|
+
|
|
12
|
+
## Trusted Publisher for `cyan-eclipse-book` (pending publisher)
|
|
13
|
+
|
|
14
|
+
On <https://pypi.org/manage/account/publishing/> - "Add a new pending
|
|
15
|
+
publisher" - **GitHub** tab. Enter these strings **exactly**:
|
|
16
|
+
|
|
17
|
+
| Field | Value |
|
|
18
|
+
|---|---|
|
|
19
|
+
| PyPI Project Name | `cyan-eclipse-book` |
|
|
20
|
+
| GitHub Repository Owner | `CYAN-ECLIPSE-TECHNOLOGIES-LLC` |
|
|
21
|
+
| GitHub Repository Name | `cyan-eclipse-book-mcp` |
|
|
22
|
+
| GitHub Workflow Name | `publish-pypi.yml` |
|
|
23
|
+
| Environment Name | `pypi` |
|
|
24
|
+
|
|
25
|
+
## Ship day (after the publisher above exists)
|
|
26
|
+
|
|
27
|
+
1. Agent verifies `VERSION` + `server.json` agree at the release
|
|
28
|
+
version and the full test suite is green.
|
|
29
|
+
2. Owner reviews; agent tags `v<version>` and pushes the tag.
|
|
30
|
+
**Do not tag before the Trusted Publisher exists** - the
|
|
31
|
+
`publish-pypi.yml` workflow fires on `v*` tags and will fail.
|
|
32
|
+
3. GitHub Actions then builds, runs `twine check`, and publishes to
|
|
33
|
+
PyPI via Trusted Publishing with PEP 740 attestations.
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
Metadata-Version: 2.5
|
|
2
|
+
Name: cyan-eclipse-book
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Market data + venue access layer — not an exchange: one book, one fee truth, one ledger of record.
|
|
5
|
+
Project-URL: Homepage, https://cetech.ai
|
|
6
|
+
Project-URL: Repository, https://github.com/CYAN-ECLIPSE-TECHNOLOGIES-LLC/eclipse-book-mcp
|
|
7
|
+
Project-URL: Vendor, https://cetech.ai
|
|
8
|
+
Author: Cyan Eclipse Technologies LLC
|
|
9
|
+
License: MIT
|
|
10
|
+
License-File: LICENSE
|
|
11
|
+
Keywords: fees,market-data,mcp,model-context-protocol,venues
|
|
12
|
+
Classifier: Development Status :: 3 - Alpha
|
|
13
|
+
Classifier: Intended Audience :: Developers
|
|
14
|
+
Classifier: License :: OSI Approved :: MIT License
|
|
15
|
+
Classifier: Programming Language :: Python :: 3
|
|
16
|
+
Classifier: Topic :: Software Development :: Libraries
|
|
17
|
+
Requires-Python: >=3.10
|
|
18
|
+
Description-Content-Type: text/markdown
|
|
19
|
+
|
|
20
|
+
# cyan-eclipse-book
|
|
21
|
+
|
|
22
|
+
mcp-name: io.github.CYAN-ECLIPSE-TECHNOLOGIES-LLC/book
|
|
23
|
+
|
|
24
|
+
**What this is:** the MCP server for **Eclipse Book MCP** - The Market Core of the Eclipse Markets suite (spec eclipse-markets-suite-spec-20261025): one canonical Instrument / Book / Quote / Order / Position / Resolution model over exchanges and prediction markets, with venue adapters that translate and never improvise. Resolution criteria are stored verbatim and hash-pinned — a venue criteria edit is a CRITERIA_CHANGED event and positions keep the criteria as of entry. Quotes carry all-in buy/sell cost for a stated size from versioned, provenance-stamped fee schedules; a stale or missing schedule degrades all-in fields to FEE_UNVERIFIED rather than quoting a wrong number. Resolutions move REPORTED -> VERIFIED only against the criteria's own named source (DISPUTED is first-class), and no core output ever carries a probability field — outputs carry price + liquidity flag + depth + verbatim criteria. M0 is data only: no accounts, no keys, no order submission at any tier; order_draft is an unsubmitted record whose mandate pre-evaluation is honestly NOT_EVALUATED until the owner-gated M2.
|
|
25
|
+
|
|
26
|
+
## Run it
|
|
27
|
+
|
|
28
|
+
```console
|
|
29
|
+
$ pip install cyan-eclipse-book
|
|
30
|
+
$ eclipse-book # MCP over stdio, Python stdlib only
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
MCP client config:
|
|
34
|
+
|
|
35
|
+
```json
|
|
36
|
+
{ "mcpServers": { "cyan-eclipse-book": { "command": "uvx", "args": ["--from", "cyan-eclipse-book", "eclipse-book"] } } }
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
## Tools (17)
|
|
40
|
+
|
|
41
|
+
`instrument_ingest` - `instrument_get` - `instrument_search` - `book_ingest` - `quote_get` - `fee_schedule_register` - `fee_schedule_get` - `position_open` - `position_list` - `position_get` - `resolution_report` - `resolution_verify` - `resolution_get` - `order_draft` - `order_get` - `venue_status` - `receipt_list`
|
|
42
|
+
|
|
43
|
+
## Honest scope
|
|
44
|
+
|
|
45
|
+
- In development — v0.1.0 M0 local build (Market Core, data only; fixtures behind transport seams; CERTIFIED(local) — Eclipse Bazaar Test Bench 2026-10-25)
|
|
46
|
+
- State and runtime data files ship in the wheel beside `server.py`,
|
|
47
|
+
at the same relative paths the server reads them from.
|
|
48
|
+
|
|
49
|
+
Powered by Cyan Eclipse Technologies LLC (cetech.ai) - a Veteran-Owned
|
|
50
|
+
Small Business. MIT licensed.
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
# cyan-eclipse-book
|
|
2
|
+
|
|
3
|
+
mcp-name: io.github.CYAN-ECLIPSE-TECHNOLOGIES-LLC/book
|
|
4
|
+
|
|
5
|
+
**What this is:** the MCP server for **Eclipse Book MCP** - The Market Core of the Eclipse Markets suite (spec eclipse-markets-suite-spec-20261025): one canonical Instrument / Book / Quote / Order / Position / Resolution model over exchanges and prediction markets, with venue adapters that translate and never improvise. Resolution criteria are stored verbatim and hash-pinned — a venue criteria edit is a CRITERIA_CHANGED event and positions keep the criteria as of entry. Quotes carry all-in buy/sell cost for a stated size from versioned, provenance-stamped fee schedules; a stale or missing schedule degrades all-in fields to FEE_UNVERIFIED rather than quoting a wrong number. Resolutions move REPORTED -> VERIFIED only against the criteria's own named source (DISPUTED is first-class), and no core output ever carries a probability field — outputs carry price + liquidity flag + depth + verbatim criteria. M0 is data only: no accounts, no keys, no order submission at any tier; order_draft is an unsubmitted record whose mandate pre-evaluation is honestly NOT_EVALUATED until the owner-gated M2.
|
|
6
|
+
|
|
7
|
+
## Run it
|
|
8
|
+
|
|
9
|
+
```console
|
|
10
|
+
$ pip install cyan-eclipse-book
|
|
11
|
+
$ eclipse-book # MCP over stdio, Python stdlib only
|
|
12
|
+
```
|
|
13
|
+
|
|
14
|
+
MCP client config:
|
|
15
|
+
|
|
16
|
+
```json
|
|
17
|
+
{ "mcpServers": { "cyan-eclipse-book": { "command": "uvx", "args": ["--from", "cyan-eclipse-book", "eclipse-book"] } } }
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
## Tools (17)
|
|
21
|
+
|
|
22
|
+
`instrument_ingest` - `instrument_get` - `instrument_search` - `book_ingest` - `quote_get` - `fee_schedule_register` - `fee_schedule_get` - `position_open` - `position_list` - `position_get` - `resolution_report` - `resolution_verify` - `resolution_get` - `order_draft` - `order_get` - `venue_status` - `receipt_list`
|
|
23
|
+
|
|
24
|
+
## Honest scope
|
|
25
|
+
|
|
26
|
+
- In development — v0.1.0 M0 local build (Market Core, data only; fixtures behind transport seams; CERTIFIED(local) — Eclipse Bazaar Test Bench 2026-10-25)
|
|
27
|
+
- State and runtime data files ship in the wheel beside `server.py`,
|
|
28
|
+
at the same relative paths the server reads them from.
|
|
29
|
+
|
|
30
|
+
Powered by Cyan Eclipse Technologies LLC (cetech.ai) - a Veteran-Owned
|
|
31
|
+
Small Business. MIT licensed.
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
# Eclipse Book MCP
|
|
2
|
+
|
|
3
|
+
**Powered by Cyan Eclipse Technologies** — https://cetech.ai
|
|
4
|
+
|
|
5
|
+
**Eclipse Book — market data + venue access layer: exchanges and prediction markets, normalized: one book, one fee truth, one ledger of record.**
|
|
6
|
+
|
|
7
|
+
> **WORKING NAME — conditional pass.** "Eclipse Book" passed the brand §3 naming test conditionally (spec §3.1): the descriptor above is **mandatory** wherever the name appears, because "book" can echo *bookmaker* — and this product is not one. **Eclipse Book is a market data + venue access layer — not an exchange**: it is not a matching engine, never crosses orders, never holds funds, and takes no other side of any trade. The name never appears shortened in sports contexts (spec §2.3).
|
|
8
|
+
|
|
9
|
+
## Why this exists
|
|
10
|
+
|
|
11
|
+
Every price an agent acts on is a fact about **a venue, at a moment, at a depth** — and for event contracts, a fact about a set of words that decide settlement. Raw venue feeds hide all three: fees sit in schedules nobody re-reads, liquidity sits behind a single headline price, and resolution criteria get edited quietly. Book is the normalization + governance core of the Markets suite: one instrument model, one book model, one fee-truth rule, one resolution-verification discipline, one hash-chained ledger — with venue adapters (Forecast, Strike first) that translate and never improvise.
|
|
12
|
+
|
|
13
|
+
## Status — honest labels
|
|
14
|
+
|
|
15
|
+
v0.1.0, phase **M0 (Market Core, data only)**. Local stdio transport, Python stdlib only, **no network calls, no accounts, no API keys, no order submission at any tier, and no certification claimed — bench pending.** Own suites: 16/16 tests + stdio smoke passing. Adapters run against fixtures behind transport seams; live venue reads are a later verification step and are labeled `not_tested` in the manifest. Placement is M2 and owner-gated per venue (spec §18, decision D3); withdrawals are T3-always by design when they arrive (§7.3).
|
|
16
|
+
|
|
17
|
+
## What the core owns
|
|
18
|
+
|
|
19
|
+
- **Canonical objects** — `Instrument`, `Book`, `Quote`, `Order` (draft records only in M0), `Position`, `Resolution`. Decimal strings end-to-end; no float math on money paths.
|
|
20
|
+
- **Native truth preserved (spec §5.2)** — venue statuses that don't map into the core vocabulary surface as `UNMAPPED` with the native string kept, never coerced to the nearest familiar state.
|
|
21
|
+
- **Resolution criteria are part of the instrument (§5.4)** — stored **verbatim**, hash-pinned at first read. If a venue edits criteria mid-market, ingest records a `CRITERIA_CHANGED` event with both hashes; a recorded **position keeps the criteria as of its entry** beside the current text, so the change is flagged, never silently absorbed.
|
|
22
|
+
- **Fee truth (§5.3)** — every `Quote` carries **all-in** buy/sell cost for a stated size, computed from a **versioned, provenance-stamped fee schedule** (source + fetched-at required). A stale or missing schedule degrades the all-in fields to **`FEE_UNVERIFIED`** rather than quoting a wrong number — a wrong all-in is worse than no number.
|
|
23
|
+
- **Resolution lifecycle (§5.4)** — a venue-reported resolution starts `REPORTED` (a claim, not a fact) and becomes `VERIFIED` only when checked against the criteria's **own named source of truth**; any other source is refused by name. `DISPUTED` is a first-class state and blocks verification until the dispute clears.
|
|
24
|
+
- **Liquidity + probability honesty (§5.5)** — every Quote carries price, a core-owned `liquidity_flag` (DEEP / FRAGILE / THIN, from notional at best), depth summary, and — for event contracts — the verbatim criteria. **The core never emits a probability field**: a guard scans every quote/position/resolution output and refuses if a probability-shaped key appears. A 0.90 price on $200 of depth renders as price · THIN · $200 at best · criteria attached — an output that cannot be honestly misread as "90% likely."
|
|
25
|
+
- **The ledger** — append-only, hash-chained receipts (GENESIS-anchored) for ingests, criteria changes, fee-schedule registrations, position records, drafts, and resolution transitions. Tamper-evident by construction and tested.
|
|
26
|
+
|
|
27
|
+
## Tools (17, all M0 data/read/record)
|
|
28
|
+
|
|
29
|
+
`instrument_ingest` · `instrument_get` · `instrument_search` · `book_ingest` · `quote_get` · `fee_schedule_register` · `fee_schedule_get` · `position_open` · `position_list` · `position_get` · `resolution_report` · `resolution_verify` · `resolution_get` · `order_draft` · `order_get` · `venue_status` · `receipt_list`
|
|
30
|
+
|
|
31
|
+
The denylist is stated in code: `order_place`, `order_submit`, `withdraw`, `account_get`, `create_api_key`, `margin_open`, `recommend`, `probability_get`, and kin return JSON-RPC `-32602` by name. `order_draft` builds an **unsubmitted** DRAFT (MARKET/LIMIT only) whose mandate pre-evaluation honestly reads `NOT_EVALUATED_M0_DATA_ONLY` — the Wallet gate is wired at M2, not simulated here.
|
|
32
|
+
|
|
33
|
+
## The line (spec §8)
|
|
34
|
+
|
|
35
|
+
No leverage, margin, or derivatives in v1. No access circumvention. No advice — the suite carries data, records, and (later) the owner's own mandates; recommendation-shaped output is a refused surface, not a disclaimed one. No market abuse, no data resale, no custody: the suite holds credentials (from M1), never assets. This is data and tooling, **not financial advice** — and Test Bench certification, when it comes, will certify normalization, gates, and receipts, never trading outcomes.
|
|
36
|
+
|
|
37
|
+
## Layout
|
|
38
|
+
|
|
39
|
+
`server.py` (MCP stdio) · `book_engine.py` (the suite law, imported by adapters) · `fixtures.json` (fee schedules + config seeds) · `tests/` · `smoke.py` · `make_icon.py` / `icon-512.png` (§6).
|
|
40
|
+
|
|
41
|
+
State: `$ECLIPSE_BOOK_STATE` or `./data/state.json`, shared with the suite's adapters — adapters hold no second copy of the law.
|
|
42
|
+
|
|
43
|
+
A Cyan Eclipse Technologies product. The "Powered by Cyan Eclipse Technologies" attribution travels with it.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
0.1.0
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
{
|
|
2
|
+
"bench": {
|
|
3
|
+
"bench_verdict": "CERTIFIED(local)",
|
|
4
|
+
"certified": true,
|
|
5
|
+
"checks": [
|
|
6
|
+
"criteria edit mid-position: one-word change -> CRITERIA_CHANGED event + receipt; position keeps as-of-entry, flag set",
|
|
7
|
+
"resolution_verify against a WRONG source refused by name; correct source verifies",
|
|
8
|
+
"DISPUTED blocks verification until cleared",
|
|
9
|
+
"fee math recomputed independently (all-in buy AND sell, per-unit + total); event-contract max payout attached",
|
|
10
|
+
"missing schedule AND stale schedule -> FEE_UNVERIFIED while bid/ask still serve",
|
|
11
|
+
"probability scan: planted keys in provenance, criteria-object field name, nested trading_window \u2014 never emitted; verbatim carriers refused by name",
|
|
12
|
+
"UNMAPPED native status preserved verbatim",
|
|
13
|
+
"order_draft: DRAFT only, NOT_EVALUATED mandate note, receipt ref; off-allowlist type refused",
|
|
14
|
+
"capability denylist by enumeration: exactly the 17 M0 tools; placement/withdraw/account/advice names refused",
|
|
15
|
+
"auth enforced",
|
|
16
|
+
"schema valid",
|
|
17
|
+
"no network surface (source-level)",
|
|
18
|
+
"no secret leak",
|
|
19
|
+
"sane errors",
|
|
20
|
+
"process health",
|
|
21
|
+
"audit completeness (receipt chain recomputed independently)",
|
|
22
|
+
"bench isolation"
|
|
23
|
+
],
|
|
24
|
+
"not_tested": [
|
|
25
|
+
"Live venue reads inside the shipped build \u2014 M0 contains no network code path; live Kalshi/Polymarket public payloads were verified through the transport seam from the Verity bench seat 2026-11-02 (BENCH-VERITY.md: PASS-WITH-CONDITIONS), but no in-build live adapter ships in v0.1.0.",
|
|
26
|
+
"Order placement, account reads, and the Wallet mandate gate \u2014 M2/M1 scope, owner-gated (spec 18, decision D3). M0 order_draft records an unsubmitted DRAFT with mandate_pre_eval NOT_EVALUATED; no submission path exists.",
|
|
27
|
+
"Fee schedules as live data \u2014 shipped schedules are fixture-shaped records with provenance labels saying so; the live fetch + account-specific tier provenance lands with the adapters' live step.",
|
|
28
|
+
"Kalshi / Polymarket US / Kraken / Binance.US / Alpaca chapters \u2014 specced (suite spec 10-12), not built in M0."
|
|
29
|
+
],
|
|
30
|
+
"scorecard_ref": "test-bench/results/eclipse-book-mcp-2026-10-25.json",
|
|
31
|
+
"status": "CERTIFIED(local) \u2014 Eclipse Bazaar Test Bench 2026-10-25 (scorecard eclipse-book-mcp-2026-10-25.json): 16 pass / 1 na / 0 fail over 17 checks incl. bench isolation. M0 data-only scope; live venue reads not_tested per the preserved not_tested list."
|
|
32
|
+
},
|
|
33
|
+
"category": "Markets / Exchange & Prediction-Market Infrastructure",
|
|
34
|
+
"created": "2026-10-25",
|
|
35
|
+
"description": "The Market Core of the Eclipse Markets suite (spec eclipse-markets-suite-spec-20261025): one canonical Instrument / Book / Quote / Order / Position / Resolution model over exchanges and prediction markets, with venue adapters that translate and never improvise. Resolution criteria are stored verbatim and hash-pinned \u2014 a venue criteria edit is a CRITERIA_CHANGED event and positions keep the criteria as of entry. Quotes carry all-in buy/sell cost for a stated size from versioned, provenance-stamped fee schedules; a stale or missing schedule degrades all-in fields to FEE_UNVERIFIED rather than quoting a wrong number. Resolutions move REPORTED -> VERIFIED only against the criteria's own named source (DISPUTED is first-class), and no core output ever carries a probability field \u2014 outputs carry price + liquidity flag + depth + verbatim criteria. M0 is data only: no accounts, no keys, no order submission at any tier; order_draft is an unsubmitted record whose mandate pre-evaluation is honestly NOT_EVALUATED until the owner-gated M2.",
|
|
36
|
+
"icon": "icon-512.png",
|
|
37
|
+
"name": "Eclipse Book MCP",
|
|
38
|
+
"powered_by": "Cyan Eclipse Technologies",
|
|
39
|
+
"price_model": "Free local v0.1; family pricing TBD per spec",
|
|
40
|
+
"repo": null,
|
|
41
|
+
"slug": "eclipse-book-mcp",
|
|
42
|
+
"status": "Live \u2014 v0.1.0 M0 local build (Market Core, data only; CERTIFIED(local) \u2014 Eclipse Bazaar Test Bench 2026-10-25; Verity bench 2026-11-02 PASS-WITH-CONDITIONS incl. live Kalshi/Polymarket public reads via the transport seam \u2014 see BENCH-VERITY.md)",
|
|
43
|
+
"tagline": "Market data + venue access layer \u2014 not an exchange: one book, one fee truth, one ledger of record.",
|
|
44
|
+
"tools": [
|
|
45
|
+
"instrument_ingest",
|
|
46
|
+
"instrument_get",
|
|
47
|
+
"instrument_search",
|
|
48
|
+
"book_ingest",
|
|
49
|
+
"quote_get",
|
|
50
|
+
"fee_schedule_register",
|
|
51
|
+
"fee_schedule_get",
|
|
52
|
+
"position_open",
|
|
53
|
+
"position_list",
|
|
54
|
+
"position_get",
|
|
55
|
+
"resolution_report",
|
|
56
|
+
"resolution_verify",
|
|
57
|
+
"resolution_get",
|
|
58
|
+
"order_draft",
|
|
59
|
+
"order_get",
|
|
60
|
+
"venue_status",
|
|
61
|
+
"receipt_list"
|
|
62
|
+
],
|
|
63
|
+
"transport": "MCP over stdio (HTTP transport on roadmap)",
|
|
64
|
+
"vendor": "Cyan Eclipse Technologies",
|
|
65
|
+
"x402_ready": false
|
|
66
|
+
}
|