pycoze 0.1.439__py3-none-any.whl → 0.1.441__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
pycoze/api/lib/web.py CHANGED
@@ -1,4 +1,5 @@
1
1
  from pycoze import utils
2
+ from bs4 import BeautifulSoup, Comment
2
3
 
3
4
 
4
5
  socket = utils.socket
@@ -10,7 +11,55 @@ class WebCls:
10
11
  "getSimplifiedWebpage", {"url": url}
11
12
  )
12
13
 
13
- def get_simplified_html(self, html: str) -> str:
14
- return socket.post_and_recv_result(
15
- "getSimplifiedHtml", {"html": html}
16
- )
14
+ def get_simplified_html(self, html: str, selector=None) -> str:
15
+ soup = BeautifulSoup(html, 'html.parser')
16
+
17
+ # 如果指定了selector,则只提取该元素的内容
18
+ if selector:
19
+ element = soup.select_one(selector)
20
+ if element:
21
+ soup = BeautifulSoup(str(element), 'html.parser')
22
+
23
+ # 定义需要移除的标签
24
+ tags_to_remove = ['script', 'style', 'noscript', 'meta', 'link']
25
+ for tag in tags_to_remove:
26
+ for element in soup(tag):
27
+ element.decompose()
28
+
29
+ # 移除注释
30
+ for element in soup.find_all(string=lambda text: isinstance(text, Comment)):
31
+ element.extract()
32
+
33
+ # 定义需要保留的交互属性
34
+ INTERACTIVE_ATTRIBUTES = {
35
+ 'a': ['href', 'onclick'],
36
+ 'button': ['onclick'],
37
+ 'img': ['src', 'onload'],
38
+ 'form': ['action', 'onsubmit'],
39
+ 'input': ['type', 'onclick', 'onchange'],
40
+ '*': ['onclick', 'onload', 'onchange', 'onsubmit', 'onmouseover']
41
+ }
42
+
43
+ # 遍历所有标签,保留交互属性并移除其他属性
44
+ for element in soup.find_all(True):
45
+ tag_name = element.name
46
+ allowed_attrs = INTERACTIVE_ATTRIBUTES.get(tag_name, []) + INTERACTIVE_ATTRIBUTES['*']
47
+ attrs = list(element.attrs.keys())
48
+ for attr in attrs:
49
+ if attr not in allowed_attrs:
50
+ del element[attr]
51
+
52
+ # 如果是<img>标签,检查src是否为Base64
53
+ if tag_name == 'img' and 'src' in element.attrs and element['src'].startswith('data:'):
54
+ del element['src']
55
+
56
+ # 处理文本内容,超过1000字符则截取
57
+ if element.string and len(element.string) > 1000:
58
+ element.string = element.string[:1000] + '...'
59
+
60
+ # 移除标签之间的多余空白
61
+ for element in soup.find_all(True):
62
+ if not element.get_text(strip=True):
63
+ element.string = ''
64
+
65
+ return str(soup)
pycoze/bot/chat.py CHANGED
@@ -8,7 +8,7 @@ from pycoze import utils
8
8
  import tempfile
9
9
  import re
10
10
  import datetime
11
- from pathlib import Path
11
+ import atexit
12
12
 
13
13
 
14
14
  def eclipse_tool_result(text, threshold=100):
@@ -78,6 +78,10 @@ async def run_with_interrupt_check(
78
78
  check_task = asyncio.create_task(
79
79
  check_interrupt_file(0.5, interrupt_file, chat_task)
80
80
  )
81
+ def cleanup():
82
+ chat_task.cancel()
83
+ check_task.cancel()
84
+ atexit.register(cleanup)
81
85
  result = await chat_task
82
86
  return result
83
87
  except asyncio.CancelledError:
pycoze/bot/chat_base.py CHANGED
@@ -300,8 +300,7 @@ async def handle_user_inputs(
300
300
  )
301
301
 
302
302
  assistant_content = (
303
- "Executing tool: \n"
304
- + dumps_markdown_json(tool_request)
303
+ dumps_markdown_json(tool_request)
305
304
  + "\n\n[Tool Result Begin]\n"
306
305
  + result
307
306
  + "\n[Tool Result End]\n"
pycoze/bot/lib.py CHANGED
@@ -66,10 +66,8 @@ def get_system_prompt(abilities, bot_setting):
66
66
  cd_prompt = "When executing outside the working directory, include the CD command, such as cd /path/to/directory && ls."
67
67
  system = platform.system()
68
68
 
69
- print("bot_setting", bot_setting)
70
- print("abilities", abilities)
69
+
71
70
  abilities_str = "\n".join([function_to_string(a) for a in abilities])
72
- print("abilities_str", abilities_str)
73
71
 
74
72
  context = {
75
73
  "prompt": bot_setting["prompt"],
@@ -96,7 +94,7 @@ def get_system_prompt(abilities, bot_setting):
96
94
  if key != "folder_context" and bot_setting["systemAbility"][key] == True:
97
95
  has_any_tool = True
98
96
  break
99
-
97
+
100
98
  context["has_any_tool"] = has_any_tool
101
99
  system_prompt = template.render(context)
102
100
 
pycoze/bot/tools.py CHANGED
@@ -132,17 +132,38 @@ class ReplaceInFileTool(Tool):
132
132
  with open(path, "r", encoding="utf-8") as f:
133
133
  content = f.read()
134
134
 
135
+ # 初始化成功和失败的计数器
136
+ success_count = 0
137
+ failure_count = 0
138
+ failure_details = [] # 用于记录匹配失败的详细信息
139
+
135
140
  # 处理差异内容
136
141
  diff_content = self.params["diff"]
137
142
  for diff_block in diff_content.split("<<<<<<< SEARCH")[1:]:
138
143
  search, replace = diff_block.split("=======")
139
144
  search = search.strip()
140
145
  replace = replace.split(">>>>>>> REPLACE")[0].strip()
141
- content = content.replace(search, replace, 1)
146
+ if search in content:
147
+ content = content.replace(search, replace, 1)
148
+ success_count += 1
149
+ else:
150
+ failure_count += 1
151
+ # 记录匹配失败的前20个字符
152
+ failure_details.append(f"Failed to match: '{search[:20]}...'")
142
153
 
143
154
  with open(path, "w", encoding="utf-8") as f:
144
155
  f.write(content)
145
- return f"The content of the file {path} has been replaced successfully."
156
+
157
+ # 构建返回结果
158
+ result = (
159
+ f"The content of the file {path} has been replaced successfully. "
160
+ f"Successfully replaced {success_count} occurrences. "
161
+ f"Failed to replace {failure_count} occurrences."
162
+ )
163
+ if failure_details:
164
+ result += "\nFailure details:\n" + "\n".join(failure_details)
165
+
166
+ return result
146
167
 
147
168
 
148
169
  class SearchFilesTool(Tool):
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: pycoze
3
- Version: 0.1.439
3
+ Version: 0.1.441
4
4
  Summary: Package for pycoze only!
5
5
  Author: Yuan Jie Xiong
6
6
  Author-email: aiqqqqqqq@qq.com
@@ -7,15 +7,15 @@ pycoze/api/__init__.py,sha256=TLKvaZlRzTTt0KiXijLjj9b_iCr7fU1siwsXqyd74b8,375
7
7
  pycoze/api/lib/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
8
8
  pycoze/api/lib/tab.py,sha256=DWO8ElI-VOODtIxqUFWaDB8VRrrFYAZRWivuIeD1wG0,2619
9
9
  pycoze/api/lib/view.py,sha256=_PIpTfeuTPPlMDKshMGsqFQYMq7ZiO4Hg5XwHwDoU60,7357
10
- pycoze/api/lib/web.py,sha256=gR2Ffaj3Pk4NfnE314UTLfZm7rW_rizZxWVDcZMeFgs,382
10
+ pycoze/api/lib/web.py,sha256=l56koyd7RUzK-4mQE_5W-POyqSD79mvwusIN0rxND-Q,2347
11
11
  pycoze/api/lib/window.py,sha256=dkzWfLwn5pE_L0DfQ38K8nx9tQyT5KO-GYyXi0rytFc,2073
12
12
  pycoze/bot/__init__.py,sha256=rL3Q-ycczRpSFfKn84fg3QBl5k22WpyeIU5qOEjEby8,79
13
- pycoze/bot/chat.py,sha256=qEuMxH0cVFU9QSU36FrOsjhRAxtsvOv7CQtuXvM3F6Y,6446
14
- pycoze/bot/chat_base.py,sha256=uwAVhhvpKHQytJYMsIOHsTThkr45xRehbXF0-kDbvjM,12614
15
- pycoze/bot/lib.py,sha256=-9zeP2GMxUtyxBbBUwU3VEybalzZnNZGOROImWftJ7E,7311
13
+ pycoze/bot/chat.py,sha256=bScsMc0hGh2NlvhQxzWEbnA_WXU9JdAJv-rx27SpEB8,6554
14
+ pycoze/bot/chat_base.py,sha256=I_QOB22Ud1HpBDg8kip9AW4stGbbLOrKpZPSMCHEMAE,12567
15
+ pycoze/bot/lib.py,sha256=_bQ52mKsWgFGAogFHnmRBJbvK_tPOwsAJ8NqJNMR5K4,7210
16
16
  pycoze/bot/message.py,sha256=udnIi-h4QgGzkbr_5VcAsVGjoLp9wXJSfBCeuOz7_Bk,802
17
17
  pycoze/bot/prompt.md,sha256=t7NQdiiNe-jCDVfeVbvTPfq5WK5nF8CxFUQUFMyXJlo,13880
18
- pycoze/bot/tools.py,sha256=uFvGIQ4VzkiH-TM9U9RenWfYVYyeUv_bP-094hB9rTc,10367
18
+ pycoze/bot/tools.py,sha256=BWMdwvqLzvcyaW38lzxUWtc0K1V-C_qPSEZ3OKlAQvU,11108
19
19
  pycoze/reference/__init__.py,sha256=zgqGqvmA9HaqytEM33B6vi0kQVk8IiCwJaXa22xsFz8,114
20
20
  pycoze/reference/bot.py,sha256=UZK24Qm8kpqpwXJy_zNZeTEEDee05luXdSBeUm0NCt0,2029
21
21
  pycoze/reference/lib.py,sha256=T-oBOKxkus5dTouc0oDgfRzUyi6aTyY-FF4yX7SzF5M,3755
@@ -31,8 +31,8 @@ pycoze/utils/arg.py,sha256=jop1tBfe5hYkHW1NSpCeaZBEznkgguBscj_7M2dWfrs,503
31
31
  pycoze/utils/env.py,sha256=5pWlXfM1F5ZU9hhv1rHlDEanjEW5wf0nbyez9bNRqqA,559
32
32
  pycoze/utils/socket.py,sha256=bZbFFRH4mfThzRqt55BAAGQ6eICx_ja4x8UGGrUdAm8,2428
33
33
  pycoze/utils/text_or_file.py,sha256=gpxZVWt2DW6YiEg_MnMuwg36VNf3TX383QD_1oZNB0Y,551
34
- pycoze-0.1.439.dist-info/LICENSE,sha256=QStd_Qsd0-kAam_-sOesCIp_uKrGWeoKwt9M49NVkNU,1090
35
- pycoze-0.1.439.dist-info/METADATA,sha256=Dt-scKTwLVWtUToYmBJDaL-i1oJEl8U2vI1o-Rt7Mr0,854
36
- pycoze-0.1.439.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
37
- pycoze-0.1.439.dist-info/top_level.txt,sha256=76dPeDhKvOCleL3ZC5gl1-y4vdS1tT_U1hxWVAn7sFo,7
38
- pycoze-0.1.439.dist-info/RECORD,,
34
+ pycoze-0.1.441.dist-info/LICENSE,sha256=QStd_Qsd0-kAam_-sOesCIp_uKrGWeoKwt9M49NVkNU,1090
35
+ pycoze-0.1.441.dist-info/METADATA,sha256=hcD7MM_qfiSIrfLURPH8qxnJqJnK6DtcbG0jnAhanfE,854
36
+ pycoze-0.1.441.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
37
+ pycoze-0.1.441.dist-info/top_level.txt,sha256=76dPeDhKvOCleL3ZC5gl1-y4vdS1tT_U1hxWVAn7sFo,7
38
+ pycoze-0.1.441.dist-info/RECORD,,