class_docstr: Base world for running TOD model-model chats. Includes the following agents:
  
  * User utt agent
  * API call agent
      * Currently assumed to be same as system utt agent in script code, though used as if separate in this world for clarity
  * API responder agent
  * System utt agent
  * API schema groundinger agent (given to api call + response agent)
  * Goal groundinger agent (given to user)
  
  As is standard for ParlAI, these agents may be models or may be standalone classes that extend the "Agent" class. The models for these *are* expected to have their utterances in a standard format.
  
  We do expect these agents to be passed in with a set order (see above), since some assumptions of regular ParlAI Worlds (ex. task = agent[0], model = agent[1]) are broken here since there is no "task agent" and one agent can be two "roles" (ex. system agent also making API calls)
code: def __init__(self, opt: Opt, agents=None, shared=None):
      super().__init__(opt, agents, shared)
      self.batchsize = opt["batchsize"]
      self.batch_agents = []
      self.batch_acts = []
      self.batch_goals = []  # for case when num_episodes < batchsize
      self.batch_tod_world_metrics = []
      for i in range(self.batchsize):
          here_agents = []
          for j, agent in enumerate(agents):
              if (
                  j == SYSTEM_UTT_IDX
              ):  # handle separately cause we expect it to be same as API_CALL agent
                  here_agents.append(here_agents[API_CALL_IDX])
                  continue
              share = agent.share()
              batch_opt = copy.deepcopy(share["opt"])
              batch_opt["batchindex"] = i
              here_agents.append(share["class"](batch_opt, share))
          self.batch_agents.append(here_agents)
          self.batch_acts.append([Message.padding_example()] * 4)
          self.batch_tod_world_metrics.append(tod_metrics.TodMetrics())
      self.end_episode = [False] * self.batchsize
  
      self.max_turns = self.opt.get("max_turns", 30)
      self.turns = 0
      self.need_grounding = True
  
imports: from parlai.core.metrics import Metric, LegacyMetric
  from parlai.core.message import Message
  from parlai.core.opt import Opt
  from parlai.core.worlds import World
  from parlai.agents.local_human.local_human import LocalHumanAgent
  from parlai.utils.misc import display_messages
  import parlai.core.tod.tod_core
  import parlai.core.tod.world_metrics
  import sys
  import copy
label_desc: Use image node_id 1 to create a new TodWorld object from inherited base classes: World with example: obj = TodWorld(opt, agents, shared)