-
Notifications
You must be signed in to change notification settings - Fork 3
Planning refactors #116
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: devel
Are you sure you want to change the base?
Planning refactors #116
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It looks like most of the changes to this file are typing changes now that we use Python 3.12. As well as the change from io_node to io holding a node as a member variable.
| """ | ||
|
|
||
| def __init__(self, node: Node): | ||
| self.logger = node.get_logger() |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Great change!!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I support the name change from periodic_io.py --> io_interface.py.
This file changes from being a node to having a node passed into it. It also adds pitch because it wasn't there before.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Other than overhauling DoubleTimedState, changes to this file are mainly updating instance of io_node --> io.node and updating the typing to be consistent with Python 3.12.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
DoubleTimedState didn't actually change all that much; ForwardAndWait changed from being a subclass of TimedState to being a subclass of DoubleTimedState, which significantly simplified its implementation. To reflect this change, I swapped the order of the two classes in source which confused git, so it looks like both classes changed significantly.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Understood
imzaynb
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks good. Though I do want @alexanderbowler to look at these changes before we merge since he was in charge of migrating this from ROS1.
|
|
||
|
|
||
| TransitionMap = Dict[Type[Outcome], Type[State]] | ||
| TransitionMap = dict[type[Outcome], type[State]] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this the recommended way to type python types, I always used tje upercase typing version instead of the lowercase python version
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Uppercase version is from the typing module, lowercase just uses the built-in types. There's no longer any reason to import the uppercase names in recent python versions because the built-in types now support the type[generic] syntax.
https://docs.python.org/3/library/typing.html#typing.Dict
"Deprecated since version 3.9"
| rate.sleep() | ||
|
|
||
|
|
||
| def main() -> None: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
does main return None? doesn't it return an int
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This function doesnt?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
main returns whatever you want in python
| def __init__(self, prev_outcome: Outcome, io: Interface): | ||
| super().__init__(prev_outcome, io) | ||
| self.io.reset_target_twist() | ||
| self.rate = self.io.node.create_rate(50) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i am again unsure about the use of rate here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think in this case it is fine because stop is special, in a general state we definitely do not want to rate sleep tho
| Returns the Outcome from calling handle() on StopState. | ||
| """ | ||
| rate = self.node.create_rate(hz) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i dont think rate can be used here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think in this case it is fine because of the difficulty of refactoring to not use sleep and there is a separate thread spinning in captain.py
HenryLeC
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM!
| rate.sleep() | ||
|
|
||
|
|
||
| def main() -> None: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
main returns whatever you want in python
| def __init__(self, prev_outcome: Outcome, io: Interface): | ||
| super().__init__(prev_outcome, io) | ||
| self.io.reset_target_twist() | ||
| self.rate = self.io.node.create_rate(50) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think in this case it is fine because stop is special, in a general state we definitely do not want to rate sleep tho
| Returns the Outcome from calling handle() on StopState. | ||
| """ | ||
| rate = self.node.create_rate(hz) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think in this case it is fine because of the difficulty of refactoring to not use sleep and there is a separate thread spinning in captain.py
This PR contains a lot of semi-independent refactors, so I'd like all yall's opinions on which are good and which are not.
Unrelated to planning:
mrobosub_planning changes (not necessarily exhaustive, please read through the diff):
typing.Typetotype,typing.Union[A, B]toA | B,typing.Optional[T]toT | None, etc.)abstract_statehierarchy to remove duplicate logic between statestimeandstate_runtimemethods toTimedStateso we don't have to keep writingself.io.node.get_clock().now().nanoseconds / 1e9periodic_io.Interfaceperiodic_io.Captaintoperiodic_io.Interfaceand make it take in aNodein the constructor instead of being a node itselfCaptainnode class incaptain.pyState.io_nodetoState.ioto reflect thatInterfaceis not a nodeself.io.nodecaptainmainfunction to reflect changes to the nodeperiodic_ioInterfaceto use simpler, synchronous callscall_asyncfuture and immediately callingrclpy.spin_until_future_completeactivate_bot_cam,activate_zed,deactivate_camerasinto one likeset_cameras(bot_cam_enable: bool, zed_enable: bool)that each of the three called but the order in whichactivate_zed/bot_camcall the services is opposite (better to disable the other camera first, before enabling to ensure bandwith is never overloaded)periodic_io.pytoio_interface.py