causaliq-core 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.
- causaliq_core-0.1.0/LICENSE +21 -0
- causaliq_core-0.1.0/PKG-INFO +176 -0
- causaliq_core-0.1.0/README.md +119 -0
- causaliq_core-0.1.0/pyproject.toml +175 -0
- causaliq_core-0.1.0/setup.cfg +4 -0
- causaliq_core-0.1.0/src/causaliq_core/__init__.py +30 -0
- causaliq_core-0.1.0/src/causaliq_core/cli.py +30 -0
- causaliq_core-0.1.0/src/causaliq_core/graph/__init__.py +63 -0
- causaliq_core-0.1.0/src/causaliq_core/utils/__init__.py +254 -0
- causaliq_core-0.1.0/src/causaliq_core/utils/random.py +1212 -0
- causaliq_core-0.1.0/src/causaliq_core/utils/timing.py +318 -0
- causaliq_core-0.1.0/src/causaliq_core.egg-info/PKG-INFO +176 -0
- causaliq_core-0.1.0/src/causaliq_core.egg-info/SOURCES.txt +15 -0
- causaliq_core-0.1.0/src/causaliq_core.egg-info/dependency_links.txt +1 -0
- causaliq_core-0.1.0/src/causaliq_core.egg-info/entry_points.txt +3 -0
- causaliq_core-0.1.0/src/causaliq_core.egg-info/requires.txt +32 -0
- causaliq_core-0.1.0/src/causaliq_core.egg-info/top_level.txt +1 -0
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 CausalIQ
|
|
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,176 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: causaliq-core
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Core utilities and classes for the CausalIQ ecosystem
|
|
5
|
+
Author-email: CausalIQ <info@causaliq.org>
|
|
6
|
+
Maintainer-email: "Dr. Ken Kitson" <info@causaliq.org>
|
|
7
|
+
License: MIT
|
|
8
|
+
Project-URL: Homepage, https://github.com/causaliq/causaliq-core
|
|
9
|
+
Project-URL: Documentation, https://github.com/causaliq/causaliq-core#readme
|
|
10
|
+
Project-URL: Repository, https://github.com/causaliq/causaliq-core
|
|
11
|
+
Project-URL: Bug Tracker, https://github.com/causaliq/causaliq-core/issues
|
|
12
|
+
Keywords: causaliq
|
|
13
|
+
Classifier: Development Status :: 2 - Pre-Alpha
|
|
14
|
+
Classifier: Intended Audience :: Science/Research
|
|
15
|
+
Classifier: License :: OSI Approved :: MIT License
|
|
16
|
+
Classifier: Operating System :: OS Independent
|
|
17
|
+
Classifier: Programming Language :: Python :: 3
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.9
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
20
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
22
|
+
Classifier: Topic :: Scientific/Engineering
|
|
23
|
+
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
|
24
|
+
Requires-Python: >=3.9
|
|
25
|
+
Description-Content-Type: text/markdown
|
|
26
|
+
License-File: LICENSE
|
|
27
|
+
Requires-Dist: click>=8.0.0
|
|
28
|
+
Requires-Dist: numpy>=1.20.0
|
|
29
|
+
Requires-Dist: pandas>=1.3.0
|
|
30
|
+
Requires-Dist: platformdirs>=3.0.0
|
|
31
|
+
Requires-Dist: py-cpuinfo>=9.0.0
|
|
32
|
+
Requires-Dist: psutil>=5.8.0
|
|
33
|
+
Provides-Extra: dev
|
|
34
|
+
Requires-Dist: pytest>=7.0.0; extra == "dev"
|
|
35
|
+
Requires-Dist: pytest-cov>=4.0.0; extra == "dev"
|
|
36
|
+
Requires-Dist: pytest-mock>=3.10.0; extra == "dev"
|
|
37
|
+
Requires-Dist: black>=22.0.0; extra == "dev"
|
|
38
|
+
Requires-Dist: isort>=5.10.0; extra == "dev"
|
|
39
|
+
Requires-Dist: flake8>=5.0.0; extra == "dev"
|
|
40
|
+
Requires-Dist: mypy>=1.0.0; extra == "dev"
|
|
41
|
+
Requires-Dist: types-requests>=2.32.0; extra == "dev"
|
|
42
|
+
Requires-Dist: types-psutil>=5.9.0; extra == "dev"
|
|
43
|
+
Requires-Dist: pandas-stubs>=1.5.0; extra == "dev"
|
|
44
|
+
Requires-Dist: pre-commit>=2.20.0; extra == "dev"
|
|
45
|
+
Requires-Dist: build>=0.8.0; extra == "dev"
|
|
46
|
+
Requires-Dist: twine>=4.0.0; extra == "dev"
|
|
47
|
+
Provides-Extra: test
|
|
48
|
+
Requires-Dist: pytest>=7.0.0; extra == "test"
|
|
49
|
+
Requires-Dist: pytest-cov>=4.0.0; extra == "test"
|
|
50
|
+
Requires-Dist: pytest-mock>=3.10.0; extra == "test"
|
|
51
|
+
Provides-Extra: docs
|
|
52
|
+
Requires-Dist: mkdocs>=1.5.0; extra == "docs"
|
|
53
|
+
Requires-Dist: mkdocs-material>=9.0.0; extra == "docs"
|
|
54
|
+
Requires-Dist: mkdocstrings==0.30.1; extra == "docs"
|
|
55
|
+
Requires-Dist: mkdocstrings-python==1.18.2; extra == "docs"
|
|
56
|
+
Dynamic: license-file
|
|
57
|
+
|
|
58
|
+
# causaliq-core
|
|
59
|
+
|
|
60
|
+
[](https://pypi.org/project/zenodo-sync/)
|
|
61
|
+
[](https://opensource.org/licenses/MIT)
|
|
62
|
+
|
|
63
|
+
This is a template for **creating new CausalIQ repos** which provides a new **capability** and follows CausalIQ development practices.
|
|
64
|
+
|
|
65
|
+
## Status
|
|
66
|
+
|
|
67
|
+
🚧 **Active Development** - This repository is currently in active development. It will be updated periodically to align with the latest approaches used in CausalIQ repos. New repos within the CausalIQ project should follow the naming convention causaliq-[capability], e.g. "causaliq-discovery" or "causaliq-analysis".
|
|
68
|
+
|
|
69
|
+
|
|
70
|
+
## Features
|
|
71
|
+
|
|
72
|
+
- 📁 **Standardised project structure**: following current best practices
|
|
73
|
+
- ⌨️ **CLI Interface**: An initial dummy command-line interface.
|
|
74
|
+
- 📖 **Documentation framework**: using mkdocs with shared CausalIQ branding.
|
|
75
|
+
- 🐍 **Python setup**: providing virtual environments for Python 3.9, 3.10, 3.11 and 3.12.
|
|
76
|
+
- 🔬 **pytest test framework**: for unit, functional and integration testing including code coverage.
|
|
77
|
+
- 🔄 **Continuous Integration testing**: across Python versions and operating systems using GitHub actions
|
|
78
|
+
|
|
79
|
+
|
|
80
|
+
## New CausalIQ repo creation
|
|
81
|
+
|
|
82
|
+
This section provides instructions for **creating a completely new CausalIQ repo** which offers a **new capability**. This capability will be referred to as "newcapability" in the following instructions below, but should in practice be a word which meaningfully summarises the capability e.g. "pipeline" or "score".
|
|
83
|
+
|
|
84
|
+
### Prerequisites
|
|
85
|
+
|
|
86
|
+
- Git
|
|
87
|
+
- Latest stable versions of Python 3.9, 3.10. 3.11 and 3.12
|
|
88
|
+
|
|
89
|
+
### Create the new repo on GitHub
|
|
90
|
+
|
|
91
|
+
- Create the new repo with name causaliq-newcapability specifying **this repository (i.e. causaliq-core) as the template** with an initial commit message "feat: initial project setup from causaliq-core"
|
|
92
|
+
|
|
93
|
+
### Clone the new repo locally and check that it works
|
|
94
|
+
|
|
95
|
+
Clone the causaliq-newcapability repo locally as normal
|
|
96
|
+
|
|
97
|
+
```bash
|
|
98
|
+
git clone https://github.com/causaliq/causaliq-newcapability.git
|
|
99
|
+
```
|
|
100
|
+
|
|
101
|
+
Set up the Python virtual environments and activate the default Python virtual environment. You may see
|
|
102
|
+
messages from VSCode (if you are using it as your IDE) that new Python environments are being created
|
|
103
|
+
as the scripts/setup-env runs - these messages can be safely ignored at this stage.
|
|
104
|
+
|
|
105
|
+
```text
|
|
106
|
+
scripts/setup-env -Install
|
|
107
|
+
scripts/activate
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
Check that the causaliq-core CLI is working, check that all CI tests pass, and start up the local mkdocs webserver. There should be no errors reported in any of these.
|
|
111
|
+
|
|
112
|
+
```text
|
|
113
|
+
causaliq-core --help
|
|
114
|
+
scripts/check_ci
|
|
115
|
+
mkdocs serve
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
Enter **http://127.0.0.1:8000/** in a browser and check that the
|
|
119
|
+
causaliq-core skeleton documentation is visible.
|
|
120
|
+
|
|
121
|
+
If all of the above works, this confirms that the code from the template repo is working successfully on your system.
|
|
122
|
+
|
|
123
|
+
### Change all references in package to new package name
|
|
124
|
+
|
|
125
|
+
In the IDE (e.g. VSCode) editor make the following GLOBAL changes to all files and folder names
|
|
126
|
+
|
|
127
|
+
- replace **causaliq-core** with **causaliq-newcapability** in all files (57 changes across 16 files)
|
|
128
|
+
- replace **causaliq_core** with **causaliq_newcapability** in all files (13 changes across 5 files)
|
|
129
|
+
- rename folder **src/causaliq_core** to **src/causaliq_newcapability**
|
|
130
|
+
- manually delete the **src/causaliq-core.egg-info** package file
|
|
131
|
+
- manually delete all folders under venv (which will contain references to the causaliq-core)
|
|
132
|
+
|
|
133
|
+
⚠️ **Important**: Make sure to use underscores for Python package names (`causaliq_newcapability`) and hyphens for repo names (`causaliq-newcapability`)
|
|
134
|
+
|
|
135
|
+
### Check newly named package works OK and commit to GitHub
|
|
136
|
+
|
|
137
|
+
- Remove and re-setup the virtual environments again (which will then contain the package causaliq-newcapability), and activate the default Pyhton virtual environment
|
|
138
|
+
|
|
139
|
+
```text
|
|
140
|
+
scripts/setup-env -Install
|
|
141
|
+
scripts/activate
|
|
142
|
+
```
|
|
143
|
+
|
|
144
|
+
Check the causaliq-newcapability command runs, that all CI checks pass with the new
|
|
145
|
+
package name, and that mkdocs for the renamed package can be served.
|
|
146
|
+
|
|
147
|
+
```text
|
|
148
|
+
causaliq-newcapability --help
|
|
149
|
+
scripts/check_ci
|
|
150
|
+
mkdocs serve
|
|
151
|
+
```
|
|
152
|
+
This should all work without any errors and the mkdocs should refer to causaliq-newcapability
|
|
153
|
+
rather than causaliq-core.
|
|
154
|
+
|
|
155
|
+
This confirms that the package name has been successfully changed to "causaliq-newcapability". These changes can be commited to the new repo with message "refactor: package name changed to causaliq-newcapability"
|
|
156
|
+
|
|
157
|
+
### Start work on new package
|
|
158
|
+
|
|
159
|
+
The real work of implementing the functionality of this new CausalIQ package can now begin!
|
|
160
|
+
|
|
161
|
+
### Checklist
|
|
162
|
+
- [ ] GitHub repo created from template
|
|
163
|
+
- [ ] Repo cloned locally
|
|
164
|
+
- [ ] Initial tests pass
|
|
165
|
+
- [ ] All references renamed
|
|
166
|
+
- [ ] Folder renamed
|
|
167
|
+
- [ ] venv folders deleted
|
|
168
|
+
- [ ] Final tests pass
|
|
169
|
+
- [ ] Commit changes implementing new package name to GitHub
|
|
170
|
+
- [ ] Start work on the new package functionality!
|
|
171
|
+
|
|
172
|
+
|
|
173
|
+
---
|
|
174
|
+
|
|
175
|
+
**Supported Python Versions**: 3.9, 3.10, 3.11, 3.12
|
|
176
|
+
**Default Python Version**: 3.11
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
# causaliq-core
|
|
2
|
+
|
|
3
|
+
[](https://pypi.org/project/zenodo-sync/)
|
|
4
|
+
[](https://opensource.org/licenses/MIT)
|
|
5
|
+
|
|
6
|
+
This is a template for **creating new CausalIQ repos** which provides a new **capability** and follows CausalIQ development practices.
|
|
7
|
+
|
|
8
|
+
## Status
|
|
9
|
+
|
|
10
|
+
🚧 **Active Development** - This repository is currently in active development. It will be updated periodically to align with the latest approaches used in CausalIQ repos. New repos within the CausalIQ project should follow the naming convention causaliq-[capability], e.g. "causaliq-discovery" or "causaliq-analysis".
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
## Features
|
|
14
|
+
|
|
15
|
+
- 📁 **Standardised project structure**: following current best practices
|
|
16
|
+
- ⌨️ **CLI Interface**: An initial dummy command-line interface.
|
|
17
|
+
- 📖 **Documentation framework**: using mkdocs with shared CausalIQ branding.
|
|
18
|
+
- 🐍 **Python setup**: providing virtual environments for Python 3.9, 3.10, 3.11 and 3.12.
|
|
19
|
+
- 🔬 **pytest test framework**: for unit, functional and integration testing including code coverage.
|
|
20
|
+
- 🔄 **Continuous Integration testing**: across Python versions and operating systems using GitHub actions
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
## New CausalIQ repo creation
|
|
24
|
+
|
|
25
|
+
This section provides instructions for **creating a completely new CausalIQ repo** which offers a **new capability**. This capability will be referred to as "newcapability" in the following instructions below, but should in practice be a word which meaningfully summarises the capability e.g. "pipeline" or "score".
|
|
26
|
+
|
|
27
|
+
### Prerequisites
|
|
28
|
+
|
|
29
|
+
- Git
|
|
30
|
+
- Latest stable versions of Python 3.9, 3.10. 3.11 and 3.12
|
|
31
|
+
|
|
32
|
+
### Create the new repo on GitHub
|
|
33
|
+
|
|
34
|
+
- Create the new repo with name causaliq-newcapability specifying **this repository (i.e. causaliq-core) as the template** with an initial commit message "feat: initial project setup from causaliq-core"
|
|
35
|
+
|
|
36
|
+
### Clone the new repo locally and check that it works
|
|
37
|
+
|
|
38
|
+
Clone the causaliq-newcapability repo locally as normal
|
|
39
|
+
|
|
40
|
+
```bash
|
|
41
|
+
git clone https://github.com/causaliq/causaliq-newcapability.git
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
Set up the Python virtual environments and activate the default Python virtual environment. You may see
|
|
45
|
+
messages from VSCode (if you are using it as your IDE) that new Python environments are being created
|
|
46
|
+
as the scripts/setup-env runs - these messages can be safely ignored at this stage.
|
|
47
|
+
|
|
48
|
+
```text
|
|
49
|
+
scripts/setup-env -Install
|
|
50
|
+
scripts/activate
|
|
51
|
+
```
|
|
52
|
+
|
|
53
|
+
Check that the causaliq-core CLI is working, check that all CI tests pass, and start up the local mkdocs webserver. There should be no errors reported in any of these.
|
|
54
|
+
|
|
55
|
+
```text
|
|
56
|
+
causaliq-core --help
|
|
57
|
+
scripts/check_ci
|
|
58
|
+
mkdocs serve
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
Enter **http://127.0.0.1:8000/** in a browser and check that the
|
|
62
|
+
causaliq-core skeleton documentation is visible.
|
|
63
|
+
|
|
64
|
+
If all of the above works, this confirms that the code from the template repo is working successfully on your system.
|
|
65
|
+
|
|
66
|
+
### Change all references in package to new package name
|
|
67
|
+
|
|
68
|
+
In the IDE (e.g. VSCode) editor make the following GLOBAL changes to all files and folder names
|
|
69
|
+
|
|
70
|
+
- replace **causaliq-core** with **causaliq-newcapability** in all files (57 changes across 16 files)
|
|
71
|
+
- replace **causaliq_core** with **causaliq_newcapability** in all files (13 changes across 5 files)
|
|
72
|
+
- rename folder **src/causaliq_core** to **src/causaliq_newcapability**
|
|
73
|
+
- manually delete the **src/causaliq-core.egg-info** package file
|
|
74
|
+
- manually delete all folders under venv (which will contain references to the causaliq-core)
|
|
75
|
+
|
|
76
|
+
⚠️ **Important**: Make sure to use underscores for Python package names (`causaliq_newcapability`) and hyphens for repo names (`causaliq-newcapability`)
|
|
77
|
+
|
|
78
|
+
### Check newly named package works OK and commit to GitHub
|
|
79
|
+
|
|
80
|
+
- Remove and re-setup the virtual environments again (which will then contain the package causaliq-newcapability), and activate the default Pyhton virtual environment
|
|
81
|
+
|
|
82
|
+
```text
|
|
83
|
+
scripts/setup-env -Install
|
|
84
|
+
scripts/activate
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
Check the causaliq-newcapability command runs, that all CI checks pass with the new
|
|
88
|
+
package name, and that mkdocs for the renamed package can be served.
|
|
89
|
+
|
|
90
|
+
```text
|
|
91
|
+
causaliq-newcapability --help
|
|
92
|
+
scripts/check_ci
|
|
93
|
+
mkdocs serve
|
|
94
|
+
```
|
|
95
|
+
This should all work without any errors and the mkdocs should refer to causaliq-newcapability
|
|
96
|
+
rather than causaliq-core.
|
|
97
|
+
|
|
98
|
+
This confirms that the package name has been successfully changed to "causaliq-newcapability". These changes can be commited to the new repo with message "refactor: package name changed to causaliq-newcapability"
|
|
99
|
+
|
|
100
|
+
### Start work on new package
|
|
101
|
+
|
|
102
|
+
The real work of implementing the functionality of this new CausalIQ package can now begin!
|
|
103
|
+
|
|
104
|
+
### Checklist
|
|
105
|
+
- [ ] GitHub repo created from template
|
|
106
|
+
- [ ] Repo cloned locally
|
|
107
|
+
- [ ] Initial tests pass
|
|
108
|
+
- [ ] All references renamed
|
|
109
|
+
- [ ] Folder renamed
|
|
110
|
+
- [ ] venv folders deleted
|
|
111
|
+
- [ ] Final tests pass
|
|
112
|
+
- [ ] Commit changes implementing new package name to GitHub
|
|
113
|
+
- [ ] Start work on the new package functionality!
|
|
114
|
+
|
|
115
|
+
|
|
116
|
+
---
|
|
117
|
+
|
|
118
|
+
**Supported Python Versions**: 3.9, 3.10, 3.11, 3.12
|
|
119
|
+
**Default Python Version**: 3.11
|
|
@@ -0,0 +1,175 @@
|
|
|
1
|
+
[build-system]
|
|
2
|
+
requires = ["setuptools>=61.0", "wheel"]
|
|
3
|
+
build-backend = "setuptools.build_meta"
|
|
4
|
+
|
|
5
|
+
[project]
|
|
6
|
+
name = "causaliq-core"
|
|
7
|
+
dynamic = ["version"]
|
|
8
|
+
description = "Core utilities and classes for the CausalIQ ecosystem"
|
|
9
|
+
readme = "README.md"
|
|
10
|
+
license = {text = "MIT"}
|
|
11
|
+
authors = [
|
|
12
|
+
{name = "CausalIQ", email = "info@causaliq.org"},
|
|
13
|
+
]
|
|
14
|
+
maintainers = [
|
|
15
|
+
{name = "Dr. Ken Kitson", email = "info@causaliq.org"},
|
|
16
|
+
]
|
|
17
|
+
classifiers = [
|
|
18
|
+
"Development Status :: 2 - Pre-Alpha",
|
|
19
|
+
"Intended Audience :: Science/Research",
|
|
20
|
+
"License :: OSI Approved :: MIT License",
|
|
21
|
+
"Operating System :: OS Independent",
|
|
22
|
+
"Programming Language :: Python :: 3",
|
|
23
|
+
"Programming Language :: Python :: 3.9",
|
|
24
|
+
"Programming Language :: Python :: 3.10",
|
|
25
|
+
"Programming Language :: Python :: 3.11",
|
|
26
|
+
"Programming Language :: Python :: 3.12",
|
|
27
|
+
"Topic :: Scientific/Engineering",
|
|
28
|
+
"Topic :: Software Development :: Libraries :: Python Modules",
|
|
29
|
+
]
|
|
30
|
+
keywords = ["causaliq"]
|
|
31
|
+
requires-python = ">=3.9"
|
|
32
|
+
dependencies = [
|
|
33
|
+
"click>=8.0.0",
|
|
34
|
+
"numpy>=1.20.0",
|
|
35
|
+
"pandas>=1.3.0",
|
|
36
|
+
"platformdirs>=3.0.0",
|
|
37
|
+
"py-cpuinfo>=9.0.0",
|
|
38
|
+
"psutil>=5.8.0",
|
|
39
|
+
]
|
|
40
|
+
|
|
41
|
+
[project.optional-dependencies]
|
|
42
|
+
dev = [
|
|
43
|
+
"pytest>=7.0.0",
|
|
44
|
+
"pytest-cov>=4.0.0",
|
|
45
|
+
"pytest-mock>=3.10.0",
|
|
46
|
+
"black>=22.0.0",
|
|
47
|
+
"isort>=5.10.0",
|
|
48
|
+
"flake8>=5.0.0",
|
|
49
|
+
"mypy>=1.0.0",
|
|
50
|
+
"types-requests>=2.32.0",
|
|
51
|
+
"types-psutil>=5.9.0",
|
|
52
|
+
"pandas-stubs>=1.5.0",
|
|
53
|
+
"pre-commit>=2.20.0",
|
|
54
|
+
"build>=0.8.0",
|
|
55
|
+
"twine>=4.0.0",
|
|
56
|
+
]
|
|
57
|
+
test = [
|
|
58
|
+
"pytest>=7.0.0",
|
|
59
|
+
"pytest-cov>=4.0.0",
|
|
60
|
+
"pytest-mock>=3.10.0",
|
|
61
|
+
]
|
|
62
|
+
docs = [
|
|
63
|
+
"mkdocs>=1.5.0",
|
|
64
|
+
"mkdocs-material>=9.0.0",
|
|
65
|
+
"mkdocstrings==0.30.1",
|
|
66
|
+
"mkdocstrings-python==1.18.2"
|
|
67
|
+
]
|
|
68
|
+
|
|
69
|
+
[project.urls]
|
|
70
|
+
Homepage = "https://github.com/causaliq/causaliq-core"
|
|
71
|
+
Documentation = "https://github.com/causaliq/causaliq-core#readme"
|
|
72
|
+
Repository = "https://github.com/causaliq/causaliq-core"
|
|
73
|
+
"Bug Tracker" = "https://github.com/causaliq/causaliq-core/issues"
|
|
74
|
+
|
|
75
|
+
[project.scripts]
|
|
76
|
+
causaliq-core = "causaliq_core.cli:main"
|
|
77
|
+
cqcor = "causaliq_core.cli:main"
|
|
78
|
+
|
|
79
|
+
[tool.setuptools.dynamic]
|
|
80
|
+
version = {attr = "causaliq_core.__version__"}
|
|
81
|
+
|
|
82
|
+
[tool.setuptools.packages.find]
|
|
83
|
+
where = ["src"]
|
|
84
|
+
|
|
85
|
+
[tool.setuptools.package-dir]
|
|
86
|
+
"" = "src"
|
|
87
|
+
|
|
88
|
+
[tool.pytest.ini_options]
|
|
89
|
+
minversion = "7.0"
|
|
90
|
+
addopts = "-ra -q --strict-markers --cov=causaliq_core --cov-report=term-missing --cov-report=html"
|
|
91
|
+
testpaths = [
|
|
92
|
+
"tests",
|
|
93
|
+
]
|
|
94
|
+
python_files = [
|
|
95
|
+
"test_*.py",
|
|
96
|
+
"*_test.py",
|
|
97
|
+
]
|
|
98
|
+
python_classes = [
|
|
99
|
+
"Test*",
|
|
100
|
+
]
|
|
101
|
+
python_functions = [
|
|
102
|
+
"test_*",
|
|
103
|
+
]
|
|
104
|
+
markers = [
|
|
105
|
+
"unit: Unit tests (fast, no external dependencies)",
|
|
106
|
+
"functional: Functional tests (CLI behavior, mocked external deps)",
|
|
107
|
+
"integration: Integration tests (real external dependencies)",
|
|
108
|
+
"slow: Slow tests that take significant time",
|
|
109
|
+
]
|
|
110
|
+
|
|
111
|
+
[tool.coverage.run]
|
|
112
|
+
source = ["src/causaliq_core"]
|
|
113
|
+
omit = [
|
|
114
|
+
"*/tests/*",
|
|
115
|
+
"*/test_*.py",
|
|
116
|
+
]
|
|
117
|
+
parallel = true
|
|
118
|
+
concurrency = ["thread", "multiprocessing"]
|
|
119
|
+
|
|
120
|
+
[tool.coverage.report]
|
|
121
|
+
exclude_lines = [
|
|
122
|
+
"pragma: no cover",
|
|
123
|
+
"def __repr__",
|
|
124
|
+
"if self.debug:",
|
|
125
|
+
"if settings.DEBUG",
|
|
126
|
+
"raise AssertionError",
|
|
127
|
+
"raise NotImplementedError",
|
|
128
|
+
"if 0:",
|
|
129
|
+
"if __name__ == .__main__.:",
|
|
130
|
+
"class .*\\bProtocol\\):",
|
|
131
|
+
"@(abc\\.)?abstractmethod",
|
|
132
|
+
]
|
|
133
|
+
|
|
134
|
+
[tool.black]
|
|
135
|
+
line-length = 79
|
|
136
|
+
target-version = ['py39']
|
|
137
|
+
include = '\.pyi?$'
|
|
138
|
+
extend-exclude = '''
|
|
139
|
+
/(
|
|
140
|
+
# directories
|
|
141
|
+
\.eggs
|
|
142
|
+
| \.git
|
|
143
|
+
| \.hg
|
|
144
|
+
| \.mypy_cache
|
|
145
|
+
| \.tox
|
|
146
|
+
| \.venv
|
|
147
|
+
| build
|
|
148
|
+
| dist
|
|
149
|
+
)/
|
|
150
|
+
'''
|
|
151
|
+
|
|
152
|
+
[tool.isort]
|
|
153
|
+
profile = "black"
|
|
154
|
+
multi_line_output = 3
|
|
155
|
+
line_length = 79
|
|
156
|
+
known_first_party = ["causaliq_core"]
|
|
157
|
+
|
|
158
|
+
[tool.mypy]
|
|
159
|
+
python_version = "3.9"
|
|
160
|
+
warn_return_any = true
|
|
161
|
+
warn_unused_configs = true
|
|
162
|
+
disallow_untyped_defs = true
|
|
163
|
+
disallow_incomplete_defs = true
|
|
164
|
+
check_untyped_defs = true
|
|
165
|
+
disallow_untyped_decorators = true
|
|
166
|
+
no_implicit_optional = true
|
|
167
|
+
warn_redundant_casts = true
|
|
168
|
+
warn_unused_ignores = true
|
|
169
|
+
warn_no_return = true
|
|
170
|
+
warn_unreachable = true
|
|
171
|
+
strict_equality = true
|
|
172
|
+
|
|
173
|
+
[[tool.mypy.overrides]]
|
|
174
|
+
module = "tests.*"
|
|
175
|
+
disallow_untyped_defs = false
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"""
|
|
2
|
+
causaliq-core: Core utilities and classes for the CausalIQ ecosystem
|
|
3
|
+
"""
|
|
4
|
+
|
|
5
|
+
__version__ = "0.1.0"
|
|
6
|
+
__author__ = "CausalIQ"
|
|
7
|
+
__email__ = "info@causaliq.org"
|
|
8
|
+
|
|
9
|
+
# Package metadata
|
|
10
|
+
__title__ = "causaliq-core"
|
|
11
|
+
__description__ = "Core utilities and classes for the CausalIQ ecosystem"
|
|
12
|
+
|
|
13
|
+
__url__ = "https://github.com/causaliq/causaliq-core"
|
|
14
|
+
__license__ = "MIT"
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
# Version tuple for programmatic access
|
|
18
|
+
VERSION = tuple(map(int, __version__.split(".")))
|
|
19
|
+
|
|
20
|
+
# Legacy software version constant (migrated from legacy.py)
|
|
21
|
+
SOFTWARE_VERSION: int = 229
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
__all__ = [
|
|
25
|
+
"__version__",
|
|
26
|
+
"__author__",
|
|
27
|
+
"__email__",
|
|
28
|
+
"VERSION",
|
|
29
|
+
"SOFTWARE_VERSION",
|
|
30
|
+
]
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"""Command-line interface for causaliq-core."""
|
|
2
|
+
|
|
3
|
+
import click
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
@click.command(name="causaliq-core")
|
|
7
|
+
@click.version_option(version="0.1.0")
|
|
8
|
+
@click.argument(
|
|
9
|
+
"name",
|
|
10
|
+
metavar="NAME",
|
|
11
|
+
required=True,
|
|
12
|
+
nargs=1,
|
|
13
|
+
)
|
|
14
|
+
@click.option("--greet", default="Hello", help="Greeting to use")
|
|
15
|
+
def cli(name: str, greet: str) -> None:
|
|
16
|
+
"""
|
|
17
|
+
Simple CLI example.
|
|
18
|
+
|
|
19
|
+
NAME is the person to greet
|
|
20
|
+
"""
|
|
21
|
+
click.echo(f"{greet}, {name}!")
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
def main() -> None:
|
|
25
|
+
"""Entry point for the CLI."""
|
|
26
|
+
cli(prog_name="causaliq-core (cqcor)")
|
|
27
|
+
|
|
28
|
+
|
|
29
|
+
if __name__ == "__main__": # pragma: no cover
|
|
30
|
+
main()
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Graph-related enums and utilities for CausalIQ Core.
|
|
3
|
+
"""
|
|
4
|
+
|
|
5
|
+
from enum import Enum
|
|
6
|
+
from typing import Dict, List, Optional
|
|
7
|
+
|
|
8
|
+
from pandas import DataFrame
|
|
9
|
+
|
|
10
|
+
# Supported BayeSys versions for graph comparison semantics
|
|
11
|
+
BAYESYS_VERSIONS = ["v1.3", "v1.5+"]
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
def adjmat(columns: Optional[Dict[str, List[int]]] = None) -> DataFrame:
|
|
15
|
+
"""
|
|
16
|
+
Create an adjacency matrix with specified entries.
|
|
17
|
+
|
|
18
|
+
:param dict columns: data for matrix specified by column
|
|
19
|
+
|
|
20
|
+
:raises TypeError: if arg types incorrect
|
|
21
|
+
:raises ValueError: if values specified are invalid
|
|
22
|
+
|
|
23
|
+
:returns DataFrame: the adjacency matrix
|
|
24
|
+
"""
|
|
25
|
+
if (
|
|
26
|
+
columns is None
|
|
27
|
+
or not isinstance(columns, dict)
|
|
28
|
+
or not all([isinstance(c, list) for c in columns.values()])
|
|
29
|
+
or not all([isinstance(e, int) for c in columns.values() for e in c])
|
|
30
|
+
):
|
|
31
|
+
raise TypeError("adjmat called with bad arg type")
|
|
32
|
+
|
|
33
|
+
if not all([len(c) == len(columns) for c in columns.values()]):
|
|
34
|
+
raise ValueError("some columns wrong length for adjmat")
|
|
35
|
+
|
|
36
|
+
valid = [e.value[0] for e in EdgeType] # valid edge integer codes
|
|
37
|
+
if not all([e in valid for c in columns.values() for e in c]):
|
|
38
|
+
raise ValueError("invalid integer values for adjmat")
|
|
39
|
+
|
|
40
|
+
adjmat_df = DataFrame(columns, dtype="int8")
|
|
41
|
+
adjmat_df[""] = list(adjmat_df.columns)
|
|
42
|
+
return adjmat_df.set_index("")
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
class EdgeMark(Enum):
|
|
46
|
+
"""Supported 'ends' of an edge in a graph."""
|
|
47
|
+
|
|
48
|
+
NONE = 0
|
|
49
|
+
LINE = 1
|
|
50
|
+
ARROW = 2
|
|
51
|
+
CIRCLE = 3
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
class EdgeType(Enum):
|
|
55
|
+
"""Supported edge types and their symbols."""
|
|
56
|
+
|
|
57
|
+
NONE = (0, EdgeMark.NONE, EdgeMark.NONE, "")
|
|
58
|
+
DIRECTED = (1, EdgeMark.LINE, EdgeMark.ARROW, "->")
|
|
59
|
+
UNDIRECTED = (2, EdgeMark.LINE, EdgeMark.LINE, "-")
|
|
60
|
+
BIDIRECTED = (3, EdgeMark.ARROW, EdgeMark.ARROW, "<->")
|
|
61
|
+
SEMIDIRECTED = (4, EdgeMark.CIRCLE, EdgeMark.ARROW, "o->")
|
|
62
|
+
NONDIRECTED = (5, EdgeMark.CIRCLE, EdgeMark.CIRCLE, "o-o")
|
|
63
|
+
SEMIUNDIRECTED = (6, EdgeMark.CIRCLE, EdgeMark.LINE, "o-")
|