Skip to content

Commit

Permalink
Merge pull request #595 from BDonnot/master
Browse files Browse the repository at this point in the history
Bump to version 1.10.1
  • Loading branch information
BDonnot authored Mar 15, 2024
2 parents be6acb2 + e18957b commit f2398c0
Show file tree
Hide file tree
Showing 15 changed files with 435 additions and 46 deletions.
28 changes: 28 additions & 0 deletions .circleci/config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,33 @@ jobs:
cd /tmp
grid2op.testinstall
legacy_lightsim:
executor: python38
resource_class: small
steps:
- checkout
- run:
command: |
apt-get update
apt-get install -y coinor-cbc
- run: python -m pip install virtualenv
- run: python -m virtualenv venv_test
- run:
command: |
source venv_test/bin/activate
python -m pip install -U pip setuptools wheel
python -m pip install -U lightsim2grid==0.5.3 gymnasium "numpy<1.22"
- run:
command: |
source venv_test/bin/activate
python -m pip install -e .
pip freeze
- run:
command: |
source venv_test/bin/activate
export _GRID2OP_FORCE_TEST=1
python -m unittest grid2op/tests/test_basic_env_ls.py
install39:
executor: python39
resource_class: small
Expand Down Expand Up @@ -313,6 +340,7 @@ workflows:
test:
jobs:
- test
- legacy_lightsim
install:
jobs:
- install38
Expand Down
8 changes: 8 additions & 0 deletions CHANGELOG.rst
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,14 @@ Change Log
- [???] "asynch" multienv
- [???] properly model interconnecting powerlines

[1.10.1] - 2024-03-xx
----------------------
- [FIXED] issue https://github.com/rte-france/Grid2Op/issues/593
- [FIXED] backward compatibility issues with "oldest" lightsim2grid versions
(now tested in basic settings)
- [ADDED] a "compact" way to store the data in the Runner
- [IMPROVED] the "`train_val_split`" functions, now more names (for the folders)
can be used

[1.10.0] - 2024-03-06
----------------------
Expand Down
2 changes: 1 addition & 1 deletion docs/conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@
author = 'Benjamin Donnot'

# The full version, including alpha/beta/rc tags
release = '1.10.0'
release = '1.10.1.dev0'
version = '1.10'


Expand Down
38 changes: 23 additions & 15 deletions grid2op/Backend/backend.py
Original file line number Diff line number Diff line change
Expand Up @@ -1844,8 +1844,9 @@ def get_action_to_set(self) -> "grid2op.Action.CompleteAction":
p_s, q_s, sh_v, bus_s = self.shunt_info()
dict_["shunt"] = {"shunt_bus": bus_s}
if (bus_s >= 1).sum():
p_s *= (self._sh_vnkv / sh_v) ** 2
q_s *= (self._sh_vnkv / sh_v) ** 2
sh_conn = bus_s > 0
p_s[sh_conn] *= (self._sh_vnkv[sh_conn] / sh_v[sh_conn]) ** 2
q_s[sh_conn] *= (self._sh_vnkv[sh_conn] / sh_v[sh_conn]) ** 2
p_s[bus_s == -1] = np.NaN
q_s[bus_s == -1] = np.NaN
dict_["shunt"]["shunt_p"] = p_s
Expand Down Expand Up @@ -1944,21 +1945,28 @@ def assert_grid_correct(self) -> None:
from grid2op.Action import CompleteAction
from grid2op.Action._backendAction import _BackendAction

if self._missing_two_busbars_support_info:
warnings.warn("The backend implementation you are using is probably too old to take advantage of the "
"new feature added in grid2op 1.10.0: the possibility "
"to have more than 2 busbars per substations (or not). "
"To silence this warning, you can modify the `load_grid` implementation "
"of your backend and either call:\n"
"- self.can_handle_more_than_2_busbar if the current implementation "
" can handle more than 2 busbsars OR\n"
"- self.cannot_handle_more_than_2_busbar if not."
"\nAnd of course, ideally, if the current implementation "
"of your backend cannot "
"handle more than 2 busbars per substation, then change it :-)\n"
"Your backend will behave as if it did not support it.")
if hasattr(self, "_missing_two_busbars_support_info"):
if self._missing_two_busbars_support_info:
warnings.warn("The backend implementation you are using is probably too old to take advantage of the "
"new feature added in grid2op 1.10.0: the possibility "
"to have more than 2 busbars per substations (or not). "
"To silence this warning, you can modify the `load_grid` implementation "
"of your backend and either call:\n"
"- self.can_handle_more_than_2_busbar if the current implementation "
" can handle more than 2 busbsars OR\n"
"- self.cannot_handle_more_than_2_busbar if not."
"\nAnd of course, ideally, if the current implementation "
"of your backend cannot "
"handle more than 2 busbars per substation, then change it :-)\n"
"Your backend will behave as if it did not support it.")
self._missing_two_busbars_support_info = False
self.n_busbar_per_sub = DEFAULT_N_BUSBAR_PER_SUB
else:
self._missing_two_busbars_support_info = False
self.n_busbar_per_sub = DEFAULT_N_BUSBAR_PER_SUB
warnings.warn("Your backend is missing the `_missing_two_busbars_support_info` "
"attribute. This is known issue in lightims2grid <= 0.7.5. Please "
"upgrade your backend. This will raise an error in the future.")

orig_type = type(self)
if orig_type.my_bk_act_class is None:
Expand Down
15 changes: 8 additions & 7 deletions grid2op/Environment/environment.py
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ class Environment(BaseEnv):
"""

REGEX_SPLIT = r"^[a-zA-Z0-9]*$"
REGEX_SPLIT = r"^[a-zA-Z0-9_\\.]*$"

def __init__(
self,
Expand Down Expand Up @@ -1362,21 +1362,22 @@ def train_val_split(
"""
# define all the locations
if re.match(self.REGEX_SPLIT, add_for_train) is None:
cls = type(self)
if re.match(cls.REGEX_SPLIT, add_for_train) is None:
raise EnvError(
f"The suffixes you can use for training data (add_for_train) "
f'should match the regex "{self.REGEX_SPLIT}"'
f'should match the regex "{cls.REGEX_SPLIT}"'
)
if re.match(self.REGEX_SPLIT, add_for_val) is None:
if re.match(cls.REGEX_SPLIT, add_for_val) is None:
raise EnvError(
f"The suffixes you can use for validation data (add_for_val)"
f'should match the regex "{self.REGEX_SPLIT}"'
f'should match the regex "{cls.REGEX_SPLIT}"'
)
if add_for_test is not None:
if re.match(self.REGEX_SPLIT, add_for_test) is None:
if re.match(cls.REGEX_SPLIT, add_for_test) is None:
raise EnvError(
f"The suffixes you can use for test data (add_for_test)"
f'should match the regex "{self.REGEX_SPLIT}"'
f'should match the regex "{cls.REGEX_SPLIT}"'
)

if add_for_test is None and test_scen_id is not None:
Expand Down
29 changes: 25 additions & 4 deletions grid2op/MakeEnv/MakeFromPath.py
Original file line number Diff line number Diff line change
Expand Up @@ -556,21 +556,22 @@ def make_from_dataset_path(
default_chronics_kwargs = {
"path": chronics_path_abs,
"chronicsClass": chronics_class_cfg,
# "gridvalueClass": grid_value_class_cfg,
}

dfkwargs_cfg = {} # in the config
if "data_feeding_kwargs" in config_data and config_data["data_feeding_kwargs"] is not None:
dfkwargs_cfg = config_data["data_feeding_kwargs"]
for el in dfkwargs_cfg:
default_chronics_kwargs[el] = dfkwargs_cfg[el]

data_feeding_kwargs = _get_default_aux(
data_feeding_kwargs_user_prov = _get_default_aux(
"data_feeding_kwargs",
kwargs,
defaultClassApp=dict,
defaultinstance=default_chronics_kwargs,
msg_error=ERR_MSG_KWARGS["data_feeding_kwargs"],
)
data_feeding_kwargs = data_feeding_kwargs_user_prov.copy()
for el in default_chronics_kwargs:
if el not in data_feeding_kwargs:
data_feeding_kwargs[el] = default_chronics_kwargs[el]
Expand All @@ -586,7 +587,9 @@ def make_from_dataset_path(
isclass=True,
)
if (
(chronics_class_used != ChangeNothing) and (chronics_class_used != FromNPY) and (chronics_class_used != FromChronix2grid)
((chronics_class_used != ChangeNothing) and
(chronics_class_used != FromNPY) and
(chronics_class_used != FromChronix2grid))
) and exc_chronics is not None:
raise EnvError(
f"Impossible to find the chronics for your environment. Please make sure to provide "
Expand All @@ -599,7 +602,25 @@ def make_from_dataset_path(
# parameters is not given in the "make" function but present in the config file
if "gridvalueClass" not in data_feeding_kwargs:
data_feeding_kwargs["gridvalueClass"] = grid_value_class_cfg



# code bellow is added to fix
# https://github.com/rte-france/Grid2Op/issues/593
import inspect
possible_params = inspect.signature(data_feeding_kwargs["gridvalueClass"].__init__).parameters
data_feeding_kwargs_res = data_feeding_kwargs.copy()
for el in data_feeding_kwargs:
if el == "gridvalueClass":
continue
if el == "chronicsClass":
continue
if el not in possible_params:
# if it's in the config but is not supported by the
# user, then we ignore it
# see https://github.com/rte-france/Grid2Op/issues/593
if el in dfkwargs_cfg and not el in data_feeding_kwargs_user_prov:
del data_feeding_kwargs_res[el]
data_feeding_kwargs = data_feeding_kwargs_res
# now build the chronics handler
data_feeding = _get_default_aux(
"data_feeding",
Expand Down
10 changes: 7 additions & 3 deletions grid2op/MakeEnv/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,15 @@
"change_local_dir",
"list_available_test_env",
"update_env",
# deprecated in v 0.8.0
"make_old",
]
try:
from grid2op.MakeEnv.MakeOld import make_old

# deprecated in v 0.8.0
__all__.append("make_old")
except ImportError:
pass

from grid2op.MakeEnv.MakeOld import make_old
from grid2op.MakeEnv.MakeFromPath import make_from_dataset_path
from grid2op.MakeEnv.Make import make
from grid2op.MakeEnv.UserUtils import (
Expand Down
22 changes: 21 additions & 1 deletion grid2op/Runner/runner.py
Original file line number Diff line number Diff line change
Expand Up @@ -615,12 +615,32 @@ def __init__(

self.__used = False

def _make_new_backend(self):
try:
res = self.backendClass(**self._backend_kwargs)
except TypeError:
# for backward compatibility, some backend might not
# handle full kwargs (that might be added later)
import inspect
possible_params = inspect.signature(self.backendClass.__init__).parameters
this_kwargs = {}
for el in self._backend_kwargs:
if el in possible_params:
this_kwargs[el] = self._backend_kwargs[el]
else:
warnings.warn("Runner: your backend does not support the kwargs "
f"`{el}={self._backend_kwargs[el]}`. This usually "
"means it is outdated. Please upgrade it.")
res = self.backendClass(**this_kwargs)
return res

def _new_env(self, chronics_handler, parameters) -> Tuple[BaseEnv, BaseAgent]:
# the same chronics_handler is used for all the environments.
# make sure to "reset" it properly
# (this is handled elsewhere in case of "multi chronics")
if not self.chronics_handler.chronicsClass.MULTI_CHRONICS:
self.chronics_handler.next_chronics()
backend = self._make_new_backend()
with warnings.catch_warnings():
warnings.filterwarnings("ignore")
res = self.envClass.init_obj_from_kwargs(
Expand All @@ -629,7 +649,7 @@ def _new_env(self, chronics_handler, parameters) -> Tuple[BaseEnv, BaseAgent]:
init_env_path=self.init_env_path,
init_grid_path=self.init_grid_path,
chronics_handler=chronics_handler,
backend=self.backendClass(**self._backend_kwargs),
backend=backend,
parameters=parameters,
name=self.name_env,
names_chronics_to_backend=self.names_chronics_to_backend,
Expand Down
2 changes: 1 addition & 1 deletion grid2op/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
Grid2Op
"""
__version__ = '1.10.0'
__version__ = '1.10.1.dev0'

__all__ = [
"Action",
Expand Down
23 changes: 12 additions & 11 deletions grid2op/tests/aaa_test_backend_interface.py
Original file line number Diff line number Diff line change
Expand Up @@ -1593,9 +1593,10 @@ def test_30_n_busbar_per_sub_ok(self):
"""
self.skip_if_needed()
backend = self.aux_make_backend(n_busbar=3)
n_busbar = 3
backend = self.aux_make_backend(n_busbar=n_busbar)
cls = type(backend)
if cls.n_busbar_per_sub != 3:
if cls.n_busbar_per_sub != n_busbar:
self.skipTest("Your backend does not support more than 2 busbars.")

res = backend.runpf(is_dc=False)
Expand All @@ -1604,11 +1605,11 @@ def test_30_n_busbar_per_sub_ok(self):

# line or
line_id = 0
busbar_id = 3
busbar_id = n_busbar
backend.reset(self.get_path(), self.get_casefile())
action = type(backend)._complete_action_class()
action = cls._complete_action_class()
action.update({"set_bus": {"lines_or_id": [(line_id, busbar_id)]}})
bk_act = type(backend).my_bk_act_class()
bk_act = cls.my_bk_act_class()
bk_act += action
backend.apply_action(bk_act)
res = backend.runpf(is_dc=False)
Expand All @@ -1620,11 +1621,11 @@ def test_30_n_busbar_per_sub_ok(self):

# line ex
line_id = 0
busbar_id = 3
busbar_id = n_busbar
backend.reset(self.get_path(), self.get_casefile())
action = type(backend)._complete_action_class()
action = cls._complete_action_class()
action.update({"set_bus": {"lines_ex_id": [(line_id, busbar_id)]}})
bk_act = type(backend).my_bk_act_class()
bk_act = cls.my_bk_act_class()
bk_act += action
backend.apply_action(bk_act)
res = backend.runpf(is_dc=False)
Expand All @@ -1636,7 +1637,7 @@ def test_30_n_busbar_per_sub_ok(self):

# load
backend.reset(self.get_path(), self.get_casefile())
busbar_id = 3
busbar_id = n_busbar
nb_el = cls.n_load
el_to_subid = cls.load_to_subid
el_nm = "load"
Expand All @@ -1647,7 +1648,7 @@ def test_30_n_busbar_per_sub_ok(self):

# generator
backend.reset(self.get_path(), self.get_casefile())
busbar_id = 3
busbar_id = n_busbar
nb_el = cls.n_gen
el_to_subid = cls.gen_to_subid
el_nm = "generator"
Expand All @@ -1659,7 +1660,7 @@ def test_30_n_busbar_per_sub_ok(self):
# storage
if cls.n_storage > 0:
backend.reset(self.get_path(), self.get_casefile())
busbar_id = 3
busbar_id = n_busbar
nb_el = cls.n_storage
el_to_subid = cls.storage_to_subid
el_nm = "storage"
Expand Down
1 change: 0 additions & 1 deletion grid2op/tests/test_MaskedEnvironment.py
Original file line number Diff line number Diff line change
Expand Up @@ -210,7 +210,6 @@ def test_gym_discrete(self):
act = 0
self._aux_run_envs(act, env_gym_in, env_gym_out)


def test_gym_multidiscrete(self):
"""test I can create the gym env with multi discrete act space"""
env_gym_in = GymEnv(self.env_in)
Expand Down
Loading

0 comments on commit f2398c0

Please sign in to comment.