pycityagent 2.0.0a53__cp311-cp311-macosx_11_0_arm64.whl → 2.0.0a55__cp311-cp311-macosx_11_0_arm64.whl

Sign up to get free protection for your applications and to get access to all the features.
@@ -18,12 +18,15 @@ from ..cityagent import (BankAgent, FirmAgent, GovernmentAgent, NBSAgent,
18
18
  memory_config_government, memory_config_nbs,
19
19
  memory_config_societyagent)
20
20
  from ..cityagent.initial import bind_agent_info, initialize_social_network
21
- from ..environment.simulator import Simulator
22
- from ..llm import SimpleEmbedding
23
- from ..message.messager import Messager
24
- from ..metrics import MlflowClient, init_mlflow_connection
21
+ from ..environment import Simulator
22
+ from ..llm import LLM, LLMConfig, SimpleEmbedding
23
+ from ..memory import Memory
24
+ from ..message import (MessageBlockBase, MessageBlockListenerBase,
25
+ MessageInterceptor, Messager)
26
+ from ..metrics import init_mlflow_connection
27
+ from ..metrics.mlflow_client import MlflowClient
25
28
  from ..survey import Survey
26
- from ..utils import TO_UPDATE_EXP_INFO_KEYS_AND_TYPES
29
+ from ..utils import SURVEY_SENDER_UUID, TO_UPDATE_EXP_INFO_KEYS_AND_TYPES
27
30
  from .agentgroup import AgentGroup
28
31
  from .storage.pg import PgWriter, create_pg_tables
29
32
 
@@ -80,6 +83,15 @@ class AgentSimulation:
80
83
  self.config = config
81
84
  self.exp_name = exp_name
82
85
  self._simulator = Simulator(config["simulator_request"])
86
+ if enable_economy:
87
+ self._economy_env = self._simulator._sim_env
88
+ _req_dict = self.config["simulator_request"]
89
+ if "economy" in _req_dict:
90
+ _req_dict["economy"]["server"] = self._economy_env.sim_addr
91
+ else:
92
+ _req_dict["economy"] = {
93
+ "server": self._economy_env.sim_addr,
94
+ }
83
95
  self.agent_prefix = agent_prefix
84
96
  self._groups: dict[str, AgentGroup] = {} # type:ignore
85
97
  self._agent_uuid2group: dict[str, AgentGroup] = {} # type:ignore
@@ -117,15 +129,17 @@ class AgentSimulation:
117
129
 
118
130
  # mlflow
119
131
  _mlflow_config: dict[str, Any] = config.get("metric_request", {}).get("mlflow")
120
- mlflow_run_id, _ = init_mlflow_connection(
121
- config=_mlflow_config,
122
- mlflow_run_name=f"EXP_{self.exp_name}_{1000*int(time.time())}",
123
- experiment_name=self.exp_name,
124
- )
125
132
  if _mlflow_config:
126
133
  logger.info(f"-----Creating Mlflow client...")
134
+ mlflow_run_id, _ = init_mlflow_connection(
135
+ config=_mlflow_config,
136
+ experiment_uuid=self.exp_id,
137
+ mlflow_run_name=f"EXP_{self.exp_name}_{1000*int(time.time())}",
138
+ experiment_name=self.exp_name,
139
+ )
127
140
  self.mlflow_client = MlflowClient(
128
141
  config=_mlflow_config,
142
+ experiment_uuid=self.exp_id,
129
143
  mlflow_run_name=f"EXP_{exp_name}_{1000*int(time.time())}",
130
144
  experiment_name=exp_name,
131
145
  run_id=mlflow_run_id,
@@ -225,6 +239,7 @@ class AgentSimulation:
225
239
  agent_count.append(config["agent_config"]["number_of_government"])
226
240
  agent_count.append(config["agent_config"]["number_of_bank"])
227
241
  agent_count.append(config["agent_config"]["number_of_nbs"])
242
+ # TODO(yanjunbo): support MessageInterceptor
228
243
  await simulation.init_agents(
229
244
  agent_count=agent_count,
230
245
  group_size=config["agent_config"].get("group_size", 10000),
@@ -290,9 +305,13 @@ class AgentSimulation:
290
305
  return self._agent_uuid2group
291
306
 
292
307
  @property
293
- def messager(self):
308
+ def messager(self) -> ray.ObjectRef:
294
309
  return self._messager
295
310
 
311
+ @property
312
+ def message_interceptor(self) -> ray.ObjectRef:
313
+ return self._message_interceptors[0] # type:ignore
314
+
296
315
  async def _save_exp_info(self) -> None:
297
316
  """异步保存实验信息到YAML文件"""
298
317
  try:
@@ -371,6 +390,10 @@ class AgentSimulation:
371
390
  agent_count: Union[int, list[int]],
372
391
  group_size: int = 10000,
373
392
  pg_sql_writers: int = 32,
393
+ message_interceptors: int = 1,
394
+ message_interceptor_blocks: Optional[list[MessageBlockBase]] = None,
395
+ social_black_list: Optional[list[tuple[str, str]]] = None,
396
+ message_listener: Optional[MessageBlockListenerBase] = None,
374
397
  embedding_model: Embeddings = SimpleEmbedding(),
375
398
  memory_config_func: Optional[Union[Callable, list[Callable]]] = None,
376
399
  ) -> None:
@@ -379,6 +402,8 @@ class AgentSimulation:
379
402
  Args:
380
403
  agent_count: 要创建的总智能体数量, 如果为列表,则每个元素表示一个智能体类创建的智能体数量
381
404
  group_size: 每个组的智能体数量,每一个组为一个独立的ray actor
405
+ pg_sql_writers: 独立的PgSQL writer数量
406
+ message_interceptors: message拦截器数量
382
407
  memory_config_func: 返回Memory配置的函数,需要返回(EXTRA_ATTRIBUTES, PROFILE, BASE)元组, 如果为列表,则每个元素表示一个智能体类创建的Memory配置函数
383
408
  """
384
409
  if not isinstance(agent_count, list):
@@ -499,7 +524,17 @@ class AgentSimulation:
499
524
  config_files,
500
525
  )
501
526
  )
502
-
527
+ # 初始化mlflow连接
528
+ _mlflow_config = self.config.get("metric_request", {}).get("mlflow")
529
+ if _mlflow_config:
530
+ mlflow_run_id, _ = init_mlflow_connection(
531
+ experiment_uuid=self.exp_id,
532
+ config=_mlflow_config,
533
+ mlflow_run_name=f"{self.exp_name}_{1000*int(time.time())}",
534
+ experiment_name=self.exp_name,
535
+ )
536
+ else:
537
+ mlflow_run_id = None
503
538
  # 建表
504
539
  if self.enable_pgsql:
505
540
  _num_workers = min(1, pg_sql_writers)
@@ -514,7 +549,31 @@ class AgentSimulation:
514
549
  else:
515
550
  _num_workers = 1
516
551
  self._pgsql_writers = _workers = [None for _ in range(_num_workers)]
517
-
552
+ # message interceptor
553
+ if message_listener is not None:
554
+ self._message_abort_listening_queue = _queue = ray.util.queue.Queue() # type: ignore
555
+ await message_listener.set_queue(_queue)
556
+ else:
557
+ self._message_abort_listening_queue = _queue = None
558
+ _interceptor_blocks = message_interceptor_blocks
559
+ _black_list = [] if social_black_list is None else social_black_list
560
+ _llm_config = self.config.get("llm_request", {})
561
+ if message_interceptor_blocks is not None:
562
+ _num_interceptors = min(1, message_interceptors)
563
+ self._message_interceptors = _interceptors = [
564
+ MessageInterceptor.remote(
565
+ _interceptor_blocks, # type:ignore
566
+ _black_list,
567
+ _llm_config,
568
+ _queue,
569
+ )
570
+ for _ in range(_num_interceptors)
571
+ ]
572
+ else:
573
+ _num_interceptors = 1
574
+ self._message_interceptors = _interceptors = [
575
+ None for _ in range(_num_interceptors)
576
+ ]
518
577
  creation_tasks = []
519
578
  for i, (
520
579
  agent_class,
@@ -529,11 +588,14 @@ class AgentSimulation:
529
588
  number_of_agents,
530
589
  memory_config_function_group,
531
590
  self.config,
591
+ self.exp_name,
532
592
  self.exp_id,
533
593
  self.enable_avro,
534
594
  self.avro_path,
535
595
  self.enable_pgsql,
536
596
  _workers[i % _num_workers], # type:ignore
597
+ self.message_interceptor,
598
+ mlflow_run_id,
537
599
  embedding_model,
538
600
  self.logging_level,
539
601
  config_file,
@@ -564,11 +626,15 @@ class AgentSimulation:
564
626
  for group in self._groups.values():
565
627
  init_tasks.append(group.init_agents.remote())
566
628
  ray.get(init_tasks)
567
- await self.messager.connect.remote()
568
- await self.messager.subscribe.remote([(f"exps/{self.exp_id}/user_payback", 1)], [self.exp_id])
569
- await self.messager.start_listening.remote()
629
+ await self.messager.connect.remote() # type:ignore
630
+ await self.messager.subscribe.remote( # type:ignore
631
+ [(f"exps/{self.exp_id}/user_payback", 1)], [self.exp_id]
632
+ )
633
+ await self.messager.start_listening.remote() # type:ignore
570
634
 
571
- async def gather(self, content: str, target_agent_uuids: Optional[list[str]] = None):
635
+ async def gather(
636
+ self, content: str, target_agent_uuids: Optional[list[str]] = None
637
+ ):
572
638
  """收集智能体的特定信息"""
573
639
  gather_tasks = []
574
640
  for group in self._groups.values():
@@ -612,12 +678,13 @@ class AgentSimulation:
612
678
  self, survey: Survey, agent_uuids: Optional[list[str]] = None
613
679
  ):
614
680
  """发送问卷"""
681
+ await self.messager.connect.remote() # type:ignore
615
682
  survey_dict = survey.to_dict()
616
683
  if agent_uuids is None:
617
684
  agent_uuids = self._agent_uuids
618
685
  _date_time = datetime.now(timezone.utc)
619
686
  payload = {
620
- "from": "none",
687
+ "from": SURVEY_SENDER_UUID,
621
688
  "survey_id": survey_dict["id"],
622
689
  "timestamp": int(_date_time.timestamp() * 1000),
623
690
  "data": survey_dict,
@@ -625,10 +692,10 @@ class AgentSimulation:
625
692
  }
626
693
  for uuid in agent_uuids:
627
694
  topic = self._user_survey_topics[uuid]
628
- await self.messager.send_message.remote(topic, payload)
695
+ await self.messager.send_message.remote(topic, payload) # type:ignore
629
696
  remain_payback = len(agent_uuids)
630
697
  while True:
631
- messages = await self.messager.fetch_messages.remote()
698
+ messages = await self.messager.fetch_messages.remote() # type:ignore
632
699
  logger.info(f"Received {len(messages)} payback messages [survey]")
633
700
  remain_payback -= len(messages)
634
701
  if remain_payback <= 0:
@@ -641,7 +708,7 @@ class AgentSimulation:
641
708
  """发送采访消息"""
642
709
  _date_time = datetime.now(timezone.utc)
643
710
  payload = {
644
- "from": "none",
711
+ "from": SURVEY_SENDER_UUID,
645
712
  "content": content,
646
713
  "timestamp": int(_date_time.timestamp() * 1000),
647
714
  "_date_time": _date_time,
@@ -650,19 +717,19 @@ class AgentSimulation:
650
717
  agent_uuids = [agent_uuids]
651
718
  for uuid in agent_uuids:
652
719
  topic = self._user_chat_topics[uuid]
653
- await self.messager.send_message.remote(topic, payload)
720
+ await self.messager.send_message.remote(topic, payload) # type:ignore
654
721
  remain_payback = len(agent_uuids)
655
722
  while True:
656
- messages = await self.messager.fetch_messages.remote()
723
+ messages = await self.messager.fetch_messages.remote() # type:ignore
657
724
  logger.info(f"Received {len(messages)} payback messages [interview]")
658
725
  remain_payback -= len(messages)
659
726
  if remain_payback <= 0:
660
727
  break
661
728
  await asyncio.sleep(3)
662
729
 
663
- async def extract_metric(self, metric_extractor: list[Callable]):
730
+ async def extract_metric(self, metric_extractors: list[Callable]):
664
731
  """提取指标"""
665
- for metric_extractor in metric_extractor:
732
+ for metric_extractor in metric_extractors:
666
733
  await metric_extractor(self)
667
734
 
668
735
  async def step(self):
@@ -670,7 +737,9 @@ class AgentSimulation:
670
737
  try:
671
738
  # check whether insert agents
672
739
  simulator_day = await self._simulator.get_simulator_day()
673
- print(f"simulator_day: {simulator_day}, self._simulator_day: {self._simulator_day}")
740
+ print(
741
+ f"simulator_day: {simulator_day}, self._simulator_day: {self._simulator_day}"
742
+ )
674
743
  need_insert_agents = False
675
744
  if simulator_day > self._simulator_day:
676
745
  need_insert_agents = True
@@ -698,11 +767,14 @@ class AgentSimulation:
698
767
  if self.metric_extractor is not None:
699
768
  print(f"total_steps: {self._total_steps}, excute metric")
700
769
  to_excute_metric = [
701
- metric[1] for metric in self.metric_extractor if self._total_steps % metric[0] == 0
770
+ metric[1]
771
+ for metric in self.metric_extractor
772
+ if self._total_steps % metric[0] == 0
702
773
  ]
703
774
  await self.extract_metric(to_excute_metric)
704
775
  except Exception as e:
705
776
  import traceback
777
+
706
778
  logger.error(f"模拟器运行错误: {str(e)}\n{traceback.format_exc()}")
707
779
  raise RuntimeError(str(e)) from e
708
780
 
@@ -721,10 +793,12 @@ class AgentSimulation:
721
793
  monitor_task = asyncio.create_task(self._monitor_exp_status(stop_event))
722
794
 
723
795
  try:
724
- end_time = await self._simulator.get_time() + day * 24 * 3600
796
+ end_time = (
797
+ await self._simulator.get_time() + day * 24 * 3600
798
+ ) # type:ignore
725
799
  while True:
726
800
  current_time = await self._simulator.get_time()
727
- if current_time >= end_time:
801
+ if current_time >= end_time: # type:ignore
728
802
  break
729
803
  await self.step()
730
804
  finally:
@@ -71,11 +71,11 @@ class PgWriter:
71
71
 
72
72
  @lock_decorator
73
73
  async def async_write_status(self, rows: list[tuple]):
74
- _tuple_types = [str, int, float, float, float, int, str, str, None]
74
+ _tuple_types = [str, int, float, float, float, int, list, str, str, None]
75
75
  table_name = f"socialcity_{self.exp_id.replace('-', '_')}_agent_status"
76
76
  async with await psycopg.AsyncConnection.connect(self._dsn) as aconn:
77
77
  copy_sql = psycopg.sql.SQL(
78
- "COPY {} (id, day, t, lng, lat, parent_id, action, status, created_at) FROM STDIN"
78
+ "COPY {} (id, day, t, lng, lat, parent_id, friend_ids, action, status, created_at) FROM STDIN"
79
79
  ).format(psycopg.sql.Identifier(table_name))
80
80
  _rows: list[Any] = []
81
81
  async with aconn.cursor() as cur:
@@ -1,11 +1,16 @@
1
1
  from .avro_schema import (DIALOG_SCHEMA, INSTITUTION_STATUS_SCHEMA,
2
2
  PROFILE_SCHEMA, STATUS_SCHEMA, SURVEY_SCHEMA)
3
3
  from .pg_query import PGSQL_DICT, TO_UPDATE_EXP_INFO_KEYS_AND_TYPES
4
- from .survey_util import process_survey_for_llm
4
+ from .survey_util import SURVEY_SENDER_UUID, process_survey_for_llm
5
5
 
6
6
  __all__ = [
7
- "PROFILE_SCHEMA", "DIALOG_SCHEMA", "STATUS_SCHEMA", "SURVEY_SCHEMA", "INSTITUTION_STATUS_SCHEMA",
7
+ "PROFILE_SCHEMA",
8
+ "DIALOG_SCHEMA",
9
+ "STATUS_SCHEMA",
10
+ "SURVEY_SCHEMA",
11
+ "INSTITUTION_STATUS_SCHEMA",
8
12
  "process_survey_for_llm",
9
13
  "TO_UPDATE_EXP_INFO_KEYS_AND_TYPES",
10
14
  "PGSQL_DICT",
15
+ "SURVEY_SENDER_UUID",
11
16
  ]
@@ -54,6 +54,7 @@ PGSQL_DICT: dict[str, list[Any]] = {
54
54
  lng DOUBLE PRECISION,
55
55
  lat DOUBLE PRECISION,
56
56
  parent_id INT4,
57
+ friend_ids UUID[],
57
58
  action TEXT,
58
59
  status JSONB,
59
60
  created_at TIMESTAMPTZ
@@ -8,40 +8,40 @@ Survey Description: {survey_dict['description']}
8
8
  Please answer each question in the following format:
9
9
 
10
10
  """
11
-
11
+
12
12
  question_count = 1
13
- for page in survey_dict['pages']:
14
- for question in page['elements']:
13
+ for page in survey_dict["pages"]:
14
+ for question in page["elements"]:
15
15
  prompt += f"Question {question_count}: {question['title']}\n"
16
-
16
+
17
17
  # 根据不同类型的问题生成不同的提示
18
- if question['type'] == 'radiogroup':
19
- prompt += "Options: " + ", ".join(question['choices']) + "\n"
18
+ if question["type"] == "radiogroup":
19
+ prompt += "Options: " + ", ".join(question["choices"]) + "\n"
20
20
  prompt += "Please select ONE option\n"
21
-
22
- elif question['type'] == 'checkbox':
23
- prompt += "Options: " + ", ".join(question['choices']) + "\n"
21
+
22
+ elif question["type"] == "checkbox":
23
+ prompt += "Options: " + ", ".join(question["choices"]) + "\n"
24
24
  prompt += "You can select MULTIPLE options\n"
25
-
26
- elif question['type'] == 'rating':
25
+
26
+ elif question["type"] == "rating":
27
27
  prompt += f"Rating range: {question.get('min_rating', 1)} - {question.get('max_rating', 5)}\n"
28
28
  prompt += "Please provide a rating within the range\n"
29
-
30
- elif question['type'] == 'matrix':
31
- prompt += "Rows: " + ", ".join(question['rows']) + "\n"
32
- prompt += "Columns: " + ", ".join(question['columns']) + "\n"
29
+
30
+ elif question["type"] == "matrix":
31
+ prompt += "Rows: " + ", ".join(question["rows"]) + "\n"
32
+ prompt += "Columns: " + ", ".join(question["columns"]) + "\n"
33
33
  prompt += "Please select ONE column option for EACH row\n"
34
-
35
- elif question['type'] == 'text':
34
+
35
+ elif question["type"] == "text":
36
36
  prompt += "Please provide a text response\n"
37
-
38
- elif question['type'] == 'boolean':
37
+
38
+ elif question["type"] == "boolean":
39
39
  prompt += "Options: Yes, No\n"
40
40
  prompt += "Please select either Yes or No\n"
41
-
41
+
42
42
  prompt += "\nAnswer: [Your response here]\n\n---\n\n"
43
43
  question_count += 1
44
-
44
+
45
45
  # 添加总结提示
46
46
  prompt += """Please ensure:
47
47
  1. All required questions are answered
@@ -49,5 +49,8 @@ Please answer each question in the following format:
49
49
  3. Answers are clear and specific
50
50
 
51
51
  Format your responses exactly as requested above."""
52
-
53
- return prompt
52
+
53
+ return prompt
54
+
55
+
56
+ SURVEY_SENDER_UUID = "none"
@@ -187,7 +187,7 @@ class Block:
187
187
 
188
188
  @classmethod
189
189
  def import_config(cls, config: dict[str, Union[str, dict]]) -> Block:
190
- instance = cls(name=config["name"])
190
+ instance = cls(name=config["name"]) # type: ignore
191
191
  assert isinstance(config["config"], dict)
192
192
  for field, value in config["config"].items():
193
193
  if field in cls.configurable_fields:
@@ -195,12 +195,12 @@ class Block:
195
195
 
196
196
  # 递归创建子Block
197
197
  for child_config in config.get("children", []):
198
- child_block = Block.import_config(child_config)
198
+ child_block = Block.import_config(child_config) # type: ignore
199
199
  setattr(instance, child_block.name.lower(), child_block)
200
200
 
201
201
  return instance
202
202
 
203
- def load_from_config(self, config: dict[str, list[Dict]]) -> None:
203
+ def load_from_config(self, config: dict[str, list[dict]]) -> None:
204
204
  """
205
205
  使用配置更新当前Block实例的参数,并递归更新子Block。
206
206
  """
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: pycityagent
3
- Version: 2.0.0a53
3
+ Version: 2.0.0a55
4
4
  Summary: LLM-based city environment agent building library
5
5
  Author-email: Yuwei Yan <pinkgranite86@gmail.com>, Junbo Yan <yanjb20thu@gmali.com>, Jun Zhang <zhangjun990222@gmali.com>
6
6
  License: MIT License
@@ -45,7 +45,7 @@ Requires-Dist: openai>=1.58.1
45
45
  Requires-Dist: Pillow<12.0.0,>=11.0.0
46
46
  Requires-Dist: protobuf<5.0.0,<=4.24.0
47
47
  Requires-Dist: pycitydata>=1.0.3
48
- Requires-Dist: pycityproto>=2.1.5
48
+ Requires-Dist: pycityproto>=2.2.0
49
49
  Requires-Dist: requests>=2.32.3
50
50
  Requires-Dist: Shapely>=2.0.6
51
51
  Requires-Dist: PyYAML>=6.0.2
@@ -1,25 +1,25 @@
1
- pycityagent-2.0.0a53.dist-info/RECORD,,
2
- pycityagent-2.0.0a53.dist-info/LICENSE,sha256=n2HPXiupinpyHMnIkbCf3OTYd3KMqbmldu1e7av0CAU,1084
3
- pycityagent-2.0.0a53.dist-info/WHEEL,sha256=NW1RskY9zow1Y68W-gXg0oZyBRAugI1JHywIzAIai5o,109
4
- pycityagent-2.0.0a53.dist-info/entry_points.txt,sha256=BZcne49AAIFv-hawxGnPbblea7X3MtAtoPyDX8L4OC4,132
5
- pycityagent-2.0.0a53.dist-info/top_level.txt,sha256=yOmeu6cSXmiUtScu53a3s0p7BGtLMaV0aff83EHCTic,43
6
- pycityagent-2.0.0a53.dist-info/METADATA,sha256=7iSDzvMMlwpY7leIIjVm-3V7lZ92R0uHetTQlk0PCb0,9110
1
+ pycityagent-2.0.0a55.dist-info/RECORD,,
2
+ pycityagent-2.0.0a55.dist-info/LICENSE,sha256=n2HPXiupinpyHMnIkbCf3OTYd3KMqbmldu1e7av0CAU,1084
3
+ pycityagent-2.0.0a55.dist-info/WHEEL,sha256=NW1RskY9zow1Y68W-gXg0oZyBRAugI1JHywIzAIai5o,109
4
+ pycityagent-2.0.0a55.dist-info/entry_points.txt,sha256=BZcne49AAIFv-hawxGnPbblea7X3MtAtoPyDX8L4OC4,132
5
+ pycityagent-2.0.0a55.dist-info/top_level.txt,sha256=yOmeu6cSXmiUtScu53a3s0p7BGtLMaV0aff83EHCTic,43
6
+ pycityagent-2.0.0a55.dist-info/METADATA,sha256=NI-t0FkdHsFWQ4aFpPz0i7Jg0qOS16AGo2IOiMwYG44,9110
7
7
  pycityagent/pycityagent-sim,sha256=1Nu-QYC0AuZyVWciGNa2XkYsUntbwAS15Bo7l-y6eok,35449490
8
8
  pycityagent/__init__.py,sha256=PUKWTXc-xdMG7px8oTNclodsILUgypANj2Z647sY63k,808
9
9
  pycityagent/pycityagent-ui,sha256=cHZjqtrQ4Fh4qtRahFNCNbT2DNHLmUexiDAa-72Z3RQ,40333378
10
- pycityagent/metrics/mlflow_client.py,sha256=g_tHxWkWTDijtbGL74-HmiYzWVKb1y8-w12QrY9jL30,4449
10
+ pycityagent/metrics/mlflow_client.py,sha256=bTrqYsRfNfjJd6l91hU8vN7JXzJC7DHiM2XbkhMuXIU,4613
11
11
  pycityagent/metrics/__init__.py,sha256=X08PaBbGVAd7_PRGLREXWxaqm7nS82WBQpD1zvQzcqc,128
12
12
  pycityagent/metrics/utils/const.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
13
13
  pycityagent/economy/__init__.py,sha256=aonY4WHnx-6EGJ4WKrx4S-2jAkYNLtqUA04jp6q8B7w,75
14
- pycityagent/economy/econ_client.py,sha256=GuHK9ZBnhqW3Z7F8ViDJn_iN73yOBbbwFyJv1wLEBDk,12211
14
+ pycityagent/economy/econ_client.py,sha256=Nf73GPFJgiDbisi8ghmv_Dz6iUlNE2Ey62B-eJ-tQ84,12186
15
15
  pycityagent/tools/__init__.py,sha256=XtdtGyWeFyK1YOUvWkykBWxemtmwQjWUIuuyU1-gosQ,261
16
16
  pycityagent/tools/tool.py,sha256=D-ESFlX7EESm5mcvs2zRlGEQTzXbVfQc8G7Vpz8TmAw,8651
17
17
  pycityagent/llm/llmconfig.py,sha256=4Ylf4OFSBEFy8jrOneeX0HvPhWEaF5jGvy1HkXK08Ro,436
18
18
  pycityagent/llm/__init__.py,sha256=iWs6FLgrbRVIiqOf4ILS89gkVCTvS7HFC3vG-MWuyko,205
19
- pycityagent/llm/llm.py,sha256=owTYuXmnHZnvXaAvwiiyD511P3wpU3K04xZArhhiJF0,15700
19
+ pycityagent/llm/llm.py,sha256=4AJlTj9llT909gzx9SfcBvbUJrWqHzEo3DaHWgQ3-3I,15852
20
20
  pycityagent/llm/embeddings.py,sha256=2_P4TWm3sJKFdGDx2Q1a2AEapFopDctIXsGuntvmP6E,6816
21
21
  pycityagent/llm/utils.py,sha256=hoNPhvomb1u6lhFX0GctFipw74hVKb7bvUBDqwBzBYw,160
22
- pycityagent/memory/memory.py,sha256=suU6mZIYvGySQGyNrYiqdobuTgjSHyI_PahIeRVShiQ,34506
22
+ pycityagent/memory/memory.py,sha256=MusbnD-Us5IF16CkYRSlcer-TEbaPsHxQEYzcugo0N4,34589
23
23
  pycityagent/memory/profile.py,sha256=q8ZS9IBmHCg_X1GONUvXK85P6tCepTKQgXKuvuXYNXw,5203
24
24
  pycityagent/memory/__init__.py,sha256=_Vfdo1HcLWsuuz34_i8e91nnLVYADpMlHHSVaB3xgIk,297
25
25
  pycityagent/memory/memory_base.py,sha256=QG_j3BxZvkadFEeE3uBR_kjl_xcXD1aHUVs8GEF3d6w,5654
@@ -28,31 +28,32 @@ pycityagent/memory/utils.py,sha256=oJWLdPeJy_jcdKcDTo9JAH9kDZhqjoQhhv_zT9qWC0w,8
28
28
  pycityagent/memory/const.py,sha256=6zpJPJXWoH9-yf4RARYYff586agCoud9BRn7sPERB1g,932
29
29
  pycityagent/memory/faiss_query.py,sha256=V3rIw6d1_xcpNqZBbAYz3qfjVNE7NfJ7xOS5SibPtVU,13180
30
30
  pycityagent/memory/state.py,sha256=TYItiyDtehMEQaSBN7PpNrnNxdDM5jGppr9R9Ufv3kA,5134
31
- pycityagent/simulation/simulation.py,sha256=Fm6Y54gc4wAlVhMvqlUhbDRG0tKt6OpHdGsI8as9jqs,29662
31
+ pycityagent/simulation/simulation.py,sha256=hoWOXcc5bqt-_S2MiYrtg2YWuw3A-KlBG9D_kFzk-fU,32936
32
32
  pycityagent/simulation/__init__.py,sha256=P5czbcg2d8S0nbbnsQXFIhwzO4CennAhZM8OmKvAeYw,194
33
- pycityagent/simulation/agentgroup.py,sha256=F1LJq-4xq3E7NmhmBT8j9wsJuuRmU5rGFzNgeOCwOSI,29701
34
- pycityagent/simulation/storage/pg.py,sha256=5itxKOkNPlOzN7z2_3oKU1ZK0uLTDugfld8ZkRbD69I,8407
35
- pycityagent/message/__init__.py,sha256=TCjazxqb5DVwbTu1fF0sNvaH_EPXVuj2XQ0p6W-QCLU,55
36
- pycityagent/message/messager.py,sha256=78K31EPKfC5IxbISc-Lc2babC7VOh9Vbe3c0sO-YDLA,3333
33
+ pycityagent/simulation/agentgroup.py,sha256=ANTQA2OFQpuNZBz2VRhy60pTPUM1lXHFJLzFgK1SvxQ,31633
34
+ pycityagent/simulation/storage/pg.py,sha256=xRshSOGttW-p0re0fNBOjOpb-nQ5msIE2LsdT79_E_Y,8425
35
+ pycityagent/message/message_interceptor.py,sha256=w8XTyZStQtMjILpeAX3VMhAWcYAuaxCgSMwXQU1OryM,8951
36
+ pycityagent/message/__init__.py,sha256=f5QH7DKPqEAMyfSlBMnl3uouOKlsoel909STlIe7nUk,276
37
+ pycityagent/message/messager.py,sha256=8mhTU2bb9K405_lwd9tN2ha7cCQ9m6hPFxf2fYxRjVg,4368
37
38
  pycityagent/utils/avro_schema.py,sha256=AlADbzV8FxiSfvhQhiX9KhrwMjrx0lGT-lED4TI1gJM,4152
38
- pycityagent/utils/__init__.py,sha256=xli0FuRffR9Wp4aRcMnlfeDHuGxB8Y5paDjyAt0UoeE,462
39
- pycityagent/utils/survey_util.py,sha256=Be9nptmu2JtesFNemPgORh_2GsN7rcDYGQS9Zfvc5OI,2169
40
- pycityagent/utils/pg_query.py,sha256=Nm2U1SZtWf6oFeDJV-zLnG0PxyL3xIRTGX1yX3EE-gw,2198
39
+ pycityagent/utils/__init__.py,sha256=GQEa4x_uJBK19Z57vfm9Omvqg1c4ysi3QJ9wx8xiDhI,524
40
+ pycityagent/utils/survey_util.py,sha256=o-gvmmfus3vMIN-EMWPzfLbHkDH4DfZb8B-yBd_mGYk,2076
41
+ pycityagent/utils/pg_query.py,sha256=KAcnBDLyzUu2il18SGXxk8dySdBen_8ejfpxiWuKUMA,2225
41
42
  pycityagent/utils/decorators.py,sha256=Gk3r41hfk6awui40tbwpq3C7wC7jHaRmLRlcJFlLQCE,3160
42
43
  pycityagent/utils/parsers/__init__.py,sha256=AN2xgiPxszWK4rpX7zrqRsqNwfGF3WnCA5-PFTvbaKk,281
43
44
  pycityagent/utils/parsers/code_block_parser.py,sha256=Cs2Z_hm9VfNCpPPll1TwteaJF-HAQPs-3RApsOekFm4,1173
44
45
  pycityagent/utils/parsers/parser_base.py,sha256=KBKO4zLZPNdGjPAGqIus8LseZ8W3Tlt2y0QxqeCd25Q,1713
45
46
  pycityagent/utils/parsers/json_parser.py,sha256=tjwyPluYfkWgsvLi0hzfJwFhO3L6yQfZMKza20HaGrY,2911
46
- pycityagent/agent/agent_base.py,sha256=FP2h3abIQ1Kp9qCzrzwa7tO82graDAWVg30HqYaQcPE,23620
47
+ pycityagent/agent/agent_base.py,sha256=vC1nMWahwi_nVBUXVdC1CnZpqimKZApixD2m2Iqu_bg,24196
47
48
  pycityagent/agent/__init__.py,sha256=U20yKu9QwSqAx_PHk5JwipfODkDfxONtumVfnsKjWFg,180
48
- pycityagent/agent/agent.py,sha256=rYUC6idFb2dCRa7H7-0ZFPn4UB7MSTigHXOjNSK5B2Y,10702
49
- pycityagent/cli/wrapper.py,sha256=2Tb52gOlEVgn11Ekt6ZkRXr_BGzte-EPyBKnR6g6hQ4,1143
49
+ pycityagent/agent/agent.py,sha256=FNon_OPvGrh976AEHpaAQyLQN7erbGOX-BxGnCVZza8,12038
50
+ pycityagent/cli/wrapper.py,sha256=9aG6D2cnmh6aIhiVXKPGKuMjVcdAa-TwzANudb2q_FU,1147
50
51
  pycityagent/workflow/__init__.py,sha256=H08Ko3eliZvuuCMajbEri-IP4-SeswYU6UjHBNA4Ze0,490
51
52
  pycityagent/workflow/prompt.py,sha256=6jI0Rq54JLv3-IXqZLYug62vse10wTI83xvf4ZX42nk,2929
52
- pycityagent/workflow/block.py,sha256=REetWNdCF_fUGKVH-LWgDZ1lK2Bt0tJJ0kV20eWa4_A,9890
53
+ pycityagent/workflow/block.py,sha256=4QufS8XnyP6SYp8g1gDODW-H0nAHA7lvivrPGUq1p-w,9922
53
54
  pycityagent/workflow/trigger.py,sha256=Df-MOBEDWBbM-v0dFLQLXteLsipymT4n8vqexmK2GiQ,5643
54
- pycityagent/environment/__init__.py,sha256=awHxlOud-btWbk0FCS4RmGJ13W84oVCkbGfcrhKqihA,240
55
- pycityagent/environment/simulator.py,sha256=pARK08PzqiAysy6VOR2KZAgEG7auVzt_Tecy5MBL55Q,12157
55
+ pycityagent/environment/__init__.py,sha256=MyZBwsweDIHOKSX2iSZs748foNtaiyEcyg6sc747T2g,263
56
+ pycityagent/environment/simulator.py,sha256=gqkECMzhXRh4WHTyLFEL1_X1R7F1aX4g9881zUFv7DI,12136
56
57
  pycityagent/environment/message/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
57
58
  pycityagent/environment/utils/port.py,sha256=3OM6kSUt3PxvDUOlgyiendBtETaWU8Mzk_8H0TzTmYg,295
58
59
  pycityagent/environment/utils/grpc.py,sha256=6EJwKXXktIWb1NcUiJzIRmfrY0S03QAXXGcCDHqAT00,1998
@@ -69,7 +70,7 @@ pycityagent/environment/sidecar/sidecarv2.py,sha256=beKlYZgt38EQbV1x6NWQo7xVXyB-
69
70
  pycityagent/environment/sim/pause_service.py,sha256=DcAOVRxNkHGk4jyzFkxHMUPgp0Ck4mYHoPh6qxjhhLQ,1744
70
71
  pycityagent/environment/sim/person_service.py,sha256=5r1F2Itn7dKJ2U4hSLovrk5p4qy-2n77MTAv_OlTIwA,10673
71
72
  pycityagent/environment/sim/aoi_service.py,sha256=2UjvUTF4CW4E_L30IRcdwv6t_q1ZdXN3TTLOKSOaaXE,1230
72
- pycityagent/environment/sim/sim_env.py,sha256=HI1LcS_FotDKQ6vBnx0e49prXSABOfA20aU9KM-ZkCY,4625
73
+ pycityagent/environment/sim/sim_env.py,sha256=V3Pf_nsebs07-ZaXPSCaA1HBGv4n7v8yxMz6GKQaZPk,3908
73
74
  pycityagent/environment/sim/lane_service.py,sha256=N2dUe-3XuqqKLsNXt1k4NN8uV-J_ruo08yhaUd_hwOI,3916
74
75
  pycityagent/environment/sim/client.py,sha256=j0f8qjR1nIava4VkoZNEPqW5h08WPdcC5wzM9DP3tIs,3772
75
76
  pycityagent/environment/sim/__init__.py,sha256=JVG6sSD2Hbohl1TtKjuQi7_M7tKMrFh9vl3QV3VA5O0,724
@@ -86,7 +87,8 @@ pycityagent/cityagent/__init__.py,sha256=gcBQ-a50XegFtjigQ7xDXRBZrywBKqifiQFSRnE
86
87
  pycityagent/cityagent/firmagent.py,sha256=UVlNN0lpa4cC4PZVqYzQhbc5VJ2oGsA1731mhbCjnR8,4109
87
88
  pycityagent/cityagent/nbsagent.py,sha256=WIXW__6dZ5IrqBqDCjvGbrCshpXzuFRV3Ww6gkYw7p4,4387
88
89
  pycityagent/cityagent/initial.py,sha256=7hgCt_tGdnVTXGfEQOn1GTW5dAs1b-ru_FwXxRLI6tM,4549
89
- pycityagent/cityagent/societyagent.py,sha256=QKzZecyN5npMi2IJlxei9MrJ1yJWJPCogXrNIP1VnFQ,19598
90
+ pycityagent/cityagent/societyagent.py,sha256=vvFGAr8wlZ82f4qHvpawa1VsHungDegjKn1E51bDUnc,24767
91
+ pycityagent/cityagent/message_intercept.py,sha256=HiNOtBXKq40LCmvsw2KMLxMsbmXSVcbRytAO-eI-1sU,3279
90
92
  pycityagent/cityagent/governmentagent.py,sha256=HJLuhvEmllu_1KnFEJsYCIasaBJT0BV9Cn_4Y2QGPqg,2791
91
93
  pycityagent/cityagent/blocks/dispatcher.py,sha256=mEa1r3tRS3KI1BMZR_w_sbUGzOj6aUJuiUrsHv1n2n0,2943
92
94
  pycityagent/cityagent/blocks/needs_block.py,sha256=s8LikgtKORfo_Sw9SQ5_3biNPTof15QuUs4cDynXCyM,15332
@@ -96,7 +98,7 @@ pycityagent/cityagent/blocks/__init__.py,sha256=wydR0s-cCRWgdvQetkfQnD_PU8vC3eTm
96
98
  pycityagent/cityagent/blocks/economy_block.py,sha256=m5B67cgGZ9nKWtrYeak5gxMoCoKlRbATAsXpFajYKyg,19129
97
99
  pycityagent/cityagent/blocks/utils.py,sha256=8O5p1B8JlreIJTGXKAP03rTcn7MvFSR8qJ1_hhszboU,2065
98
100
  pycityagent/cityagent/blocks/other_block.py,sha256=NnDwxQAO5XZ7Uxe-n3qtrfNItHlwFYk2MQsh2GYDKMQ,4338
99
- pycityagent/cityagent/blocks/plan_block.py,sha256=Mtbc26xZjx-HpmBYZD12rVNK09WgDPCkwLseLiJ1mS0,10995
101
+ pycityagent/cityagent/blocks/plan_block.py,sha256=YEU0pHK_fB1lvvml9u7bGz-2bzM2axE9jW-aSgPYs6M,10996
100
102
  pycityagent/cityagent/blocks/mobility_block.py,sha256=xWbARMfJ3-6fddrW3VOUKJrXfMGmroiSN0B8t8lVYXA,12725
101
103
  pycityagent/survey/models.py,sha256=YE50UUt5qJ0O_lIUsSY6XFCGUTkJVNu_L1gAhaCJ2fs,3546
102
104
  pycityagent/survey/__init__.py,sha256=rxwou8U9KeFSP7rMzXtmtp2fVFZxK4Trzi-psx9LPIs,153