Commit 573eeae666016117994bf272ef844894c84bd5b9

Authored by Etienne Pallier
1 parent ff76bcca
Exists in dev

Agent ne depend plus de AgentDevice, et TEST ok avec self pour envoyer commandes a soi meme

src/core/pyros_django/agent/Agent.py
... ... @@ -302,13 +302,13 @@ class Agent:
302 302 #"set_state",
303 303 ]
304 304  
  305 + # --- FOR TEST ONLY ---
  306 +
305 307 # Maximum duration of this agent (only for SIMULATION mode)
306 308 # If set to None, it will never exit except if asked (or CTRL-C)
307 309 # If set to 20, it will exit after 20s
308 310 TEST_MAX_DURATION_SEC = None
309 311 #TEST_MAX_DURATION_SEC = 30
310   -
311   - # FOR TEST ONLY
312 312 # Run this agent in simulator mode
313 313 TEST_MODE = True
314 314 WITH_SIMULATOR = False
... ... @@ -316,12 +316,29 @@ class Agent:
316 316 TEST_WITH_FINAL_TEST = False
317 317 # Who should I send commands to ?
318 318 TEST_COMMANDS_DEST = "myself"
319   - # Default scenario to be executed
  319 +
  320 + # (EP 2022/06) Default scenario to be executed (only in TEST mode)
  321 + #
  322 + # List of commands to be sent by this agent to other agents ("self" means himself)
  323 + #
  324 + # Command format is :
  325 + # "[Recipient] Command [Args]"
  326 + # with :
  327 + # - [Recipient] optional, the name of the Agent the command is to be sent to (use "self" to mean himself)
  328 + # - Command, the command name
  329 + # - [Args] optional, the list of command arguments, separated by blanks : arg1 arg2 arg3 ...
  330 + #
  331 + # Ex :
  332 + # - "AgentScheduler set_state ATTENTIVE" => means to send the command "set_state ATTENTIVE" to the agent AgentScheduler
  333 + # - "AgentX set_state ATTENTIVE" => means to send the command "set_state ATTENTIVE" to the agent AgentX
  334 + # - "self set_state ATTENTIVE" => means to send the command "set_state ATTENTIVE" to MYSELF
  335 + # - "self do_restart_loop" => means to send the command "do_restart_loop" to MYSELF (no args)
  336 + #
320 337 #TEST_COMMANDS = iter([
321 338 TEST_COMMANDS_LIST = [
322 339 "Agent set_state ATTENTIVE",
323   - "Agent set_state ROUTINE",
324   - "Agent set_state IDLE",
  340 + "self set_state ROUTINE",
  341 + "self set_state IDLE",
325 342  
326 343 '''
327 344 # specific0 not_executed_because_idle
... ... @@ -1656,7 +1673,7 @@ class Agent:
1656 1673 cmd.set_as_running()
1657 1674  
1658 1675 log.info("(Agent level GENERAL CMD)")
1659   - _,cmd_name,cmd_args = cmd.get_full_name_parts()
  1676 + cmd_name,cmd_args = cmd.get_name_and_args()
1660 1677 #cmd_name, cmd_args = cmd.tokenize()
1661 1678 #if cmd.name == "set_state:active":
1662 1679 #elif cmd.name == "set_state:idle":
... ... @@ -1877,11 +1894,13 @@ class Agent:
1877 1894 if cmd_full_name is None: return None
1878 1895 if ' ' not in cmd_full_name: raise Exception('Command is malformed:', cmd_full_name)
1879 1896 agent_recipient,cmd_name = cmd_full_name.split(' ', 1)
  1897 + # Command is to be sent to myself ?
  1898 + if agent_recipient == 'self': agent_recipient = self.name
1880 1899 ##recipient_agent = self.name if self.TEST_COMMANDS_DEST=="myself" else self.TEST_COMMANDS_DEST
1881 1900 #return Command(sender=self.name, recipient=recipient_agent, name=cmd_name)
1882 1901 cmd = self.create_cmd_for(agent_recipient, cmd_name)
1883 1902 # If no cmd created (because of error, bad AgentDevice name), call again this method for next cmd
1884   - if cmd is None: return self._TEST_get_next_command_to_send()
  1903 + #if cmd is None: return self._TEST_get_next_command_to_send()
1885 1904 return cmd
1886 1905  
1887 1906 """
... ...
src/core/pyros_django/common/models.py
... ... @@ -8,7 +8,7 @@ from datetime import datetime, timedelta, date
8 8 from dateutil.relativedelta import relativedelta
9 9 import os
10 10 import sys
11   -from typing import List
  11 +from typing import List, Tuple
12 12 from django.core.validators import MaxValueValidator, MinValueValidator
13 13  
14 14 # DJANGO imports
... ... @@ -423,8 +423,14 @@ class Alert(Request):
423 423  
424 424  
425 425 class AgentCmd(models.Model):
426   -
427 426 """
  427 + Command sent to an Agent
  428 +
  429 + Can be either :
  430 + - an "agent level" (general or specific) command
  431 + OR
  432 + - a "device level" command
  433 +
428 434 | id | sender | recipient | name | validity_duration (default=60) | s_deposit_time | r_read_time
429 435  
430 436 See doc/models_Command_state_diag.pu for PlantUML state diagram
... ... @@ -459,11 +465,28 @@ class AgentCmd(models.Model):
459 465 "CMD_OUTOFDATE" # cde pรฉrimรฉe
460 466 )
461 467 _AGENT_GENERAL_COMMANDS = [
462   - #"do_eval", "set_state:idle", "set_state:active",
  468 + # DO commands
  469 + # - Evaluate the expression given (ex: do_eval 4+3)
463 470 "do_eval",
  471 + # GET commands
  472 + # - Get agent current state (idle, routine, attentive)
  473 + "get_state",
  474 + # SET commands
  475 + # - Set agent current state (idle, routine, attentive)
464 476 "set_state",
465 477 # Commands executed in priority (even if other pending commands exist)
466   - "do_flush_commands", "do_abort", "do_exit", "do_restart_init"
  478 + # - Remove all your pending commands
  479 + "do_flush_commands",
  480 + # - Abort the command you are currently running
  481 + "do_abort_current_command",
  482 + # - do_abort_current_command and then stop immediately
  483 + "do_abort",
  484 + # - finish your current command and then make a normal clean stop
  485 + "do_exit",
  486 + # - restart your global loop (starting with init())
  487 + "do_restart_loop",
  488 + # - restart completely an agent (only AgentSST can do this) : do_exit + start again
  489 + "do_restart_agent",
467 490 ]
468 491 #COMMANDS_PEREMPTION_HOURS = 48
469 492 COMMANDS_PEREMPTION_HOURS = 60/60
... ... @@ -696,7 +719,7 @@ class AgentCmd(models.Model):
696 719 return (f"Commmand '{self.full_name}' ({self.state}) sent to agent {self.recipient}{cmd_sent_time} [by agent {self.sender}]")
697 720  
698 721 @property
699   - def device_command(self):
  722 + def device_command(self) -> DeviceCmd :
700 723 if not self._device_command:
701 724 self._device_command = DeviceCmd(self.full_name)
702 725 #dc = self._device_command
... ... @@ -713,18 +736,42 @@ class AgentCmd(models.Model):
713 736 return cmd_name_and_args
714 737 '''
715 738  
716   - def get_full_name_parts(self):
717   - return self.device_command.get_full_name_parts()
718   - '''
719   - cmd_name = self.full_name
720   - cmd_type = None
  739 +
  740 + #def get_name_and_args(self) -> list(str, str) :
  741 + def get_name_and_args(self) -> list :
  742 + ''' Return command name and args if exist '''
  743 + # By default, no args
721 744 cmd_args = None
722   - if '.' in cmd_name:
723   - cmd_type, cmd_name = cmd_name.split('.')
  745 + cmd_name = self.full_name
724 746 if ' ' in cmd_name:
725 747 cmd_name, *cmd_args = cmd_name.split(' ')
726   - return cmd_type, cmd_name, cmd_args
727   - '''
  748 + print(cmd_name, cmd_args)
  749 + return cmd_name, cmd_args
  750 +
  751 +
  752 + #def get_full_name_parts(self) -> tuple(str, str, str) :
  753 + def get_full_name_parts(self) -> list :
  754 + ''' Return command device type, name, and args from any command type (agent or device level) '''
  755 +
  756 + # No device type by default for an Agent command
  757 + # cmd_type ?
  758 + dev_type = None
  759 +
  760 + # By default, no args
  761 + cmd_args = None
  762 +
  763 + cmd_name = self.full_name
  764 +
  765 + # Device command with device component type (dev_type)
  766 + if '.' in cmd_name:
  767 + return self.device_command.get_full_name_parts()
  768 +
  769 + # Simple command with args (no dev_type)
  770 + if ' ' in cmd_name:
  771 + cmd_name, *cmd_args = self.get_name_and_args()
  772 +
  773 + return dev_type, cmd_name, cmd_args
  774 +
728 775  
729 776 @property
730 777 def name(self):
... ...