pygpt-net 2.6.20__py3-none-any.whl → 2.6.22__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.
Files changed (221) hide show
  1. pygpt_net/CHANGELOG.txt +13 -0
  2. pygpt_net/__init__.py +3 -3
  3. pygpt_net/app.py +3 -1
  4. pygpt_net/controller/__init__.py +4 -8
  5. pygpt_net/controller/access/voice.py +2 -2
  6. pygpt_net/controller/agent/agent.py +130 -2
  7. pygpt_net/controller/agent/experts.py +93 -96
  8. pygpt_net/controller/agent/llama.py +2 -1
  9. pygpt_net/controller/assistant/assistant.py +18 -1
  10. pygpt_net/controller/assistant/batch.py +2 -3
  11. pygpt_net/controller/assistant/editor.py +2 -2
  12. pygpt_net/controller/assistant/files.py +2 -3
  13. pygpt_net/controller/assistant/store.py +2 -2
  14. pygpt_net/controller/attachment/attachment.py +17 -1
  15. pygpt_net/controller/audio/audio.py +2 -2
  16. pygpt_net/controller/camera/camera.py +15 -7
  17. pygpt_net/controller/chat/chat.py +2 -2
  18. pygpt_net/controller/chat/common.py +50 -33
  19. pygpt_net/controller/chat/image.py +67 -77
  20. pygpt_net/controller/chat/input.py +94 -166
  21. pygpt_net/controller/chat/output.py +83 -140
  22. pygpt_net/controller/chat/response.py +83 -102
  23. pygpt_net/controller/chat/text.py +116 -149
  24. pygpt_net/controller/ctx/common.py +2 -1
  25. pygpt_net/controller/ctx/ctx.py +87 -6
  26. pygpt_net/controller/files/files.py +13 -1
  27. pygpt_net/controller/idx/idx.py +26 -2
  28. pygpt_net/controller/idx/indexer.py +85 -76
  29. pygpt_net/controller/kernel/reply.py +53 -66
  30. pygpt_net/controller/kernel/stack.py +16 -16
  31. pygpt_net/controller/lang/lang.py +52 -34
  32. pygpt_net/controller/model/importer.py +3 -2
  33. pygpt_net/controller/model/model.py +62 -3
  34. pygpt_net/controller/notepad/notepad.py +86 -84
  35. pygpt_net/controller/plugins/settings.py +3 -4
  36. pygpt_net/controller/settings/editor.py +4 -4
  37. pygpt_net/controller/settings/profile.py +105 -124
  38. pygpt_net/controller/theme/menu.py +154 -57
  39. pygpt_net/controller/theme/nodes.py +51 -44
  40. pygpt_net/controller/theme/theme.py +33 -9
  41. pygpt_net/controller/tools/tools.py +2 -2
  42. pygpt_net/controller/ui/tabs.py +2 -3
  43. pygpt_net/controller/ui/ui.py +16 -2
  44. pygpt_net/core/agents/observer/evaluation.py +3 -3
  45. pygpt_net/core/agents/provider.py +25 -3
  46. pygpt_net/core/agents/runner.py +4 -1
  47. pygpt_net/core/agents/runners/llama_workflow.py +19 -7
  48. pygpt_net/core/agents/runners/loop.py +3 -1
  49. pygpt_net/core/agents/runners/openai_workflow.py +17 -3
  50. pygpt_net/core/agents/tools.py +4 -1
  51. pygpt_net/core/bridge/context.py +34 -37
  52. pygpt_net/core/ctx/container.py +13 -12
  53. pygpt_net/core/ctx/ctx.py +1 -1
  54. pygpt_net/core/ctx/output.py +7 -4
  55. pygpt_net/core/db/database.py +2 -2
  56. pygpt_net/core/debug/console/console.py +2 -2
  57. pygpt_net/core/debug/debug.py +12 -1
  58. pygpt_net/core/dispatcher/dispatcher.py +24 -1
  59. pygpt_net/core/events/app.py +7 -7
  60. pygpt_net/core/events/control.py +26 -26
  61. pygpt_net/core/events/event.py +6 -3
  62. pygpt_net/core/events/kernel.py +2 -2
  63. pygpt_net/core/events/render.py +13 -13
  64. pygpt_net/core/experts/experts.py +76 -82
  65. pygpt_net/core/experts/worker.py +12 -12
  66. pygpt_net/core/filesystem/actions.py +1 -2
  67. pygpt_net/core/models/models.py +5 -1
  68. pygpt_net/core/models/ollama.py +14 -5
  69. pygpt_net/core/render/plain/helpers.py +2 -5
  70. pygpt_net/core/render/plain/renderer.py +26 -30
  71. pygpt_net/core/render/web/body.py +1 -1
  72. pygpt_net/core/render/web/helpers.py +2 -2
  73. pygpt_net/core/render/web/renderer.py +4 -4
  74. pygpt_net/core/settings/settings.py +43 -13
  75. pygpt_net/core/tabs/tabs.py +20 -13
  76. pygpt_net/core/types/__init__.py +2 -1
  77. pygpt_net/core/types/agent.py +4 -4
  78. pygpt_net/core/types/base.py +19 -0
  79. pygpt_net/core/types/console.py +6 -6
  80. pygpt_net/core/types/mode.py +8 -8
  81. pygpt_net/core/types/multimodal.py +3 -3
  82. pygpt_net/core/types/openai.py +2 -1
  83. pygpt_net/data/config/config.json +5 -5
  84. pygpt_net/data/config/models.json +19 -3
  85. pygpt_net/data/config/settings.json +14 -14
  86. pygpt_net/data/locale/locale.de.ini +4 -1
  87. pygpt_net/data/locale/locale.en.ini +6 -3
  88. pygpt_net/data/locale/locale.es.ini +4 -1
  89. pygpt_net/data/locale/locale.fr.ini +4 -1
  90. pygpt_net/data/locale/locale.it.ini +4 -1
  91. pygpt_net/data/locale/locale.pl.ini +5 -4
  92. pygpt_net/data/locale/locale.uk.ini +4 -1
  93. pygpt_net/data/locale/locale.zh.ini +4 -1
  94. pygpt_net/item/ctx.py +256 -240
  95. pygpt_net/item/model.py +59 -116
  96. pygpt_net/item/preset.py +122 -105
  97. pygpt_net/plugin/twitter/plugin.py +2 -2
  98. pygpt_net/provider/agents/llama_index/workflow/planner.py +3 -3
  99. pygpt_net/provider/agents/openai/agent.py +4 -12
  100. pygpt_net/provider/agents/openai/agent_b2b.py +10 -15
  101. pygpt_net/provider/agents/openai/agent_planner.py +4 -4
  102. pygpt_net/provider/agents/openai/agent_with_experts.py +3 -7
  103. pygpt_net/provider/agents/openai/agent_with_experts_feedback.py +4 -8
  104. pygpt_net/provider/agents/openai/agent_with_feedback.py +4 -8
  105. pygpt_net/provider/agents/openai/bot_researcher.py +2 -18
  106. pygpt_net/provider/agents/openai/bots/__init__.py +0 -0
  107. pygpt_net/provider/agents/openai/bots/research_bot/__init__.py +0 -0
  108. pygpt_net/provider/agents/openai/bots/research_bot/agents/__init__.py +0 -0
  109. pygpt_net/provider/agents/openai/bots/research_bot/agents/planner_agent.py +1 -1
  110. pygpt_net/provider/agents/openai/bots/research_bot/agents/search_agent.py +1 -0
  111. pygpt_net/provider/agents/openai/bots/research_bot/agents/writer_agent.py +1 -1
  112. pygpt_net/provider/agents/openai/bots/research_bot/manager.py +1 -10
  113. pygpt_net/provider/agents/openai/evolve.py +5 -9
  114. pygpt_net/provider/agents/openai/supervisor.py +4 -8
  115. pygpt_net/provider/core/config/patch.py +10 -3
  116. pygpt_net/provider/core/ctx/db_sqlite/utils.py +43 -43
  117. pygpt_net/provider/core/model/patch.py +11 -1
  118. pygpt_net/provider/core/preset/json_file.py +47 -49
  119. pygpt_net/provider/gpt/agents/experts.py +2 -2
  120. pygpt_net/tools/audio_transcriber/ui/dialogs.py +44 -54
  121. pygpt_net/tools/code_interpreter/body.py +1 -2
  122. pygpt_net/tools/code_interpreter/tool.py +7 -4
  123. pygpt_net/tools/code_interpreter/ui/html.py +1 -3
  124. pygpt_net/tools/code_interpreter/ui/widgets.py +2 -3
  125. pygpt_net/tools/html_canvas/ui/widgets.py +1 -3
  126. pygpt_net/tools/image_viewer/ui/dialogs.py +40 -37
  127. pygpt_net/tools/indexer/ui/widgets.py +2 -4
  128. pygpt_net/tools/media_player/tool.py +2 -5
  129. pygpt_net/tools/media_player/ui/widgets.py +60 -36
  130. pygpt_net/tools/text_editor/ui/widgets.py +18 -19
  131. pygpt_net/tools/translator/ui/widgets.py +39 -35
  132. pygpt_net/ui/base/context_menu.py +9 -4
  133. pygpt_net/ui/dialog/db.py +1 -3
  134. pygpt_net/ui/dialog/models.py +1 -3
  135. pygpt_net/ui/dialog/models_importer.py +2 -4
  136. pygpt_net/ui/dialogs.py +34 -30
  137. pygpt_net/ui/layout/chat/attachments.py +72 -84
  138. pygpt_net/ui/layout/chat/attachments_ctx.py +40 -44
  139. pygpt_net/ui/layout/chat/attachments_uploaded.py +36 -39
  140. pygpt_net/ui/layout/chat/calendar.py +100 -70
  141. pygpt_net/ui/layout/chat/chat.py +23 -17
  142. pygpt_net/ui/layout/chat/input.py +95 -118
  143. pygpt_net/ui/layout/chat/output.py +100 -162
  144. pygpt_net/ui/layout/chat/painter.py +89 -61
  145. pygpt_net/ui/layout/ctx/ctx_list.py +43 -52
  146. pygpt_net/ui/layout/status.py +23 -14
  147. pygpt_net/ui/layout/toolbox/agent.py +27 -38
  148. pygpt_net/ui/layout/toolbox/agent_llama.py +42 -45
  149. pygpt_net/ui/layout/toolbox/assistants.py +42 -38
  150. pygpt_net/ui/layout/toolbox/computer_env.py +32 -23
  151. pygpt_net/ui/layout/toolbox/footer.py +13 -16
  152. pygpt_net/ui/layout/toolbox/image.py +18 -21
  153. pygpt_net/ui/layout/toolbox/indexes.py +46 -89
  154. pygpt_net/ui/layout/toolbox/mode.py +20 -7
  155. pygpt_net/ui/layout/toolbox/model.py +12 -10
  156. pygpt_net/ui/layout/toolbox/presets.py +68 -52
  157. pygpt_net/ui/layout/toolbox/prompt.py +31 -58
  158. pygpt_net/ui/layout/toolbox/toolbox.py +25 -21
  159. pygpt_net/ui/layout/toolbox/vision.py +20 -22
  160. pygpt_net/ui/main.py +2 -4
  161. pygpt_net/ui/menu/about.py +64 -84
  162. pygpt_net/ui/menu/audio.py +87 -63
  163. pygpt_net/ui/menu/config.py +121 -127
  164. pygpt_net/ui/menu/debug.py +69 -76
  165. pygpt_net/ui/menu/file.py +32 -35
  166. pygpt_net/ui/menu/menu.py +2 -3
  167. pygpt_net/ui/menu/plugins.py +69 -33
  168. pygpt_net/ui/menu/theme.py +45 -46
  169. pygpt_net/ui/menu/tools.py +56 -60
  170. pygpt_net/ui/menu/video.py +20 -25
  171. pygpt_net/ui/tray.py +1 -2
  172. pygpt_net/ui/widget/audio/bar.py +1 -3
  173. pygpt_net/ui/widget/audio/input_button.py +3 -4
  174. pygpt_net/ui/widget/calendar/select.py +1 -2
  175. pygpt_net/ui/widget/dialog/base.py +12 -9
  176. pygpt_net/ui/widget/dialog/editor_file.py +20 -23
  177. pygpt_net/ui/widget/dialog/find.py +25 -24
  178. pygpt_net/ui/widget/dialog/profile.py +57 -53
  179. pygpt_net/ui/widget/draw/painter.py +62 -93
  180. pygpt_net/ui/widget/element/button.py +42 -30
  181. pygpt_net/ui/widget/element/checkbox.py +23 -15
  182. pygpt_net/ui/widget/element/group.py +6 -5
  183. pygpt_net/ui/widget/element/labels.py +1 -2
  184. pygpt_net/ui/widget/filesystem/explorer.py +93 -102
  185. pygpt_net/ui/widget/image/display.py +1 -2
  186. pygpt_net/ui/widget/lists/assistant.py +1 -2
  187. pygpt_net/ui/widget/lists/attachment.py +1 -2
  188. pygpt_net/ui/widget/lists/attachment_ctx.py +1 -2
  189. pygpt_net/ui/widget/lists/context.py +2 -4
  190. pygpt_net/ui/widget/lists/index.py +1 -2
  191. pygpt_net/ui/widget/lists/model.py +1 -2
  192. pygpt_net/ui/widget/lists/model_editor.py +1 -2
  193. pygpt_net/ui/widget/lists/model_importer.py +1 -2
  194. pygpt_net/ui/widget/lists/preset.py +1 -2
  195. pygpt_net/ui/widget/lists/preset_plugins.py +1 -2
  196. pygpt_net/ui/widget/lists/profile.py +1 -2
  197. pygpt_net/ui/widget/lists/uploaded.py +1 -2
  198. pygpt_net/ui/widget/option/checkbox.py +2 -4
  199. pygpt_net/ui/widget/option/checkbox_list.py +1 -4
  200. pygpt_net/ui/widget/option/cmd.py +1 -4
  201. pygpt_net/ui/widget/option/dictionary.py +25 -28
  202. pygpt_net/ui/widget/option/input.py +1 -3
  203. pygpt_net/ui/widget/tabs/Input.py +16 -12
  204. pygpt_net/ui/widget/tabs/body.py +5 -3
  205. pygpt_net/ui/widget/tabs/layout.py +36 -25
  206. pygpt_net/ui/widget/tabs/output.py +96 -74
  207. pygpt_net/ui/widget/textarea/calendar_note.py +1 -2
  208. pygpt_net/ui/widget/textarea/editor.py +41 -73
  209. pygpt_net/ui/widget/textarea/find.py +11 -10
  210. pygpt_net/ui/widget/textarea/html.py +3 -6
  211. pygpt_net/ui/widget/textarea/input.py +63 -64
  212. pygpt_net/ui/widget/textarea/notepad.py +54 -38
  213. pygpt_net/ui/widget/textarea/output.py +65 -54
  214. pygpt_net/ui/widget/textarea/search_input.py +5 -4
  215. pygpt_net/ui/widget/textarea/web.py +2 -4
  216. pygpt_net/ui/widget/vision/camera.py +2 -31
  217. {pygpt_net-2.6.20.dist-info → pygpt_net-2.6.22.dist-info}/METADATA +25 -154
  218. {pygpt_net-2.6.20.dist-info → pygpt_net-2.6.22.dist-info}/RECORD +218 -217
  219. {pygpt_net-2.6.20.dist-info → pygpt_net-2.6.22.dist-info}/LICENSE +0 -0
  220. {pygpt_net-2.6.20.dist-info → pygpt_net-2.6.22.dist-info}/WHEEL +0 -0
  221. {pygpt_net-2.6.20.dist-info → pygpt_net-2.6.22.dist-info}/entry_points.txt +0 -0
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.08.01 19:00:00 #
9
+ # Updated Date: 2025.08.23 15:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  import json
@@ -22,32 +22,32 @@ class BridgeContext:
22
22
 
23
23
  :param kwargs: keyword arguments
24
24
  """
25
+ self.assistant_id = kwargs.get("assistant_id", "")
26
+ self.attachments = kwargs.get("attachments", [])
25
27
  self.ctx = kwargs.get("ctx", None)
28
+ self.external_functions = kwargs.get("external_functions", [])
29
+ self.file_ids = kwargs.get("file_ids", [])
30
+ self.force = kwargs.get("force", False) # Force mode flag
31
+ self.force_sync = kwargs.get("force_sync", False) # Force sync flag
26
32
  self.history = kwargs.get("history", [])
33
+ self.idx = kwargs.get("idx", None)
34
+ self.idx_mode = kwargs.get("idx_mode", "chat")
35
+ self.is_expert_call = kwargs.get("is_expert_call", False) # Expert call flag
36
+ self.max_tokens = kwargs.get("max_tokens", 0)
27
37
  self.mode = kwargs.get("mode", None)
28
- self.parent_mode = kwargs.get("parent_mode", None) # real mode (global)
29
38
  self.model = kwargs.get("model", None) # model instance, not model name
30
- self.temperature = kwargs.get("temperature", 1.0)
39
+ self.multimodal_ctx = kwargs.get("multimodal_ctx", MultimodalContext()) # AudioContext
40
+ self.parent_mode = kwargs.get("parent_mode", None) # real mode (global)
41
+ self.preset = kwargs.get("preset", None) # PresetItem
31
42
  self.prompt = kwargs.get("prompt", "")
43
+ self.reply_context = kwargs.get("reply_ctx", None) # ReplyContext
44
+ self.request = kwargs.get("request", False) # Use normal request instead of quick call
45
+ self.stream = kwargs.get("stream", False)
32
46
  self.system_prompt = kwargs.get("system_prompt", "")
33
47
  self.system_prompt_raw = kwargs.get("system_prompt_raw", "") # without plugins addons
34
- self.stream = kwargs.get("stream", False)
35
- self.assistant_id = kwargs.get("assistant_id", "")
48
+ self.temperature = kwargs.get("temperature", 1.0)
36
49
  self.thread_id = kwargs.get("thread_id", "")
37
- self.external_functions = kwargs.get("external_functions", [])
38
50
  self.tools_outputs = kwargs.get("tools_outputs", [])
39
- self.max_tokens = kwargs.get("max_tokens", 150)
40
- self.idx = kwargs.get("idx", None)
41
- self.idx_mode = kwargs.get("idx_mode", "chat")
42
- self.attachments = kwargs.get("attachments", [])
43
- self.file_ids = kwargs.get("file_ids", [])
44
- self.reply_context = kwargs.get("reply_ctx", None) # ReplyContext
45
- self.multimodal_ctx = kwargs.get("multimodal_ctx", MultimodalContext()) # AudioContext
46
- self.is_expert_call = kwargs.get("is_expert_call", False) # Expert call flag
47
- self.force_sync = kwargs.get("force_sync", False) # Force sync flag
48
- self.request = kwargs.get("request", False) # Use normal request instead of quick call
49
- self.preset = kwargs.get("preset", None) # PresetItem
50
- self.force = kwargs.get("force", False) # Force mode flag
51
51
 
52
52
  # check types
53
53
  if self.ctx is not None and not isinstance(self.ctx, CtxItem):
@@ -62,38 +62,36 @@ class BridgeContext:
62
62
  :return: dictionary
63
63
  """
64
64
  data = {
65
+ "assistant_id": self.assistant_id,
66
+ "attachments": self.attachments,
65
67
  "ctx": self.ctx,
66
- "reply_context": self.reply_context.to_dict() if self.reply_context else None,
68
+ "external_functions": self.external_functions,
69
+ "file_ids": self.file_ids,
70
+ "force_sync": self.force_sync,
67
71
  "history": len(self.history),
72
+ "idx": self.idx,
73
+ "idx_mode": self.idx_mode,
74
+ "is_expert_call": self.is_expert_call,
75
+ "max_tokens": self.max_tokens,
68
76
  "mode": self.mode,
69
- "parent_mode": self.parent_mode,
70
77
  "model": self.model,
71
- "temperature": self.temperature,
78
+ "parent_mode": self.parent_mode,
72
79
  "prompt": self.prompt,
80
+ "reply_context": self.reply_context.to_dict() if self.reply_context else None,
81
+ "request": self.request,
82
+ "stream": self.stream,
73
83
  "system_prompt": self.system_prompt,
74
84
  "system_prompt_raw": self.system_prompt_raw,
75
- "stream": self.stream,
76
- "assistant_id": self.assistant_id,
85
+ "temperature": self.temperature,
77
86
  "thread_id": self.thread_id,
78
- "external_functions": self.external_functions,
79
87
  "tools_outputs": self.tools_outputs,
80
- "max_tokens": self.max_tokens,
81
- "idx": self.idx,
82
- "idx_mode": self.idx_mode,
83
- "attachments": self.attachments,
84
- "file_ids": self.file_ids,
85
- "is_expert_call": self.is_expert_call,
86
- "force_sync": self.force_sync,
87
- "request": self.request,
88
88
  }
89
89
  if self.ctx is not None:
90
90
  data["ctx"] = self.ctx.to_dict(True)
91
91
  if self.model is not None:
92
92
  data["model"] = self.model.to_dict()
93
93
 
94
- # sort by keys
95
- data = dict(sorted(data.items(), key=lambda item: item[0]))
96
- return data
94
+ return dict(sorted(data.items(), key=lambda item: item[0])) # sort by keys
97
95
 
98
96
  def dump(self) -> str:
99
97
  """
@@ -135,5 +133,4 @@ class MultimodalContext:
135
133
  "audio_format": self.audio_format,
136
134
  }
137
135
  # sort by keys
138
- data = dict(sorted(data.items(), key=lambda item: item[0]))
139
- return data
136
+ return dict(sorted(data.items(), key=lambda item: item[0]))
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.08.05 21:00:00 #
9
+ # Updated Date: 2025.08.24 23:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  from typing import List
@@ -15,9 +15,9 @@ from PySide6.QtWidgets import QVBoxLayout, QWidget
15
15
 
16
16
  from pygpt_net.core.tabs.tab import Tab
17
17
  from pygpt_net.ui.widget.textarea.output import ChatOutput
18
+ from pygpt_net.item.ctx import CtxItem
18
19
 
19
20
  from .bag import Bag
20
- from ...item.ctx import CtxItem
21
21
 
22
22
 
23
23
  class Container:
@@ -28,8 +28,7 @@ class Container:
28
28
  :param window: Window
29
29
  """
30
30
  self.window = window
31
- self.bags = {}
32
- self.bags[0] = Bag(window) # always create initial bag
31
+ self.bags = {0: Bag(window)}
33
32
 
34
33
  def get(self, tab: Tab) -> QWidget:
35
34
  """
@@ -92,14 +91,16 @@ class Container:
92
91
 
93
92
  :param tab: Tab
94
93
  """
95
- if tab.pid in self.window.ui.nodes['output_plain']:
96
- self.window.ui.nodes['output_plain'][tab.pid].on_delete() # clean up
97
- self.window.ui.nodes['output_plain'][tab.pid] = None
98
- del self.window.ui.nodes['output_plain'][tab.pid]
99
- if tab.pid in self.window.ui.nodes['output']:
100
- self.window.ui.nodes['output'][tab.pid].on_delete() # clean up
101
- self.window.ui.nodes['output'][tab.pid] = None
102
- del self.window.ui.nodes['output'][tab.pid]
94
+ nodes = self.window.ui.nodes
95
+
96
+ if tab.pid in nodes['output_plain']:
97
+ nodes['output_plain'][tab.pid].on_delete() # clean up
98
+ nodes['output_plain'][tab.pid] = None
99
+ del nodes['output_plain'][tab.pid]
100
+ if tab.pid in nodes['output']:
101
+ nodes['output'][tab.pid].on_delete() # clean up
102
+ nodes['output'][tab.pid] = None
103
+ del nodes['output'][tab.pid]
103
104
 
104
105
  self.window.controller.chat.render.remove_pid(tab.pid) # remove pid data from renderer registry
105
106
  self.window.core.ctx.output.remove_pid(tab.pid) # remove pid from ctx output mapping
pygpt_net/core/ctx/ctx.py CHANGED
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.08.15 23:00:00 #
9
+ # Updated Date: 2025.08.24 02:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  import copy
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2024.12.14 08:00:00 #
9
+ # Updated Date: 2025.08.24 23:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  from typing import Optional, List, Dict
@@ -87,6 +87,9 @@ class Output:
87
87
  def is_mapped(self, meta: CtxMeta) -> bool:
88
88
  """
89
89
  Check if meta is mapped anywhere
90
+
91
+ :param meta: Meta
92
+ :return: True if mapped, False otherwise
90
93
  """
91
94
  self.init()
92
95
 
@@ -182,6 +185,8 @@ class Output:
182
185
  def is_empty(self) -> bool:
183
186
  """
184
187
  Check if mapping is empty for the active PID across columns
188
+
189
+ :return: True if empty, False otherwise
185
190
  """
186
191
  self.init()
187
192
 
@@ -211,9 +216,7 @@ class Output:
211
216
  return self.store(meta)
212
217
 
213
218
  def clear(self):
214
- """
215
- Clear mapping
216
- """
219
+ """Clear mapping"""
217
220
  self.mapping.clear()
218
221
  self.last_pids.clear()
219
222
  self.last_pid = 0
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2024.12.14 08:00:00 #
9
+ # Updated Date: 2025.08.24 02:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  import os
@@ -60,6 +60,7 @@ class Database:
60
60
  'output',
61
61
  'input_name',
62
62
  'output_name',
63
+ 'extra',
63
64
  'input_ts',
64
65
  'output_ts',
65
66
  'mode',
@@ -74,7 +75,6 @@ class Database:
74
75
  'files_json',
75
76
  'attachments_json',
76
77
  'additional_ctx_json',
77
- 'extra',
78
78
  'hidden_input',
79
79
  'hidden_output',
80
80
  'input_tokens',
@@ -6,10 +6,10 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.08.11 18:00:00 #
9
+ # Updated Date: 2025.08.24 23:00:00 #
10
10
  # ================================================== #
11
11
 
12
- from qasync import QApplication
12
+ from PySide6.QtWidgets import QApplication
13
13
 
14
14
  from pygpt_net.utils import mem_clean
15
15
 
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.08.19 07:00:00 #
9
+ # Updated Date: 2025.08.24 02:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  import gc
@@ -416,6 +416,17 @@ class Debug:
416
416
  print("\n".join(stats))
417
417
  return res
418
418
 
419
+ def trace(self):
420
+ """
421
+ Print current stack trace
422
+
423
+ Prints the current stack trace and returns it as a string.
424
+ """
425
+ stack = traceback.format_stack()
426
+ formatted_trace = "".join(stack)
427
+ print(formatted_trace)
428
+ return formatted_trace
429
+
419
430
  def pause(self, *args):
420
431
  """
421
432
  Pause execution
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.08.18 01:00:00 #
9
+ # Updated Date: 2025.08.23 15:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  from typing import List, Tuple
@@ -47,6 +47,9 @@ class Dispatcher:
47
47
  :param all: bool: If True, dispatch to all plugins regardless of their state.
48
48
  :return: Tuple[List[str], BaseEvent]: A tuple containing a list of affected plugin IDs and the event.
49
49
  """
50
+ if not isinstance(event, BaseEvent):
51
+ raise RuntimeError(f"Not an event object: {event}")
52
+
50
53
  if not isinstance(event, RenderEvent):
51
54
  event.call_id = self.call_id
52
55
 
@@ -68,6 +71,7 @@ class Dispatcher:
68
71
 
69
72
  handled = False
70
73
 
74
+ # kernel
71
75
  if isinstance(event, KernelEvent):
72
76
  kernel_auto = (KernelEvent.INIT, KernelEvent.RESTART, KernelEvent.STOP, KernelEvent.TERMINATE)
73
77
  if event.name not in kernel_auto:
@@ -78,6 +82,7 @@ class Dispatcher:
78
82
  if event.name not in kernel_auto:
79
83
  handled = True
80
84
 
85
+ # render
81
86
  elif isinstance(event, RenderEvent):
82
87
  controller.chat.render.handle(event)
83
88
  if log_event:
@@ -85,11 +90,28 @@ class Dispatcher:
85
90
  self.call_id += 1
86
91
  handled = True
87
92
 
93
+ # tools
88
94
  wnd.tools.handle(event)
89
95
 
90
96
  if handled:
91
97
  return [], event
92
98
 
99
+ # agents
100
+ controller.agent.handle(event)
101
+
102
+ # ctx
103
+ controller.ctx.handle(event)
104
+
105
+ # model
106
+ controller.model.handle(event)
107
+
108
+ # idx
109
+ controller.idx.handle(event)
110
+
111
+ # ui
112
+ controller.ui.handle(event)
113
+
114
+ # access
93
115
  if isinstance(event, (ControlEvent, AppEvent)):
94
116
  controller.access.handle(event)
95
117
 
@@ -98,6 +120,7 @@ class Dispatcher:
98
120
  plugins_dict = plugins_mgr.plugins
99
121
  plugin_ids = tuple(plugins_dict.keys())
100
122
 
123
+ # plugins
101
124
  for pid in plugin_ids:
102
125
  if controller.plugins.is_enabled(pid) or all:
103
126
  if event.stop:
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2024.12.14 08:00:00 #
9
+ # Updated Date: 2025.08.23 21:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  from typing import Optional
@@ -16,16 +16,16 @@ from .base import BaseEvent
16
16
  class AppEvent(BaseEvent):
17
17
  """Events dispatched by application"""
18
18
  APP_STARTED = "app.started"
19
+ CAMERA_CAPTURED = "camera.captured"
20
+ CAMERA_DISABLED = "camera.disabled"
21
+ CAMERA_ENABLED = "camera.enabled"
22
+ CTX_ATTACHMENTS_CLEAR = "ctx.attachments.clear"
19
23
  CTX_CREATED = "ctx.created"
20
24
  CTX_END = "ctx.end"
21
25
  CTX_SELECTED = "ctx.selected"
22
- CTX_ATTACHMENTS_CLEAR = "ctx.attachments.clear"
23
- CAMERA_ENABLED = "camera.enabled"
24
- CAMERA_DISABLED = "camera.disabled"
25
- CAMERA_CAPTURED = "camera.captured"
26
+ INPUT_CALL = "input.call"
26
27
  INPUT_ERROR = "input.error"
27
28
  INPUT_SENT = "input.sent"
28
- INPUT_CALL = "input.call"
29
29
  INPUT_STOPPED = "input.stopped"
30
30
  INPUT_VOICE_LISTEN_STARTED = "input.voice.listen.started"
31
31
  INPUT_VOICE_LISTEN_STOPPED = "input.voice.listen.stopped"
@@ -33,10 +33,10 @@ class AppEvent(BaseEvent):
33
33
  MODEL_SELECTED = "model.selected"
34
34
  PRESET_SELECTED = "preset.selected"
35
35
  TAB_SELECTED = "tab.switch"
36
- VOICE_CONTROL_TOGGLE = "voice.control.toggle"
37
36
  VOICE_CONTROL_STARTED = "voice.control.started"
38
37
  VOICE_CONTROL_STOPPED = "voice.control.stopped"
39
38
  VOICE_CONTROL_SENT = "voice.control.sent"
39
+ VOICE_CONTROL_TOGGLE = "voice.control.toggle"
40
40
  VOICE_CONTROL_UNRECOGNIZED = "voice.control.unrecognized"
41
41
 
42
42
  def __init__(
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.03.02 19:00:00 #
9
+ # Updated Date: 2025.08.23 21:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  from typing import Optional
@@ -16,42 +16,42 @@ from .base import BaseEvent
16
16
 
17
17
  class ControlEvent(BaseEvent):
18
18
  """Events used for app control"""
19
- APP_STATUS = "app.status"
20
19
  APP_EXIT = "app.exit"
21
- CMD_CONFIRM = "cmd.confirm"
22
- CMD_LIST = "cmd.list"
23
- AUDIO_OUTPUT_ENABLE = "audio.output.enable"
24
- AUDIO_OUTPUT_DISABLE = "audio.output.disable"
25
- AUDIO_INPUT_ENABLE = "audio.input.enable"
20
+ APP_STATUS = "app.status"
26
21
  AUDIO_INPUT_DISABLE = "audio.input.disable"
22
+ AUDIO_INPUT_ENABLE = "audio.input.enable"
23
+ AUDIO_OUTPUT_DISABLE = "audio.output.disable"
24
+ AUDIO_OUTPUT_ENABLE = "audio.output.enable"
27
25
  CALENDAR_ADD = "calendar.add"
28
26
  CALENDAR_CLEAR = "calendar.clear"
29
27
  CALENDAR_READ = "calendar.read"
30
- CAMERA_ENABLE = "camera.enable"
31
- CAMERA_DISABLE = "camera.disable"
32
28
  CAMERA_CAPTURE = "camera.capture"
33
- CTX_NEW = "ctx.new"
34
- CTX_PREV = "ctx.prev"
35
- CTX_NEXT = "ctx.next"
36
- CTX_LAST = "ctx.last"
37
- CTX_INPUT_FOCUS = "ctx.input.focus"
38
- CTX_INPUT_SEND = "ctx.input.send"
39
- CTX_INPUT_CLEAR = "ctx.input.clear"
40
- CTX_STOP = "ctx.stop"
29
+ CAMERA_DISABLE = "camera.disable"
30
+ CAMERA_ENABLE = "camera.enable"
31
+ CMD_CONFIRM = "cmd.confirm"
32
+ CMD_LIST = "cmd.list"
41
33
  CTX_ATTACHMENTS_CLEAR = "ctx.attachments.clear"
42
34
  CTX_CURRENT = "ctx.current"
43
- CTX_READ_LAST = "ctx.read.last"
35
+ CTX_INPUT_CLEAR = "ctx.input.clear"
36
+ CTX_INPUT_FOCUS = "ctx.input.focus"
37
+ CTX_INPUT_SEND = "ctx.input.send"
38
+ CTX_LAST = "ctx.last"
39
+ CTX_NEW = "ctx.new"
40
+ CTX_NEXT = "ctx.next"
41
+ CTX_PREV = "ctx.prev"
44
42
  CTX_READ_ALL = "ctx.read.all"
43
+ CTX_READ_LAST = "ctx.read.last"
45
44
  CTX_RENAME = "ctx.rename"
46
- CTX_SEARCH_STRING = "ctx.search.string"
47
45
  CTX_SEARCH_CLEAR = "ctx.search.clear"
48
- INPUT_SEND = "input.send"
46
+ CTX_SEARCH_STRING = "ctx.search.string"
47
+ CTX_STOP = "ctx.stop"
49
48
  INPUT_APPEND = "input.append"
49
+ INPUT_SEND = "input.send"
50
50
  MODE_CHAT = "mode.chat"
51
- MODE_RESEARCH = "mode.research"
52
51
  MODE_LLAMA_INDEX = "mode.llama_index"
53
52
  MODE_NEXT = "mode.next"
54
53
  MODE_PREV = "mode.prev"
54
+ MODE_RESEARCH = "mode.research"
55
55
  MODEL_NEXT = "model.next"
56
56
  MODEL_PREV = "model.prev"
57
57
  NOTE_ADD = "note.add"
@@ -59,20 +59,20 @@ class ControlEvent(BaseEvent):
59
59
  NOTEPAD_READ = "notepad.read"
60
60
  PRESET_NEXT = "preset.next"
61
61
  PRESET_PREV = "preset.prev"
62
- TAB_CHAT = "tab.chat"
63
62
  TAB_CALENDAR = "tab.calendar"
63
+ TAB_CHAT = "tab.chat"
64
64
  TAB_DRAW = "tab.draw"
65
65
  TAB_FILES = "tab.files"
66
- TAB_NOTEPAD = "tab.notepad"
67
66
  TAB_NEXT = "tab.next"
67
+ TAB_NOTEPAD = "tab.notepad"
68
68
  TAB_PREV = "tab.prev"
69
- VOICE_MESSAGE_START = "voice_msg.start"
70
- VOICE_MESSAGE_STOP = "voice_msg.stop"
71
- VOICE_MESSAGE_TOGGLE = "voice_msg.toggle"
72
69
  VOICE_COMMAND_START = "voice_cmd.start"
73
70
  VOICE_COMMAND_STOP = "voice_cmd.stop"
74
71
  VOICE_COMMAND_TOGGLE = "voice_cmd.toggle"
75
72
  VOICE_CONTROL_UNRECOGNIZED = "unrecognized"
73
+ VOICE_MESSAGE_START = "voice_msg.start"
74
+ VOICE_MESSAGE_STOP = "voice_msg.stop"
75
+ VOICE_MESSAGE_TOGGLE = "voice_msg.toggle"
76
76
 
77
77
  def __init__(
78
78
  self,
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.06.30 02:00:00 #
9
+ # Updated Date: 2025.08.23 21:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  import json
@@ -23,13 +23,14 @@ class Event(BaseEvent):
23
23
  AUDIO_INPUT_RECORD_START = "audio.input.record.start" # start audio input recording
24
24
  AUDIO_INPUT_RECORD_STOP = "audio.input.record.stop" # stop audio input recording
25
25
  AUDIO_INPUT_RECORD_TOGGLE = "audio.input.record.toggle" # toggle audio input recording
26
- AUDIO_INPUT_TRANSCRIBE = "audio.input.transcribe" # transcribe audio file
27
26
  AUDIO_INPUT_STOP = "audio.input.stop"
28
27
  AUDIO_INPUT_TOGGLE = "audio.input.toggle"
28
+ AUDIO_INPUT_TRANSCRIBE = "audio.input.transcribe" # transcribe audio file
29
29
  AUDIO_OUTPUT_STOP = "audio.output.stop"
30
30
  AUDIO_OUTPUT_TOGGLE = "audio.output.toggle"
31
31
  AUDIO_PLAYBACK = "audio.playback"
32
32
  AUDIO_READ_TEXT = "audio.read_text"
33
+ BRIDGE_BEFORE = "bridge.before"
33
34
  CMD_EXECUTE = "cmd.execute"
34
35
  CMD_INLINE = "cmd.inline"
35
36
  CMD_SYNTAX = "cmd.syntax"
@@ -42,14 +43,16 @@ class Event(BaseEvent):
42
43
  DISABLE = "disable"
43
44
  ENABLE = "enable"
44
45
  FORCE_STOP = "force.stop"
46
+ INPUT_ACCEPT = "input.accept"
45
47
  INPUT_BEFORE = "input.before"
48
+ INPUT_BEGIN = "input.begin"
46
49
  MODE_BEFORE = "mode.before"
47
50
  MODE_SELECT = "mode.select"
48
51
  MODEL_BEFORE = "model.before"
49
52
  MODEL_SELECT = "model.select"
50
53
  MODELS_CHANGED = "models.changed"
51
- PLUGIN_SETTINGS_CHANGED = "plugin.settings.changed"
52
54
  PLUGIN_OPTION_GET = "plugin.option.get"
55
+ PLUGIN_SETTINGS_CHANGED = "plugin.settings.changed"
53
56
  POST_PROMPT = "post.prompt"
54
57
  POST_PROMPT_ASYNC = "post.prompt.async"
55
58
  POST_PROMPT_END = "post.prompt.end"
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.08.01 19:00:00 #
9
+ # Updated Date: 2025.08.23 21:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  from typing import Optional
@@ -50,8 +50,8 @@ class KernelEvent(BaseEvent):
50
50
  # state
51
51
  STATE = "kernel.state"
52
52
  STATE_BUSY = "kernel.state.busy"
53
- STATE_IDLE = "kernel.state.idle"
54
53
  STATE_ERROR = "kernel.state.error"
54
+ STATE_IDLE = "kernel.state.idle"
55
55
  STATUS = "kernel.status"
56
56
 
57
57
  LIVE_APPEND = "kernel.live.append"
@@ -6,7 +6,7 @@
6
6
  # GitHub: https://github.com/szczyglis-dev/py-gpt #
7
7
  # MIT License #
8
8
  # Created By : Marcin Szczygliński #
9
- # Updated Date: 2025.08.01 19:00:00 #
9
+ # Updated Date: 2025.08.23 21:00:00 #
10
10
  # ================================================== #
11
11
 
12
12
  from typing import Optional
@@ -18,13 +18,13 @@ class RenderEvent(BaseEvent):
18
18
  """Events used for rendering"""
19
19
  BEGIN = "render.begin"
20
20
  END = "render.end"
21
+ FRESH = "render.fresh"
22
+ PREPARE = "render.prepare"
21
23
  RELOAD = "render.reload"
22
24
  RESET = "render.reset"
23
- PREPARE = "render.prepare"
24
- FRESH = "render.fresh"
25
25
 
26
- STREAM_BEGIN = "render.stream.begin"
27
26
  STREAM_APPEND = "render.stream.append"
27
+ STREAM_BEGIN = "render.stream.begin"
28
28
  STREAM_END = "render.stream.end"
29
29
  STREAM_NEXT = "render.stream.next"
30
30
 
@@ -33,37 +33,37 @@ class RenderEvent(BaseEvent):
33
33
  CLEAR_INPUT = "render.clear.input"
34
34
  CLEAR_OUTPUT = "render.clear.output"
35
35
 
36
+ CTX_APPEND = "render.ctx.append"
36
37
  INPUT_APPEND = "render.input.append"
37
38
  OUTPUT_APPEND = "render.output.append"
38
- CTX_APPEND = "render.ctx.append"
39
39
 
40
- EXTRA_BEGIN = "render.extra.begin"
41
40
  EXTRA_APPEND = "render.extra.append"
41
+ EXTRA_BEGIN = "render.extra.begin"
42
42
  EXTRA_END = "render.extra.end"
43
43
 
44
+ ON_EDIT_DISABLE = "render.on.edit.disable"
45
+ ON_EDIT_ENABLE = "render.on.edit.enable"
44
46
  ON_LOAD = "render.on.load"
45
47
  ON_PAGE_LOAD = "render.on.page.load"
48
+ ON_SWITCH = "render.on.switch"
46
49
  ON_THEME_CHANGE = "render.on.theme.change"
47
- ON_EDIT_ENABLE = "render.on.edit.enable"
48
- ON_EDIT_DISABLE = "render.on.edit.disable"
49
- ON_TS_ENABLE = "render.on.ts.enable"
50
50
  ON_TS_DISABLE = "render.on.ts.disable"
51
- ON_SWITCH = "render.on.switch"
51
+ ON_TS_ENABLE = "render.on.ts.enable"
52
52
 
53
53
  TOOL_BEGIN = "render.tool.begin"
54
- TOOL_UPDATE = "render.tool.update"
55
54
  TOOL_CLEAR = "render.tool.clear"
56
55
  TOOL_END = "render.tool.end"
56
+ TOOL_UPDATE = "render.tool.update"
57
57
 
58
- ACTION_REGEN_SUBMIT = "render.action.regen.submit"
59
58
  ACTION_EDIT_SUBMIT = "render.action.edit.submit"
59
+ ACTION_REGEN_SUBMIT = "render.action.regen.submit"
60
60
 
61
61
  ITEM_DELETE_ID = "render.item.delete.id"
62
62
  ITEM_DELETE_FROM_ID = "render.item.delete.from_id"
63
63
 
64
- STATE_IDLE = "render.state.idle"
65
64
  STATE_BUSY = "render.state.busy"
66
65
  STATE_ERROR = "render.state.error"
66
+ STATE_IDLE = "render.state.idle"
67
67
 
68
68
  LIVE_APPEND = "render.live.append"
69
69
  LIVE_CLEAR = "render.live.clear"