PyMetaAnalysis 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.
- pymetaanalysis-0.1.0/.github/workflows/ci.yml +201 -0
- pymetaanalysis-0.1.0/.github/workflows/pages.yml +66 -0
- pymetaanalysis-0.1.0/.github/workflows/release.yml +125 -0
- pymetaanalysis-0.1.0/.gitignore +19 -0
- pymetaanalysis-0.1.0/CHANGELOG.md +43 -0
- pymetaanalysis-0.1.0/CITATION.cff +21 -0
- pymetaanalysis-0.1.0/CONTRIBUTING.md +32 -0
- pymetaanalysis-0.1.0/LICENSE +21 -0
- pymetaanalysis-0.1.0/PKG-INFO +218 -0
- pymetaanalysis-0.1.0/README.md +169 -0
- pymetaanalysis-0.1.0/SECURITY.md +24 -0
- pymetaanalysis-0.1.0/benchmarks/README.md +26 -0
- pymetaanalysis-0.1.0/benchmarks/benchmark_core.py +123 -0
- pymetaanalysis-0.1.0/docs/adr/0001-optional-matplotlib.md +29 -0
- pymetaanalysis-0.1.0/docs/adr/0002-statistical-policy.md +92 -0
- pymetaanalysis-0.1.0/docs/citation.md +47 -0
- pymetaanalysis-0.1.0/docs/development.md +87 -0
- pymetaanalysis-0.1.0/docs/getting-started.md +181 -0
- pymetaanalysis-0.1.0/docs/guides/binary-outcomes.md +108 -0
- pymetaanalysis-0.1.0/docs/guides/continuous-outcomes.md +81 -0
- pymetaanalysis-0.1.0/docs/guides/generic-effects.md +101 -0
- pymetaanalysis-0.1.0/docs/guides/input-data.md +119 -0
- pymetaanalysis-0.1.0/docs/guides/method-selection.md +121 -0
- pymetaanalysis-0.1.0/docs/guides/plotting.md +109 -0
- pymetaanalysis-0.1.0/docs/guides/provenance-reporting.md +144 -0
- pymetaanalysis-0.1.0/docs/guides/r-interoperability.md +166 -0
- pymetaanalysis-0.1.0/docs/guides/sensitivity-analysis.md +108 -0
- pymetaanalysis-0.1.0/docs/guides/zero-events.md +95 -0
- pymetaanalysis-0.1.0/docs/index.md +90 -0
- pymetaanalysis-0.1.0/docs/installation.md +88 -0
- pymetaanalysis-0.1.0/docs/limitations.md +79 -0
- pymetaanalysis-0.1.0/docs/methods/statistical-methods.md +286 -0
- pymetaanalysis-0.1.0/docs/reference/api.md +263 -0
- pymetaanalysis-0.1.0/docs/reference/report-schema.md +151 -0
- pymetaanalysis-0.1.0/docs/reference/results.md +224 -0
- pymetaanalysis-0.1.0/docs/releasing.md +121 -0
- pymetaanalysis-0.1.0/docs/stylesheets/extra.css +22 -0
- pymetaanalysis-0.1.0/docs/validation.md +119 -0
- pymetaanalysis-0.1.0/examples/README.md +19 -0
- pymetaanalysis-0.1.0/examples/quickstart.ipynb +200 -0
- pymetaanalysis-0.1.0/mkdocs.yml +64 -0
- pymetaanalysis-0.1.0/pyproject.toml +121 -0
- pymetaanalysis-0.1.0/src/meta_analyze/__init__.py +62 -0
- pymetaanalysis-0.1.0/src/meta_analyze/_version.py +3 -0
- pymetaanalysis-0.1.0/src/meta_analyze/api.py +330 -0
- pymetaanalysis-0.1.0/src/meta_analyze/binary_api.py +539 -0
- pymetaanalysis-0.1.0/src/meta_analyze/config.py +34 -0
- pymetaanalysis-0.1.0/src/meta_analyze/continuous_api.py +353 -0
- pymetaanalysis-0.1.0/src/meta_analyze/data.py +181 -0
- pymetaanalysis-0.1.0/src/meta_analyze/effect_sizes/__init__.py +17 -0
- pymetaanalysis-0.1.0/src/meta_analyze/effect_sizes/binary.py +412 -0
- pymetaanalysis-0.1.0/src/meta_analyze/effect_sizes/continuous.py +271 -0
- pymetaanalysis-0.1.0/src/meta_analyze/estimators/__init__.py +14 -0
- pymetaanalysis-0.1.0/src/meta_analyze/estimators/inverse_variance.py +169 -0
- pymetaanalysis-0.1.0/src/meta_analyze/estimators/mantel_haenszel.py +101 -0
- pymetaanalysis-0.1.0/src/meta_analyze/estimators/tau2.py +182 -0
- pymetaanalysis-0.1.0/src/meta_analyze/exceptions.py +21 -0
- pymetaanalysis-0.1.0/src/meta_analyze/heterogeneity.py +99 -0
- pymetaanalysis-0.1.0/src/meta_analyze/plotting/__init__.py +7 -0
- pymetaanalysis-0.1.0/src/meta_analyze/plotting/_utils.py +67 -0
- pymetaanalysis-0.1.0/src/meta_analyze/plotting/forest.py +193 -0
- pymetaanalysis-0.1.0/src/meta_analyze/plotting/funnel.py +168 -0
- pymetaanalysis-0.1.0/src/meta_analyze/plotting/subgroup_forest.py +284 -0
- pymetaanalysis-0.1.0/src/meta_analyze/provenance.py +185 -0
- pymetaanalysis-0.1.0/src/meta_analyze/py.typed +1 -0
- pymetaanalysis-0.1.0/src/meta_analyze/reporting.py +433 -0
- pymetaanalysis-0.1.0/src/meta_analyze/results.py +519 -0
- pymetaanalysis-0.1.0/src/meta_analyze/sensitivity.py +546 -0
- pymetaanalysis-0.1.0/src/meta_analyze/subgroups.py +165 -0
- pymetaanalysis-0.1.0/tests/reference/README.md +40 -0
- pymetaanalysis-0.1.0/tests/reference/binary_input.csv +5 -0
- pymetaanalysis-0.1.0/tests/reference/binary_metafor.json +146 -0
- pymetaanalysis-0.1.0/tests/reference/binary_sparse_input.csv +6 -0
- pymetaanalysis-0.1.0/tests/reference/continuous_input.csv +5 -0
- pymetaanalysis-0.1.0/tests/reference/continuous_metafor.json +20 -0
- pymetaanalysis-0.1.0/tests/reference/generate_binary_metafor.R +158 -0
- pymetaanalysis-0.1.0/tests/reference/generate_continuous_metafor.R +52 -0
- pymetaanalysis-0.1.0/tests/reference/generate_generic_metafor.R +107 -0
- pymetaanalysis-0.1.0/tests/reference/generate_workflow_metafor.R +119 -0
- pymetaanalysis-0.1.0/tests/reference/generic_input.csv +6 -0
- pymetaanalysis-0.1.0/tests/reference/generic_metafor.json +62 -0
- pymetaanalysis-0.1.0/tests/reference/workflow_input.csv +7 -0
- pymetaanalysis-0.1.0/tests/reference/workflow_metafor.json +92 -0
- pymetaanalysis-0.1.0/tests/test_api.py +278 -0
- pymetaanalysis-0.1.0/tests/test_binary.py +509 -0
- pymetaanalysis-0.1.0/tests/test_continuous.py +289 -0
- pymetaanalysis-0.1.0/tests/test_documentation.py +53 -0
- pymetaanalysis-0.1.0/tests/test_estimators.py +147 -0
- pymetaanalysis-0.1.0/tests/test_funnel_plot.py +198 -0
- pymetaanalysis-0.1.0/tests/test_numerical_stability.py +155 -0
- pymetaanalysis-0.1.0/tests/test_plotting.py +183 -0
- pymetaanalysis-0.1.0/tests/test_properties.py +84 -0
- pymetaanalysis-0.1.0/tests/test_r_references.py +481 -0
- pymetaanalysis-0.1.0/tests/test_reference_results.py +59 -0
- pymetaanalysis-0.1.0/tests/test_release_readiness.py +87 -0
- pymetaanalysis-0.1.0/tests/test_reporting.py +417 -0
- pymetaanalysis-0.1.0/tests/test_sensitivity.py +398 -0
- pymetaanalysis-0.1.0/tests/test_subgroups.py +277 -0
- pymetaanalysis-0.1.0/tools/check_release.py +77 -0
- pymetaanalysis-0.1.0/tools/execute_notebooks.py +36 -0
- pymetaanalysis-0.1.0/tools/inspect_distribution.py +115 -0
|
@@ -0,0 +1,201 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
pull_request:
|
|
5
|
+
push:
|
|
6
|
+
branches:
|
|
7
|
+
- main
|
|
8
|
+
workflow_dispatch:
|
|
9
|
+
|
|
10
|
+
permissions:
|
|
11
|
+
contents: read
|
|
12
|
+
|
|
13
|
+
concurrency:
|
|
14
|
+
group: ci-${{ github.workflow }}-${{ github.ref }}
|
|
15
|
+
cancel-in-progress: true
|
|
16
|
+
|
|
17
|
+
jobs:
|
|
18
|
+
test:
|
|
19
|
+
name: Test (Python ${{ matrix.python-version }})
|
|
20
|
+
runs-on: ubuntu-latest
|
|
21
|
+
timeout-minutes: 15
|
|
22
|
+
strategy:
|
|
23
|
+
fail-fast: false
|
|
24
|
+
matrix:
|
|
25
|
+
python-version: ["3.10", "3.11", "3.12", "3.13"]
|
|
26
|
+
|
|
27
|
+
steps:
|
|
28
|
+
- name: Check out repository
|
|
29
|
+
uses: actions/checkout@v7
|
|
30
|
+
with:
|
|
31
|
+
persist-credentials: false
|
|
32
|
+
|
|
33
|
+
- name: Set up Python ${{ matrix.python-version }}
|
|
34
|
+
uses: actions/setup-python@v6
|
|
35
|
+
with:
|
|
36
|
+
python-version: ${{ matrix.python-version }}
|
|
37
|
+
cache: pip
|
|
38
|
+
cache-dependency-path: pyproject.toml
|
|
39
|
+
|
|
40
|
+
- name: Install test dependencies
|
|
41
|
+
run: |
|
|
42
|
+
python -m pip install --upgrade pip
|
|
43
|
+
python -m pip install ".[test]"
|
|
44
|
+
|
|
45
|
+
- name: Run tests with branch coverage
|
|
46
|
+
run: python -m pytest --cov=meta_analyze --cov-branch --cov-report=term-missing
|
|
47
|
+
|
|
48
|
+
minimum-dependencies:
|
|
49
|
+
name: Minimum direct dependencies (Python 3.10)
|
|
50
|
+
runs-on: ubuntu-latest
|
|
51
|
+
timeout-minutes: 15
|
|
52
|
+
|
|
53
|
+
steps:
|
|
54
|
+
- name: Check out repository
|
|
55
|
+
uses: actions/checkout@v7
|
|
56
|
+
with:
|
|
57
|
+
persist-credentials: false
|
|
58
|
+
|
|
59
|
+
- name: Set up Python 3.10
|
|
60
|
+
uses: actions/setup-python@v6
|
|
61
|
+
with:
|
|
62
|
+
python-version: "3.10"
|
|
63
|
+
cache: pip
|
|
64
|
+
cache-dependency-path: pyproject.toml
|
|
65
|
+
|
|
66
|
+
- name: Install declared lower bounds
|
|
67
|
+
run: |
|
|
68
|
+
python -m pip install --upgrade pip
|
|
69
|
+
python -m pip install \
|
|
70
|
+
"numpy==1.24.0" \
|
|
71
|
+
"pandas==2.0.0" \
|
|
72
|
+
"scipy==1.10.0" \
|
|
73
|
+
"hypothesis==6.100.0" \
|
|
74
|
+
"matplotlib==3.7.0" \
|
|
75
|
+
"pytest==8.0.0" \
|
|
76
|
+
"pytest-cov==5.0.0"
|
|
77
|
+
python -m pip install --no-deps --editable .
|
|
78
|
+
|
|
79
|
+
- name: Report resolved dependency versions
|
|
80
|
+
run: |
|
|
81
|
+
python -m pip list
|
|
82
|
+
python -m pip check
|
|
83
|
+
|
|
84
|
+
- name: Run tests at declared lower bounds
|
|
85
|
+
run: python -m pytest --cov=meta_analyze --cov-branch --cov-report=term-missing
|
|
86
|
+
|
|
87
|
+
quality:
|
|
88
|
+
name: Static checks
|
|
89
|
+
runs-on: ubuntu-latest
|
|
90
|
+
timeout-minutes: 10
|
|
91
|
+
|
|
92
|
+
steps:
|
|
93
|
+
- name: Check out repository
|
|
94
|
+
uses: actions/checkout@v7
|
|
95
|
+
with:
|
|
96
|
+
persist-credentials: false
|
|
97
|
+
|
|
98
|
+
- name: Set up Python 3.12
|
|
99
|
+
uses: actions/setup-python@v6
|
|
100
|
+
with:
|
|
101
|
+
python-version: "3.12"
|
|
102
|
+
cache: pip
|
|
103
|
+
cache-dependency-path: pyproject.toml
|
|
104
|
+
|
|
105
|
+
- name: Install development dependencies
|
|
106
|
+
run: |
|
|
107
|
+
python -m pip install --upgrade pip
|
|
108
|
+
python -m pip install ".[dev,plot]"
|
|
109
|
+
|
|
110
|
+
- name: Check formatting
|
|
111
|
+
run: python -m ruff format --check .
|
|
112
|
+
|
|
113
|
+
- name: Lint
|
|
114
|
+
run: python -m ruff check .
|
|
115
|
+
|
|
116
|
+
- name: Validate GitHub Actions workflows
|
|
117
|
+
run: actionlint
|
|
118
|
+
|
|
119
|
+
- name: Type check
|
|
120
|
+
run: python -m mypy
|
|
121
|
+
|
|
122
|
+
- name: Check release metadata consistency
|
|
123
|
+
run: python tools/check_release.py
|
|
124
|
+
|
|
125
|
+
docs:
|
|
126
|
+
name: Documentation
|
|
127
|
+
runs-on: ubuntu-latest
|
|
128
|
+
timeout-minutes: 10
|
|
129
|
+
|
|
130
|
+
steps:
|
|
131
|
+
- name: Check out repository
|
|
132
|
+
uses: actions/checkout@v7
|
|
133
|
+
with:
|
|
134
|
+
persist-credentials: false
|
|
135
|
+
|
|
136
|
+
- name: Set up Python 3.12
|
|
137
|
+
uses: actions/setup-python@v6
|
|
138
|
+
with:
|
|
139
|
+
python-version: "3.12"
|
|
140
|
+
cache: pip
|
|
141
|
+
cache-dependency-path: pyproject.toml
|
|
142
|
+
|
|
143
|
+
- name: Install documentation dependencies
|
|
144
|
+
run: |
|
|
145
|
+
python -m pip install --upgrade pip
|
|
146
|
+
python -m pip install ".[docs,notebook]"
|
|
147
|
+
|
|
148
|
+
- name: Build documentation
|
|
149
|
+
run: python -m mkdocs build --strict
|
|
150
|
+
|
|
151
|
+
- name: Execute example notebooks
|
|
152
|
+
run: python tools/execute_notebooks.py
|
|
153
|
+
|
|
154
|
+
build:
|
|
155
|
+
name: Build and inspect distributions
|
|
156
|
+
runs-on: ubuntu-latest
|
|
157
|
+
timeout-minutes: 10
|
|
158
|
+
|
|
159
|
+
steps:
|
|
160
|
+
- name: Check out repository
|
|
161
|
+
uses: actions/checkout@v7
|
|
162
|
+
with:
|
|
163
|
+
persist-credentials: false
|
|
164
|
+
|
|
165
|
+
- name: Set up Python 3.12
|
|
166
|
+
uses: actions/setup-python@v6
|
|
167
|
+
with:
|
|
168
|
+
python-version: "3.12"
|
|
169
|
+
cache: pip
|
|
170
|
+
cache-dependency-path: pyproject.toml
|
|
171
|
+
|
|
172
|
+
- name: Install build frontend
|
|
173
|
+
run: |
|
|
174
|
+
python -m pip install --upgrade pip
|
|
175
|
+
python -m pip install build
|
|
176
|
+
|
|
177
|
+
- name: Build wheel and source distribution
|
|
178
|
+
run: python -m build
|
|
179
|
+
|
|
180
|
+
- name: Verify distribution contents
|
|
181
|
+
run: python tools/inspect_distribution.py dist
|
|
182
|
+
|
|
183
|
+
- name: Smoke test the installed wheel
|
|
184
|
+
shell: bash
|
|
185
|
+
run: |
|
|
186
|
+
python -m pip install --force-reinstall dist/*.whl
|
|
187
|
+
cd "$RUNNER_TEMP"
|
|
188
|
+
python - <<'PY'
|
|
189
|
+
import importlib.metadata
|
|
190
|
+
|
|
191
|
+
import meta_analyze as ma
|
|
192
|
+
|
|
193
|
+
result = ma.meta_analysis(
|
|
194
|
+
effect=[1.0, 2.0, 3.0],
|
|
195
|
+
variance=[1.0, 1.0, 1.0],
|
|
196
|
+
model="common",
|
|
197
|
+
)
|
|
198
|
+
assert result.k == 3
|
|
199
|
+
assert result.estimate == 2.0
|
|
200
|
+
print(importlib.metadata.version("PyMetaAnalysis"))
|
|
201
|
+
PY
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
name: Documentation site
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
branches:
|
|
6
|
+
- main
|
|
7
|
+
workflow_dispatch:
|
|
8
|
+
|
|
9
|
+
concurrency:
|
|
10
|
+
group: pages
|
|
11
|
+
cancel-in-progress: true
|
|
12
|
+
|
|
13
|
+
jobs:
|
|
14
|
+
build:
|
|
15
|
+
name: Build documentation site
|
|
16
|
+
runs-on: ubuntu-latest
|
|
17
|
+
timeout-minutes: 10
|
|
18
|
+
permissions:
|
|
19
|
+
contents: read
|
|
20
|
+
pages: write
|
|
21
|
+
|
|
22
|
+
steps:
|
|
23
|
+
- name: Check out repository
|
|
24
|
+
uses: actions/checkout@v7
|
|
25
|
+
with:
|
|
26
|
+
persist-credentials: false
|
|
27
|
+
|
|
28
|
+
- name: Set up Python
|
|
29
|
+
uses: actions/setup-python@v6
|
|
30
|
+
with:
|
|
31
|
+
python-version: "3.12"
|
|
32
|
+
cache: pip
|
|
33
|
+
cache-dependency-path: pyproject.toml
|
|
34
|
+
|
|
35
|
+
- name: Install documentation dependencies
|
|
36
|
+
run: |
|
|
37
|
+
python -m pip install --upgrade pip
|
|
38
|
+
python -m pip install ".[docs]"
|
|
39
|
+
|
|
40
|
+
- name: Configure GitHub Pages
|
|
41
|
+
uses: actions/configure-pages@v6
|
|
42
|
+
|
|
43
|
+
- name: Build strict MkDocs site
|
|
44
|
+
run: python -m mkdocs build --strict
|
|
45
|
+
|
|
46
|
+
- name: Upload GitHub Pages artifact
|
|
47
|
+
uses: actions/upload-pages-artifact@v5
|
|
48
|
+
with:
|
|
49
|
+
path: site
|
|
50
|
+
|
|
51
|
+
deploy:
|
|
52
|
+
name: Deploy documentation site
|
|
53
|
+
needs: build
|
|
54
|
+
runs-on: ubuntu-latest
|
|
55
|
+
timeout-minutes: 10
|
|
56
|
+
environment:
|
|
57
|
+
name: github-pages
|
|
58
|
+
url: ${{ steps.deployment.outputs.page_url }}
|
|
59
|
+
permissions:
|
|
60
|
+
pages: write
|
|
61
|
+
id-token: write
|
|
62
|
+
|
|
63
|
+
steps:
|
|
64
|
+
- name: Deploy to GitHub Pages
|
|
65
|
+
id: deployment
|
|
66
|
+
uses: actions/deploy-pages@v5
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
name: Release
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
tags:
|
|
6
|
+
- "v*"
|
|
7
|
+
|
|
8
|
+
concurrency:
|
|
9
|
+
group: release-${{ github.ref }}
|
|
10
|
+
cancel-in-progress: false
|
|
11
|
+
|
|
12
|
+
permissions:
|
|
13
|
+
contents: read
|
|
14
|
+
|
|
15
|
+
jobs:
|
|
16
|
+
build:
|
|
17
|
+
name: Build release artifacts
|
|
18
|
+
runs-on: ubuntu-latest
|
|
19
|
+
timeout-minutes: 15
|
|
20
|
+
|
|
21
|
+
steps:
|
|
22
|
+
- name: Check out tagged revision
|
|
23
|
+
uses: actions/checkout@v7
|
|
24
|
+
with:
|
|
25
|
+
fetch-depth: 0
|
|
26
|
+
persist-credentials: false
|
|
27
|
+
|
|
28
|
+
- name: Require the tagged commit to belong to main
|
|
29
|
+
run: git merge-base --is-ancestor "$GITHUB_SHA" origin/main
|
|
30
|
+
|
|
31
|
+
- name: Set up Python
|
|
32
|
+
uses: actions/setup-python@v6
|
|
33
|
+
with:
|
|
34
|
+
python-version: "3.12"
|
|
35
|
+
cache: pip
|
|
36
|
+
cache-dependency-path: pyproject.toml
|
|
37
|
+
|
|
38
|
+
- name: Install build tools
|
|
39
|
+
run: |
|
|
40
|
+
python -m pip install --upgrade pip
|
|
41
|
+
python -m pip install build twine
|
|
42
|
+
|
|
43
|
+
- name: Validate release metadata
|
|
44
|
+
run: python tools/check_release.py --tag "$GITHUB_REF_NAME"
|
|
45
|
+
|
|
46
|
+
- name: Build distributions
|
|
47
|
+
run: python -m build
|
|
48
|
+
|
|
49
|
+
- name: Check distribution metadata and contents
|
|
50
|
+
run: |
|
|
51
|
+
python -m twine check dist/*
|
|
52
|
+
python tools/inspect_distribution.py dist
|
|
53
|
+
|
|
54
|
+
- name: Benchmark the built wheel
|
|
55
|
+
run: |
|
|
56
|
+
python -m pip install --force-reinstall dist/*.whl
|
|
57
|
+
python benchmarks/benchmark_core.py --output release-benchmark.json
|
|
58
|
+
|
|
59
|
+
- name: Upload distributions
|
|
60
|
+
uses: actions/upload-artifact@v7
|
|
61
|
+
with:
|
|
62
|
+
name: python-package-distributions
|
|
63
|
+
path: dist/
|
|
64
|
+
if-no-files-found: error
|
|
65
|
+
retention-days: 7
|
|
66
|
+
|
|
67
|
+
- name: Upload release benchmark
|
|
68
|
+
uses: actions/upload-artifact@v7
|
|
69
|
+
with:
|
|
70
|
+
name: release-benchmark
|
|
71
|
+
path: release-benchmark.json
|
|
72
|
+
if-no-files-found: error
|
|
73
|
+
retention-days: 7
|
|
74
|
+
|
|
75
|
+
publish:
|
|
76
|
+
name: Publish distributions to PyPI
|
|
77
|
+
needs: build
|
|
78
|
+
runs-on: ubuntu-latest
|
|
79
|
+
timeout-minutes: 10
|
|
80
|
+
environment:
|
|
81
|
+
name: pypi
|
|
82
|
+
url: https://pypi.org/p/PyMetaAnalysis
|
|
83
|
+
permissions:
|
|
84
|
+
id-token: write
|
|
85
|
+
|
|
86
|
+
steps:
|
|
87
|
+
- name: Download distributions
|
|
88
|
+
uses: actions/download-artifact@v8
|
|
89
|
+
with:
|
|
90
|
+
name: python-package-distributions
|
|
91
|
+
path: dist/
|
|
92
|
+
|
|
93
|
+
- name: Publish to PyPI
|
|
94
|
+
uses: pypa/gh-action-pypi-publish@release/v1
|
|
95
|
+
|
|
96
|
+
github-release:
|
|
97
|
+
name: Create GitHub Release
|
|
98
|
+
needs: publish
|
|
99
|
+
runs-on: ubuntu-latest
|
|
100
|
+
timeout-minutes: 10
|
|
101
|
+
permissions:
|
|
102
|
+
contents: write
|
|
103
|
+
|
|
104
|
+
steps:
|
|
105
|
+
- name: Download distributions
|
|
106
|
+
uses: actions/download-artifact@v8
|
|
107
|
+
with:
|
|
108
|
+
name: python-package-distributions
|
|
109
|
+
path: dist/
|
|
110
|
+
|
|
111
|
+
- name: Download release benchmark
|
|
112
|
+
uses: actions/download-artifact@v8
|
|
113
|
+
with:
|
|
114
|
+
name: release-benchmark
|
|
115
|
+
|
|
116
|
+
- name: Create release
|
|
117
|
+
env:
|
|
118
|
+
GH_TOKEN: ${{ github.token }}
|
|
119
|
+
run: |
|
|
120
|
+
args=("$GITHUB_REF_NAME" dist/* release-benchmark.json --verify-tag --generate-notes)
|
|
121
|
+
version="${GITHUB_REF_NAME#v}"
|
|
122
|
+
if [[ "$version" =~ [[:alpha:]] ]]; then
|
|
123
|
+
args+=(--prerelease)
|
|
124
|
+
fi
|
|
125
|
+
gh release create "${args[@]}"
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
# Local design notes are intentionally not part of the published project.
|
|
2
|
+
/DESIGN.md
|
|
3
|
+
|
|
4
|
+
# Python environments and generated files
|
|
5
|
+
/.venv/
|
|
6
|
+
/.release-smoke/
|
|
7
|
+
.ipynb_checkpoints/
|
|
8
|
+
__pycache__/
|
|
9
|
+
*.py[cod]
|
|
10
|
+
*.egg-info/
|
|
11
|
+
/.pytest_cache/
|
|
12
|
+
/.hypothesis/
|
|
13
|
+
/.mypy_cache/
|
|
14
|
+
/.ruff_cache/
|
|
15
|
+
/.coverage
|
|
16
|
+
/htmlcov/
|
|
17
|
+
/build/
|
|
18
|
+
/dist/
|
|
19
|
+
/site/
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to PyMetaAnalysis will be documented in this file.
|
|
4
|
+
|
|
5
|
+
Changes planned for the next release accumulate under `Unreleased`.
|
|
6
|
+
|
|
7
|
+
## Unreleased
|
|
8
|
+
|
|
9
|
+
## 0.1.0 - 2026-07-15
|
|
10
|
+
|
|
11
|
+
### Added
|
|
12
|
+
|
|
13
|
+
- pandas-first generic, binary, and continuous study-level meta-analysis APIs;
|
|
14
|
+
- common-effect and random-effects inverse-variance models;
|
|
15
|
+
- common-effect Mantel-Haenszel OR/RR pooling;
|
|
16
|
+
- REML, Paule-Mandel, and DerSimonian-Laird tau-squared estimators;
|
|
17
|
+
- normal, Hartung-Knapp, and safeguarded Hartung-Knapp confidence intervals;
|
|
18
|
+
- HTS random-effects prediction intervals;
|
|
19
|
+
- subgroup, leave-one-out, and cumulative workflows;
|
|
20
|
+
- optional Matplotlib forest, subgroup forest, and funnel plots;
|
|
21
|
+
- immutable results, diagnostics, provenance, Methods text, and JSON/Markdown
|
|
22
|
+
reports;
|
|
23
|
+
- R `metafor` cross-software fixtures, property tests, and numerical edge-case
|
|
24
|
+
coverage;
|
|
25
|
+
- explicit RD zero-variance boundary policy and heterogeneity-definition
|
|
26
|
+
reporting;
|
|
27
|
+
- complete MkDocs user, methods, API, validation, limitation, and development
|
|
28
|
+
documentation;
|
|
29
|
+
- R `meta`/`metafor` terminology and parameter mappings;
|
|
30
|
+
- machine-readable citation metadata and an executable end-to-end notebook;
|
|
31
|
+
- GitHub Pages and PyPI Trusted Publishing release workflows;
|
|
32
|
+
- release metadata, distribution-content, notebook-execution, and performance
|
|
33
|
+
baseline tooling.
|
|
34
|
+
|
|
35
|
+
### Changed
|
|
36
|
+
|
|
37
|
+
- independent external statistical review is documented as a recommended
|
|
38
|
+
validation activity rather than a release requirement;
|
|
39
|
+
- report schema 1.1 records `heterogeneity.i2_method`;
|
|
40
|
+
- random-effects I-squared/H-squared use tau-squared and typical within-study
|
|
41
|
+
variance, while common-effect/MH analyses retain Q-based definitions;
|
|
42
|
+
- random-effects summaries provide method-selection notes for small-study and
|
|
43
|
+
positive-heterogeneity cases.
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
cff-version: 1.2.0
|
|
2
|
+
message: >-
|
|
3
|
+
If you use PyMetaAnalysis in research, cite the exact software release and
|
|
4
|
+
report the statistical methods used in the analysis.
|
|
5
|
+
title: PyMetaAnalysis
|
|
6
|
+
type: software
|
|
7
|
+
authors:
|
|
8
|
+
- name: PyMetaAnalysis contributors
|
|
9
|
+
version: 0.1.0
|
|
10
|
+
date-released: 2026-07-15
|
|
11
|
+
repository-code: https://github.com/ZhaoboDing/PyMetaAnalysis
|
|
12
|
+
url: https://zhaoboding.github.io/PyMetaAnalysis/
|
|
13
|
+
license: MIT
|
|
14
|
+
abstract: >-
|
|
15
|
+
A pandas-first Python library for auditable, conventional study-level
|
|
16
|
+
meta-analysis.
|
|
17
|
+
keywords:
|
|
18
|
+
- meta-analysis
|
|
19
|
+
- statistics
|
|
20
|
+
- systematic review
|
|
21
|
+
- evidence-based medicine
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
# Contributing to PyMetaAnalysis
|
|
2
|
+
|
|
3
|
+
Thank you for helping improve PyMetaAnalysis. Contributions may include code,
|
|
4
|
+
documentation, reproducible bug reports, statistical review, and independent
|
|
5
|
+
reference cases.
|
|
6
|
+
|
|
7
|
+
## Development setup
|
|
8
|
+
|
|
9
|
+
```console
|
|
10
|
+
git clone https://github.com/ZhaoboDing/PyMetaAnalysis.git
|
|
11
|
+
cd PyMetaAnalysis
|
|
12
|
+
python -m pip install -e ".[test,dev,docs,plot]"
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
Run the project checks before opening a pull request:
|
|
16
|
+
|
|
17
|
+
```console
|
|
18
|
+
python -m ruff format .
|
|
19
|
+
python -m ruff check .
|
|
20
|
+
python -m mypy
|
|
21
|
+
python -m pytest --cov=meta_analyze --cov-branch --cov-report=term-missing
|
|
22
|
+
python -m mkdocs build --strict
|
|
23
|
+
python -m build
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
Statistical changes need formula documentation, boundary tests, and an
|
|
27
|
+
independent reference comparison where possible. Do not replace committed
|
|
28
|
+
golden values without explaining and reviewing the discrepancy.
|
|
29
|
+
|
|
30
|
+
See the full [development and contribution guide](docs/development.md) for
|
|
31
|
+
statistical-change requirements, R fixture regeneration, documentation rules,
|
|
32
|
+
and issue-reporting guidance.
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 PyMetaAnalysis contributors
|
|
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.
|