srmech 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.
@@ -0,0 +1,140 @@
1
+ # PlatformIO
2
+ .pio/
3
+ .vscode/
4
+ .vscode/.browse.c_cpp.db*
5
+ .vscode/c_cpp_properties.json
6
+ .vscode/launch.json
7
+
8
+ # Build outputs
9
+ build/
10
+ build_output.log
11
+
12
+ # MkDocs build output (mlehaptics docs site)
13
+ /site/
14
+
15
+ # ESP-IDF
16
+ sdkconfig
17
+ sdkconfig.old
18
+ sdkconfig.defaults
19
+
20
+ # ESP-IDF Component Manager
21
+ managed_components/
22
+ dependencies.lock
23
+
24
+ # Editor files
25
+ *.swp
26
+ *.swo
27
+ *~
28
+ .DS_Store
29
+
30
+ # Python
31
+ __pycache__/
32
+ *.py[cod]
33
+ *$py.class
34
+ *.egg-info/
35
+ dist/
36
+ .pytest_cache/
37
+ .venv/
38
+
39
+ # Temporary files
40
+ *.tmp
41
+ *.bak
42
+ *.log
43
+
44
+ # Documentation build outputs
45
+ docs/_build/
46
+ docs/html/
47
+ docs/latex/
48
+
49
+ # Google Drive sync files
50
+ .tmp.driveupload
51
+ .tmp.drivedownload
52
+
53
+ # Windows
54
+ Thumbs.db
55
+ desktop.ini
56
+
57
+ # Claude Code
58
+ .claude/
59
+ nul
60
+
61
+ # Temporary source files
62
+ temp_*.c
63
+
64
+ # serial logs
65
+ serial_log*.txt
66
+
67
+ # freecad backup
68
+ *.FCBak
69
+
70
+
71
+
72
+
73
+ src/CMakeLists.txt
74
+
75
+ docs/chess-maths/stockfish/
76
+ docs/chess-maths/.pgn_cache/
77
+ docs/antikythera-maths/research/_cache/
78
+ docs/chess-maths/**/*.7z
79
+ docs/chess-maths/results/*_logs/
80
+ docs/chess-maths/results/delta_sigma_*/
81
+ docs/chess-maths/results/*/
82
+ docs/othello-maths/edax*/
83
+
84
+ # antikythera-maths skyfield ephemeris cache (de421.bsp ~15MB; downloaded on demand)
85
+ docs/antikythera-maths/skyfield_data/
86
+
87
+ # Large .spectralz binaries that exceed GitHub file-size limits
88
+ # (keep smaller corpora like barcelona.spectralz, wc2005.spectralz;
89
+ # regenerate the big ones on demand via `othello_spectral.cli encode-pgn`).
90
+ docs/othello-maths/results/all2025.spectralz
91
+ docs/othello-maths/results/apr2026.spectralz
92
+
93
+ # Generated C encoder table header (regenerate via
94
+ # `python -m othello_spectral.codegen.emit_c_tables`).
95
+ docs/othello-maths/research/othello_spectral/c_encoder/include/othello_spectral_tables.h
96
+
97
+ # Compiled C encoder (rebuild via clang invocation in c_encoder/README.md)
98
+ docs/othello-maths/research/othello_spectral/c_encoder/encode_cli
99
+ docs/othello-maths/research/othello_spectral/c_encoder/encode_cli.exe
100
+
101
+ # Compiled C encoder DLL (rebuild via clang -shared per c_encoder/README.md)
102
+ docs/othello-maths/research/othello_spectral/c_encoder/othello_spectral.dll
103
+ docs/othello-maths/research/othello_spectral/c_encoder/othello_spectral.so
104
+ docs/othello-maths/research/othello_spectral/c_encoder/othello_spectral.dylib
105
+
106
+ # Windows import library from clang -shared (alongside .dll)
107
+ docs/othello-maths/research/othello_spectral/c_encoder/othello_spectral.lib
108
+
109
+ # Process stdout logs from background runs (regenerate by rerunning)
110
+ docs/othello-maths/results/*_log.txt
111
+
112
+ # Windows import lib from encode_cli.exe build
113
+ docs/othello-maths/research/othello_spectral/c_encoder/encode_cli.lib
114
+ *.bsp
115
+
116
+ *.bsp.download
117
+ skyfield_data/
118
+
119
+ # ephemerides-spectral native C build output (rebuild via `cmake --build
120
+ # ../build` then `cp ../build/ephemerides_spectral.dll
121
+ # ephemerides_spectral/_native/`). Per-platform; not portable; not
122
+ # shipped in source.
123
+ docs/antikythera-maths/ephemerides-spectral/python/ephemerides_spectral/_native/
124
+
125
+ # linuxdoom-1.10 build artifacts and CVS metadata (vendored from 1997
126
+ # id Software cvsroot; per-platform .o files should not be tracked).
127
+ docs/antikythera-maths/doom-spectral/source/linuxdoom-1.10/linux/*.o
128
+ docs/antikythera-maths/doom-spectral/source/linuxdoom-1.10/linux/linuxxdoom
129
+ docs/antikythera-maths/doom-spectral/source/linuxdoom-1.10/CVS/
130
+ docs/antikythera-maths/doom-spectral/source/ipx/CVS/
131
+ docs/antikythera-maths/doom-spectral/source/sersrc/CVS/
132
+ docs/antikythera-maths/doom-spectral/source/sndserv/CVS/
133
+
134
+ # Datasets downloaded from external repositories (Dryad, etc.) — fetched on
135
+ # demand by scripts/fetch_*.py; not redistributed in this repo.
136
+ /data/
137
+
138
+ # Per-run logs from spike scripts.
139
+ /logs/
140
+ *.o
@@ -0,0 +1,29 @@
1
+ # srmech changelog
2
+
3
+ All notable changes to this package will be documented here. The format follows [Keep a Changelog](https://keepachangelog.com/en/1.1.0/); this package uses semantic versioning.
4
+
5
+ ## [Unreleased]
6
+
7
+ ## [0.1.0] - 2026-05-13
8
+
9
+ ### Added
10
+
11
+ - **Initial extract of the AMSC framework from `ephemerides-spectral`** as part of Task #197 (AMSC-to-srmech refactor, Phase 2). The framework lives under `srmech.amsc.*`:
12
+ - `srmech.amsc.format` — Mathematical Provenance Record (MPR) v1 format: `MPRRecord` dataclass, NDJSON streaming IO (`read_ndjson` / `write_ndjson`), `validate_mpr_record`, `sha256_bytes`, schema-version + mandatory-field constants.
13
+ - `srmech.amsc.descriptor` — descriptor TOML loader: `Descriptor`, `load_descriptor`, `discover_descriptors`, `render_template` (deliberately minimal name-substitution + Python format-spec; no Jinja), `descriptor_hash` (canonical-serialised), `DescriptorValidationError`.
14
+ - `srmech.amsc.catalog` — universal bridge surface: `list_attested_sources` (with `adapter_class` filter), `get_attested_dataset` (paginated, T0+T1+T2+T3 tiered), `get_attested_descriptor`, `attestation_audit`, `iter_attested_dataset`, T2 local-kernel overlay (`use_local_kernel` / `clear_local_kernel` / `get_local_kernel_state`).
15
+ - `srmech.amsc.gap_suggester` — schema-gap-driven trigger (`suggest_gap_collections`); the lazy-imported classifier + probe sources are ephemerides-specific and remain in ephemerides-spectral.
16
+ - `srmech.amsc.adapters` — six adapter modules: `html_scraper`, `json_api`, `csv_bulk`, `netcdf_grid` (stub), `geotiff_bbox` (stub), `literature_curated`; plus `_base.py` (`ADAPTERS` registry, `attest`, `parser_rule_hash`, `run` composer).
17
+ - **`register_attested_root(path, *, source)`** — the load-bearing cross-package API added in `srmech.amsc.catalog`. Downstream packages whose catalog SSOTs live outside `srmech/amsc/attested/` push their roots at package-import time; subsequent `_descriptors()` calls enumerate the union of srmech's own root + all registered roots in registration order. Conflict policy: first-registered wins with a warning.
18
+ - **`list_registered_roots()`** — introspection of currently-registered roots (srmech's own + every external). Used by tests and diagnostic output.
19
+ - **`srmech/amsc/attested/`** — empty SSOT subtree reserved for future srmech-primary catalogs (e.g. the `citations_curated` catalog planned for Spike #23).
20
+ - **CI workflows** under `.github/workflows/`:
21
+ - `srmech-ci.yml` — pytest on push/PR against `docs/srmech/python/**`, 4-cell matrix (Ubuntu/macOS/Windows × Py3.12 + Ubuntu × Py3.10 floor).
22
+ - `srmech-publish.yml` — build sdist + py3-none-any wheel on `srmech-v*` tag, publish to PyPI via trusted OIDC; manual workflow_dispatch can target TestPyPI.
23
+ - `srmech-autotag.yml` — autotag on `pyproject.toml` version bump.
24
+
25
+ ### Notes
26
+
27
+ - **Phase 2 is purely additive.** No ephemerides-spectral files are touched. Phase 3 (separate PR, not yet open) will rewire ephemerides-spectral's bridge to import from `srmech.amsc.*`; the byte-identical-wheel parity gate from the Phase 1 scope document applies there, not here.
28
+ - **Cross-package gap_suggester deviation.** `srmech.amsc.gap_suggester.suggest_gap_collections()` lazy-imports `.dynamical_regime_catalog` and `.dynamical_regime_probes_data`, which are ephemerides-specific and not shipped by srmech. Calling the function from a context where those modules aren't reachable (e.g. srmech in isolation, no ephemerides installed) will raise `ImportError` at call time. The Phase 1 scope did not flag this; ephemerides-spectral consumers (the only known caller) are unaffected because the relative imports resolve inside ephemerides's `_research/` mirror until Phase 3, then via Phase 3's import-swap.
29
+ - **`parser_version` stamp.** Changed from `"ephemerides-spectral X.Y.Z"` to `"srmech X.Y.Z"` in T3 live-fetch attestation blocks: srmech is now the parser. Committed NDJSON files retain whatever `parser_version` was stamped at collection time; only future T3 runs differ. No effect on the Phase 3 wheel parity gate (T3 is runtime, not committed bytes).
srmech-0.1.0/LICENSE ADDED
@@ -0,0 +1,63 @@
1
+ GNU GENERAL PUBLIC LICENSE
2
+ Version 3, 29 June 2007
3
+
4
+ Copyright (C) 2007 Free Software Foundation, Inc. <https://fsf.org/>
5
+ Everyone is permitted to copy and distribute verbatim copies
6
+ of this license document, but changing it is not allowed.
7
+
8
+ Preamble
9
+
10
+ The GNU General Public License is a free, copyleft license for
11
+ software and other kinds of works.
12
+
13
+ The licenses for most software and other practical works are designed
14
+ to take away your freedom to share and change the works. By contrast,
15
+ the GNU General Public License is intended to guarantee your freedom to
16
+ share and change all versions of a program--to make sure it remains free
17
+ software for all its users. We, the Free Software Foundation, use the
18
+ GNU General Public License for most of our software; it applies also to
19
+ any other work released this way by its authors. You can apply it to
20
+ your programs, too.
21
+
22
+ When we speak of free software, we are referring to freedom, not
23
+ price. Our General Public Licenses are designed to make sure that you
24
+ have the freedom to distribute copies of free software (and charge for
25
+ them if you wish), that you receive source code or can get it if you
26
+ want it, that you can change the software or use pieces of it in new
27
+ free programs, and that you know you can do these things.
28
+
29
+ To protect your rights, we need to prevent others from denying you
30
+ these rights or asking you to surrender the rights. Therefore, you have
31
+ certain responsibilities if you distribute copies of the software, or if
32
+ you modify it: responsibilities to respect the freedom of others.
33
+
34
+ For example, if you distribute copies of such a program, whether
35
+ gratis or for a fee, you must pass on to the recipients the same
36
+ freedoms that you received. You must make sure that they, too, receive
37
+ or can get the source code. And you must show them these terms so they
38
+ know their rights.
39
+
40
+ Developers that use the GNU GPL protect your rights with two steps:
41
+ (1) assert copyright on the software, and (2) offer you this License
42
+ giving you legal permission to copy, distribute and/or modify it.
43
+
44
+ For the developers' and authors' protection, the GPL clearly explains
45
+ that there is no warranty for this free software. For both users' and
46
+ authors' sake, the GPL requires that modified versions be marked as
47
+ changed, so that their problems will not be attributed erroneously to
48
+ authors of previous versions.
49
+
50
+ Some devices are designed to deny users access to install or run
51
+ modified versions of the software inside them, although the manufacturer
52
+ can do so. This is fundamentally incompatible with the aim of
53
+ protecting users' freedom to change the software. The systematic
54
+ pattern of such abuse occurs in the area of products for individuals to
55
+ use, which is precisely where it is most unacceptable. Therefore, we
56
+ have designed this version of the GPL to prohibit the practice for those
57
+ products. If such problems arise substantially in other domains, we
58
+ stand ready to extend this provision to those domains in future versions
59
+ of the GPL, as needed to protect the freedom of users.
60
+
61
+ Finally, every program is threatened constantly by software patents.
62
+ States should not allow patents to restrict development and use of
63
+ software on general-purpose
srmech-0.1.0/PKG-INFO ADDED
@@ -0,0 +1,105 @@
1
+ Metadata-Version: 2.4
2
+ Name: srmech
3
+ Version: 0.1.0
4
+ Summary: Spectral-resonance mechanism research package: home of the Attested Multi-Source Collector (AMSC) framework — Mathematical Provenance Record v1 on-disk format, descriptor TOML loader, six adapters (html/json/csv/netcdf/geotiff/literature), universal catalog bridge with register_attested_root cross-package overlay, and schema-gap-driven trigger. Pure Python.
5
+ Project-URL: Homepage, https://github.com/lemonforest/mlehaptics/tree/main/docs/srmech/python
6
+ Project-URL: Repository, https://github.com/lemonforest/mlehaptics
7
+ Project-URL: Issues, https://github.com/lemonforest/mlehaptics/issues
8
+ Project-URL: Changelog, https://github.com/lemonforest/mlehaptics/blob/main/docs/srmech/python/CHANGELOG.md
9
+ Project-URL: Research notebook, https://github.com/lemonforest/mlehaptics/blob/main/docs/srmech/srmech_research_notebook.md
10
+ Author: Steven Kirkland
11
+ License-Expression: GPL-3.0-or-later
12
+ License-File: LICENSE
13
+ Keywords: attested,ground-proof,mechanism,ndjson,provenance,research,spectral-resonance
14
+ Classifier: Development Status :: 3 - Alpha
15
+ Classifier: Intended Audience :: Science/Research
16
+ Classifier: Programming Language :: Python :: 3
17
+ Classifier: Programming Language :: Python :: 3.10
18
+ Classifier: Programming Language :: Python :: 3.11
19
+ Classifier: Programming Language :: Python :: 3.12
20
+ Classifier: Programming Language :: Python :: 3.13
21
+ Classifier: Programming Language :: Python :: 3.14
22
+ Classifier: Topic :: Scientific/Engineering
23
+ Classifier: Typing :: Typed
24
+ Requires-Python: >=3.10
25
+ Requires-Dist: tomli>=2.0; python_version < '3.11'
26
+ Provides-Extra: collectors
27
+ Requires-Dist: beautifulsoup4>=4.11; extra == 'collectors'
28
+ Requires-Dist: requests>=2.28; extra == 'collectors'
29
+ Provides-Extra: dev
30
+ Requires-Dist: beautifulsoup4>=4.11; extra == 'dev'
31
+ Requires-Dist: build; extra == 'dev'
32
+ Requires-Dist: hatchling>=1.18; extra == 'dev'
33
+ Requires-Dist: jsonschema>=4.0; extra == 'dev'
34
+ Requires-Dist: pytest>=7.0; extra == 'dev'
35
+ Requires-Dist: requests>=2.28; extra == 'dev'
36
+ Requires-Dist: twine; extra == 'dev'
37
+ Provides-Extra: tests
38
+ Requires-Dist: pytest>=7.0; extra == 'tests'
39
+ Provides-Extra: validation
40
+ Requires-Dist: jsonschema>=4.0; extra == 'validation'
41
+ Description-Content-Type: text/markdown
42
+
43
+ # srmech
44
+
45
+ **Status:** v0.1.0 (Phase 2 bootstrap — Task #197 of the AMSC-to-srmech refactor)
46
+
47
+ `srmech` (spectral-resonance mechanism) is a research package. As of v0.1.0 it ships the **Attested Multi-Source Collector (AMSC) framework** — the Mathematical Provenance Record (MPR) v1 on-disk format, descriptor TOML loader, six fetch/parse adapters, and a universal catalog bridge surface that downstream packages register their own catalog SSOTs with at import time.
48
+
49
+ The package was extracted from `ephemerides-spectral`'s `_research/` mirror in Task #197 so that other spectral-research packages can consume the AMSC framework without depending on ephemerides-spectral. The catalog SSOTs themselves do NOT migrate — each downstream package registers its own root via `srmech.amsc.catalog.register_attested_root(path, source=...)`.
50
+
51
+ ## Public API
52
+
53
+ ```python
54
+ from srmech.amsc import (
55
+ MPRRecord, MPR_SCHEMA_VERSION, read_ndjson, write_ndjson, sha256_bytes,
56
+ Descriptor, load_descriptor, discover_descriptors, render_template, descriptor_hash,
57
+ list_attested_sources, get_attested_dataset, get_attested_descriptor,
58
+ attestation_audit, register_attested_root, list_registered_roots,
59
+ use_local_kernel, clear_local_kernel, get_local_kernel_state,
60
+ )
61
+ ```
62
+
63
+ ## Cross-package catalog registration
64
+
65
+ The load-bearing API for cross-package use:
66
+
67
+ ```python
68
+ from pathlib import Path
69
+ from srmech.amsc import catalog as _amsc_catalog
70
+
71
+ _amsc_catalog.register_attested_root(
72
+ Path(__file__).resolve().parent / "_research" / "attested",
73
+ source="ephemerides-spectral",
74
+ )
75
+ ```
76
+
77
+ Call this once at package-import time. Subsequent `list_attested_sources()`, `get_attested_dataset()`, etc. enumerate the union of srmech's own `amsc/attested/` plus every registered root, in registration order. Duplicate `source_key` resolves first-registered-wins with a warning.
78
+
79
+ ## Adapter classes
80
+
81
+ Six adapters cover the realistic source space:
82
+
83
+ | adapter | class | network? |
84
+ |---|---|---|
85
+ | `html_scraper` | fetched | yes (BeautifulSoup) |
86
+ | `json_api` | fetched | yes (paginated JSON) |
87
+ | `csv_bulk` | fetched | yes (CSV/XYZ bulk) |
88
+ | `netcdf_grid` | fetched | stub (gated behind extras) |
89
+ | `geotiff_bbox` | fetched | stub (gated behind extras) |
90
+ | `literature_curated` | curated | no (NDJSON committed directly) |
91
+
92
+ The `curated` class never touches the network: rows are committed as data-only NDJSON and srmech synthesises full MPR attestation blocks at read time from each row's per-row DOI.
93
+
94
+ ## Install
95
+
96
+ ```bash
97
+ pip install srmech # core (no jsonschema, no network adapters)
98
+ pip install srmech[validation] # adds jsonschema for strict data-block validation
99
+ pip install srmech[collectors] # adds requests + beautifulsoup4 for fetched adapters
100
+ pip install srmech[dev] # everything
101
+ ```
102
+
103
+ ## License
104
+
105
+ GPL-3.0-or-later. See [LICENSE](LICENSE).
srmech-0.1.0/README.md ADDED
@@ -0,0 +1,63 @@
1
+ # srmech
2
+
3
+ **Status:** v0.1.0 (Phase 2 bootstrap — Task #197 of the AMSC-to-srmech refactor)
4
+
5
+ `srmech` (spectral-resonance mechanism) is a research package. As of v0.1.0 it ships the **Attested Multi-Source Collector (AMSC) framework** — the Mathematical Provenance Record (MPR) v1 on-disk format, descriptor TOML loader, six fetch/parse adapters, and a universal catalog bridge surface that downstream packages register their own catalog SSOTs with at import time.
6
+
7
+ The package was extracted from `ephemerides-spectral`'s `_research/` mirror in Task #197 so that other spectral-research packages can consume the AMSC framework without depending on ephemerides-spectral. The catalog SSOTs themselves do NOT migrate — each downstream package registers its own root via `srmech.amsc.catalog.register_attested_root(path, source=...)`.
8
+
9
+ ## Public API
10
+
11
+ ```python
12
+ from srmech.amsc import (
13
+ MPRRecord, MPR_SCHEMA_VERSION, read_ndjson, write_ndjson, sha256_bytes,
14
+ Descriptor, load_descriptor, discover_descriptors, render_template, descriptor_hash,
15
+ list_attested_sources, get_attested_dataset, get_attested_descriptor,
16
+ attestation_audit, register_attested_root, list_registered_roots,
17
+ use_local_kernel, clear_local_kernel, get_local_kernel_state,
18
+ )
19
+ ```
20
+
21
+ ## Cross-package catalog registration
22
+
23
+ The load-bearing API for cross-package use:
24
+
25
+ ```python
26
+ from pathlib import Path
27
+ from srmech.amsc import catalog as _amsc_catalog
28
+
29
+ _amsc_catalog.register_attested_root(
30
+ Path(__file__).resolve().parent / "_research" / "attested",
31
+ source="ephemerides-spectral",
32
+ )
33
+ ```
34
+
35
+ Call this once at package-import time. Subsequent `list_attested_sources()`, `get_attested_dataset()`, etc. enumerate the union of srmech's own `amsc/attested/` plus every registered root, in registration order. Duplicate `source_key` resolves first-registered-wins with a warning.
36
+
37
+ ## Adapter classes
38
+
39
+ Six adapters cover the realistic source space:
40
+
41
+ | adapter | class | network? |
42
+ |---|---|---|
43
+ | `html_scraper` | fetched | yes (BeautifulSoup) |
44
+ | `json_api` | fetched | yes (paginated JSON) |
45
+ | `csv_bulk` | fetched | yes (CSV/XYZ bulk) |
46
+ | `netcdf_grid` | fetched | stub (gated behind extras) |
47
+ | `geotiff_bbox` | fetched | stub (gated behind extras) |
48
+ | `literature_curated` | curated | no (NDJSON committed directly) |
49
+
50
+ The `curated` class never touches the network: rows are committed as data-only NDJSON and srmech synthesises full MPR attestation blocks at read time from each row's per-row DOI.
51
+
52
+ ## Install
53
+
54
+ ```bash
55
+ pip install srmech # core (no jsonschema, no network adapters)
56
+ pip install srmech[validation] # adds jsonschema for strict data-block validation
57
+ pip install srmech[collectors] # adds requests + beautifulsoup4 for fetched adapters
58
+ pip install srmech[dev] # everything
59
+ ```
60
+
61
+ ## License
62
+
63
+ GPL-3.0-or-later. See [LICENSE](LICENSE).
@@ -0,0 +1,111 @@
1
+ # srmech — spectral-resonance mechanism research package.
2
+ #
3
+ # Phase 2 (Task #197) ships srmech as the new home of the Attested
4
+ # Multi-Source Collector (AMSC) framework, previously living inside
5
+ # ephemerides-spectral's _research/ mirror. Pure Python; no native
6
+ # binary; one wheel (py3-none-any).
7
+ #
8
+ # See docs/srmech/notes/task_197_phase_1_amsc_refactor_scope_2026-05-13.md
9
+ # (on branch refactor/amsc-to-srmech-phase-1-scope) for the design
10
+ # document. Phase 3 (planned) rewires ephemerides-spectral's bridge
11
+ # to import from srmech.amsc.* instead of its in-tree mirror.
12
+
13
+ [build-system]
14
+ requires = ["hatchling>=1.18"]
15
+ build-backend = "hatchling.build"
16
+
17
+ [project]
18
+ name = "srmech"
19
+ version = "0.1.0"
20
+ description = "Spectral-resonance mechanism research package: home of the Attested Multi-Source Collector (AMSC) framework — Mathematical Provenance Record v1 on-disk format, descriptor TOML loader, six adapters (html/json/csv/netcdf/geotiff/literature), universal catalog bridge with register_attested_root cross-package overlay, and schema-gap-driven trigger. Pure Python."
21
+ readme = "README.md"
22
+ requires-python = ">=3.10"
23
+ license = "GPL-3.0-or-later"
24
+ authors = [{ name = "Steven Kirkland" }]
25
+ keywords = [
26
+ "spectral-resonance",
27
+ "mechanism",
28
+ "attested",
29
+ "provenance",
30
+ "ndjson",
31
+ "ground-proof",
32
+ "research",
33
+ ]
34
+ classifiers = [
35
+ "Development Status :: 3 - Alpha",
36
+ "Intended Audience :: Science/Research",
37
+ "Programming Language :: Python :: 3",
38
+ "Programming Language :: Python :: 3.10",
39
+ "Programming Language :: Python :: 3.11",
40
+ "Programming Language :: Python :: 3.12",
41
+ "Programming Language :: Python :: 3.13",
42
+ "Programming Language :: Python :: 3.14",
43
+ "Topic :: Scientific/Engineering",
44
+ "Typing :: Typed",
45
+ ]
46
+ # Runtime deps are minimal: jsonschema is optional (the format module
47
+ # falls back to a `required`-fields-only check when jsonschema is not
48
+ # installed). TOML parsing uses stdlib `tomllib` on Python 3.11+; the
49
+ # 3.10 path requires `tomli` (declared as a conditional dep here).
50
+ dependencies = [
51
+ "tomli>=2.0; python_version<'3.11'",
52
+ ]
53
+
54
+ [project.optional-dependencies]
55
+ # Validation extra: enables strict per-source JSON Schema checks
56
+ # inside `validate_mpr_record` when `data_schemas` is supplied.
57
+ validation = ["jsonschema>=4.0"]
58
+ # Collector extra: deps needed by the `fetched`-class adapters
59
+ # (html_scraper / json_api / csv_bulk). netcdf_grid + geotiff_bbox
60
+ # stubs raise NotImplementedError unless their own extras are
61
+ # installed (left as a follow-up; not blocking Phase 2).
62
+ collectors = [
63
+ "requests>=2.28",
64
+ "beautifulsoup4>=4.11",
65
+ ]
66
+ # Tests extra: runs srmech's own pytest suite.
67
+ tests = ["pytest>=7.0"]
68
+ # Dev extra: everything plus build tooling.
69
+ dev = [
70
+ "pytest>=7.0",
71
+ "build",
72
+ "twine",
73
+ "hatchling>=1.18",
74
+ "jsonschema>=4.0",
75
+ "requests>=2.28",
76
+ "beautifulsoup4>=4.11",
77
+ ]
78
+
79
+ [project.urls]
80
+ Homepage = "https://github.com/lemonforest/mlehaptics/tree/main/docs/srmech/python"
81
+ Repository = "https://github.com/lemonforest/mlehaptics"
82
+ Issues = "https://github.com/lemonforest/mlehaptics/issues"
83
+ Changelog = "https://github.com/lemonforest/mlehaptics/blob/main/docs/srmech/python/CHANGELOG.md"
84
+ "Research notebook" = "https://github.com/lemonforest/mlehaptics/blob/main/docs/srmech/srmech_research_notebook.md"
85
+
86
+ [tool.hatch.build.targets.wheel]
87
+ # Include the `srmech` package directory; py.typed marker is included
88
+ # by virtue of being inside the package.
89
+ packages = ["srmech"]
90
+
91
+ [tool.hatch.build.targets.wheel.force-include]
92
+ # Future srmech-primary catalogs land under srmech/amsc/attested/.
93
+ # Phase 2 ships an empty subtree (just __init__.py); Spike #23 adds
94
+ # the first catalog. Hatchling picks up the __init__.py automatically
95
+ # via `packages`; this force-include slot is reserved for the eventual
96
+ # descriptor.toml + row.ndjson + row.schema.json data files that
97
+ # packages= alone wouldn't include.
98
+
99
+ [tool.hatch.build.targets.sdist]
100
+ include = [
101
+ "srmech/**",
102
+ "tests/**",
103
+ "README.md",
104
+ "CHANGELOG.md",
105
+ "LICENSE",
106
+ "pyproject.toml",
107
+ ]
108
+ exclude = [
109
+ "**/__pycache__",
110
+ "**/*.pyc",
111
+ ]
@@ -0,0 +1,26 @@
1
+ """srmech — spectral-resonance mechanism research package.
2
+
3
+ Phase 2 (Task #197) ships srmech as the home of the Attested
4
+ Multi-Source Collector (AMSC) framework — previously living inside
5
+ ephemerides-spectral's ``_research/`` mirror. The framework is the
6
+ mechanical-provenance discipline (every ground-proof row carries
7
+ mandatory attestation) generalised so downstream packages can
8
+ declare their own catalog SSOTs and consume them through one universal
9
+ bridge surface (``srmech.amsc.catalog``).
10
+
11
+ The Phase 3 cutover (planned) rewires ephemerides-spectral's bridge
12
+ to import from ``srmech.amsc.*`` instead of its in-tree mirror; the
13
+ catalog SSOTs do NOT migrate (ephemerides's 19 catalogs stay where
14
+ they are, registered into srmech via
15
+ ``register_attested_root(path, source=...)`` at package-import time).
16
+
17
+ Public surfaces
18
+ ---------------
19
+ * ``srmech.amsc`` — Attested Multi-Source Collector framework.
20
+ * ``srmech.__version__`` — package version string (SSOT in
21
+ ``srmech.version``).
22
+ """
23
+
24
+ from .version import __version__
25
+
26
+ __all__ = ["__version__"]
@@ -0,0 +1,87 @@
1
+ """Attested Multi-Source Collector (AMSC) framework.
2
+
3
+ The framework's modules and their public re-exports:
4
+
5
+ * :mod:`srmech.amsc.format` — Mathematical Provenance Record (MPR) v1
6
+ on-disk format (``MPRRecord``, NDJSON IO, ``sha256_bytes``).
7
+ * :mod:`srmech.amsc.descriptor` — descriptor TOML loader
8
+ (``Descriptor``, ``load_descriptor``, ``discover_descriptors``,
9
+ ``render_template``, ``descriptor_hash``).
10
+ * :mod:`srmech.amsc.catalog` — universal bridge surface
11
+ (``list_attested_sources``, ``get_attested_dataset``,
12
+ ``get_attested_descriptor``, ``attestation_audit``,
13
+ ``register_attested_root``, T2 local-kernel overlay).
14
+ * :mod:`srmech.amsc.gap_suggester` — schema-gap-driven trigger.
15
+ * :mod:`srmech.amsc.adapters` — adapter implementations
16
+ (html_scraper, json_api, csv_bulk, netcdf_grid, geotiff_bbox,
17
+ literature_curated).
18
+
19
+ The ergonomic re-exports below let consumers ``from srmech.amsc
20
+ import MPRRecord, Descriptor`` etc. without reaching into each
21
+ submodule.
22
+ """
23
+
24
+ from __future__ import annotations
25
+
26
+ from .catalog import (
27
+ attestation_audit,
28
+ clear_local_kernel,
29
+ get_attested_dataset,
30
+ get_attested_descriptor,
31
+ get_local_kernel_state,
32
+ iter_attested_dataset,
33
+ list_attested_sources,
34
+ list_registered_roots,
35
+ register_attested_root,
36
+ use_local_kernel,
37
+ )
38
+ from .descriptor import (
39
+ Descriptor,
40
+ DescriptorValidationError,
41
+ descriptor_hash,
42
+ discover_descriptors,
43
+ load_descriptor,
44
+ render_template,
45
+ )
46
+ from .format import (
47
+ MANDATORY_ATTESTATION_FIELDS,
48
+ MANDATORY_RENDERING_FIELDS,
49
+ MPR_SCHEMA_VERSION,
50
+ MPRRecord,
51
+ MPRValidationError,
52
+ read_ndjson,
53
+ sha256_bytes,
54
+ validate_mpr_record,
55
+ write_ndjson,
56
+ )
57
+
58
+ __all__ = [
59
+ # format
60
+ "MANDATORY_ATTESTATION_FIELDS",
61
+ "MANDATORY_RENDERING_FIELDS",
62
+ "MPR_SCHEMA_VERSION",
63
+ "MPRRecord",
64
+ "MPRValidationError",
65
+ "read_ndjson",
66
+ "sha256_bytes",
67
+ "validate_mpr_record",
68
+ "write_ndjson",
69
+ # descriptor
70
+ "Descriptor",
71
+ "DescriptorValidationError",
72
+ "descriptor_hash",
73
+ "discover_descriptors",
74
+ "load_descriptor",
75
+ "render_template",
76
+ # catalog
77
+ "attestation_audit",
78
+ "clear_local_kernel",
79
+ "get_attested_dataset",
80
+ "get_attested_descriptor",
81
+ "get_local_kernel_state",
82
+ "iter_attested_dataset",
83
+ "list_attested_sources",
84
+ "list_registered_roots",
85
+ "register_attested_root",
86
+ "use_local_kernel",
87
+ ]