yasmin icon indicating copy to clipboard operation
yasmin copied to clipboard

ros2 service for skip state

Open aminballoon opened this issue 1 year ago • 12 comments

@mgonzs13 Hi, I'm ask for advice. I'm going to add code to skip the state with human trigger, I will add outcome "SKIPPED" to yasmin_ros pkg. So do you have any guide about how to trigger the state controller for set current node outcomes to "SKIPPED", I think it should be good with ros2 service call to trigger it.

I don't sure about this part we can discuss about this feature 👍 .

aminballoon avatar Jan 23 '24 04:01 aminballoon

Hi @aminballoon, do you want a feature to skip a state and move to another state using the transitions? Maybe something similar to the state cancel from the StateMachine that can be controlled by a topic or a service. What do you think of this?

I am thinking about a node that can expose some topics and services to control a state machine.

mgonzs13 avatar Jan 23 '24 09:01 mgonzs13

@mgonzs13, I think cancel and skip is not the same situation its can be design another way , such as outcome "Cancel" while node cannot complete that task but "Skip" its only human doesn't want to wait node complete the task .

aminballoon avatar Jan 23 '24 09:01 aminballoon

Well, another solution could be implementing a new state with a service as you suggest. What about the following code?

from typing import List, Callable
from std_srvs.srv import SetBool

from yasmin import State
from yasmin import Blackboard
from simple_node import Node
from .basic_outcomes import SKIPPED


class SkippableState(State):

    def __init__(
        self,
        node: Node,
        skip_srv_name: str,
        execute_handler: Callable,
        outcomes: List[str] = None,
    ) -> None:

        _outcomes = [SKIPPED]

        if outcomes:
            _outcomes = _outcomes + outcomes

        self._skipped = False
        self.__srv = node.create_service(
            SetBool, skip_srv_name, self._skip_state)

        self.__execute_handler = execute_handler

        super().__init__(_outcomes)

    def _skip_state(
        self,
        req: SetBool.Request,
        res: SetBool.Response
    ) -> SetBool.Response:
        self._skipped = req.data
        return SetBool.Response()

    def execute(self, blackboard: Blackboard) -> str:

        if self._skipped:
            return SKIPPED

        return self.__execute_handler(blackboard)

mgonzs13 avatar Jan 23 '24 18:01 mgonzs13

In my mind this way is very good. Does it possible to integrated skip_state to there node yasmin_ros the example case is while you are waiting to ros2_action call you can be cancel or skip that process with difference out_come .

aminballoon avatar Feb 01 '24 04:02 aminballoon

How do you want to control the skip? I mean, in the above example, you can use the service to enable or disable if the state is skipped before executing the state, not during state execution. Do you want to skip it during the execution? In this case, as I mentioned before, the needed code could be similar but not equal to the case of canceling a state.

mgonzs13 avatar Feb 01 '24 17:02 mgonzs13

I want to skip while that node in executing, cancel state will be trigger by external process.

aminballoon avatar Feb 05 '24 04:02 aminballoon

If you want to skip a state while executing, how do you want to stop that state, canceling it?

mgonzs13 avatar Feb 05 '24 08:02 mgonzs13

yes, that node will be cancel but skip and cancel difference outcome .

aminballoon avatar Feb 09 '24 06:02 aminballoon

You can cancel the state inside the _skip_state:

    def _skip_state(
        self,
        req: SetBool.Request,
        res: SetBool.Response
    ) -> SetBool.Response:
        self._skipped = req.data

        if self._skipped:
            self.cancel_state()

        return SetBool.Response()

mgonzs13 avatar Feb 12 '24 08:02 mgonzs13

Okay, Next step How to cancel ros_action_client_example while client is still executing with service method like your example ?

aminballoon avatar Feb 13 '24 07:02 aminballoon

You can use the same cancel_state function to cancel an ActionState. This will cancel the action client, which means that will cancel the action server.

mgonzs13 avatar Feb 13 '24 08:02 mgonzs13

Hey @aminballoon, how is this going?

mgonzs13 avatar Jun 03 '24 09:06 mgonzs13