priorityx 0.2.5__tar.gz → 0.3.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.
- {priorityx-0.2.5 → priorityx-0.3.0}/PKG-INFO +5 -14
- {priorityx-0.2.5 → priorityx-0.3.0}/README.md +4 -13
- priorityx-0.3.0/docs/README.md +15 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/docs/api-reference.md +14 -14
- priorityx-0.3.0/docs/output_naming.md +168 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/docs/quickstart.md +18 -14
- {priorityx-0.2.5 → priorityx-0.3.0}/examples/bugs/bugs_monitoring.py +3 -4
- {priorityx-0.2.5 → priorityx-0.3.0}/examples/incidents/incident_monitoring.py +11 -20
- {priorityx-0.2.5 → priorityx-0.3.0}/examples/violations/violations_monitoring.py +6 -10
- {priorityx-0.2.5 → priorityx-0.3.0}/pyproject.toml +1 -1
- priorityx-0.3.0/src/priorityx/__init__.py +43 -0
- priorityx-0.3.0/src/priorityx/api.py +41 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/core/glmm.py +39 -4
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/tracking/drivers.py +8 -5
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/tracking/movement.py +206 -56
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/tracking/transitions.py +12 -13
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/utils/helpers.py +18 -1
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/viz/matrix.py +11 -9
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/viz/timeline.py +34 -7
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/viz/trajectory.py +20 -15
- {priorityx-0.2.5 → priorityx-0.3.0}/tests/test_glmm.py +66 -14
- priorityx-0.3.0/tests/test_movement_monthly.py +108 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/tests/test_transitions.py +21 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/uv.lock +82 -92
- priorityx-0.2.5/src/priorityx/__init__.py +0 -7
- {priorityx-0.2.5 → priorityx-0.3.0}/.github/workflows/release.yml +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/.github/workflows/test.yml +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/.gitignore +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/LICENSE +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/Makefile +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/docs/methodology.md +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/docs/priority_classification.md +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/examples/README.md +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/scripts/version.py +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/core/__init__.py +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/core/filters.py +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/core/quadrants.py +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/tracking/__init__.py +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/utils/__init__.py +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/src/priorityx/viz/__init__.py +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/tests/test_drivers.py +0 -0
- {priorityx-0.2.5 → priorityx-0.3.0}/tests/test_quadrants.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: priorityx
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.3.0
|
|
4
4
|
Summary: Entity prioritization and escalation detection using GLMM statistical models
|
|
5
5
|
Project-URL: Homepage, https://github.com/okkymabruri/priorityx
|
|
6
6
|
Project-URL: Repository, https://github.com/okkymabruri/priorityx
|
|
@@ -44,29 +44,20 @@ pip install priorityx
|
|
|
44
44
|
|
|
45
45
|
## Quick Start
|
|
46
46
|
|
|
47
|
-
### Deterministic runs
|
|
48
|
-
|
|
49
|
-
Set `PRIORITYX_GLMM_SEED` (or call `set_glmm_random_seed()`) before running analyses to obtain repeatable GLMM estimates during debugging or CI checks:
|
|
50
|
-
|
|
51
|
-
```bash
|
|
52
|
-
PRIORITYX_GLMM_SEED=1234 python your_script.py
|
|
53
|
-
```
|
|
54
|
-
|
|
55
47
|
```python
|
|
56
48
|
import pandas as pd
|
|
57
|
-
|
|
58
|
-
from priorityx.viz.matrix import plot_priority_matrix
|
|
49
|
+
import priorityx as px
|
|
59
50
|
|
|
60
51
|
df = pd.read_csv("data.csv")
|
|
61
52
|
|
|
62
|
-
results, stats = fit_priority_matrix(
|
|
53
|
+
results, stats = px.fit_priority_matrix(
|
|
63
54
|
df,
|
|
64
55
|
entity_col="service",
|
|
65
56
|
timestamp_col="date",
|
|
66
|
-
temporal_granularity="quarterly"
|
|
57
|
+
temporal_granularity="quarterly",
|
|
67
58
|
)
|
|
68
59
|
|
|
69
|
-
plot_priority_matrix(results, entity_name="Service", save_plot=True)
|
|
60
|
+
px.plot_priority_matrix(results, entity_name="Service", save_plot=True)
|
|
70
61
|
```
|
|
71
62
|
|
|
72
63
|
## Features
|
|
@@ -16,29 +16,20 @@ pip install priorityx
|
|
|
16
16
|
|
|
17
17
|
## Quick Start
|
|
18
18
|
|
|
19
|
-
### Deterministic runs
|
|
20
|
-
|
|
21
|
-
Set `PRIORITYX_GLMM_SEED` (or call `set_glmm_random_seed()`) before running analyses to obtain repeatable GLMM estimates during debugging or CI checks:
|
|
22
|
-
|
|
23
|
-
```bash
|
|
24
|
-
PRIORITYX_GLMM_SEED=1234 python your_script.py
|
|
25
|
-
```
|
|
26
|
-
|
|
27
19
|
```python
|
|
28
20
|
import pandas as pd
|
|
29
|
-
|
|
30
|
-
from priorityx.viz.matrix import plot_priority_matrix
|
|
21
|
+
import priorityx as px
|
|
31
22
|
|
|
32
23
|
df = pd.read_csv("data.csv")
|
|
33
24
|
|
|
34
|
-
results, stats = fit_priority_matrix(
|
|
25
|
+
results, stats = px.fit_priority_matrix(
|
|
35
26
|
df,
|
|
36
27
|
entity_col="service",
|
|
37
28
|
timestamp_col="date",
|
|
38
|
-
temporal_granularity="quarterly"
|
|
29
|
+
temporal_granularity="quarterly",
|
|
39
30
|
)
|
|
40
31
|
|
|
41
|
-
plot_priority_matrix(results, entity_name="Service", save_plot=True)
|
|
32
|
+
px.plot_priority_matrix(results, entity_name="Service", save_plot=True)
|
|
42
33
|
```
|
|
43
34
|
|
|
44
35
|
## Features
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
# Docs overview
|
|
2
|
+
|
|
3
|
+
This folder holds the main reference material for `priorityx`.
|
|
4
|
+
|
|
5
|
+
- `quickstart.md` – short walk‑through: install, load data, run a first
|
|
6
|
+
priority matrix and plot it.
|
|
7
|
+
- `api-reference.md` – function‑by‑function notes for the core modules
|
|
8
|
+
(GLMM, movement, transitions, plots, helpers).
|
|
9
|
+
- `methodology.md` – background on the modelling choices: Poisson GLMM,
|
|
10
|
+
time aggregation, movement tracking, and how we think about risk
|
|
11
|
+
quadrants.
|
|
12
|
+
- `priority_classification.md` – how P1–P4 priorities and spike markers
|
|
13
|
+
are defined and used in timelines.
|
|
14
|
+
- `output_naming.md` – how plot/CSV artifacts are named and where they
|
|
15
|
+
are written on disk (e.g. `results/plot`, `results/csv`).
|
|
@@ -5,9 +5,9 @@
|
|
|
5
5
|
### fit_priority_matrix
|
|
6
6
|
|
|
7
7
|
```python
|
|
8
|
-
|
|
8
|
+
import priorityx as px
|
|
9
9
|
|
|
10
|
-
results, stats = fit_priority_matrix(
|
|
10
|
+
results, stats = px.fit_priority_matrix(
|
|
11
11
|
df,
|
|
12
12
|
entity_col,
|
|
13
13
|
timestamp_col,
|
|
@@ -50,9 +50,9 @@ Fits Poisson GLMM to classify entities into priority quadrants.
|
|
|
50
50
|
### track_cumulative_movement
|
|
51
51
|
|
|
52
52
|
```python
|
|
53
|
-
|
|
53
|
+
import priorityx as px
|
|
54
54
|
|
|
55
|
-
movement, meta = track_cumulative_movement(
|
|
55
|
+
movement, meta = px.track_cumulative_movement(
|
|
56
56
|
df,
|
|
57
57
|
entity_col,
|
|
58
58
|
timestamp_col,
|
|
@@ -74,9 +74,9 @@ Tracks entity movement through priority quadrants over time.
|
|
|
74
74
|
### extract_transitions
|
|
75
75
|
|
|
76
76
|
```python
|
|
77
|
-
|
|
77
|
+
import priorityx as px
|
|
78
78
|
|
|
79
|
-
transitions = extract_transitions(
|
|
79
|
+
transitions = px.extract_transitions(
|
|
80
80
|
movement_df,
|
|
81
81
|
focus_risk_increasing=True
|
|
82
82
|
)
|
|
@@ -90,9 +90,9 @@ Extracts quadrant transitions from movement data.
|
|
|
90
90
|
### extract_transition_drivers
|
|
91
91
|
|
|
92
92
|
```python
|
|
93
|
-
|
|
93
|
+
import priorityx as px
|
|
94
94
|
|
|
95
|
-
analysis = extract_transition_drivers(
|
|
95
|
+
analysis = px.extract_transition_drivers(
|
|
96
96
|
movement_df,
|
|
97
97
|
df_raw,
|
|
98
98
|
entity_name="Service A",
|
|
@@ -156,9 +156,9 @@ Classifies supervisory priority (1=Critical, 2=Investigate, 3=Monitor, 4=Low).
|
|
|
156
156
|
### plot_priority_matrix
|
|
157
157
|
|
|
158
158
|
```python
|
|
159
|
-
|
|
159
|
+
import priorityx as px
|
|
160
160
|
|
|
161
|
-
fig = plot_priority_matrix(
|
|
161
|
+
fig = px.plot_priority_matrix(
|
|
162
162
|
results_df,
|
|
163
163
|
entity_name="Entity",
|
|
164
164
|
figsize=(16, 12),
|
|
@@ -174,9 +174,9 @@ Creates scatter plot of priority matrix.
|
|
|
174
174
|
### plot_transition_timeline
|
|
175
175
|
|
|
176
176
|
```python
|
|
177
|
-
|
|
177
|
+
import priorityx as px
|
|
178
178
|
|
|
179
|
-
fig = plot_transition_timeline(
|
|
179
|
+
fig = px.plot_transition_timeline(
|
|
180
180
|
transitions_df,
|
|
181
181
|
entity_name="Entity",
|
|
182
182
|
filter_risk_levels=["critical", "high"],
|
|
@@ -192,9 +192,9 @@ Creates timeline heatmap of transitions. Passing `movement_df` is required to co
|
|
|
192
192
|
### plot_entity_trajectories
|
|
193
193
|
|
|
194
194
|
```python
|
|
195
|
-
|
|
195
|
+
import priorityx as px
|
|
196
196
|
|
|
197
|
-
fig = plot_entity_trajectories(
|
|
197
|
+
fig = px.plot_entity_trajectories(
|
|
198
198
|
movement_df,
|
|
199
199
|
entity_name="Entity",
|
|
200
200
|
max_entities=10,
|
|
@@ -0,0 +1,168 @@
|
|
|
1
|
+
% PriorityX Output Naming
|
|
2
|
+
|
|
3
|
+
This note documents where PriorityX writes plots/CSVs and how filenames
|
|
4
|
+
are constructed. It is meant as a quick reference when wiring outputs
|
|
5
|
+
into EWS pipelines or BI tools.
|
|
6
|
+
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
## Directories
|
|
10
|
+
|
|
11
|
+
By default, PriorityX writes artifacts under the current working
|
|
12
|
+
directory, using two main folders:
|
|
13
|
+
|
|
14
|
+
- `results/plot/` – PNG plots
|
|
15
|
+
- `results/csv/` – CSV tables (movement, matrices, transitions, etc.)
|
|
16
|
+
|
|
17
|
+
You can override these via the `plot_dir` / `csv_dir` / `output_dir`
|
|
18
|
+
arguments on the plotting and helper functions.
|
|
19
|
+
|
|
20
|
+
---
|
|
21
|
+
|
|
22
|
+
## Priority Matrix
|
|
23
|
+
|
|
24
|
+
Function: `priorityx.viz.matrix.plot_priority_matrix`
|
|
25
|
+
|
|
26
|
+
- Default `plot_dir`: `results/plot`
|
|
27
|
+
- Default `csv_dir`: `results/csv`
|
|
28
|
+
- Filename pattern (plot):
|
|
29
|
+
|
|
30
|
+
```text
|
|
31
|
+
priority_matrix-<entity_name_slug>-<granularity_suffix>-<YYYYMMDD>.png
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
- Filename pattern (CSV):
|
|
35
|
+
|
|
36
|
+
```text
|
|
37
|
+
priority_matrix-<entity_name_slug>-<granularity_suffix>-<YYYYMMDD>.csv
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
Where:
|
|
41
|
+
|
|
42
|
+
- `<entity_name_slug>` is `entity_name.lower().replace(" ", "_")`
|
|
43
|
+
- `<granularity_suffix>` is:
|
|
44
|
+
- `Q` for quarterly
|
|
45
|
+
- `Y` for yearly
|
|
46
|
+
- `S` for semiannual
|
|
47
|
+
|
|
48
|
+
Example (topics, quarterly):
|
|
49
|
+
|
|
50
|
+
```text
|
|
51
|
+
results/plot/priority_matrix-topic-Q-20251126.png
|
|
52
|
+
results/csv/priority_matrix-topic-Q-20251126.csv
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
---
|
|
56
|
+
|
|
57
|
+
## Transition Timelines
|
|
58
|
+
|
|
59
|
+
Function: `priorityx.viz.timeline.plot_transition_timeline`
|
|
60
|
+
|
|
61
|
+
- Default `plot_dir`: `results/plot`
|
|
62
|
+
- Default `csv_dir`: `results/csv`
|
|
63
|
+
- Filename pattern (plot):
|
|
64
|
+
|
|
65
|
+
```text
|
|
66
|
+
transition_timeline-<entity_name_slug>-<granularity_suffix>-<YYYYMMDD>.png
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
- Filename pattern (CSV):
|
|
70
|
+
|
|
71
|
+
```text
|
|
72
|
+
transition_timeline-<entity_name_slug>-<granularity_suffix>-<YYYYMMDD>.csv
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Example (FSPs, quarterly):
|
|
76
|
+
|
|
77
|
+
```text
|
|
78
|
+
results/plot/transition_timeline-fsp-Q-20251126.png
|
|
79
|
+
results/csv/transition_timeline-fsp-Q-20251126.csv
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
---
|
|
83
|
+
|
|
84
|
+
## Trajectories
|
|
85
|
+
|
|
86
|
+
Function: `priorityx.viz.trajectory.plot_entity_trajectories`
|
|
87
|
+
|
|
88
|
+
- Default `plot_dir`: `results/plot`
|
|
89
|
+
- Default `csv_dir`: `results/csv`
|
|
90
|
+
- Filename pattern (plot):
|
|
91
|
+
|
|
92
|
+
```text
|
|
93
|
+
trajectories-<entity_name_slug>-<granularity_suffix>-<YYYYMMDD>.png
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
- When `save_csv=True` (default is `False`), CSV is saved via
|
|
97
|
+
`priorityx.utils.helpers.save_dataframe_to_csv` with artifact name
|
|
98
|
+
`"trajectories"` (see next section).
|
|
99
|
+
|
|
100
|
+
Example (topics, quarterly):
|
|
101
|
+
|
|
102
|
+
```text
|
|
103
|
+
results/plot/trajectories-topic-Q-20251126.png
|
|
104
|
+
results/csv/trajectories-topic-Q-20251126.csv # only when save_csv=True
|
|
105
|
+
```
|
|
106
|
+
|
|
107
|
+
---
|
|
108
|
+
|
|
109
|
+
## Helpers: CSV Naming
|
|
110
|
+
|
|
111
|
+
Utility: `priorityx.utils.helpers.save_dataframe_to_csv`
|
|
112
|
+
|
|
113
|
+
This helper centralises CSV naming using `generate_output_path`:
|
|
114
|
+
|
|
115
|
+
```text
|
|
116
|
+
<output_dir>/<artifact>-<entity_slug>-<granularity_suffix>-<YYYYMMDD>.csv
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
Where:
|
|
120
|
+
|
|
121
|
+
- `<output_dir>` defaults to `results/csv`
|
|
122
|
+
- `<artifact>` is a short key such as `movement`, `trajectories`,
|
|
123
|
+
`priority_matrix`
|
|
124
|
+
- `<entity_slug>` is `entity_name.lower().replace(" ", "_")`
|
|
125
|
+
- `<granularity_suffix>` is `Q`, `Y`, or `S` (as above)
|
|
126
|
+
|
|
127
|
+
Examples:
|
|
128
|
+
|
|
129
|
+
```text
|
|
130
|
+
results/csv/movement-topic-Q-20251126.csv
|
|
131
|
+
results/csv/trajectories-fsp-Q-20251126.csv
|
|
132
|
+
```
|
|
133
|
+
|
|
134
|
+
### EWS canonical CSV outputs
|
|
135
|
+
|
|
136
|
+
For the complaints Early Warning System (EWS) pipelines, the canonical
|
|
137
|
+
CSV artifacts per run are:
|
|
138
|
+
|
|
139
|
+
```text
|
|
140
|
+
movement-*.csv
|
|
141
|
+
priority_matrix-*.csv
|
|
142
|
+
transitions-*.csv
|
|
143
|
+
```
|
|
144
|
+
|
|
145
|
+
Trajectory CSVs (`trajectories-*.csv`) are optional and are typically
|
|
146
|
+
only written for selected custom views (for example, a focus list of
|
|
147
|
+
FSPs or products) by explicitly passing `save_csv=True` to
|
|
148
|
+
`plot_entity_trajectories`.
|
|
149
|
+
|
|
150
|
+
---
|
|
151
|
+
|
|
152
|
+
## Overriding locations
|
|
153
|
+
|
|
154
|
+
All plotting and helper functions accept directories as keyword
|
|
155
|
+
arguments (`plot_dir`, `csv_dir`, `output_dir`). To write outputs into a
|
|
156
|
+
custom EWS workspace, pass explicit paths, for example:
|
|
157
|
+
|
|
158
|
+
```python
|
|
159
|
+
plot_priority_matrix(
|
|
160
|
+
results_df,
|
|
161
|
+
entity_name="Topic",
|
|
162
|
+
plot_dir="ews/results/plot",
|
|
163
|
+
csv_dir="ews/results/csv",
|
|
164
|
+
)
|
|
165
|
+
```
|
|
166
|
+
|
|
167
|
+
This keeps file naming consistent while letting each project choose
|
|
168
|
+
where artifacts live.
|
|
@@ -10,36 +10,32 @@ pip install priorityx
|
|
|
10
10
|
|
|
11
11
|
```python
|
|
12
12
|
import pandas as pd
|
|
13
|
-
|
|
14
|
-
from priorityx.viz.matrix import plot_priority_matrix
|
|
13
|
+
import priorityx as px
|
|
15
14
|
|
|
16
15
|
# load your data
|
|
17
16
|
df = pd.read_csv("your_data.csv")
|
|
18
17
|
df["date"] = pd.to_datetime(df["date"])
|
|
19
18
|
|
|
20
19
|
# fit priority matrix
|
|
21
|
-
results, stats = fit_priority_matrix(
|
|
20
|
+
results, stats = px.fit_priority_matrix(
|
|
22
21
|
df,
|
|
23
22
|
entity_col="service", # your entity column
|
|
24
23
|
timestamp_col="date", # your date column
|
|
25
24
|
temporal_granularity="quarterly",
|
|
26
|
-
min_observations=8
|
|
25
|
+
min_observations=8,
|
|
27
26
|
)
|
|
28
27
|
|
|
29
28
|
# visualize
|
|
30
|
-
plot_priority_matrix(results, entity_name="Service", save_plot=True)
|
|
29
|
+
px.plot_priority_matrix(results, entity_name="Service", save_plot=True)
|
|
31
30
|
```
|
|
32
31
|
|
|
33
32
|
## Full Workflow
|
|
34
33
|
|
|
35
34
|
```python
|
|
36
|
-
|
|
37
|
-
from priorityx.tracking.transitions import extract_transitions
|
|
38
|
-
from priorityx.tracking.drivers import extract_transition_drivers, display_transition_drivers
|
|
39
|
-
from priorityx.viz.timeline import plot_transition_timeline
|
|
35
|
+
import priorityx as px
|
|
40
36
|
|
|
41
37
|
# track movement over time
|
|
42
|
-
movement, meta = track_cumulative_movement(
|
|
38
|
+
movement, meta = px.track_cumulative_movement(
|
|
43
39
|
df,
|
|
44
40
|
entity_col="service",
|
|
45
41
|
timestamp_col="date",
|
|
@@ -47,15 +43,15 @@ movement, meta = track_cumulative_movement(
|
|
|
47
43
|
)
|
|
48
44
|
|
|
49
45
|
# detect transitions
|
|
50
|
-
transitions = extract_transitions(movement)
|
|
46
|
+
transitions = px.extract_transitions(movement)
|
|
51
47
|
|
|
52
48
|
# visualize transitions
|
|
53
|
-
plot_transition_timeline(transitions, entity_name="Service", save_plot=True)
|
|
49
|
+
px.plot_transition_timeline(transitions, entity_name="Service", save_plot=True)
|
|
54
50
|
|
|
55
51
|
# analyze drivers for specific transition
|
|
56
52
|
if not transitions.empty:
|
|
57
53
|
first_transition = transitions.iloc[0]
|
|
58
|
-
analysis = extract_transition_drivers(
|
|
54
|
+
analysis = px.extract_transition_drivers(
|
|
59
55
|
movement_df=movement,
|
|
60
56
|
df_raw=df,
|
|
61
57
|
entity_name=first_transition["entity"],
|
|
@@ -66,7 +62,7 @@ if not transitions.empty:
|
|
|
66
62
|
top_n_subcategories=5,
|
|
67
63
|
min_subcategory_delta=2
|
|
68
64
|
)
|
|
69
|
-
display_transition_drivers(analysis)
|
|
65
|
+
px.display_transition_drivers(analysis)
|
|
70
66
|
|
|
71
67
|
# subcategory columns (e.g., severity/product/topic) are auto-detected
|
|
72
68
|
# when not provided; pass subcategory_cols=[...] to override.
|
|
@@ -86,3 +82,11 @@ By default, outputs saved to:
|
|
|
86
82
|
- **`results/`** - All CSV data files (entity scores, transitions, movement tracking)
|
|
87
83
|
|
|
88
84
|
You can customize output directories using the `output_dir` parameter in visualization functions.
|
|
85
|
+
|
|
86
|
+
## Deterministic runs
|
|
87
|
+
|
|
88
|
+
Set `PRIORITYX_GLMM_SEED` (or call `set_glmm_random_seed()`) before running analyses to obtain repeatable GLMM estimates during debugging or CI checks:
|
|
89
|
+
|
|
90
|
+
```bash
|
|
91
|
+
PRIORITYX_GLMM_SEED=1234 python your_script.py
|
|
92
|
+
```
|
|
@@ -2,8 +2,7 @@
|
|
|
2
2
|
# software bug tracking example (data pulled from GitHub raw)
|
|
3
3
|
import pandas as pd
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
from priorityx.viz.matrix import plot_priority_matrix
|
|
5
|
+
import priorityx as px
|
|
7
6
|
|
|
8
7
|
RAW_DATA_URL = "https://raw.githubusercontent.com/okkymabruri/priorityx/main/examples/bugs/bugs.csv"
|
|
9
8
|
|
|
@@ -15,7 +14,7 @@ df["date"] = df["reported_date"]
|
|
|
15
14
|
temporal_granularity = "quarterly"
|
|
16
15
|
entity_name = "Component"
|
|
17
16
|
|
|
18
|
-
results, stats = fit_priority_matrix(
|
|
17
|
+
results, stats = px.fit_priority_matrix(
|
|
19
18
|
df,
|
|
20
19
|
entity_col="component",
|
|
21
20
|
timestamp_col="date",
|
|
@@ -28,7 +27,7 @@ print("Software Bug Priority Matrix:")
|
|
|
28
27
|
print(results[["entity", "Random_Intercept", "Random_Slope", "count", "quadrant"]])
|
|
29
28
|
|
|
30
29
|
# visualize
|
|
31
|
-
plot_priority_matrix(
|
|
30
|
+
px.plot_priority_matrix(
|
|
32
31
|
results,
|
|
33
32
|
entity_name=entity_name,
|
|
34
33
|
show_quadrant_labels=True,
|
|
@@ -3,24 +3,15 @@
|
|
|
3
3
|
|
|
4
4
|
import pandas as pd
|
|
5
5
|
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
from priorityx.core.glmm import fit_priority_matrix
|
|
9
|
-
from priorityx.tracking.movement import track_cumulative_movement
|
|
10
|
-
from priorityx.tracking.transitions import extract_transitions
|
|
11
|
-
from priorityx.tracking.drivers import (
|
|
12
|
-
extract_transition_drivers,
|
|
13
|
-
display_transition_drivers,
|
|
14
|
-
)
|
|
15
|
-
from priorityx.viz.matrix import plot_priority_matrix
|
|
16
|
-
from priorityx.viz.timeline import plot_transition_timeline
|
|
17
|
-
from priorityx.viz.trajectory import plot_entity_trajectories
|
|
6
|
+
import priorityx as px
|
|
18
7
|
from priorityx.utils.helpers import (
|
|
19
8
|
display_quadrant_summary,
|
|
20
9
|
display_transition_summary,
|
|
21
10
|
save_dataframe_to_csv,
|
|
22
11
|
)
|
|
23
12
|
|
|
13
|
+
RAW_DATA_URL = "https://raw.githubusercontent.com/okkymabruri/priorityx/main/examples/incidents/incidents.csv"
|
|
14
|
+
|
|
24
15
|
# load data from GitHub raw
|
|
25
16
|
df = pd.read_csv(RAW_DATA_URL, parse_dates=["date"])
|
|
26
17
|
print("Loaded incidents from GitHub raw URL")
|
|
@@ -34,7 +25,7 @@ print("PRIORITY MATRIX ANALYSIS")
|
|
|
34
25
|
|
|
35
26
|
temporal_granularity = "quarterly"
|
|
36
27
|
entity_name = "Service"
|
|
37
|
-
results, stats = fit_priority_matrix(
|
|
28
|
+
results, stats = px.fit_priority_matrix(
|
|
38
29
|
df,
|
|
39
30
|
entity_col="service",
|
|
40
31
|
timestamp_col="date",
|
|
@@ -49,7 +40,7 @@ print(results[["entity", "Random_Intercept", "Random_Slope", "count", "quadrant"
|
|
|
49
40
|
display_quadrant_summary(results, entity_name=entity_name, min_count=0)
|
|
50
41
|
|
|
51
42
|
# visualize
|
|
52
|
-
plot_priority_matrix(
|
|
43
|
+
px.plot_priority_matrix(
|
|
53
44
|
results,
|
|
54
45
|
entity_name=entity_name,
|
|
55
46
|
show_quadrant_labels=True,
|
|
@@ -61,7 +52,7 @@ plot_priority_matrix(
|
|
|
61
52
|
print()
|
|
62
53
|
print("CUMULATIVE MOVEMENT TRACKING")
|
|
63
54
|
|
|
64
|
-
movement, meta = track_cumulative_movement(
|
|
55
|
+
movement, meta = px.track_cumulative_movement(
|
|
65
56
|
df,
|
|
66
57
|
entity_col="service",
|
|
67
58
|
timestamp_col="date",
|
|
@@ -84,7 +75,7 @@ movement_path = save_dataframe_to_csv(
|
|
|
84
75
|
print(f"Movement CSV saved: {movement_path}")
|
|
85
76
|
|
|
86
77
|
# visualize entity trajectories
|
|
87
|
-
plot_entity_trajectories(
|
|
78
|
+
px.plot_entity_trajectories(
|
|
88
79
|
movement,
|
|
89
80
|
entity_name=entity_name,
|
|
90
81
|
max_entities=5,
|
|
@@ -93,12 +84,12 @@ plot_entity_trajectories(
|
|
|
93
84
|
)
|
|
94
85
|
|
|
95
86
|
# detect transitions
|
|
96
|
-
transitions = extract_transitions(movement, focus_risk_increasing=True)
|
|
87
|
+
transitions = px.extract_transitions(movement, focus_risk_increasing=True)
|
|
97
88
|
|
|
98
89
|
print(f"\nDetected {len(transitions)} risk-increasing transitions")
|
|
99
90
|
display_transition_summary(transitions, entity_name=entity_name)
|
|
100
91
|
|
|
101
|
-
plot_transition_timeline(
|
|
92
|
+
px.plot_transition_timeline(
|
|
102
93
|
transitions,
|
|
103
94
|
entity_name=entity_name,
|
|
104
95
|
save_plot=True,
|
|
@@ -129,7 +120,7 @@ if len(critical_transitions) > 0:
|
|
|
129
120
|
)
|
|
130
121
|
|
|
131
122
|
if prev_quarter:
|
|
132
|
-
driver_analysis = extract_transition_drivers(
|
|
123
|
+
driver_analysis = px.extract_transition_drivers(
|
|
133
124
|
movement_df=movement,
|
|
134
125
|
df_raw=df,
|
|
135
126
|
entity_name=trans["entity"],
|
|
@@ -141,7 +132,7 @@ if len(critical_transitions) > 0:
|
|
|
141
132
|
min_subcategory_delta=2,
|
|
142
133
|
)
|
|
143
134
|
|
|
144
|
-
display_transition_drivers(driver_analysis)
|
|
135
|
+
px.display_transition_drivers(driver_analysis)
|
|
145
136
|
|
|
146
137
|
print()
|
|
147
138
|
print("Analysis complete. Check plot/ and results/ in the current working directory.")
|
|
@@ -4,11 +4,7 @@ from datetime import datetime, timedelta
|
|
|
4
4
|
|
|
5
5
|
import pandas as pd
|
|
6
6
|
|
|
7
|
-
|
|
8
|
-
from priorityx.tracking.movement import track_cumulative_movement
|
|
9
|
-
from priorityx.tracking.transitions import extract_transitions
|
|
10
|
-
from priorityx.viz.matrix import plot_priority_matrix
|
|
11
|
-
from priorityx.viz.timeline import plot_transition_timeline
|
|
7
|
+
import priorityx as px
|
|
12
8
|
from priorityx.utils.helpers import (
|
|
13
9
|
display_quadrant_summary,
|
|
14
10
|
display_transition_summary,
|
|
@@ -64,7 +60,7 @@ df = pd.DataFrame(data)
|
|
|
64
60
|
temporal_granularity = "quarterly"
|
|
65
61
|
entity_name = "Department"
|
|
66
62
|
|
|
67
|
-
results, stats = fit_priority_matrix(
|
|
63
|
+
results, stats = px.fit_priority_matrix(
|
|
68
64
|
df,
|
|
69
65
|
entity_col="department",
|
|
70
66
|
timestamp_col="date",
|
|
@@ -76,7 +72,7 @@ print(results[["entity", "Random_Intercept", "Random_Slope", "count", "quadrant"
|
|
|
76
72
|
|
|
77
73
|
display_quadrant_summary(results, entity_name=entity_name, min_count=0)
|
|
78
74
|
|
|
79
|
-
plot_priority_matrix(
|
|
75
|
+
px.plot_priority_matrix(
|
|
80
76
|
results,
|
|
81
77
|
entity_name=entity_name,
|
|
82
78
|
show_quadrant_labels=True,
|
|
@@ -84,7 +80,7 @@ plot_priority_matrix(
|
|
|
84
80
|
save_csv=True,
|
|
85
81
|
)
|
|
86
82
|
|
|
87
|
-
movement, meta = track_cumulative_movement(
|
|
83
|
+
movement, meta = px.track_cumulative_movement(
|
|
88
84
|
df,
|
|
89
85
|
entity_col="department",
|
|
90
86
|
timestamp_col="date",
|
|
@@ -100,12 +96,12 @@ movement_path = save_dataframe_to_csv(
|
|
|
100
96
|
temporal_granularity=temporal_granularity,
|
|
101
97
|
)
|
|
102
98
|
print(f"Movement CSV saved: {movement_path}")
|
|
103
|
-
transitions = extract_transitions(movement, focus_risk_increasing=True)
|
|
99
|
+
transitions = px.extract_transitions(movement, focus_risk_increasing=True)
|
|
104
100
|
|
|
105
101
|
print(f"\nDetected {len(transitions)} risk-increasing transitions")
|
|
106
102
|
display_transition_summary(transitions, entity_name=entity_name)
|
|
107
103
|
|
|
108
|
-
plot_transition_timeline(
|
|
104
|
+
px.plot_transition_timeline(
|
|
109
105
|
transitions,
|
|
110
106
|
entity_name=entity_name,
|
|
111
107
|
save_plot=True,
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
"""priorityx: Entity prioritization and escalation detection using GLMM statistical models.
|
|
2
|
+
|
|
3
|
+
The :mod:`priorityx.api` module exposes a small convenience facade so
|
|
4
|
+
users can write::
|
|
5
|
+
|
|
6
|
+
import priorityx as px
|
|
7
|
+
results, stats = px.fit_priority_matrix(...)
|
|
8
|
+
|
|
9
|
+
while more advanced workflows can continue to import from the
|
|
10
|
+
``core``, ``tracking`` and ``viz`` subpackages directly.
|
|
11
|
+
"""
|
|
12
|
+
|
|
13
|
+
from .api import ( # noqa: F401
|
|
14
|
+
display_transition_drivers,
|
|
15
|
+
extract_transition_drivers,
|
|
16
|
+
extract_transitions,
|
|
17
|
+
fit,
|
|
18
|
+
fit_priority_matrix,
|
|
19
|
+
load_or_track_movement,
|
|
20
|
+
plot_entity_trajectories,
|
|
21
|
+
plot_priority_matrix,
|
|
22
|
+
plot_transition_timeline,
|
|
23
|
+
set_glmm_random_seed,
|
|
24
|
+
track_cumulative_movement,
|
|
25
|
+
)
|
|
26
|
+
|
|
27
|
+
__version__ = "0.3.0"
|
|
28
|
+
|
|
29
|
+
__all__ = [
|
|
30
|
+
"__version__",
|
|
31
|
+
"fit_priority_matrix",
|
|
32
|
+
"fit",
|
|
33
|
+
"set_glmm_random_seed",
|
|
34
|
+
"track_cumulative_movement",
|
|
35
|
+
"load_or_track_movement",
|
|
36
|
+
"extract_transitions",
|
|
37
|
+
"extract_transition_drivers",
|
|
38
|
+
"display_transition_drivers",
|
|
39
|
+
"plot_priority_matrix",
|
|
40
|
+
"plot_transition_timeline",
|
|
41
|
+
"plot_entity_trajectories",
|
|
42
|
+
]
|
|
43
|
+
|