ert 16.0.9__py3-none-any.whl → 19.0.0rc2__py3-none-any.whl
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.
- _ert/events.py +19 -2
- _ert/forward_model_runner/client.py +6 -2
- _ert/forward_model_runner/fm_dispatch.py +9 -6
- _ert/forward_model_runner/reporting/event.py +1 -0
- _ert/forward_model_runner/runner.py +1 -2
- _ert/utils.py +12 -0
- ert/__main__.py +58 -38
- ert/analysis/_enif_update.py +8 -4
- ert/analysis/_es_update.py +19 -6
- ert/analysis/_update_commons.py +16 -6
- ert/base_model_context.py +1 -1
- ert/cli/main.py +17 -12
- ert/cli/monitor.py +7 -0
- ert/config/__init__.py +17 -6
- ert/config/_create_observation_dataframes.py +118 -21
- ert/config/_get_num_cpu.py +1 -1
- ert/config/_observations.py +91 -2
- ert/config/_read_summary.py +74 -328
- ert/config/design_matrix.py +62 -23
- ert/config/distribution.py +1 -1
- ert/config/ensemble_config.py +9 -17
- ert/config/ert_config.py +155 -58
- ert/config/everest_control.py +234 -0
- ert/config/{everest_constraints_config.py → everest_response.py} +27 -15
- ert/config/field.py +99 -90
- ert/config/forward_model_step.py +122 -17
- ert/config/gen_data_config.py +5 -10
- ert/config/gen_kw_config.py +11 -41
- ert/config/known_response_types.py +14 -0
- ert/config/parameter_config.py +1 -33
- ert/config/parsing/_option_dict.py +10 -2
- ert/config/parsing/config_errors.py +1 -1
- ert/config/parsing/config_keywords.py +2 -1
- ert/config/parsing/config_schema.py +23 -11
- ert/config/parsing/config_schema_deprecations.py +3 -3
- ert/config/parsing/config_schema_item.py +26 -11
- ert/config/parsing/context_values.py +3 -3
- ert/config/parsing/file_context_token.py +1 -1
- ert/config/parsing/observations_parser.py +6 -2
- ert/config/parsing/queue_system.py +9 -0
- ert/config/parsing/schema_item_type.py +1 -0
- ert/config/queue_config.py +42 -50
- ert/config/response_config.py +0 -8
- ert/config/rft_config.py +275 -0
- ert/config/summary_config.py +3 -8
- ert/config/surface_config.py +73 -26
- ert/config/workflow_fixtures.py +2 -1
- ert/config/workflow_job.py +135 -54
- ert/dark_storage/client/__init__.py +2 -2
- ert/dark_storage/client/_session.py +4 -4
- ert/dark_storage/client/client.py +2 -2
- ert/dark_storage/common.py +12 -3
- ert/dark_storage/compute/misfits.py +11 -7
- ert/dark_storage/endpoints/compute/misfits.py +6 -4
- ert/dark_storage/endpoints/ensembles.py +4 -0
- ert/dark_storage/endpoints/experiment_server.py +30 -24
- ert/dark_storage/endpoints/experiments.py +2 -2
- ert/dark_storage/endpoints/observations.py +8 -6
- ert/dark_storage/endpoints/parameters.py +4 -12
- ert/dark_storage/endpoints/responses.py +24 -5
- ert/dark_storage/json_schema/ensemble.py +3 -0
- ert/dark_storage/json_schema/experiment.py +1 -1
- ert/data/_measured_data.py +6 -5
- ert/ensemble_evaluator/__init__.py +8 -1
- ert/ensemble_evaluator/config.py +2 -1
- ert/ensemble_evaluator/evaluator.py +81 -29
- ert/ensemble_evaluator/event.py +6 -0
- ert/ensemble_evaluator/snapshot.py +3 -1
- ert/ensemble_evaluator/state.py +1 -0
- ert/field_utils/__init__.py +8 -0
- ert/field_utils/field_utils.py +228 -15
- ert/field_utils/grdecl_io.py +1 -1
- ert/field_utils/roff_io.py +1 -1
- ert/gui/__init__.py +5 -2
- ert/gui/ertnotifier.py +1 -1
- ert/gui/ertwidgets/__init__.py +23 -16
- ert/gui/ertwidgets/analysismoduleedit.py +2 -2
- ert/gui/ertwidgets/checklist.py +1 -1
- ert/gui/ertwidgets/closabledialog.py +2 -0
- ert/gui/ertwidgets/copyablelabel.py +2 -0
- ert/gui/ertwidgets/create_experiment_dialog.py +3 -1
- ert/gui/ertwidgets/ensembleselector.py +2 -2
- ert/gui/ertwidgets/listeditbox.py +2 -0
- ert/gui/ertwidgets/models/__init__.py +2 -0
- ert/gui/ertwidgets/models/activerealizationsmodel.py +5 -1
- ert/gui/ertwidgets/models/path_model.py +1 -1
- ert/gui/ertwidgets/models/targetensemblemodel.py +5 -1
- ert/gui/ertwidgets/models/text_model.py +4 -1
- ert/gui/ertwidgets/pathchooser.py +0 -3
- ert/gui/ertwidgets/searchbox.py +17 -4
- ert/gui/ertwidgets/stringbox.py +2 -0
- ert/gui/{suggestor → ertwidgets/suggestor}/_suggestor_message.py +13 -4
- ert/gui/{suggestor → ertwidgets/suggestor}/suggestor.py +63 -30
- ert/gui/main.py +41 -13
- ert/gui/main_window.py +3 -7
- ert/gui/model/fm_step_list.py +3 -0
- ert/gui/model/real_list.py +1 -0
- ert/gui/model/snapshot.py +1 -0
- ert/gui/simulation/combobox_with_description.py +3 -0
- ert/gui/simulation/ensemble_experiment_panel.py +8 -2
- ert/gui/simulation/ensemble_information_filter_panel.py +7 -2
- ert/gui/simulation/ensemble_smoother_panel.py +8 -2
- ert/gui/simulation/evaluate_ensemble_panel.py +17 -7
- ert/gui/simulation/experiment_panel.py +18 -6
- ert/gui/simulation/manual_update_panel.py +35 -10
- ert/gui/simulation/multiple_data_assimilation_panel.py +13 -9
- ert/gui/simulation/run_dialog.py +47 -20
- ert/gui/simulation/single_test_run_panel.py +6 -3
- ert/gui/simulation/view/progress_widget.py +2 -0
- ert/gui/simulation/view/realization.py +5 -1
- ert/gui/simulation/view/update.py +2 -0
- ert/gui/summarypanel.py +20 -1
- ert/gui/tools/event_viewer/panel.py +3 -4
- ert/gui/tools/event_viewer/tool.py +2 -0
- ert/gui/tools/load_results/load_results_panel.py +1 -1
- ert/gui/tools/load_results/load_results_tool.py +2 -0
- ert/gui/tools/manage_experiments/export_dialog.py +136 -0
- ert/gui/tools/manage_experiments/manage_experiments_panel.py +2 -0
- ert/gui/tools/manage_experiments/storage_info_widget.py +121 -16
- ert/gui/tools/manage_experiments/storage_widget.py +4 -3
- ert/gui/tools/plot/customize/color_chooser.py +5 -2
- ert/gui/tools/plot/customize/customize_plot_dialog.py +2 -0
- ert/gui/tools/plot/customize/default_customization_view.py +4 -0
- ert/gui/tools/plot/customize/limits_customization_view.py +3 -0
- ert/gui/tools/plot/customize/statistics_customization_view.py +3 -0
- ert/gui/tools/plot/customize/style_chooser.py +2 -0
- ert/gui/tools/plot/customize/style_customization_view.py +3 -0
- ert/gui/tools/plot/data_type_keys_widget.py +2 -0
- ert/gui/tools/plot/data_type_proxy_model.py +3 -0
- ert/gui/tools/plot/plot_api.py +50 -28
- ert/gui/tools/plot/plot_ensemble_selection_widget.py +17 -10
- ert/gui/tools/plot/plot_widget.py +15 -2
- ert/gui/tools/plot/plot_window.py +41 -19
- ert/gui/tools/plot/plottery/plot_config.py +2 -0
- ert/gui/tools/plot/plottery/plot_context.py +14 -0
- ert/gui/tools/plot/plottery/plots/__init__.py +2 -0
- ert/gui/tools/plot/plottery/plots/cesp.py +3 -1
- ert/gui/tools/plot/plottery/plots/distribution.py +6 -1
- ert/gui/tools/plot/plottery/plots/ensemble.py +13 -5
- ert/gui/tools/plot/plottery/plots/gaussian_kde.py +12 -2
- ert/gui/tools/plot/plottery/plots/histogram.py +3 -1
- ert/gui/tools/plot/plottery/plots/misfits.py +436 -0
- ert/gui/tools/plot/plottery/plots/observations.py +18 -4
- ert/gui/tools/plot/plottery/plots/statistics.py +62 -20
- ert/gui/tools/plot/plottery/plots/std_dev.py +3 -1
- ert/gui/tools/plot/widgets/clearable_line_edit.py +9 -0
- ert/gui/tools/plot/widgets/filter_popup.py +2 -0
- ert/gui/tools/plot/widgets/filterable_kw_list_model.py +3 -0
- ert/gui/tools/plugins/plugin.py +1 -1
- ert/gui/tools/plugins/plugins_tool.py +2 -0
- ert/gui/tools/plugins/process_job_dialog.py +3 -0
- ert/gui/tools/workflows/workflow_dialog.py +2 -0
- ert/gui/tools/workflows/workflows_tool.py +2 -0
- ert/libres_facade.py +5 -7
- ert/logging/__init__.py +4 -1
- ert/mode_definitions.py +2 -0
- ert/plugins/__init__.py +4 -6
- ert/plugins/hook_implementations/workflows/csv_export.py +2 -3
- ert/plugins/hook_implementations/workflows/gen_data_rft_export.py +10 -2
- ert/plugins/hook_specifications/__init__.py +0 -10
- ert/plugins/hook_specifications/jobs.py +0 -9
- ert/plugins/plugin_manager.py +53 -124
- ert/resources/forward_models/run_reservoirsimulator.py +8 -4
- ert/resources/forward_models/template_render.py +10 -10
- ert/resources/shell_scripts/delete_directory.py +2 -2
- ert/run_models/__init__.py +24 -6
- ert/run_models/_create_run_path.py +133 -38
- ert/run_models/ensemble_experiment.py +10 -4
- ert/run_models/ensemble_information_filter.py +8 -1
- ert/run_models/ensemble_smoother.py +9 -3
- ert/run_models/evaluate_ensemble.py +8 -6
- ert/run_models/event.py +7 -3
- ert/run_models/everest_run_model.py +337 -113
- ert/run_models/initial_ensemble_run_model.py +25 -24
- ert/run_models/manual_update.py +6 -3
- ert/run_models/manual_update_enif.py +37 -0
- ert/run_models/model_factory.py +78 -18
- ert/run_models/multiple_data_assimilation.py +22 -11
- ert/run_models/run_model.py +72 -73
- ert/run_models/single_test_run.py +7 -4
- ert/run_models/update_run_model.py +4 -2
- ert/runpaths.py +5 -6
- ert/sample_prior.py +9 -4
- ert/scheduler/__init__.py +10 -5
- ert/scheduler/driver.py +40 -0
- ert/scheduler/event.py +3 -1
- ert/scheduler/job.py +23 -13
- ert/scheduler/lsf_driver.py +15 -5
- ert/scheduler/openpbs_driver.py +10 -4
- ert/scheduler/scheduler.py +5 -0
- ert/scheduler/slurm_driver.py +20 -5
- ert/services/__init__.py +2 -2
- ert/services/_base_service.py +37 -20
- ert/services/_storage_main.py +20 -18
- ert/services/ert_server.py +317 -0
- ert/shared/_doc_utils/__init__.py +4 -2
- ert/shared/_doc_utils/ert_jobs.py +1 -4
- ert/shared/net_utils.py +43 -18
- ert/shared/storage/connection.py +3 -3
- ert/shared/version.py +3 -3
- ert/storage/__init__.py +14 -1
- ert/storage/local_ensemble.py +44 -13
- ert/storage/local_experiment.py +54 -34
- ert/storage/local_storage.py +90 -58
- ert/storage/migration/to10.py +3 -2
- ert/storage/migration/to11.py +9 -10
- ert/storage/migration/to12.py +19 -20
- ert/storage/migration/to13.py +28 -27
- ert/storage/migration/to14.py +3 -3
- ert/storage/migration/to15.py +25 -0
- ert/storage/migration/to16.py +38 -0
- ert/storage/migration/to17.py +42 -0
- ert/storage/migration/to18.py +11 -0
- ert/storage/migration/to19.py +34 -0
- ert/storage/migration/to20.py +23 -0
- ert/storage/migration/to21.py +25 -0
- ert/storage/migration/to6.py +3 -2
- ert/storage/migration/to7.py +12 -13
- ert/storage/migration/to8.py +9 -11
- ert/storage/migration/to9.py +5 -4
- ert/storage/realization_storage_state.py +7 -7
- ert/substitutions.py +12 -28
- ert/validation/active_range.py +7 -7
- ert/validation/ensemble_realizations_argument.py +4 -2
- ert/validation/rangestring.py +16 -16
- ert/workflow_runner.py +6 -3
- {ert-16.0.9.dist-info → ert-19.0.0rc2.dist-info}/METADATA +21 -15
- ert-19.0.0rc2.dist-info/RECORD +524 -0
- {ert-16.0.9.dist-info → ert-19.0.0rc2.dist-info}/WHEEL +1 -1
- everest/api/everest_data_api.py +14 -1
- everest/assets/everest_logo.svg +406 -0
- everest/bin/config_branch_script.py +30 -14
- everest/bin/everconfigdump_script.py +2 -10
- everest/bin/everest_script.py +53 -33
- everest/bin/everlint_script.py +3 -5
- everest/bin/kill_script.py +7 -5
- everest/bin/main.py +11 -24
- everest/bin/monitor_script.py +64 -35
- everest/bin/utils.py +58 -43
- everest/bin/visualization_script.py +23 -13
- everest/config/__init__.py +4 -1
- everest/config/control_config.py +81 -6
- everest/config/control_variable_config.py +4 -3
- everest/config/everest_config.py +102 -79
- everest/config/forward_model_config.py +5 -3
- everest/config/install_data_config.py +7 -5
- everest/config/install_job_config.py +45 -3
- everest/config/install_template_config.py +3 -3
- everest/config/optimization_config.py +19 -6
- everest/config/output_constraint_config.py +8 -2
- everest/config/server_config.py +6 -55
- everest/config/simulator_config.py +62 -17
- everest/config/utils.py +25 -105
- everest/config/validation_utils.py +34 -15
- everest/config_file_loader.py +30 -21
- everest/detached/__init__.py +0 -6
- everest/detached/client.py +7 -52
- everest/detached/everserver.py +19 -45
- everest/everest_storage.py +24 -40
- everest/gui/everest_client.py +2 -3
- everest/gui/main_window.py +2 -2
- everest/optimizer/everest2ropt.py +68 -42
- everest/optimizer/opt_model_transforms.py +15 -20
- everest/optimizer/utils.py +0 -29
- everest/plugins/hook_specs.py +0 -24
- everest/strings.py +1 -6
- everest/util/__init__.py +3 -1
- ert/config/everest_objective_config.py +0 -95
- ert/config/ext_param_config.py +0 -107
- ert/gui/tools/export/__init__.py +0 -3
- ert/gui/tools/export/export_panel.py +0 -83
- ert/gui/tools/export/export_tool.py +0 -67
- ert/gui/tools/export/exporter.py +0 -36
- ert/plugins/hook_specifications/ecl_config.py +0 -29
- ert/services/storage_service.py +0 -127
- ert/summary_key_type.py +0 -234
- ert-16.0.9.dist-info/RECORD +0 -521
- everest/bin/everexport_script.py +0 -53
- everest/config/sampler_config.py +0 -103
- everest/simulator/__init__.py +0 -88
- everest/simulator/everest_to_ert.py +0 -252
- /ert/gui/{suggestor → ertwidgets/suggestor}/__init__.py +0 -0
- /ert/gui/{suggestor → ertwidgets/suggestor}/_colors.py +0 -0
- {ert-16.0.9.dist-info → ert-19.0.0rc2.dist-info}/entry_points.txt +0 -0
- {ert-16.0.9.dist-info → ert-19.0.0rc2.dist-info}/licenses/COPYING +0 -0
- {ert-16.0.9.dist-info → ert-19.0.0rc2.dist-info}/top_level.txt +0 -0
ert/storage/migration/to13.py
CHANGED
|
@@ -16,37 +16,39 @@ info = (
|
|
|
16
16
|
def point_experiments_to_ensembles(path: Path) -> None:
|
|
17
17
|
experiment_to_ensemble: dict[str, list[str]] = {}
|
|
18
18
|
for ensemble in path.glob("ensembles/*"):
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
experiment_id = index_["experiment_id"]
|
|
19
|
+
index_ = json.loads((ensemble / "index.json").read_text(encoding="utf-8"))
|
|
20
|
+
ensemble_id = index_["id"]
|
|
21
|
+
experiment_id = index_["experiment_id"]
|
|
23
22
|
|
|
24
|
-
|
|
25
|
-
|
|
23
|
+
if experiment_id not in experiment_to_ensemble:
|
|
24
|
+
experiment_to_ensemble[experiment_id] = []
|
|
26
25
|
|
|
27
|
-
|
|
26
|
+
experiment_to_ensemble[experiment_id].append(ensemble_id)
|
|
28
27
|
|
|
29
28
|
for experiment_path in path.glob("experiments/*"):
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
29
|
+
old_json = json.loads(
|
|
30
|
+
(experiment_path / "index.json").read_text(encoding="utf-8")
|
|
31
|
+
)
|
|
32
|
+
exp_id = old_json["id"]
|
|
33
33
|
|
|
34
34
|
if exp_id not in experiment_to_ensemble:
|
|
35
|
-
|
|
36
|
-
json.
|
|
35
|
+
(experiment_path / "index.json").write_text(
|
|
36
|
+
json.dumps(
|
|
37
37
|
old_json | {"ensembles": []},
|
|
38
|
-
fout,
|
|
39
38
|
indent=2,
|
|
40
|
-
)
|
|
39
|
+
),
|
|
40
|
+
encoding="utf-8",
|
|
41
|
+
)
|
|
41
42
|
continue
|
|
42
43
|
|
|
43
|
-
|
|
44
|
-
json.
|
|
44
|
+
(experiment_path / "index.json").write_text(
|
|
45
|
+
json.dumps(
|
|
45
46
|
old_json
|
|
46
47
|
| {"ensembles": sorted(experiment_to_ensemble.get(exp_id, []))},
|
|
47
|
-
fout,
|
|
48
48
|
indent=2,
|
|
49
|
-
)
|
|
49
|
+
),
|
|
50
|
+
encoding="utf-8",
|
|
51
|
+
)
|
|
50
52
|
|
|
51
53
|
|
|
52
54
|
tfd_to_distributions = {
|
|
@@ -101,12 +103,12 @@ def migrate_genkw(path: Path) -> None:
|
|
|
101
103
|
ensembles = path.glob("ensembles/*")
|
|
102
104
|
|
|
103
105
|
experiment_id = None
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
experiment_id = exp_index["id"]
|
|
106
|
+
exp_index = json.loads((experiment / "index.json").read_text(encoding="utf-8"))
|
|
107
|
+
experiment_id = exp_index["id"]
|
|
107
108
|
|
|
108
|
-
|
|
109
|
-
|
|
109
|
+
parameters_json = json.loads(
|
|
110
|
+
(experiment / "parameter.json").read_text(encoding="utf-8")
|
|
111
|
+
)
|
|
110
112
|
|
|
111
113
|
new_parameter_configs = migrate_gen_kw_param(parameters_json)
|
|
112
114
|
Path(experiment / "parameter.json").write_text(
|
|
@@ -115,10 +117,9 @@ def migrate_genkw(path: Path) -> None:
|
|
|
115
117
|
|
|
116
118
|
# migrate parquet files
|
|
117
119
|
for ens in ensembles:
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
continue
|
|
120
|
+
ens_file = json.loads((ens / "index.json").read_text(encoding="utf-8"))
|
|
121
|
+
if ens_file["experiment_id"] != experiment_id:
|
|
122
|
+
continue
|
|
122
123
|
|
|
123
124
|
group_dfs = []
|
|
124
125
|
for param_config in parameters_json.values():
|
ert/storage/migration/to14.py
CHANGED
|
@@ -30,9 +30,9 @@ def migrate_field_param(parameters_json: dict[str, Any]) -> dict[str, Any]:
|
|
|
30
30
|
|
|
31
31
|
def migrate_fields(path: Path) -> None:
|
|
32
32
|
for experiment in path.glob("experiments/*"):
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
33
|
+
parameters_json = json.loads(
|
|
34
|
+
(experiment / "parameter.json").read_text(encoding="utf-8")
|
|
35
|
+
)
|
|
36
36
|
new_parameter_configs = migrate_field_param(parameters_json)
|
|
37
37
|
Path(experiment / "parameter.json").write_text(
|
|
38
38
|
json.dumps(new_parameter_configs, indent=2), encoding="utf-8"
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import json
|
|
2
|
+
import pathlib
|
|
3
|
+
from pathlib import Path
|
|
4
|
+
from typing import Any
|
|
5
|
+
|
|
6
|
+
info = "Add status field to experiment index.json files"
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
def add_experiment_status_to_index_json(index_json: dict[str, Any]) -> dict[str, Any]:
|
|
10
|
+
index_json["status"] = {"message": "", "status": "completed"}
|
|
11
|
+
return index_json
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
def migrate_index_json(path: Path) -> None:
|
|
15
|
+
for experiment in path.glob("experiments/*"):
|
|
16
|
+
index_path = experiment / "index.json"
|
|
17
|
+
index_data = json.loads(pathlib.Path(index_path).read_text(encoding="utf-8"))
|
|
18
|
+
pathlib.Path(index_path).write_text(
|
|
19
|
+
json.dumps(add_experiment_status_to_index_json(index_data), indent=2),
|
|
20
|
+
encoding="utf-8",
|
|
21
|
+
)
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
def migrate(path: Path) -> None:
|
|
25
|
+
migrate_index_json(path)
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import json
|
|
2
|
+
from pathlib import Path
|
|
3
|
+
from typing import Any
|
|
4
|
+
|
|
5
|
+
info = "Remove mask file from field config"
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
def migrate_field_param(parameters_json: dict[str, Any]) -> dict[str, Any]:
|
|
9
|
+
new_configs = {}
|
|
10
|
+
for param_config in parameters_json.values():
|
|
11
|
+
if param_config["type"] == "field":
|
|
12
|
+
del param_config["mask_file"]
|
|
13
|
+
|
|
14
|
+
new_configs[param_config["name"]] = param_config
|
|
15
|
+
return new_configs
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
def delete_mask_file(experiment: Path) -> None:
|
|
19
|
+
# delete grid mask file if it exists
|
|
20
|
+
grid_mask_file = experiment / "grid_mask.npy"
|
|
21
|
+
if grid_mask_file.exists():
|
|
22
|
+
grid_mask_file.unlink()
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
def migrate_fields(experiment: Path) -> None:
|
|
26
|
+
with open(experiment / "parameter.json", encoding="utf-8") as fin:
|
|
27
|
+
parameters_json = json.load(fin)
|
|
28
|
+
|
|
29
|
+
new_parameter_configs = migrate_field_param(parameters_json)
|
|
30
|
+
Path(experiment / "parameter.json").write_text(
|
|
31
|
+
json.dumps(new_parameter_configs, indent=2), encoding="utf-8"
|
|
32
|
+
)
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
def migrate(path: Path) -> None:
|
|
36
|
+
for experiment in path.glob("experiments/*"):
|
|
37
|
+
migrate_fields(experiment)
|
|
38
|
+
delete_mask_file(experiment)
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import json
|
|
2
|
+
from pathlib import Path
|
|
3
|
+
from typing import Any
|
|
4
|
+
|
|
5
|
+
info = "Migrate realization error type from IntEnum to StrEnum"
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
def migrate_realization_errors_json_content(
|
|
9
|
+
error_json: dict[str, Any],
|
|
10
|
+
) -> dict[str, Any]:
|
|
11
|
+
int_to_str = {
|
|
12
|
+
1: "undefined",
|
|
13
|
+
2: "parameters_loaded",
|
|
14
|
+
4: "responses_loaded",
|
|
15
|
+
8: "failure_in_current",
|
|
16
|
+
16: "failure_in_parent",
|
|
17
|
+
# To cover cases who ran with storage version 16
|
|
18
|
+
# and StrEnum _RealizationStorageState
|
|
19
|
+
"undefined": "undefined",
|
|
20
|
+
"parameters_loaded": "parameters_loaded",
|
|
21
|
+
"responses_loaded": "responses_loaded",
|
|
22
|
+
"failure_in_current": "failure_in_current",
|
|
23
|
+
"failure_in_parent": "failure_in_parent",
|
|
24
|
+
}
|
|
25
|
+
return error_json | {"type": int_to_str[error_json["type"]]}
|
|
26
|
+
|
|
27
|
+
|
|
28
|
+
def migrate_realization_errors(path: Path) -> None:
|
|
29
|
+
for realization_error in path.glob("ensembles/*/realization-*/error.json"):
|
|
30
|
+
old_error_json_content = json.loads(
|
|
31
|
+
realization_error.read_text(encoding="utf-8")
|
|
32
|
+
)
|
|
33
|
+
realization_error.write_text(
|
|
34
|
+
json.dumps(
|
|
35
|
+
migrate_realization_errors_json_content(old_error_json_content),
|
|
36
|
+
indent=2,
|
|
37
|
+
)
|
|
38
|
+
)
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
def migrate(path: Path) -> None:
|
|
42
|
+
migrate_realization_errors(path)
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import json
|
|
2
|
+
from pathlib import Path
|
|
3
|
+
from typing import Any
|
|
4
|
+
|
|
5
|
+
info = "Add dimensionality attribute to parameters"
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
def migrate_param(parameters_json: dict[str, Any]) -> dict[str, Any]:
|
|
9
|
+
new_configs = {}
|
|
10
|
+
for param_config in parameters_json.values():
|
|
11
|
+
if param_config["type"] == "surface":
|
|
12
|
+
param_config["dimensionality"] = 2
|
|
13
|
+
elif param_config["type"] == "field":
|
|
14
|
+
param_config["dimensionality"] = 3
|
|
15
|
+
else:
|
|
16
|
+
param_config["dimensionality"] = 1
|
|
17
|
+
|
|
18
|
+
new_configs[param_config["name"]] = param_config
|
|
19
|
+
return new_configs
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
def migrate_parameters_for_experiment(experiment: Path) -> None:
|
|
23
|
+
with open(experiment / "parameter.json", encoding="utf-8") as fin:
|
|
24
|
+
parameters_json = json.load(fin)
|
|
25
|
+
|
|
26
|
+
new_parameter_configs = migrate_param(parameters_json)
|
|
27
|
+
Path(experiment / "parameter.json").write_text(
|
|
28
|
+
json.dumps(new_parameter_configs, indent=2), encoding="utf-8"
|
|
29
|
+
)
|
|
30
|
+
|
|
31
|
+
|
|
32
|
+
def migrate(path: Path) -> None:
|
|
33
|
+
for experiment in path.glob("experiments/*"):
|
|
34
|
+
migrate_parameters_for_experiment(experiment)
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import json
|
|
2
|
+
from pathlib import Path
|
|
3
|
+
from typing import Any
|
|
4
|
+
|
|
5
|
+
info = "Remove redundant .name attribute from responses."
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
def config_without_name_attr(config: dict[str, Any]) -> dict[str, Any]:
|
|
9
|
+
new_json = {**config}
|
|
10
|
+
new_json.pop("name", None)
|
|
11
|
+
|
|
12
|
+
return new_json
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
def migrate(path: Path) -> None:
|
|
16
|
+
for response_json_path in path.glob("experiments/*/responses.json"):
|
|
17
|
+
old_json = json.loads((response_json_path).read_text(encoding="utf-8"))
|
|
18
|
+
new_json = {
|
|
19
|
+
response_type: config_without_name_attr(config)
|
|
20
|
+
for response_type, config in old_json.items()
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
response_json_path.write_text(json.dumps(new_json, indent=2), encoding="utf-8")
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import json
|
|
2
|
+
from pathlib import Path
|
|
3
|
+
from typing import Any
|
|
4
|
+
|
|
5
|
+
info = "Remove refcase from summary response configs"
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
def config_without_refcase(summary_config: dict[str, Any]) -> dict[str, Any]:
|
|
9
|
+
new_json = {**summary_config}
|
|
10
|
+
new_json.pop("refcase", None)
|
|
11
|
+
|
|
12
|
+
return new_json
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
def migrate(path: Path) -> None:
|
|
16
|
+
for response_json_path in path.glob("experiments/*/responses.json"):
|
|
17
|
+
old_json = json.loads((response_json_path).read_text(encoding="utf-8"))
|
|
18
|
+
new_json = {
|
|
19
|
+
response_type: config_without_refcase(response_config)
|
|
20
|
+
if response_config["type"] == "summary"
|
|
21
|
+
else response_config
|
|
22
|
+
for response_type, response_config in old_json.items()
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
response_json_path.write_text(json.dumps(new_json, indent=2), encoding="utf-8")
|
ert/storage/migration/to6.py
CHANGED
|
@@ -6,8 +6,9 @@ info = "Rename and change transfer_function_definitions"
|
|
|
6
6
|
|
|
7
7
|
def migrate(path: Path) -> None:
|
|
8
8
|
for experiment in path.glob("experiments/*"):
|
|
9
|
-
|
|
10
|
-
|
|
9
|
+
parameters_json = json.loads(
|
|
10
|
+
(experiment / "parameter.json").read_text(encoding="utf-8")
|
|
11
|
+
)
|
|
11
12
|
|
|
12
13
|
for param in parameters_json.values():
|
|
13
14
|
if "transfer_function_definitions" in param:
|
ert/storage/migration/to7.py
CHANGED
|
@@ -9,8 +9,9 @@ info = "Standardize response configs"
|
|
|
9
9
|
|
|
10
10
|
def _migrate_response_configs(path: Path) -> None:
|
|
11
11
|
for experiment in path.glob("experiments/*"):
|
|
12
|
-
|
|
13
|
-
|
|
12
|
+
responses = json.loads(
|
|
13
|
+
(experiment / "responses.json").read_text(encoding="utf-8")
|
|
14
|
+
)
|
|
14
15
|
|
|
15
16
|
# If we for example do a .to2() migration
|
|
16
17
|
# this will implicitly upgrade it to v7 since
|
|
@@ -58,8 +59,9 @@ def _migrate_response_configs(path: Path) -> None:
|
|
|
58
59
|
}
|
|
59
60
|
)
|
|
60
61
|
|
|
61
|
-
|
|
62
|
-
json.
|
|
62
|
+
(experiment / "responses.json").write_text(
|
|
63
|
+
json.dumps(migrated), encoding="utf-8"
|
|
64
|
+
)
|
|
63
65
|
|
|
64
66
|
|
|
65
67
|
def _ensure_coord_order(
|
|
@@ -83,13 +85,11 @@ def _migrate_response_datasets(path: Path) -> None:
|
|
|
83
85
|
ensembles = path.glob("ensembles/*")
|
|
84
86
|
|
|
85
87
|
experiment_id = None
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
experiment_id = exp_index["id"]
|
|
88
|
+
exp_index = json.loads((experiment / "index.json").read_text(encoding="utf-8"))
|
|
89
|
+
experiment_id = exp_index["id"]
|
|
89
90
|
|
|
90
91
|
responses_file = experiment / "responses.json"
|
|
91
|
-
|
|
92
|
-
responses_obj = json.load(f)
|
|
92
|
+
responses_obj = json.loads(responses_file.read_text(encoding="utf-8"))
|
|
93
93
|
|
|
94
94
|
assert responses_obj is not None, (
|
|
95
95
|
f"Failed to load responses.json @ {responses_file}"
|
|
@@ -98,10 +98,9 @@ def _migrate_response_datasets(path: Path) -> None:
|
|
|
98
98
|
gendata_keys = responses_obj.get("gen_data", {}).get("keys", [])
|
|
99
99
|
|
|
100
100
|
for ens in ensembles:
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
continue
|
|
101
|
+
ens_file = json.loads((ens / "index.json").read_text(encoding="utf-8"))
|
|
102
|
+
if ens_file["experiment_id"] != experiment_id:
|
|
103
|
+
continue
|
|
105
104
|
|
|
106
105
|
real_dirs = [*ens.glob("realization-*")]
|
|
107
106
|
|
ert/storage/migration/to8.py
CHANGED
|
@@ -63,15 +63,13 @@ def _migrate_responses_from_netcdf_to_parquet(path: Path) -> None:
|
|
|
63
63
|
ensembles = path.glob("ensembles/*")
|
|
64
64
|
|
|
65
65
|
experiment_id = None
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
experiment_id = exp_index["id"]
|
|
66
|
+
exp_index = json.loads((experiment / "index.json").read_text(encoding="utf-8"))
|
|
67
|
+
experiment_id = exp_index["id"]
|
|
69
68
|
|
|
70
69
|
for ens in ensembles:
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
continue
|
|
70
|
+
ens_file = json.loads((ens / "index.json").read_text(encoding="utf-8"))
|
|
71
|
+
if ens_file["experiment_id"] != experiment_id:
|
|
72
|
+
continue
|
|
75
73
|
|
|
76
74
|
real_dirs = [*ens.glob("realization-*")]
|
|
77
75
|
|
|
@@ -140,14 +138,14 @@ def _migrate_observations_to_grouped_parquet(path: Path) -> None:
|
|
|
140
138
|
|
|
141
139
|
for response_type in ["gen_data", "summary"]:
|
|
142
140
|
infos = [
|
|
143
|
-
|
|
141
|
+
info_ for info_ in obs_ds_infos if info_.response_type == response_type
|
|
144
142
|
]
|
|
145
143
|
if len(infos) > 0:
|
|
146
|
-
concatd_df = pl.concat([
|
|
144
|
+
concatd_df = pl.concat([info_.polars_df for info_ in infos])
|
|
147
145
|
concatd_df.write_parquet(experiment / "observations" / response_type)
|
|
148
146
|
|
|
149
|
-
for
|
|
150
|
-
os.remove(
|
|
147
|
+
for info_ in infos:
|
|
148
|
+
os.remove(info_.original_ds_path)
|
|
151
149
|
|
|
152
150
|
|
|
153
151
|
def migrate(path: Path) -> None:
|
ert/storage/migration/to9.py
CHANGED
|
@@ -39,10 +39,11 @@ def migrate(path: Path) -> None:
|
|
|
39
39
|
if not config.get("has_finalized_keys"):
|
|
40
40
|
# Read a sample response and write the keys
|
|
41
41
|
for ens in ensembles:
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
42
|
+
ens_file = json.loads(
|
|
43
|
+
(ens / "index.json").read_text(encoding="utf-8")
|
|
44
|
+
)
|
|
45
|
+
if ens_file["experiment_id"] != experiment_id:
|
|
46
|
+
continue
|
|
46
47
|
|
|
47
48
|
real_dirs = [*ens.glob("realization-*")]
|
|
48
49
|
|
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
from enum import
|
|
1
|
+
from enum import StrEnum, auto
|
|
2
2
|
|
|
3
3
|
|
|
4
|
-
class RealizationStorageState(
|
|
5
|
-
UNDEFINED =
|
|
6
|
-
PARAMETERS_LOADED =
|
|
7
|
-
RESPONSES_LOADED =
|
|
8
|
-
FAILURE_IN_CURRENT =
|
|
9
|
-
FAILURE_IN_PARENT =
|
|
4
|
+
class RealizationStorageState(StrEnum):
|
|
5
|
+
UNDEFINED = auto()
|
|
6
|
+
PARAMETERS_LOADED = auto()
|
|
7
|
+
RESPONSES_LOADED = auto()
|
|
8
|
+
FAILURE_IN_CURRENT = auto()
|
|
9
|
+
FAILURE_IN_PARENT = auto()
|
ert/substitutions.py
CHANGED
|
@@ -4,6 +4,7 @@ import logging
|
|
|
4
4
|
import re
|
|
5
5
|
from collections import UserDict
|
|
6
6
|
from collections.abc import Mapping
|
|
7
|
+
from typing import Self
|
|
7
8
|
|
|
8
9
|
logger = logging.getLogger(__name__)
|
|
9
10
|
_PATTERN = re.compile(r"<[^<>]+>")
|
|
@@ -25,44 +26,27 @@ class Substitutions(UserDict[str, str]):
|
|
|
25
26
|
"""
|
|
26
27
|
return _substitute(self, to_substitute, context, max_iterations, warn_max_iter)
|
|
27
28
|
|
|
28
|
-
|
|
29
|
-
def substitute_parameters(
|
|
30
|
-
to_substitute: str, parameter_values: Mapping[str, Mapping[str, str | float]]
|
|
31
|
-
) -> str:
|
|
32
|
-
"""Applies the substitution '<param_name>' to parameter value
|
|
33
|
-
Args:
|
|
34
|
-
parameter_values: Mapping from parameter name to parameter value
|
|
35
|
-
to_substitute: string to substitute magic strings in
|
|
36
|
-
Returns:
|
|
37
|
-
substituted string
|
|
38
|
-
"""
|
|
39
|
-
for values in parameter_values.values():
|
|
40
|
-
for param_name, value in values.items():
|
|
41
|
-
if isinstance(value, (int, float)):
|
|
42
|
-
formatted_value = f"{value:.6g}"
|
|
43
|
-
else:
|
|
44
|
-
formatted_value = str(value)
|
|
45
|
-
to_substitute = to_substitute.replace(
|
|
46
|
-
f"<{param_name}>", formatted_value
|
|
47
|
-
)
|
|
48
|
-
return to_substitute
|
|
49
|
-
|
|
50
|
-
def substitute_real_iter(
|
|
51
|
-
self, to_substitute: str, realization: int, iteration: int
|
|
52
|
-
) -> str:
|
|
29
|
+
def real_iter_substituter(self, realization: int, iteration: int) -> Self:
|
|
53
30
|
extra_data = {
|
|
54
31
|
"<IENS>": str(realization),
|
|
55
32
|
"<ITER>": str(iteration),
|
|
56
33
|
}
|
|
57
34
|
|
|
58
|
-
model_id_key = f"<
|
|
35
|
+
model_id_key = f"<REALIZATION_ID_{realization}_{iteration}>"
|
|
59
36
|
if model_id_key in self:
|
|
60
|
-
extra_data["<
|
|
37
|
+
extra_data["<REALIZATION_ID>"] = self[model_id_key]
|
|
61
38
|
sim_id_key = f"<SIM_DIR_{realization}_{iteration}>"
|
|
62
39
|
if sim_id_key in self:
|
|
63
40
|
extra_data["<SIM_DIR>"] = self[sim_id_key]
|
|
64
41
|
|
|
65
|
-
return
|
|
42
|
+
return type(self)({**self, **extra_data})
|
|
43
|
+
|
|
44
|
+
def substitute_real_iter(
|
|
45
|
+
self, to_substitute: str, realization: int, iteration: int
|
|
46
|
+
) -> str:
|
|
47
|
+
return self.real_iter_substituter(realization, iteration).substitute(
|
|
48
|
+
to_substitute
|
|
49
|
+
)
|
|
66
50
|
|
|
67
51
|
def _concise_representation(self) -> str:
|
|
68
52
|
return (
|
ert/validation/active_range.py
CHANGED
|
@@ -47,19 +47,19 @@ class ActiveRange:
|
|
|
47
47
|
raise ValueError(
|
|
48
48
|
f"Only digits, commas, dashes and spaces are allowed, got {rangestring}"
|
|
49
49
|
)
|
|
50
|
-
for
|
|
51
|
-
if "-" in
|
|
52
|
-
if len(
|
|
53
|
-
raise ValueError(f"Invalid range specified, got {
|
|
54
|
-
realization_bounds =
|
|
50
|
+
for range_ in rangestring.split(","):
|
|
51
|
+
if "-" in range_:
|
|
52
|
+
if len(range_.split("-")) != 2:
|
|
53
|
+
raise ValueError(f"Invalid range specified, got {range_}")
|
|
54
|
+
realization_bounds = range_.split("-")
|
|
55
55
|
start = int(realization_bounds[0])
|
|
56
56
|
end = int(realization_bounds[1])
|
|
57
57
|
if end < start:
|
|
58
58
|
raise ValueError(
|
|
59
|
-
f"Invalid direction in range specified, got {
|
|
59
|
+
f"Invalid direction in range specified, got {range_}"
|
|
60
60
|
)
|
|
61
61
|
else:
|
|
62
|
-
int(
|
|
62
|
+
int(range_)
|
|
63
63
|
return rangestring
|
|
64
64
|
|
|
65
65
|
@classmethod
|
|
@@ -17,11 +17,13 @@ class EnsembleRealizationsArgument(RangeStringArgument):
|
|
|
17
17
|
def __init__(
|
|
18
18
|
self,
|
|
19
19
|
ensemble: Callable[[], Union["Ensemble", None]],
|
|
20
|
-
max_value: int | None,
|
|
21
20
|
required_realization_storage_states: Iterable["RealizationStorageState"],
|
|
22
21
|
**kwargs: bool,
|
|
23
22
|
) -> None:
|
|
24
|
-
|
|
23
|
+
ens = ensemble()
|
|
24
|
+
size = ens.ensemble_size if ens is not None else None
|
|
25
|
+
super().__init__(size, **kwargs)
|
|
26
|
+
|
|
25
27
|
self.__ensemble_getter = ensemble
|
|
26
28
|
self._required_realization_storage_states: Iterable[RealizationStorageState] = (
|
|
27
29
|
required_realization_storage_states
|
ert/validation/rangestring.py
CHANGED
|
@@ -66,11 +66,11 @@ def rangestring_to_mask(rangestring: str, length: int) -> list[bool]:
|
|
|
66
66
|
# An empty string means no active indecies. Note that an
|
|
67
67
|
# IndexRange-typed instance being None means the opposite
|
|
68
68
|
return mask
|
|
69
|
-
for
|
|
70
|
-
if "-" in
|
|
71
|
-
if len(
|
|
72
|
-
raise ValueError(f"Wrong range syntax {
|
|
73
|
-
start, end = map(int,
|
|
69
|
+
for range_ in rangestring.split(","):
|
|
70
|
+
if "-" in range_:
|
|
71
|
+
if len(range_.strip().split("-")) != 2:
|
|
72
|
+
raise ValueError(f"Wrong range syntax {range_}")
|
|
73
|
+
start, end = map(int, range_.strip().split("-"))
|
|
74
74
|
if end < start:
|
|
75
75
|
raise ValueError(f"Range {start}-{end} has invalid direction")
|
|
76
76
|
if end + 1 > length:
|
|
@@ -78,12 +78,12 @@ def rangestring_to_mask(rangestring: str, length: int) -> list[bool]:
|
|
|
78
78
|
f"Range endpoint {end} is beyond the mask length {length}"
|
|
79
79
|
)
|
|
80
80
|
mask[start : end + 1] = [True] * (end + 1 - start)
|
|
81
|
-
elif
|
|
82
|
-
if int(
|
|
81
|
+
elif range_:
|
|
82
|
+
if int(range_) + 1 > length:
|
|
83
83
|
raise ValueError(
|
|
84
|
-
f"Realization index {
|
|
84
|
+
f"Realization index {range_} is beyond the mask length {length}"
|
|
85
85
|
)
|
|
86
|
-
mask[int(
|
|
86
|
+
mask[int(range_)] = True
|
|
87
87
|
return mask
|
|
88
88
|
|
|
89
89
|
|
|
@@ -102,14 +102,14 @@ def rangestring_to_list(rangestring: str) -> list[int]:
|
|
|
102
102
|
result: set[int] = set()
|
|
103
103
|
if not rangestring:
|
|
104
104
|
return []
|
|
105
|
-
for
|
|
106
|
-
if "-" in
|
|
107
|
-
if len(
|
|
108
|
-
raise ValueError(f"Wrong range syntax {
|
|
109
|
-
start, end = map(int,
|
|
105
|
+
for range_ in rangestring.split(","):
|
|
106
|
+
if "-" in range_:
|
|
107
|
+
if len(range_.strip().split("-")) != 2:
|
|
108
|
+
raise ValueError(f"Wrong range syntax {range_}")
|
|
109
|
+
start, end = map(int, range_.strip().split("-"))
|
|
110
110
|
if end < start:
|
|
111
111
|
raise ValueError(f"Range {start}-{end} has invalid direction")
|
|
112
112
|
result.update(range(start, end + 1))
|
|
113
|
-
elif
|
|
114
|
-
result.add(int(
|
|
113
|
+
elif range_:
|
|
114
|
+
result.add(int(range_))
|
|
115
115
|
return list(result)
|
ert/workflow_runner.py
CHANGED
|
@@ -1,12 +1,14 @@
|
|
|
1
1
|
from __future__ import annotations
|
|
2
2
|
|
|
3
3
|
import logging
|
|
4
|
+
import types
|
|
4
5
|
from concurrent import futures
|
|
5
6
|
from concurrent.futures import Future
|
|
6
7
|
from typing import Any, Self
|
|
7
8
|
|
|
8
9
|
from ert import ErtScript
|
|
9
10
|
from ert.config import (
|
|
11
|
+
BaseErtScriptWorkflow,
|
|
10
12
|
ErtScriptWorkflow,
|
|
11
13
|
ExternalErtScript,
|
|
12
14
|
Workflow,
|
|
@@ -43,8 +45,9 @@ class WorkflowJobRunner:
|
|
|
43
45
|
f"{self.job.max_args} arguments, {len(arguments)} given."
|
|
44
46
|
)
|
|
45
47
|
|
|
46
|
-
if isinstance(self.job,
|
|
47
|
-
|
|
48
|
+
if isinstance(self.job, BaseErtScriptWorkflow):
|
|
49
|
+
ert_script_class = self.job.load_ert_script_class()
|
|
50
|
+
self.__script = ert_script_class()
|
|
48
51
|
# We let stop on fail either from class or config take precedence
|
|
49
52
|
self.stop_on_fail = self.job.stop_on_fail or self.__script.stop_on_fail
|
|
50
53
|
|
|
@@ -125,7 +128,7 @@ class WorkflowRunner:
|
|
|
125
128
|
self,
|
|
126
129
|
exc_type: type[BaseException] | None,
|
|
127
130
|
exc_value: BaseException | None,
|
|
128
|
-
traceback:
|
|
131
|
+
traceback: types.TracebackType | None,
|
|
129
132
|
) -> None:
|
|
130
133
|
self.wait()
|
|
131
134
|
|