diff --git a/.github/workflows/ci-format.yml b/.github/workflows/ci-format.yml index 777ad8bf40..bd3a00df3b 100644 --- a/.github/workflows/ci-format.yml +++ b/.github/workflows/ci-format.yml @@ -100,7 +100,7 @@ jobs: pip install wheel==0.38.4 pip install .[camera_obs,doc,train,ray,envision,argoverse,opendrive,waymo] cd ${GITHUB_WORKSPACE}/docs - make html SPHINXOPTS="-W -T -E --keep-going -b spelling" + make html SPHINXOPTS="-W -T -E -n --keep-going -b spelling" - name: Check build output run: | cd $GITHUB_WORKSPACE diff --git a/Makefile b/Makefile index c742e8740c..7d06a01a9f 100644 --- a/Makefile +++ b/Makefile @@ -154,7 +154,7 @@ format: gen-header .PHONY: docs docs: - cd docs && make clean html + cd docs && make clean html SPHINXOPTS="-W -T -n --keep-going -b spelling" .PHONY: wheel wheel: docs diff --git a/docs/conf.py b/docs/conf.py index 8eb346dafb..35547463e4 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -107,6 +107,45 @@ # This pattern also affects html_static_path and html_extra_path. exclude_patterns = ["_build", "Thumbs.db", ".DS_Store"] +# -- Options for nit-pick (-n) ---------------------------------------------------- + +nitpick_ignore = { + ("py:class", "optional"), + ("py:class", "ellipsis"), + ("py:class", "function"), + # Most of these dynamic type ignores would go away in python>=3.10 + # See for more context: https:github.com/sphinx-doc/sphinx/issues/10090 + ("py:class", "T"), + ("py:class", "Score"), + ("py:class", "Done"), + ("py:class", "CostFuncs"), + ("py:class", "ActType"), + ("py:class", "ObsType"), + ("py:class", "smarts.env.gymnasium.wrappers.metric.utils.T"), +} +nitpick_ignore_regex = { + (r"py:.*", r"av2\..*"), + (r"py:.*", r"google\.protobuf\..*"), + (r"py:.*", r"grpc\..*"), + (r"py:.*", r"gym\..*"), + (r"py:.*", r"gymnasium\..*"), + (r"py:.*", r"logging\..*"), + (r"py:.*", r"multiprocessing\..*"), + (r"py:.*", r"np\..*"), + (r"py:.*", r"numpy\..*"), + (r"py:.*", r"opendrive2lanelet\..*"), + (r"py:.*", r"panda3d\..*"), + (r"py:.*", r"pathlib\..*"), + (r"py:.*", r"pybullet(_utils)?\..*"), + (r"py:.*", r"re\..*"), + (r"py:.*", r"shapely\..*"), + (r"py:.*", r"sumo(lib)?\..*"), + (r"py:.*", r"tornado\..*"), + (r"py:.*", r"traci\..*"), + (r"py:.*", r"typing(_extensions)?\..*"), + (r"py:.*", r"configparser\..*"), +} + # -- Options for spelling ---------------------------------------------------- spelling_exclude_patterns = ["ignored_*", "**/*_pb2*"] spelling_ignore_pypi_package_names = True diff --git a/docs/sim/obs_action_reward.rst b/docs/sim/obs_action_reward.rst index 156f3b2a87..24e0f1857d 100644 --- a/docs/sim/obs_action_reward.rst +++ b/docs/sim/obs_action_reward.rst @@ -100,5 +100,5 @@ An agent can be configured to emit any one of the following action types from :c .. tip:: Depending on the agent's policy, :attr:`~smarts.core.controllers.action_space_type.ActionSpaceType.ActuatorDynamic` action type might - allow the agent to learn faster than :attr:`~smarts.core.controllers.action_space_type.ActionSpaceType.Continous` action type because + allow the agent to learn faster than :attr:`~smarts.core.controllers.action_space_type.ActionSpaceType.Continuous` action type because learning to correct steering could be simpler than learning a mapping to all the absolute steering angle values. diff --git a/smarts/benchmark/__init__.py b/smarts/benchmark/__init__.py index 2199c5311a..9530f4660d 100644 --- a/smarts/benchmark/__init__.py +++ b/smarts/benchmark/__init__.py @@ -20,12 +20,14 @@ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. import importlib +import pathlib import subprocess import sys -from pathlib import Path from typing import Any, Dict, List, Optional -BENCHMARK_LISTING_FILE = Path(__file__).parent.absolute() / "benchmark_listing.yaml" +BENCHMARK_LISTING_FILE = ( + pathlib.Path(__file__).parent.absolute() / "benchmark_listing.yaml" +) def auto_install_requirements(benchmark_spec: Dict[str, Any]): @@ -71,7 +73,7 @@ def run_benchmark( benchmark_name: str, benchmark_version: Optional[float], agent_locator: str, - benchmark_listing: Path, + benchmark_listing: pathlib.Path, debug_log: bool = False, auto_install: bool = False, ): @@ -82,7 +84,7 @@ def run_benchmark( benchmark_name(str): The name of the benchmark to run. benchmark_version(float|None): The version of the benchmark. agent_locator(str): Locator string for the registered agent. - benchmark_listing(Path): A configuration file that lists benchmark metadata and must list + benchmark_listing(pathlib.Path): A configuration file that lists benchmark metadata and must list the target benchmark. debug_log: Debug to `stdout`. """ @@ -117,4 +119,4 @@ def list_benchmarks(benchmark_listing): """Lists details of the currently available benchmarks.""" from smarts.core.utils.resources import load_yaml_config_with_substitution - return load_yaml_config_with_substitution(Path(benchmark_listing)) + return load_yaml_config_with_substitution(pathlib.Path(benchmark_listing)) diff --git a/smarts/benchmark/entrypoints/benchmark_runner_v0.py b/smarts/benchmark/entrypoints/benchmark_runner_v0.py index 538275c910..bedd9e2d53 100644 --- a/smarts/benchmark/entrypoints/benchmark_runner_v0.py +++ b/smarts/benchmark/entrypoints/benchmark_runner_v0.py @@ -212,9 +212,9 @@ def benchmark_from_configs(benchmark_config, agent_locator, debug_log=False): """Runs a benchmark given the following. Args: - benchmark_config(file path): The file path to the benchmark configuration. - agent_locator(str): Locator string for the registered agent. - debug_log(bool): Whether the benchmark should log to `stdout`. + benchmark_config (str): The file path to the benchmark configuration. + agent_locator (str): Locator string for the registered agent. + debug_log (bool): Whether the benchmark should log to `stdout`. """ benchmark_args = load_config(benchmark_config) diff --git a/smarts/core/bezier_motion_planner.py b/smarts/core/bezier_motion_planner.py index 4ac043275b..ab4fe3be1d 100644 --- a/smarts/core/bezier_motion_planner.py +++ b/smarts/core/bezier_motion_planner.py @@ -38,14 +38,14 @@ def trajectory_batched(self, current_poses, target_poses_at_t, n, dt) -> np.ndar """Generate a batch of trajectories Args: - current_poses: np.array([[x, y, heading]]) - target_poses_at_t: np.array([[x, y, heading, seconds_into_future]] + current_poses: ``np.array([[x, y, heading]])`` + target_poses_at_t: ``np.array([[x, y, heading, seconds_into_future]]`` pose we would like to have this many seconds into the future n: number of trajectory points to return dt: time delta between trajectory points Returns: - Stacked np.array of the form: - np.array([[x], [y], [heading], [desired_speed]]) + A stacked ``np.array`` of the form + ``np.array([[x], [y], [heading], [desired_speed]])`` """ assert len(current_poses) == len(target_poses_at_t) # vectorized cubic bezier computation diff --git a/smarts/core/chassis.py b/smarts/core/chassis.py index da292d7447..14c613d3c4 100644 --- a/smarts/core/chassis.py +++ b/smarts/core/chassis.py @@ -143,7 +143,7 @@ def pose(self) -> Pose: @property def steering(self) -> float: - """The steering value of the chassis in radians [-math.pi:math.pi].""" + """The steering value of the chassis in radians [-math.pi, math.pi].""" raise NotImplementedError @property diff --git a/smarts/core/configuration.py b/smarts/core/configuration.py index ef781f8b90..7642b1c1a4 100644 --- a/smarts/core/configuration.py +++ b/smarts/core/configuration.py @@ -23,7 +23,7 @@ import configparser import functools import os -from pathlib import Path +import pathlib from typing import Any, Callable, Optional, Union _UNSET = object() @@ -49,7 +49,7 @@ class Config: """A configuration utility that handles configuration from file and environment variable. Args: - config_file (Union[str, Path]): The path to the configuration file. + config_file (Union[str, pathlib.Path]): The path to the configuration file. environment_prefix (str, optional): The prefix given to the environment variables. Defaults to "". Raises: @@ -57,7 +57,7 @@ class Config: """ def __init__( - self, config_file: Union[str, Path], environment_prefix: str = "" + self, config_file: Union[str, pathlib.Path], environment_prefix: str = "" ) -> None: self._config = configparser.ConfigParser( interpolation=configparser.ExtendedInterpolation() @@ -66,7 +66,7 @@ def __init__( self._environment_variable_format_string = self._environment_prefix + "_{}_{}" if isinstance(config_file, str): - config_file = Path(config_file) + config_file = pathlib.Path(config_file) config_file = config_file.resolve() if not config_file.is_file(): raise FileNotFoundError(f"Configuration file not found at {config_file}") diff --git a/smarts/core/road_map.py b/smarts/core/road_map.py index ad4be6505b..5e6d9dacb0 100644 --- a/smarts/core/road_map.py +++ b/smarts/core/road_map.py @@ -362,18 +362,28 @@ def lanes_in_same_direction(self) -> List[RoadMap.Lane]: @property def lane_to_left(self) -> Tuple[RoadMap.Lane, bool]: - """Note: left is defined as 90 degrees clockwise relative to the lane heading. - (I.e., positive `t` in the RefLine coordinate system.) - Second result is True if lane is in the same direction as this one - In junctions, diverging lanes should not be included.""" + """Get the parallel lane to the left side of the direction this current lane. + + .. note:: + + Left is defined as 90 degrees clockwise relative to the lane heading. + (I.e., positive `t` in the RefLine coordinate system.) + Second result is True if lane is in the same direction as this one + In junctions, diverging lanes should not be included. + """ raise NotImplementedError() @property def lane_to_right(self) -> Tuple[RoadMap.Lane, bool]: - """Note: right is defined as 90 degrees counter-clockwise relative to the lane heading. - (I.e., negative `t` in the RefLine coordinate system.) - Second result is True if lane is in the same direction as this one. - In junctions, diverging lanes should not be included.""" + """Get the parallel lane to the right side of the direction this current lane. + + .. note:: + + Right is defined as 90 degrees counter-clockwise relative to the lane heading. + (I.e., negative `t` in the RefLine coordinate system.) + Second result is True if lane is in the same direction as this one. + In junctions, diverging lanes should not be included. + """ raise NotImplementedError() @property diff --git a/smarts/core/scenario.py b/smarts/core/scenario.py index dc3d9d6903..997152fdbc 100644 --- a/smarts/core/scenario.py +++ b/smarts/core/scenario.py @@ -631,7 +631,7 @@ def create_dynamic_traffic_history_mission( positional_radius: The goal radius for the positional goal. Returns: - (positional_mission, traverse_mission): A positional mission that follows the initial + (smarts.core.plan.Mission, smarts.core.plan.Mission): A positional mission that follows the initial original vehicle's travel as well as a traverse style mission which is done when the vehicle leaves the map. """ diff --git a/smarts/core/smarts.py b/smarts/core/smarts.py index 94ec6b6532..07074f8ae1 100644 --- a/smarts/core/smarts.py +++ b/smarts/core/smarts.py @@ -98,7 +98,7 @@ class SMARTS(ProviderManager): Args: agent_interfaces (Dict[str, AgentInterface]): The interfaces providing SMARTS with the understanding of what features each agent needs. traffic_sims (Optional[List[TrafficProvider]], optional): An optional list of traffic simulators for providing non-agent traffic. Defaults to None. - envision (Optional[EnvisionClient], optional): An envision client for connecting to an envision visualization server. Defaults to None. + envision (Optional[envision.client.Client], optional): An envision client for connecting to an envision visualization server. Defaults to None. visdom (Union[bool, Any], optional): Deprecated. Use SMARTS_VISDOM_ENABLED. A visdom client for connecting to a visdom visualization server. fixed_timestep_sec (Optional[float], optional): The fixed timestep that will be default if time is not otherwise specified at step. Defaults to 0.1. reset_agents_only (bool, optional): When specified the simulation will continue use of the current scenario. Defaults to False. @@ -244,7 +244,7 @@ def step( Overrides the simulation step length. Progress simulation time by the given amount. Note the time_delta_since_last_step param is in (nominal) seconds. Returns: - Tuple[observations, rewards, dones, infos]: The simulation step return. + The simulation step return as (observations, rewards, dones, infos). """ if not self._is_setup: raise SMARTSNotSetupError("Must call reset() or setup() before stepping.") @@ -428,15 +428,19 @@ def reset( are no agents in the simulation. Args: - scenario(smarts.core.scenario.Scenario): The scenario to reset the simulation with. - start_time(float): + scenario (smarts.core.scenario.Scenario): The scenario to reset the simulation with. + start_time (float): The initial amount of simulation time to skip. This has implications on all time - dependent systems. NOTE: SMARTS simulates a step and then updates vehicle control. - If you want a vehicle to enter at exactly `0.3` with a step of `0.1` it means the - simulation should start at `start_time==0.2`. + dependent systems. + + .. note:: + + SMARTS simulates a step and then updates vehicle control. + If you want a vehicle to enter at exactly ``0.3`` with a step of ``0.1`` it means the + simulation should start at ``start_time==0.2``. Returns: - Agent observations. This observation is as follows: + Dict[str, Observation]. This observation is as follows... - If no agents: the initial simulation observation at `start_time` - If agents: the first step of the simulation with an agent observation """ diff --git a/smarts/core/trap_manager.py b/smarts/core/trap_manager.py index 8179e37342..4c9e71b938 100644 --- a/smarts/core/trap_manager.py +++ b/smarts/core/trap_manager.py @@ -116,14 +116,16 @@ def add_trap_for_agent( :param agent_id: The agent to associate to this trap. :type agent_id: str :param mission: The mission to assign to the agent and vehicle. - :type mission: class: Mission + :type mission: smarts.core.plan.Mission :param road_map: The road map to provide information to about the map. - :type road_map: class: RoadMap + :type road_map: RoadMap :param sim_time: The current simulator time. :type sim_time: float :param reject_expired: If traps should be ignored if their patience would already be expired on creation - :type reject_expired: Tuple[bool, bool] If the trap was added and if the trap is already expired. + :type reject_expired: bool + :return: If the trap was added and if the trap is already expired. + :rtype: Tuple[bool, bool] """ if mission is None: mission = Mission.random_endless_mission(road_map) diff --git a/smarts/core/utils/math.py b/smarts/core/utils/math.py index de2b339aee..b6abc3affb 100644 --- a/smarts/core/utils/math.py +++ b/smarts/core/utils/math.py @@ -436,7 +436,7 @@ def position_to_ego_frame(position, ego_position, ego_heading): ego_position: Ego vehicle [x,y,z] ego_heading: Ego vehicle heading in radians Returns: - new_pose: The pose [x,y,z] in egocentric view + list: The position [x,y,z] in egocentric view """ transform_matrix = _gen_ego_frame_matrix(ego_heading) ego_rel_position = np.asarray(position) - np.asarray(ego_position) @@ -453,7 +453,7 @@ def world_position_from_ego_frame(position, ego_world_position, ego_world_headin ego_world_position: Ego vehicle [x,y,z] ego_world_heading: Ego vehicle heading in radians Returns: - new_pose: The pose [x,y,z] in world frame + list: The position [x,y,z] in world frame """ transform_matrix = _gen_ego_frame_matrix(ego_world_heading) transform_matrix = np.linalg.inv(transform_matrix) diff --git a/smarts/env/gymnasium/driving_smarts_2022_env.py b/smarts/env/gymnasium/driving_smarts_2022_env.py index c47b4650d3..7063c26e34 100644 --- a/smarts/env/gymnasium/driving_smarts_2022_env.py +++ b/smarts/env/gymnasium/driving_smarts_2022_env.py @@ -69,7 +69,7 @@ def driving_smarts_2022_env( Action space for each agent is configured through its `AgentInterface`. The action space could be either of the following. - (i) :attr:`~smarts.core.controllers.ActionSpaceType.RelativeTargetPose` + (i) :attr:`~smarts.core.controllers.action_space_type.ActionSpaceType.RelativeTargetPose` +------------------------------------+-------------+-------+ | Action | Values | Units | @@ -81,7 +81,7 @@ def driving_smarts_2022_env( | Δheading | [-π, π] | rad | +------------------------------------+-------------+-------+ - (ii) :attr:`~smarts.core.controllers.ActionSpaceType.TargetPose` + (ii) :attr:`~smarts.core.controllers.action_space_type.ActionSpaceType.TargetPose` +------------------------------------+---------------+-------+ | Action | Values | Units | diff --git a/smarts/env/gymnasium/driving_smarts_2023_env.py b/smarts/env/gymnasium/driving_smarts_2023_env.py index 6dd2df511e..86cb84edbd 100644 --- a/smarts/env/gymnasium/driving_smarts_2023_env.py +++ b/smarts/env/gymnasium/driving_smarts_2023_env.py @@ -68,8 +68,8 @@ def driving_smarts_2023_env( a sample formatted observation data structure. Action space for each agent: - Action space for an ego can be either :attr:`~smarts.core.controllers.ActionSpaceType.Continuous` - or :attr:`~smarts.core.controllers.ActionSpaceType.RelativeTargetPose`. User should choose + Action space for an ego can be either :attr:`~smarts.core.controllers.action_space_type.ActionSpaceType.Continuous` + or :attr:`~smarts.core.controllers.action_space_type.ActionSpaceType.RelativeTargetPose`. User should choose one of the action spaces and specify the chosen action space through the ego's agent interface. Agent interface: diff --git a/smarts/env/gymnasium/hiway_env_v1.py b/smarts/env/gymnasium/hiway_env_v1.py index 764669b697..074d66dcfe 100644 --- a/smarts/env/gymnasium/hiway_env_v1.py +++ b/smarts/env/gymnasium/hiway_env_v1.py @@ -108,7 +108,7 @@ class HiWayEnvV1(gym.Env): all components of the simulation. May be None if time deltas are externally-driven. Defaults to None. seed (int, optional): Random number generator seed. Defaults to 42. - sumo_options (SumoOptions, Dict[str, any]): The configuration for the + sumo_options (SumoOptions, Dict[str, Any]): The configuration for the sumo instance. A dictionary with the fields can be used instead. See :class:`SumoOptions`. visualization_client_builder: A method that must must construct an @@ -117,14 +117,14 @@ class HiWayEnvV1(gym.Env): zoo_addrs (str, optional): List of (`ip`, `port`) tuples of zoo server, used to instantiate remote social agents. Defaults to None. - observation_options (ObservationOptions, string): Defines the options + observation_options (ObservationOptions, str): Defines the options for how the formatting matches the observation space. String version - can be used instead. See :class:`ObservationOptions`. Defaults to - :attr:`ObservationOptions.default`. - action_options (ActionOptions, string): Defines the options + can be used instead. See :class:`~smarts.env.utils.observation_conversion.ObservationOptions`. Defaults to + :attr:`~smarts.env.utils.observation_conversion.ObservationOptions.default`. + action_options (ActionOptions, str): Defines the options for how the formatting matches the action space. String version - can be used instead. See :class:`ActionOptions`. Defaults to - :attr:`ActionOptions.default`. + can be used instead. See :class:`~smarts.env.utils.action_conversion.ActionOptions`. Defaults to + :attr:`~smarts.env.utils.action_conversion.ActionOptions.default`. """ metadata = {"render_modes": ["human"]} @@ -244,25 +244,25 @@ def step( action (ActType): an action provided by the agent to update the environment state. Returns: - observation (dict): An element of the environment's :attr:`observation_space` as the - next observation due to the agent actions. This observation will change based on - the provided :attr:`agent_interfaces`. Check :attr:`observation_space` after - initialization. - reward (SupportsFloat): The reward as a result of taking the - action. - terminated (bool): Whether the agent reaches the terminal state (as defined under the MDP of the task) - which can be positive or negative. An example is reaching the goal state. If true, the user needs to call :meth:`reset`. - truncated (bool): Whether the truncation condition outside the scope of the MDP is satisfied. - Typically, this is a time-limit, but could also be used to indicate an agent physically going out of bounds. - Can be used to end the episode prematurely before a terminal state is reached. - If true, the user needs to call :meth:`reset`. - info (dict): Contains auxiliary diagnostic information (helpful for debugging, learning, and logging). - This might, for instance, contain: metrics that describe the agent's performance state, variables that are - hidden from observations, or individual reward terms that are combined to produce the total reward. + (dict, SupportsFloat, bool, bool, dict): + - observation. An element of the environment's :attr:`observation_space` as the + next observation due to the agent actions. This observation will change based on + the provided :attr:`agent_interfaces`. Check :attr:`observation_space` after + initialization. + - reward. The reward as a result of taking the action. + - terminated. Whether the agent reaches the terminal state (as defined under the MDP of the task) + which can be positive or negative. An example is reaching the goal state. If true, the user needs to call :meth:`reset`. + - truncated. Whether the truncation condition outside the scope of the MDP is satisfied. + Typically, this is a time-limit, but could also be used to indicate an agent physically going out of bounds. + Can be used to end the episode prematurely before a terminal state is reached. + If true, the user needs to call :meth:`reset`. + - info. Contains auxiliary diagnostic information (helpful for debugging, learning, and logging). + This might, for instance, contain: metrics that describe the agent's performance state, variables that are + hidden from observations, or individual reward terms that are combined to produce the total reward. """ assert isinstance(action, dict) and all( isinstance(key, str) for key in action.keys() - ), "Expected Dict[str, any]" + ), "Expected Dict[str, Any]" formatted_action = self._action_formatter.format(action) observations, rewards, dones, extras = self._smarts.step(formatted_action) @@ -322,21 +322,21 @@ def reset( Therefore, :meth:`reset` should (in the typical use case) be called with a seed right after initialization and then never again. Args: - seed (optional int): The seed that is used to initialize the environment's PRNG (`np_random`). + seed (int, optional): The seed that is used to initialize the environment's PRNG (`np_random`). If the environment does not already have a PRNG and ``seed=None`` (the default option) is passed, a seed will be chosen from some source of entropy (e.g. timestamp or `/dev/urandom`). However, if the environment already has a PRNG and ``seed=None`` is passed, the PRNG will *not* be reset. If you pass an integer, the PRNG will be reset even if it already exists. Usually, you want to pass an integer *right after the environment has been initialized and then never again*. - options (optional dict): Additional information to specify how the environment is reset (optional, + options (dict, optional): Additional information to specify how the environment is reset (optional, depending on the specific environment). Forwards to :meth:`~smarts.core.smarts.SMARTS.reset`. - "scenario" (:class:`~smarts.sstudio.types.scenario.Scenario`): An explicit scenario to reset to. The default is a scenario from the scenario iter. - "start_time" (float): Forwards the start time of the current scenario. The default is 0. Returns: - observation (dict): Observation of the initial state. This will be an element of :attr:`observation_space` + dict: observation. Observation of the initial state. This will be an element of :attr:`observation_space` and is analogous to the observation returned by :meth:`step`. - info (dict): This dictionary contains auxiliary information complementing ``observation``. It should be analogous to + dict: info. This dictionary contains auxiliary information complementing ``observation``. It should be analogous to the ``info`` returned by :meth:`step`. """ super().reset(seed=seed, options=options) @@ -424,10 +424,10 @@ def unwrapped(self) -> gym.Env[ObsType, ActType]: @property def np_random(self) -> np.random.Generator: - """Returns the environment's internal :attr:`_np_random` that if not set will initialize with a random seed. + """Returns the environment's internal random number generator that if not set will initialize with a random seed. Returns: - Instances of `np.random.Generator`. + The internal instance of :class:`np.random.Generator`. """ return super().np_random diff --git a/smarts/env/gymnasium/platoon_env.py b/smarts/env/gymnasium/platoon_env.py index 0d231bba19..ff8e6662f5 100644 --- a/smarts/env/gymnasium/platoon_env.py +++ b/smarts/env/gymnasium/platoon_env.py @@ -73,8 +73,8 @@ def platoon_env( a sample formatted observation data structure. Action space for each agent: - Action space for an ego can be either :attr:`~smarts.core.controllers.ActionSpaceType.Continuous` - or :attr:`~smarts.core.controllers.ActionSpaceType.RelativeTargetPose`. User should choose + Action space for an ego can be either :attr:`~smarts.core.controllers.action_space_type.ActionSpaceType.Continuous` + or :attr:`~smarts.core.controllers.action_space_type.ActionSpaceType.RelativeTargetPose`. User should choose one of the action spaces and specify the chosen action space through the ego's agent interface. Agent interface: diff --git a/smarts/env/gymnasium/wrappers/api_reversion.py b/smarts/env/gymnasium/wrappers/api_reversion.py index 1fd83fc2e6..110ccfbc0a 100644 --- a/smarts/env/gymnasium/wrappers/api_reversion.py +++ b/smarts/env/gymnasium/wrappers/api_reversion.py @@ -25,18 +25,18 @@ class Api021Reversion(gym.Wrapper): - """This wrapper reverts the API of a gym/gymnasium environment to v0.21 of gym.""" + """This wrapper reverts the API of a gym|gymnasium environment to v0.21 of gym.""" def step(self, action) -> Tuple[Dict, SupportsFloat, bool, Dict[str, Any]]: - """Converts :meth:`step` return from `obs, reward, term, trunc, info` to `obs, reward, done, info`.""" + """Converts :meth:`step` return from ``obs, reward, term, trunc, info`` to ``obs, reward, done, info``.""" obs, reward, terminated, _, info = super().step(action) return obs, reward, terminated, info def reset(self, **kwargs) -> Dict[str, Tuple[Any]]: - """Converts :meth:`reset` return from `obs, info` to `obs`.""" + """Converts :meth:`reset` return from ``obs, info`` to ``obs``.""" obs, _ = super().reset() return obs def render(self, mode="human", **kwargs) -> Any: - """Uses the :meth:`render` of the :attr:`env` that can be overwritten to change the returned data.""" + """Uses the :meth:`render` of the env that can be overwritten to change the returned data.""" return self.env.render() diff --git a/smarts/env/gymnasium/wrappers/metric/costs.py b/smarts/env/gymnasium/wrappers/metric/costs.py index 124c22241c..14443f9282 100644 --- a/smarts/env/gymnasium/wrappers/metric/costs.py +++ b/smarts/env/gymnasium/wrappers/metric/costs.py @@ -17,6 +17,7 @@ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. +from __future__ import annotations import warnings from collections import deque diff --git a/smarts/env/gymnasium/wrappers/metric/formula.py b/smarts/env/gymnasium/wrappers/metric/formula.py index e0308d7fb4..0e947c8740 100644 --- a/smarts/env/gymnasium/wrappers/metric/formula.py +++ b/smarts/env/gymnasium/wrappers/metric/formula.py @@ -19,6 +19,7 @@ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN # THE SOFTWARE. +from __future__ import annotations import functools from typing import Dict, NewType @@ -57,7 +58,7 @@ def score(self, records_sum: Dict[str, Dict[str, Record]]) -> Score: "Overall" on the wrapped environment. Returns: - Score: Contains "Overall" score and other sub-component scores. + "Overall" score and other sub-component scores. """ raise NotImplementedError @@ -99,7 +100,7 @@ def score(self, records_sum: Dict[str, Dict[str, Record]]) -> Score: +-------------------+--------+-----------------------------------------------------------+ Returns: - Score: Contains "Overall", "DistToDestination", "Time", + "Overall", "DistToDestination", "Time", "HumannessError", and "RuleViolation" scores. """ diff --git a/smarts/env/gymnasium/wrappers/metric/metrics.py b/smarts/env/gymnasium/wrappers/metric/metrics.py index 0d7b9bba00..22999a8add 100644 --- a/smarts/env/gymnasium/wrappers/metric/metrics.py +++ b/smarts/env/gymnasium/wrappers/metric/metrics.py @@ -432,7 +432,7 @@ class Metrics(gym.Wrapper): env (gym.Env): The gym environment to be wrapped. Raises: - AttributeError: Upon accessing (i) a protected attribute or (ii) an + AttributeError: Upon accessing (i) a protected attribute or (ii) an \ attribute beginning with an underscore. Returns: diff --git a/smarts/env/utils/action_conversion.py b/smarts/env/utils/action_conversion.py index f6a5371d5c..0cbafe6fcd 100644 --- a/smarts/env/utils/action_conversion.py +++ b/smarts/env/utils/action_conversion.py @@ -141,7 +141,7 @@ class _FormattingGroup: @lru_cache(maxsize=1) -def get_formats() -> Dict[ActionSpaceType, _FormattingGroup]: +def _get_formats() -> Dict[ActionSpaceType, _FormattingGroup]: """Get the currently available formatting groups for converting actions from `gym` space standard to SMARTS accepted observations. @@ -240,7 +240,7 @@ def format(self, actions: Dict[str, Any]): return actions out_actions = {} - formatting_groups = get_formats() + formatting_groups = _get_formats() for agent_id, action in actions.items(): agent_interface = self._agent_interfaces[agent_id] format_ = formatting_groups[agent_interface.action] @@ -267,7 +267,7 @@ def supported(action_type: ActionSpaceType): Returns: bool: If the action type is supported by the formatter. """ - return action_type in get_formats() + return action_type in _get_formats() @cached_property def space(self) -> gym.spaces.Dict: @@ -280,7 +280,7 @@ def space(self) -> gym.spaces.Dict: return None return gym.spaces.Dict( { - agent_id: get_formats()[agent_interface.action].space + agent_id: _get_formats()[agent_interface.action].space for agent_id, agent_interface in self._agent_interfaces.items() } ) diff --git a/smarts/env/utils/observation_conversion.py b/smarts/env/utils/observation_conversion.py index f1a009b88f..7cea403307 100644 --- a/smarts/env/utils/observation_conversion.py +++ b/smarts/env/utils/observation_conversion.py @@ -288,7 +288,7 @@ class BaseSpaceFormat: """Defines the base interface for an observation formatter.""" def format(self, obs: Observation): - """Selects and formats the given observation to get a value that matches the :attr:`space`.""" + """Selects and formats the given observation to get a value that matches the space attribute.""" raise NotImplementedError() def active(self, agent_interface: AgentInterface) -> bool: diff --git a/smarts/p3d/renderer.py b/smarts/p3d/renderer.py index 01f25cb23d..a70b8e108a 100644 --- a/smarts/p3d/renderer.py +++ b/smarts/p3d/renderer.py @@ -28,7 +28,6 @@ import re from dataclasses import dataclass from pathlib import Path -from re import Pattern from threading import Lock from typing import Optional, Tuple, Union @@ -260,7 +259,7 @@ def __init__(self, simid: str, debug_mode: DEBUG_MODE = DEBUG_MODE.ERROR): # Note: Each instance of the SMARTS simulation will have its own Renderer, # but all Renderer objects share the same ShowBaseInstance. self._showbase_instance: _ShowBaseInstance = _ShowBaseInstance() - self._interest_filter: Optional[Pattern] = None + self._interest_filter: Optional[re.Pattern] = None self._interest_color: Optional[Union[Colors, SceneColors]] = None @property @@ -426,14 +425,14 @@ def destroy(self): def __del__(self): self.destroy() - def set_interest(self, interest_filter: Pattern, interest_color: Colors): + def set_interest(self, interest_filter: re.Pattern, interest_color: Colors): """Sets the color of all vehicles that have ids that match the given pattern. Args: - interest_filter (Pattern): The regular expression pattern to match. + interest_filter (re.Pattern): The regular expression pattern to match. interest_color (Colors): The color that the vehicle should show as. """ - assert isinstance(interest_filter, Pattern) + assert isinstance(interest_filter, re.Pattern) self._interest_filter = interest_filter self._interest_color = interest_color diff --git a/smarts/sstudio/generators.py b/smarts/sstudio/generators.py index 20ad95a60f..4762fa9634 100644 --- a/smarts/sstudio/generators.py +++ b/smarts/sstudio/generators.py @@ -406,7 +406,7 @@ def resolve_route(self, route, fill_in_gaps: bool) -> types.Route: Args: route: An incomplete route. Returns: - types.Route: A complete route listing all road segments it passes through. + smarts.sstudio.types.route.Route: A complete route listing all road segments it passes through. """ if not isinstance(route, types.RandomRoute): return self._fill_in_gaps(route) if fill_in_gaps else route diff --git a/smarts/sstudio/genscenario.py b/smarts/sstudio/genscenario.py index 12bbdac304..65c3d85926 100644 --- a/smarts/sstudio/genscenario.py +++ b/smarts/sstudio/genscenario.py @@ -409,8 +409,8 @@ def gen_social_agent_missions( The scenario directory missions: A sequence of missions for social agents to perform - social_agent_actor(s): - The actor(s) to use + social_agent_actor: + The social agent actor(s) this scenario will use. name: A short name for this grouping of social agents. Is also used as the name of the social agent traffic file @@ -695,7 +695,7 @@ def gen_metadata(scenario: str, scenario_metadata: types.ScenarioMetadata): Args: scenario (str):The scenario directory - scenario_metadata (types.ScenarioMetadata): _description_ + scenario_metadata (ScenarioMetadata): Metadata of the scenario. """ _check_if_called_externally() output_path = os.path.join(scenario, "build", "scenario_metadata.pkl") diff --git a/smarts/sstudio/types/dataset.py b/smarts/sstudio/types/dataset.py index 91adef8c97..35af32a69d 100644 --- a/smarts/sstudio/types/dataset.py +++ b/smarts/sstudio/types/dataset.py @@ -38,7 +38,7 @@ class TrafficHistoryDataset: name: str """a unique name for the dataset""" source_type: str - """the type of the dataset; supported values include: NGSIM, INTERACTION, Waymo""" + """the type of the dataset; supports values in (``NGSIM``, ``INTERACTION``, ``Waymo``, ``Argoverse``)""" input_path: Optional[str] = None """a relative or absolute path to the dataset; if omitted, dataset will not be imported""" scenario_id: Optional[str] = None diff --git a/smarts/sstudio/types/traffic.py b/smarts/sstudio/types/traffic.py index 6896046ed0..ae28ae7307 100644 --- a/smarts/sstudio/types/traffic.py +++ b/smarts/sstudio/types/traffic.py @@ -43,7 +43,7 @@ class Flow: end: float = 1 * 60 * 60 """End time in seconds.""" actors: Dict[TrafficActor, float] = field(default_factory=dict) - """An actor to weight mapping associated as\\: { actor: weight } + """An actor to weight mapping associated as { actor -> weight }. :param actor: The traffic actors that are provided. :param weight: The chance of this actor appearing as a ratio over total weight. diff --git a/smarts/sstudio/types/zone.py b/smarts/sstudio/types/zone.py index e88acec0de..58bf164cf3 100644 --- a/smarts/sstudio/types/zone.py +++ b/smarts/sstudio/types/zone.py @@ -63,10 +63,10 @@ class MapZone(Zone): lane_index: The lane index from the rightmost lane. offset: - The offset in meters into the lane. Also acceptable\\: 'max', 'random' + The offset in meters into the lane. Also acceptable 'max' or 'random'. """ length: float - """The length of the geometry along the center of the lane. Also acceptable\\: 'max'""" + """The length of the geometry along the center of the lane. Also acceptable 'max'.""" n_lanes: int = 2 """The number of lanes from right to left that this zone covers."""