plexosdb 1.4.1__tar.gz → 1.6.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.
- {plexosdb-1.4.1 → plexosdb-1.6.0}/PKG-INFO +48 -1
- {plexosdb-1.4.1 → plexosdb-1.6.0}/README.md +45 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/pyproject.toml +3 -10
- plexosdb-1.6.0/src/plexosdb/__init__.py +43 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/checks.py +14 -6
- plexosdb-1.6.0/src/plexosdb/config/master_10.0R2_btu.xml +199909 -0
- plexosdb-1.6.0/src/plexosdb/config/master_11.0R4_btu.xml +212844 -0
- plexosdb-1.6.0/src/plexosdb/config/master_12.0R3_btu.xml +219660 -0
- plexosdb-1.6.0/src/plexosdb/config/master_9.2R6_btu.xml +186158 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/db.py +454 -86
- plexosdb-1.6.0/src/plexosdb/db_solution.py +292 -0
- plexosdb-1.6.0/src/plexosdb/db_solution_helpers.py +614 -0
- plexosdb-1.6.0/src/plexosdb/db_solution_models.py +108 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/enums.py +28 -0
- plexosdb-1.6.0/src/plexosdb/solution_reader/__init__.py +56 -0
- plexosdb-1.6.0/src/plexosdb/solution_reader/archive.py +42 -0
- plexosdb-1.6.0/src/plexosdb/solution_reader/bin_decoder.py +166 -0
- plexosdb-1.6.0/src/plexosdb/solution_reader/display.py +177 -0
- plexosdb-1.6.0/src/plexosdb/solution_reader/materialize.py +567 -0
- plexosdb-1.6.0/src/plexosdb/solution_reader/solution.py +410 -0
- plexosdb-1.6.0/src/plexosdb/solution_reader/types.py +52 -0
- plexosdb-1.6.0/src/plexosdb/solution_reader/utils.py +33 -0
- plexosdb-1.6.0/src/plexosdb/solution_reader/xml_parser.py +98 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/utils.py +34 -1
- plexosdb-1.4.1/src/plexosdb/__init__.py +0 -23
- {plexosdb-1.4.1 → plexosdb-1.6.0}/LICENSE.txt +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/__main__.py +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/db_manager.py +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/exceptions.py +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/py.typed +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/schema.sql +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/sql/object_properties.sql +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/sql/object_query.sql +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/sql/property.sql +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/sql/property_query.sql +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/sql/simple_object_query.sql +0 -0
- {plexosdb-1.4.1 → plexosdb-1.6.0}/src/plexosdb/xml_handler.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.3
|
|
2
2
|
Name: plexosdb
|
|
3
|
-
Version: 1.
|
|
3
|
+
Version: 1.6.0
|
|
4
4
|
Summary: SQLite API for plexos XMLs
|
|
5
5
|
Keywords: PLEXOS,Database,SQLite
|
|
6
6
|
Author: Pedro Andres Sanchez Perez, Kodi Obika, mcllerena
|
|
@@ -33,6 +33,8 @@ Classifier: Topic :: Software Development :: Build Tools
|
|
|
33
33
|
Classifier: Topic :: Database
|
|
34
34
|
Classifier: Typing :: Typed
|
|
35
35
|
Requires-Dist: loguru
|
|
36
|
+
Requires-Dist: plexos2duckdb>=0.1.0b11
|
|
37
|
+
Requires-Dist: pre-commit>=4.6.0
|
|
36
38
|
Maintainer: Pedro Andres Sanchez Perez, Kodi Obika, mcllerena
|
|
37
39
|
Maintainer-email: Pedro Andres Sanchez Perez <psanchez@nrel.gov>, Kodi Obika <kodi.obika@nrel.gov>, mcllerena <mcllerena@users.noreply.github.com>
|
|
38
40
|
Requires-Python: >=3.11, <3.15
|
|
@@ -100,11 +102,56 @@ db.add_membership(
|
|
|
100
102
|
db.to_xml("modified_model.xml")
|
|
101
103
|
```
|
|
102
104
|
|
|
105
|
+
## Versioned Schema Initialization
|
|
106
|
+
|
|
107
|
+
When creating a brand-new database (not importing XML), you can preload the
|
|
108
|
+
matching PLEXOS master template by version:
|
|
109
|
+
|
|
110
|
+
```python
|
|
111
|
+
from plexosdb import PlexosDB
|
|
112
|
+
|
|
113
|
+
db = PlexosDB()
|
|
114
|
+
db.create_schema(version=10)
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
Supported versions: 9, 10, 11, 12.
|
|
118
|
+
|
|
119
|
+
Accepted inputs include integers, strings, and tuples. For example:
|
|
120
|
+
|
|
121
|
+
```python
|
|
122
|
+
db.create_schema(version="v11.0R4")
|
|
123
|
+
db.create_schema(version=(12, 0, 3))
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
## Read PLEXOS Solution ZIP Tables with pandas
|
|
127
|
+
|
|
128
|
+
```python
|
|
129
|
+
from plexosdb import PlexosSolution
|
|
130
|
+
import pandas as pd
|
|
131
|
+
|
|
132
|
+
PLEXOS_SOLUTION = "/path/to/solution.zip"
|
|
133
|
+
|
|
134
|
+
sol = PlexosSolution.from_zip(PLEXOS_SOLUTION)
|
|
135
|
+
sol.to_sqlite("output.sqlite", if_exists="replace")
|
|
136
|
+
|
|
137
|
+
table = "ST__Interval__Regions__Fixed_Load"
|
|
138
|
+
sol.materialize_table(table, schema="report")
|
|
139
|
+
df_table = pd.read_sql_query(f'SELECT * FROM report."{table}"', sol.connection)
|
|
140
|
+
```
|
|
141
|
+
|
|
142
|
+
This pattern is useful when you only need a few report/data tables from a large
|
|
143
|
+
solution ZIP, because it materializes tables on demand.
|
|
144
|
+
|
|
103
145
|
## Documentation
|
|
104
146
|
|
|
105
147
|
Full documentation is available at
|
|
106
148
|
[natlabrockies.github.io/plexosdb](https://natlabrockies.github.io/plexosdb/).
|
|
107
149
|
|
|
150
|
+
## Related Work
|
|
151
|
+
|
|
152
|
+
For related previous/current work on querying PLEXOS outputs with DuckDB, see
|
|
153
|
+
[plexos2duckdb](https://github.com/NatLabRockies/plexos2duckdb).
|
|
154
|
+
|
|
108
155
|
## Developer Setup
|
|
109
156
|
|
|
110
157
|
plexosdb uses [uv](https://docs.astral.sh/uv/) for dependency management.
|
|
@@ -56,11 +56,56 @@ db.add_membership(
|
|
|
56
56
|
db.to_xml("modified_model.xml")
|
|
57
57
|
```
|
|
58
58
|
|
|
59
|
+
## Versioned Schema Initialization
|
|
60
|
+
|
|
61
|
+
When creating a brand-new database (not importing XML), you can preload the
|
|
62
|
+
matching PLEXOS master template by version:
|
|
63
|
+
|
|
64
|
+
```python
|
|
65
|
+
from plexosdb import PlexosDB
|
|
66
|
+
|
|
67
|
+
db = PlexosDB()
|
|
68
|
+
db.create_schema(version=10)
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
Supported versions: 9, 10, 11, 12.
|
|
72
|
+
|
|
73
|
+
Accepted inputs include integers, strings, and tuples. For example:
|
|
74
|
+
|
|
75
|
+
```python
|
|
76
|
+
db.create_schema(version="v11.0R4")
|
|
77
|
+
db.create_schema(version=(12, 0, 3))
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
## Read PLEXOS Solution ZIP Tables with pandas
|
|
81
|
+
|
|
82
|
+
```python
|
|
83
|
+
from plexosdb import PlexosSolution
|
|
84
|
+
import pandas as pd
|
|
85
|
+
|
|
86
|
+
PLEXOS_SOLUTION = "/path/to/solution.zip"
|
|
87
|
+
|
|
88
|
+
sol = PlexosSolution.from_zip(PLEXOS_SOLUTION)
|
|
89
|
+
sol.to_sqlite("output.sqlite", if_exists="replace")
|
|
90
|
+
|
|
91
|
+
table = "ST__Interval__Regions__Fixed_Load"
|
|
92
|
+
sol.materialize_table(table, schema="report")
|
|
93
|
+
df_table = pd.read_sql_query(f'SELECT * FROM report."{table}"', sol.connection)
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
This pattern is useful when you only need a few report/data tables from a large
|
|
97
|
+
solution ZIP, because it materializes tables on demand.
|
|
98
|
+
|
|
59
99
|
## Documentation
|
|
60
100
|
|
|
61
101
|
Full documentation is available at
|
|
62
102
|
[natlabrockies.github.io/plexosdb](https://natlabrockies.github.io/plexosdb/).
|
|
63
103
|
|
|
104
|
+
## Related Work
|
|
105
|
+
|
|
106
|
+
For related previous/current work on querying PLEXOS outputs with DuckDB, see
|
|
107
|
+
[plexos2duckdb](https://github.com/NatLabRockies/plexos2duckdb).
|
|
108
|
+
|
|
64
109
|
## Developer Setup
|
|
65
110
|
|
|
66
111
|
plexosdb uses [uv](https://docs.astral.sh/uv/) for dependency management.
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[project]
|
|
2
2
|
name = "plexosdb"
|
|
3
|
-
version = "1.
|
|
3
|
+
version = "1.6.0"
|
|
4
4
|
readme = "README.md"
|
|
5
5
|
license = {file = "LICENSE.txt"}
|
|
6
6
|
keywords = ["PLEXOS", "Database", "SQLite"]
|
|
@@ -35,6 +35,8 @@ classifiers = [
|
|
|
35
35
|
]
|
|
36
36
|
dependencies = [
|
|
37
37
|
"loguru",
|
|
38
|
+
"plexos2duckdb>=0.1.0b11",
|
|
39
|
+
"pre-commit>=4.6.0",
|
|
38
40
|
]
|
|
39
41
|
|
|
40
42
|
[project.urls]
|
|
@@ -71,15 +73,6 @@ dev = [
|
|
|
71
73
|
"ruff>=0.11.5",
|
|
72
74
|
]
|
|
73
75
|
|
|
74
|
-
[tool.setuptools]
|
|
75
|
-
include-package-data = true
|
|
76
|
-
|
|
77
|
-
[tool.setuptools.package-data]
|
|
78
|
-
"*" = ["*.json", "*.csv", "*.xml", ".sql"]
|
|
79
|
-
|
|
80
|
-
[tool.setuptools.packages.find]
|
|
81
|
-
where = ["src"]
|
|
82
|
-
|
|
83
76
|
[tool.ty.src]
|
|
84
77
|
include = ["src/plexosdb"]
|
|
85
78
|
exclude = ["tests/"]
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
"""Entrypoint for the PlexosDB client providing its exports."""
|
|
2
|
+
|
|
3
|
+
from importlib.metadata import version
|
|
4
|
+
|
|
5
|
+
from loguru import logger
|
|
6
|
+
|
|
7
|
+
from .db import PlexosDB, PropertyRecord
|
|
8
|
+
from .db_manager import SQLiteManager
|
|
9
|
+
from .db_solution import PlexosSolution
|
|
10
|
+
from .db_solution_models import (
|
|
11
|
+
DuckDBResult,
|
|
12
|
+
DuckDBSchema,
|
|
13
|
+
DuckDBSolutionInfo,
|
|
14
|
+
IfExists,
|
|
15
|
+
ResultSchema,
|
|
16
|
+
ResultTable,
|
|
17
|
+
TableInfo,
|
|
18
|
+
)
|
|
19
|
+
from .enums import ClassEnum, CollectionEnum, PeriodEnum, PhaseEnum, TableTypeEnum
|
|
20
|
+
from .xml_handler import XMLHandler
|
|
21
|
+
|
|
22
|
+
__version__ = version("plexosdb")
|
|
23
|
+
|
|
24
|
+
logger.disable("r2x_core")
|
|
25
|
+
|
|
26
|
+
__all__ = (
|
|
27
|
+
"ClassEnum",
|
|
28
|
+
"CollectionEnum",
|
|
29
|
+
"DuckDBResult",
|
|
30
|
+
"DuckDBSchema",
|
|
31
|
+
"DuckDBSolutionInfo",
|
|
32
|
+
"IfExists",
|
|
33
|
+
"PeriodEnum",
|
|
34
|
+
"PhaseEnum",
|
|
35
|
+
"PlexosDB",
|
|
36
|
+
"PlexosSolution",
|
|
37
|
+
"PropertyRecord",
|
|
38
|
+
"ResultSchema",
|
|
39
|
+
"ResultTable",
|
|
40
|
+
"TableInfo",
|
|
41
|
+
"TableTypeEnum",
|
|
42
|
+
"XMLHandler",
|
|
43
|
+
)
|
|
@@ -60,13 +60,21 @@ def check_attribute_exists(
|
|
|
60
60
|
Returns
|
|
61
61
|
-------
|
|
62
62
|
bool
|
|
63
|
-
True if the
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
63
|
+
True if the object has an assigned value for the attribute.
|
|
64
|
+
"""
|
|
65
|
+
query = """
|
|
66
|
+
SELECT 1
|
|
67
|
+
FROM t_attribute_data AS data
|
|
68
|
+
JOIN t_object AS obj ON obj.object_id = data.object_id
|
|
69
|
+
JOIN t_attribute AS attr ON attr.attribute_id = data.attribute_id
|
|
70
|
+
JOIN t_class AS class ON class.class_id = obj.class_id
|
|
71
|
+
WHERE obj.name = ?
|
|
72
|
+
AND class.name = ?
|
|
73
|
+
AND attr.name = ?
|
|
74
|
+
AND attr.class_id = obj.class_id
|
|
75
|
+
LIMIT 1
|
|
68
76
|
"""
|
|
69
|
-
|
|
77
|
+
return bool(db._db.query(query, (object_name, object_class, attribute_name)))
|
|
70
78
|
|
|
71
79
|
|
|
72
80
|
def check_class_exists(db: PlexosDB, class_enum: ClassEnum) -> bool:
|