ommlds 0.0.0.dev440__py3-none-any.whl → 0.0.0.dev480__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 (271) hide show
  1. ommlds/.omlish-manifests.json +332 -35
  2. ommlds/__about__.py +15 -9
  3. ommlds/_hacks/__init__.py +4 -0
  4. ommlds/_hacks/funcs.py +110 -0
  5. ommlds/_hacks/names.py +158 -0
  6. ommlds/_hacks/params.py +73 -0
  7. ommlds/_hacks/patches.py +0 -3
  8. ommlds/backends/anthropic/protocol/_marshal.py +2 -2
  9. ommlds/backends/anthropic/protocol/sse/_marshal.py +1 -1
  10. ommlds/backends/anthropic/protocol/sse/assemble.py +23 -7
  11. ommlds/backends/anthropic/protocol/sse/events.py +13 -0
  12. ommlds/backends/anthropic/protocol/types.py +30 -9
  13. ommlds/backends/google/protocol/__init__.py +3 -0
  14. ommlds/backends/google/protocol/_marshal.py +16 -0
  15. ommlds/backends/google/protocol/types.py +626 -0
  16. ommlds/backends/groq/_marshal.py +23 -0
  17. ommlds/backends/groq/protocol.py +249 -0
  18. ommlds/backends/mlx/generation.py +1 -1
  19. ommlds/backends/mlx/loading.py +58 -1
  20. ommlds/backends/ollama/__init__.py +0 -0
  21. ommlds/backends/ollama/protocol.py +170 -0
  22. ommlds/backends/openai/protocol/__init__.py +9 -28
  23. ommlds/backends/openai/protocol/_common.py +18 -0
  24. ommlds/backends/openai/protocol/_marshal.py +27 -0
  25. ommlds/backends/openai/protocol/chatcompletion/chunk.py +58 -31
  26. ommlds/backends/openai/protocol/chatcompletion/contentpart.py +49 -44
  27. ommlds/backends/openai/protocol/chatcompletion/message.py +55 -43
  28. ommlds/backends/openai/protocol/chatcompletion/request.py +114 -66
  29. ommlds/backends/openai/protocol/chatcompletion/response.py +71 -45
  30. ommlds/backends/openai/protocol/chatcompletion/responseformat.py +27 -20
  31. ommlds/backends/openai/protocol/chatcompletion/tokenlogprob.py +16 -7
  32. ommlds/backends/openai/protocol/completionusage.py +24 -15
  33. ommlds/backends/tavily/__init__.py +0 -0
  34. ommlds/backends/tavily/protocol.py +301 -0
  35. ommlds/backends/tinygrad/models/llama3/__init__.py +22 -14
  36. ommlds/backends/transformers/__init__.py +0 -0
  37. ommlds/backends/transformers/filecache.py +109 -0
  38. ommlds/backends/transformers/streamers.py +73 -0
  39. ommlds/cli/asyncs.py +30 -0
  40. ommlds/cli/backends/catalog.py +93 -0
  41. ommlds/cli/backends/configs.py +9 -0
  42. ommlds/cli/backends/inject.py +31 -36
  43. ommlds/cli/backends/injection.py +16 -0
  44. ommlds/cli/backends/types.py +46 -0
  45. ommlds/cli/content/__init__.py +0 -0
  46. ommlds/cli/content/messages.py +34 -0
  47. ommlds/cli/content/strings.py +42 -0
  48. ommlds/cli/inject.py +15 -32
  49. ommlds/cli/inputs/__init__.py +0 -0
  50. ommlds/cli/inputs/asyncs.py +32 -0
  51. ommlds/cli/inputs/sync.py +75 -0
  52. ommlds/cli/main.py +270 -110
  53. ommlds/cli/rendering/__init__.py +0 -0
  54. ommlds/cli/rendering/configs.py +9 -0
  55. ommlds/cli/rendering/inject.py +31 -0
  56. ommlds/cli/rendering/markdown.py +52 -0
  57. ommlds/cli/rendering/raw.py +73 -0
  58. ommlds/cli/rendering/types.py +21 -0
  59. ommlds/cli/secrets.py +21 -0
  60. ommlds/cli/sessions/base.py +1 -1
  61. ommlds/cli/sessions/chat/chat/__init__.py +0 -0
  62. ommlds/cli/sessions/chat/chat/ai/__init__.py +0 -0
  63. ommlds/cli/sessions/chat/chat/ai/configs.py +11 -0
  64. ommlds/cli/sessions/chat/chat/ai/inject.py +74 -0
  65. ommlds/cli/sessions/chat/chat/ai/injection.py +14 -0
  66. ommlds/cli/sessions/chat/chat/ai/rendering.py +70 -0
  67. ommlds/cli/sessions/chat/chat/ai/services.py +79 -0
  68. ommlds/cli/sessions/chat/chat/ai/tools.py +44 -0
  69. ommlds/cli/sessions/chat/chat/ai/types.py +28 -0
  70. ommlds/cli/sessions/chat/chat/state/__init__.py +0 -0
  71. ommlds/cli/sessions/chat/chat/state/configs.py +11 -0
  72. ommlds/cli/sessions/chat/chat/state/inject.py +36 -0
  73. ommlds/cli/sessions/chat/chat/state/inmemory.py +33 -0
  74. ommlds/cli/sessions/chat/chat/state/storage.py +52 -0
  75. ommlds/cli/sessions/chat/chat/state/types.py +38 -0
  76. ommlds/cli/sessions/chat/chat/user/__init__.py +0 -0
  77. ommlds/cli/sessions/chat/chat/user/configs.py +17 -0
  78. ommlds/cli/sessions/chat/chat/user/inject.py +62 -0
  79. ommlds/cli/sessions/chat/chat/user/interactive.py +31 -0
  80. ommlds/cli/sessions/chat/chat/user/oneshot.py +25 -0
  81. ommlds/cli/sessions/chat/chat/user/types.py +15 -0
  82. ommlds/cli/sessions/chat/configs.py +27 -0
  83. ommlds/cli/sessions/chat/driver.py +43 -0
  84. ommlds/cli/sessions/chat/inject.py +33 -65
  85. ommlds/cli/sessions/chat/phases/__init__.py +0 -0
  86. ommlds/cli/sessions/chat/phases/inject.py +27 -0
  87. ommlds/cli/sessions/chat/phases/injection.py +14 -0
  88. ommlds/cli/sessions/chat/phases/manager.py +29 -0
  89. ommlds/cli/sessions/chat/phases/types.py +29 -0
  90. ommlds/cli/sessions/chat/session.py +27 -0
  91. ommlds/cli/sessions/chat/tools/__init__.py +0 -0
  92. ommlds/cli/sessions/chat/tools/configs.py +22 -0
  93. ommlds/cli/sessions/chat/tools/confirmation.py +46 -0
  94. ommlds/cli/sessions/chat/tools/execution.py +66 -0
  95. ommlds/cli/sessions/chat/tools/fs/__init__.py +0 -0
  96. ommlds/cli/sessions/chat/tools/fs/configs.py +12 -0
  97. ommlds/cli/sessions/chat/tools/fs/inject.py +35 -0
  98. ommlds/cli/sessions/chat/tools/inject.py +88 -0
  99. ommlds/cli/sessions/chat/tools/injection.py +44 -0
  100. ommlds/cli/sessions/chat/tools/rendering.py +58 -0
  101. ommlds/cli/sessions/chat/tools/todo/__init__.py +0 -0
  102. ommlds/cli/sessions/chat/tools/todo/configs.py +12 -0
  103. ommlds/cli/sessions/chat/tools/todo/inject.py +31 -0
  104. ommlds/cli/sessions/chat/tools/weather/__init__.py +0 -0
  105. ommlds/cli/sessions/chat/tools/weather/configs.py +12 -0
  106. ommlds/cli/sessions/chat/tools/weather/inject.py +22 -0
  107. ommlds/cli/{tools/weather.py → sessions/chat/tools/weather/tools.py} +1 -1
  108. ommlds/cli/sessions/completion/configs.py +21 -0
  109. ommlds/cli/sessions/completion/inject.py +42 -0
  110. ommlds/cli/sessions/completion/session.py +35 -0
  111. ommlds/cli/sessions/embedding/configs.py +21 -0
  112. ommlds/cli/sessions/embedding/inject.py +42 -0
  113. ommlds/cli/sessions/embedding/session.py +33 -0
  114. ommlds/cli/sessions/inject.py +28 -11
  115. ommlds/cli/state/__init__.py +0 -0
  116. ommlds/cli/state/inject.py +28 -0
  117. ommlds/cli/{state.py → state/storage.py} +41 -24
  118. ommlds/minichain/__init__.py +84 -24
  119. ommlds/minichain/_marshal.py +49 -9
  120. ommlds/minichain/_typedvalues.py +2 -4
  121. ommlds/minichain/backends/catalogs/base.py +20 -1
  122. ommlds/minichain/backends/catalogs/simple.py +2 -2
  123. ommlds/minichain/backends/catalogs/strings.py +10 -8
  124. ommlds/minichain/backends/impls/anthropic/chat.py +65 -27
  125. ommlds/minichain/backends/impls/anthropic/names.py +10 -8
  126. ommlds/minichain/backends/impls/anthropic/protocol.py +109 -0
  127. ommlds/minichain/backends/impls/anthropic/stream.py +111 -43
  128. ommlds/minichain/backends/impls/duckduckgo/search.py +1 -1
  129. ommlds/minichain/backends/impls/dummy/__init__.py +0 -0
  130. ommlds/minichain/backends/impls/dummy/chat.py +69 -0
  131. ommlds/minichain/backends/impls/google/chat.py +114 -22
  132. ommlds/minichain/backends/impls/google/search.py +7 -2
  133. ommlds/minichain/backends/impls/google/stream.py +219 -0
  134. ommlds/minichain/backends/impls/google/tools.py +149 -0
  135. ommlds/minichain/backends/impls/groq/__init__.py +0 -0
  136. ommlds/minichain/backends/impls/groq/chat.py +75 -0
  137. ommlds/minichain/backends/impls/groq/names.py +48 -0
  138. ommlds/minichain/backends/impls/groq/protocol.py +143 -0
  139. ommlds/minichain/backends/impls/groq/stream.py +125 -0
  140. ommlds/minichain/backends/impls/llamacpp/chat.py +33 -18
  141. ommlds/minichain/backends/impls/llamacpp/completion.py +1 -1
  142. ommlds/minichain/backends/impls/llamacpp/format.py +4 -2
  143. ommlds/minichain/backends/impls/llamacpp/stream.py +37 -20
  144. ommlds/minichain/backends/impls/mistral.py +20 -5
  145. ommlds/minichain/backends/impls/mlx/chat.py +96 -22
  146. ommlds/minichain/backends/impls/ollama/__init__.py +0 -0
  147. ommlds/minichain/backends/impls/ollama/chat.py +199 -0
  148. ommlds/minichain/backends/impls/openai/chat.py +18 -8
  149. ommlds/minichain/backends/impls/openai/completion.py +10 -3
  150. ommlds/minichain/backends/impls/openai/embedding.py +10 -3
  151. ommlds/minichain/backends/impls/openai/format.py +131 -106
  152. ommlds/minichain/backends/impls/openai/names.py +31 -5
  153. ommlds/minichain/backends/impls/openai/stream.py +43 -25
  154. ommlds/minichain/backends/impls/tavily.py +66 -0
  155. ommlds/minichain/backends/impls/tinygrad/chat.py +23 -16
  156. ommlds/minichain/backends/impls/transformers/sentence.py +1 -1
  157. ommlds/minichain/backends/impls/transformers/tokens.py +1 -1
  158. ommlds/minichain/backends/impls/transformers/transformers.py +155 -34
  159. ommlds/minichain/backends/strings/parsing.py +1 -1
  160. ommlds/minichain/backends/strings/resolving.py +4 -1
  161. ommlds/minichain/chat/_marshal.py +16 -9
  162. ommlds/minichain/chat/choices/adapters.py +4 -4
  163. ommlds/minichain/chat/choices/services.py +1 -1
  164. ommlds/minichain/chat/choices/stream/__init__.py +0 -0
  165. ommlds/minichain/chat/choices/stream/adapters.py +35 -0
  166. ommlds/minichain/chat/choices/stream/joining.py +31 -0
  167. ommlds/minichain/chat/choices/stream/services.py +45 -0
  168. ommlds/minichain/chat/choices/stream/types.py +43 -0
  169. ommlds/minichain/chat/choices/types.py +2 -2
  170. ommlds/minichain/chat/history.py +3 -3
  171. ommlds/minichain/chat/messages.py +55 -19
  172. ommlds/minichain/chat/services.py +3 -3
  173. ommlds/minichain/chat/stream/_marshal.py +16 -0
  174. ommlds/minichain/chat/stream/joining.py +85 -0
  175. ommlds/minichain/chat/stream/services.py +15 -21
  176. ommlds/minichain/chat/stream/types.py +32 -19
  177. ommlds/minichain/chat/tools/execution.py +8 -7
  178. ommlds/minichain/chat/tools/ids.py +9 -15
  179. ommlds/minichain/chat/tools/parsing.py +17 -26
  180. ommlds/minichain/chat/transforms/base.py +29 -38
  181. ommlds/minichain/chat/transforms/metadata.py +30 -4
  182. ommlds/minichain/chat/transforms/services.py +9 -11
  183. ommlds/minichain/content/_marshal.py +44 -20
  184. ommlds/minichain/content/json.py +13 -0
  185. ommlds/minichain/content/materialize.py +14 -21
  186. ommlds/minichain/content/prepare.py +4 -0
  187. ommlds/minichain/content/transforms/interleave.py +1 -1
  188. ommlds/minichain/content/transforms/squeeze.py +1 -1
  189. ommlds/minichain/content/transforms/stringify.py +1 -1
  190. ommlds/minichain/json.py +20 -0
  191. ommlds/minichain/lib/code/__init__.py +0 -0
  192. ommlds/minichain/lib/code/prompts.py +6 -0
  193. ommlds/minichain/lib/fs/binfiles.py +108 -0
  194. ommlds/minichain/lib/fs/context.py +126 -0
  195. ommlds/minichain/lib/fs/errors.py +101 -0
  196. ommlds/minichain/lib/fs/suggestions.py +36 -0
  197. ommlds/minichain/lib/fs/tools/__init__.py +0 -0
  198. ommlds/minichain/lib/fs/tools/edit.py +104 -0
  199. ommlds/minichain/lib/fs/tools/ls.py +38 -0
  200. ommlds/minichain/lib/fs/tools/read.py +115 -0
  201. ommlds/minichain/lib/fs/tools/recursivels/__init__.py +0 -0
  202. ommlds/minichain/lib/fs/tools/recursivels/execution.py +40 -0
  203. ommlds/minichain/lib/todo/__init__.py +0 -0
  204. ommlds/minichain/lib/todo/context.py +54 -0
  205. ommlds/minichain/lib/todo/tools/__init__.py +0 -0
  206. ommlds/minichain/lib/todo/tools/read.py +44 -0
  207. ommlds/minichain/lib/todo/tools/write.py +335 -0
  208. ommlds/minichain/lib/todo/types.py +60 -0
  209. ommlds/minichain/llms/_marshal.py +25 -17
  210. ommlds/minichain/llms/types.py +4 -0
  211. ommlds/minichain/registries/globals.py +18 -4
  212. ommlds/minichain/resources.py +66 -43
  213. ommlds/minichain/search.py +1 -1
  214. ommlds/minichain/services/_marshal.py +46 -39
  215. ommlds/minichain/services/facades.py +3 -3
  216. ommlds/minichain/services/services.py +1 -1
  217. ommlds/minichain/standard.py +8 -0
  218. ommlds/minichain/stream/services.py +152 -38
  219. ommlds/minichain/stream/wrap.py +22 -24
  220. ommlds/minichain/tools/_marshal.py +1 -1
  221. ommlds/minichain/tools/execution/catalog.py +2 -1
  222. ommlds/minichain/tools/execution/context.py +34 -14
  223. ommlds/minichain/tools/execution/errors.py +15 -0
  224. ommlds/minichain/tools/execution/executors.py +8 -3
  225. ommlds/minichain/tools/execution/reflect.py +40 -5
  226. ommlds/minichain/tools/fns.py +46 -9
  227. ommlds/minichain/tools/jsonschema.py +14 -5
  228. ommlds/minichain/tools/reflect.py +54 -18
  229. ommlds/minichain/tools/types.py +33 -1
  230. ommlds/minichain/utils.py +27 -0
  231. ommlds/minichain/vectors/_marshal.py +11 -10
  232. ommlds/nanochat/LICENSE +21 -0
  233. ommlds/nanochat/__init__.py +0 -0
  234. ommlds/nanochat/rustbpe/LICENSE +21 -0
  235. ommlds/nanochat/tokenizers.py +406 -0
  236. ommlds/server/server.py +3 -3
  237. ommlds/specs/__init__.py +0 -0
  238. ommlds/specs/mcp/__init__.py +0 -0
  239. ommlds/specs/mcp/_marshal.py +23 -0
  240. ommlds/specs/mcp/protocol.py +266 -0
  241. ommlds/tools/git.py +27 -10
  242. ommlds/tools/ocr.py +8 -9
  243. ommlds/wiki/analyze.py +2 -2
  244. ommlds/wiki/text/mfh.py +1 -5
  245. ommlds/wiki/text/wtp.py +1 -3
  246. ommlds/wiki/utils/xml.py +5 -5
  247. {ommlds-0.0.0.dev440.dist-info → ommlds-0.0.0.dev480.dist-info}/METADATA +24 -21
  248. ommlds-0.0.0.dev480.dist-info/RECORD +427 -0
  249. ommlds/cli/backends/standard.py +0 -20
  250. ommlds/cli/sessions/chat/base.py +0 -42
  251. ommlds/cli/sessions/chat/interactive.py +0 -73
  252. ommlds/cli/sessions/chat/printing.py +0 -96
  253. ommlds/cli/sessions/chat/prompt.py +0 -143
  254. ommlds/cli/sessions/chat/state.py +0 -109
  255. ommlds/cli/sessions/chat/tools.py +0 -91
  256. ommlds/cli/sessions/completion/completion.py +0 -44
  257. ommlds/cli/sessions/embedding/embedding.py +0 -42
  258. ommlds/cli/tools/config.py +0 -13
  259. ommlds/cli/tools/inject.py +0 -64
  260. ommlds/minichain/chat/stream/adapters.py +0 -69
  261. ommlds/minichain/lib/fs/ls/execution.py +0 -32
  262. ommlds-0.0.0.dev440.dist-info/RECORD +0 -303
  263. /ommlds/{cli/tools → backends/google}/__init__.py +0 -0
  264. /ommlds/{minichain/lib/fs/ls → backends/groq}/__init__.py +0 -0
  265. /ommlds/{huggingface.py → backends/huggingface.py} +0 -0
  266. /ommlds/minichain/lib/fs/{ls → tools/recursivels}/rendering.py +0 -0
  267. /ommlds/minichain/lib/fs/{ls → tools/recursivels}/running.py +0 -0
  268. {ommlds-0.0.0.dev440.dist-info → ommlds-0.0.0.dev480.dist-info}/WHEEL +0 -0
  269. {ommlds-0.0.0.dev440.dist-info → ommlds-0.0.0.dev480.dist-info}/entry_points.txt +0 -0
  270. {ommlds-0.0.0.dev440.dist-info → ommlds-0.0.0.dev480.dist-info}/licenses/LICENSE +0 -0
  271. {ommlds-0.0.0.dev440.dist-info → ommlds-0.0.0.dev480.dist-info}/top_level.txt +0 -0
@@ -1,96 +0,0 @@
1
- import abc
2
- import typing as ta
3
-
4
- from omlish import check
5
- from omlish import lang
6
-
7
- from .... import minichain as mc
8
-
9
-
10
- if ta.TYPE_CHECKING:
11
- from omdev import ptk
12
- from omdev.ptk import markdown as ptk_md
13
- else:
14
- ptk = lang.proxy_import('omdev.ptk')
15
- ptk_md = lang.proxy_import('omdev.ptk.markdown')
16
-
17
-
18
- ##
19
-
20
-
21
- class ChatSessionPrinter(lang.Abstract):
22
- @abc.abstractmethod
23
- def print(self, obj: mc.Message | mc.Content) -> None:
24
- raise NotImplementedError
25
-
26
-
27
- ##
28
-
29
-
30
- class StringChatSessionPrinter(ChatSessionPrinter, lang.Abstract):
31
- @abc.abstractmethod
32
- def _print_str(self, s: str) -> None:
33
- raise NotImplementedError
34
-
35
- def print(self, obj: mc.Message | mc.Content) -> None:
36
- if obj is None:
37
- pass
38
-
39
- elif isinstance(obj, mc.Message):
40
- if isinstance(obj, mc.SystemMessage):
41
- if obj.c is not None:
42
- self._print_str(check.isinstance(obj.c, str))
43
- elif isinstance(obj, mc.UserMessage):
44
- if obj.c is not None:
45
- self._print_str(check.isinstance(obj.c, str))
46
- elif isinstance(obj, mc.AiMessage):
47
- if obj.c is not None:
48
- self._print_str(check.isinstance(obj.c, str))
49
- elif isinstance(obj, mc.ToolExecResultMessage):
50
- self._print_str(check.isinstance(obj.c, str))
51
- else:
52
- raise TypeError(obj)
53
-
54
- elif isinstance(obj, str):
55
- self._print_str(obj)
56
-
57
- else:
58
- raise TypeError(obj)
59
-
60
-
61
- ##
62
-
63
-
64
- class SimpleStringChatSessionPrinter(StringChatSessionPrinter):
65
- def __init__(
66
- self,
67
- *,
68
- str_printer: ta.Callable[[str], None] | None = None,
69
- ) -> None:
70
- super().__init__()
71
-
72
- if str_printer is None:
73
- str_printer = print
74
- self._str_printer = str_printer
75
-
76
- def _print_str(self, s: str) -> None:
77
- s = s.strip()
78
- if not s:
79
- return
80
-
81
- self._str_printer(s)
82
-
83
-
84
- ##
85
-
86
-
87
- class MarkdownStringChatSessionPrinter(StringChatSessionPrinter):
88
- def _print_str(self, s: str) -> None:
89
- s = s.strip()
90
- if not s:
91
- return
92
-
93
- ptk.print_formatted_text(
94
- ptk_md.Markdown(s),
95
- style=ptk.Style(list(ptk_md.MARKDOWN_STYLE)),
96
- )
@@ -1,143 +0,0 @@
1
- import dataclasses as dc
2
-
3
- from omlish import check
4
- from omlish import lang
5
-
6
- from .... import minichain as mc
7
- from .base import DEFAULT_CHAT_MODEL_BACKEND
8
- from .base import ChatOptions
9
- from .base import ChatSession
10
- from .printing import ChatSessionPrinter
11
- from .state import ChatStateManager
12
- from .tools import ToolExecRequestExecutor
13
-
14
-
15
- ##
16
-
17
-
18
- class ToolExecutionRequestDeniedError(Exception):
19
- pass
20
-
21
-
22
- class PromptChatSession(ChatSession['PromptChatSession.Config']):
23
- @dc.dataclass(frozen=True)
24
- class Config(ChatSession.Config): # noqa
25
- content: mc.Content
26
-
27
- _: dc.KW_ONLY
28
-
29
- new: bool = False
30
-
31
- backend: str | None = None
32
- model_name: str | None = None
33
-
34
- stream: bool = False
35
-
36
- def __init__(
37
- self,
38
- config: Config,
39
- *,
40
- state_manager: ChatStateManager,
41
- chat_options: ChatOptions | None = None,
42
- printer: ChatSessionPrinter,
43
- backend_catalog: mc.BackendCatalog,
44
- tool_exec_request_executor: ToolExecRequestExecutor,
45
- ) -> None:
46
- super().__init__(config)
47
-
48
- self._state_manager = state_manager
49
- self._chat_options = chat_options
50
- self._printer = printer
51
- self._backend_catalog = backend_catalog
52
- self._tool_exec_request_executor = tool_exec_request_executor
53
-
54
- async def run(self) -> None:
55
- if self._config.stream:
56
- await self._run_stream()
57
- else:
58
- await self._run_immediate()
59
-
60
- async def _run_stream(self) -> None:
61
- prompt = check.isinstance(self._config.content, str)
62
-
63
- if self._config.new:
64
- state = self._state_manager.clear_state()
65
- else:
66
- state = self._state_manager.get_state()
67
-
68
- new_chat: list[mc.Message] = [
69
- mc.UserMessage(prompt),
70
- ]
71
-
72
- mdl: mc.ChatChoicesStreamService
73
- with lang.maybe_managing(self._backend_catalog.get_backend(
74
- mc.ChatChoicesStreamService,
75
- self._config.backend or DEFAULT_CHAT_MODEL_BACKEND,
76
- *([mc.ModelName(mn)] if (mn := self._config.model_name) is not None else []),
77
- )) as mdl:
78
- with mdl.invoke(mc.ChatChoicesStreamRequest(
79
- [*state.chat, *new_chat],
80
- (self._chat_options or []),
81
- )).v as st_resp:
82
- lst: list[str] = []
83
- for o in st_resp:
84
- if o:
85
- m = check.single(o).m
86
- if m.c is not None:
87
- print(check.isinstance(m.c, str), end='', flush=True)
88
- lst.append(check.isinstance(m.c, str))
89
- check.none(m.tool_exec_requests)
90
- print()
91
-
92
- resp_m = mc.AiMessage(''.join(lst))
93
- new_chat.append(resp_m)
94
-
95
- self._state_manager.extend_chat(new_chat)
96
-
97
- async def _run_immediate(self) -> None:
98
- prompt = check.isinstance(self._config.content, str)
99
-
100
- if self._config.new:
101
- state = self._state_manager.clear_state()
102
- else:
103
- state = self._state_manager.get_state()
104
-
105
- new_chat: list[mc.Message] = [
106
- mc.UserMessage(prompt),
107
- ]
108
-
109
- mdl: mc.ChatChoicesService
110
- with lang.maybe_managing(self._backend_catalog.get_backend(
111
- mc.ChatChoicesService,
112
- self._config.backend or DEFAULT_CHAT_MODEL_BACKEND,
113
- *([mc.ModelName(mn)] if (mn := self._config.model_name) is not None else []),
114
- )) as mdl:
115
- response: mc.ChatChoicesResponse = mdl.invoke(mc.ChatChoicesRequest(
116
- [*state.chat, *new_chat],
117
- (self._chat_options or []),
118
- ))
119
-
120
- resp_m = response.v[0].m
121
- new_chat.append(resp_m)
122
-
123
- if (trs := resp_m.tool_exec_requests):
124
- check.state(resp_m.c is None)
125
-
126
- tr: mc.ToolExecRequest = check.single(check.not_none(trs))
127
-
128
- trm = await self._tool_exec_request_executor.execute_tool_request(tr)
129
-
130
- print(trm.c)
131
- new_chat.append(trm)
132
-
133
- response = mdl.invoke(mc.ChatChoicesRequest(
134
- [*state.chat, *new_chat],
135
- (self._chat_options or []),
136
- ))
137
-
138
- resp_m = response.v[0].m
139
- new_chat.append(resp_m)
140
-
141
- self._printer.print(resp_m)
142
-
143
- self._state_manager.extend_chat(new_chat)
@@ -1,109 +0,0 @@
1
- import abc
2
- import dataclasses as dc
3
- import datetime
4
-
5
- from omlish import check
6
- from omlish import lang
7
-
8
- from .... import minichain as mc
9
- from ...state import StateStorage
10
-
11
-
12
- ##
13
-
14
-
15
- @dc.dataclass(frozen=True)
16
- class ChatState:
17
- name: str | None = None
18
-
19
- created_at: datetime.datetime = dc.field(default_factory=lang.utcnow)
20
- updated_at: datetime.datetime = dc.field(default_factory=lang.utcnow)
21
-
22
- chat: mc.Chat = ()
23
-
24
-
25
- ##
26
-
27
-
28
- class ChatStateManager(lang.Abstract):
29
- @abc.abstractmethod
30
- def get_state(self) -> ChatState:
31
- raise NotImplementedError
32
-
33
- @abc.abstractmethod
34
- def clear_state(self) -> ChatState:
35
- raise NotImplementedError
36
-
37
- @abc.abstractmethod
38
- def extend_chat(self, chat_additions: mc.Chat) -> ChatState:
39
- raise NotImplementedError
40
-
41
-
42
- ##
43
-
44
-
45
- class InMemoryChatStateManager(ChatStateManager):
46
- def __init__(self, initial_state: ChatState | None = None) -> None:
47
- super().__init__()
48
-
49
- if initial_state is None:
50
- initial_state = ChatState()
51
- self._state = initial_state
52
-
53
- def get_state(self) -> ChatState:
54
- return self._state
55
-
56
- def clear_state(self) -> ChatState:
57
- self._state = ChatState()
58
- return self._state
59
-
60
- def extend_chat(self, chat_additions: mc.Chat) -> ChatState:
61
- self._state = dc.replace(
62
- self._state,
63
- chat=[*self._state.chat, *chat_additions],
64
- updated_at=lang.utcnow(),
65
- )
66
- return self._state
67
-
68
-
69
- ##
70
-
71
-
72
- class StateStorageChatStateManager(ChatStateManager):
73
- def __init__(
74
- self,
75
- *,
76
- storage: StateStorage,
77
- key: str = 'chat',
78
- ) -> None:
79
- super().__init__()
80
-
81
- self._storage = storage
82
- self._key = check.non_empty_str(key)
83
-
84
- self._state: ChatState | None = None
85
-
86
- def get_state(self) -> ChatState:
87
- if self._state is not None:
88
- return self._state
89
- state: ChatState | None = self._storage.load_state(self._key, ChatState)
90
- if state is None:
91
- state = ChatState()
92
- self._state = state
93
- return state
94
-
95
- def clear_state(self) -> ChatState:
96
- state = ChatState()
97
- self._storage.save_state(self._key, state, ChatState)
98
- self._state = state
99
- return state
100
-
101
- def extend_chat(self, chat_additions: mc.Chat) -> ChatState:
102
- state = self.get_state()
103
- state = dc.replace(
104
- state,
105
- chat=[*state.chat, *chat_additions],
106
- updated_at=lang.utcnow(),
107
- )
108
- self._storage.save_state(self._key, state, ChatState)
109
- return state
@@ -1,91 +0,0 @@
1
- import abc
2
- import typing as ta
3
-
4
- from omlish import check
5
- from omlish import lang
6
- from omlish import marshal as msh
7
- from omlish.formats import json
8
-
9
- from .... import minichain as mc
10
-
11
-
12
- if ta.TYPE_CHECKING:
13
- from omdev import ptk
14
- else:
15
- ptk = lang.proxy_import('omdev.ptk')
16
-
17
-
18
- ##
19
-
20
-
21
- class ToolExecutionRequestDeniedError(Exception):
22
- pass
23
-
24
-
25
- class ToolExecutionConfirmation(lang.Abstract):
26
- @abc.abstractmethod
27
- def confirm_tool_execution_or_raise(
28
- self,
29
- tr: mc.ToolExecRequest,
30
- tce: mc.ToolCatalogEntry,
31
- ) -> ta.Awaitable[None]:
32
- raise NotImplementedError
33
-
34
-
35
- class NopToolExecutionConfirmation(ToolExecutionConfirmation):
36
- async def confirm_tool_execution_or_raise(
37
- self,
38
- tr: mc.ToolExecRequest,
39
- tce: mc.ToolCatalogEntry,
40
- ) -> None:
41
- pass
42
-
43
-
44
- class AskingToolExecutionConfirmation(ToolExecutionConfirmation):
45
- async def confirm_tool_execution_or_raise(
46
- self,
47
- tr: mc.ToolExecRequest,
48
- tce: mc.ToolCatalogEntry,
49
- ) -> None:
50
- tr_dct = dict(
51
- id=tr.id,
52
- spec=msh.marshal(tce.spec),
53
- args=tr.args,
54
- )
55
- cr = await ptk.strict_confirm(f'Execute requested tool?\n\n{json.dumps_pretty(tr_dct)}\n\n')
56
-
57
- if not cr:
58
- raise ToolExecutionRequestDeniedError
59
-
60
-
61
- ##
62
-
63
-
64
- class ToolExecRequestExecutor(lang.Abstract):
65
- @abc.abstractmethod
66
- def execute_tool_request(self, tr: mc.ToolExecRequest) -> ta.Awaitable[mc.ToolExecResultMessage]:
67
- raise NotImplementedError
68
-
69
-
70
- class ToolExecRequestExecutorImpl(ToolExecRequestExecutor):
71
- def __init__(
72
- self,
73
- *,
74
- catalog: mc.ToolCatalog,
75
- confirmation: ToolExecutionConfirmation,
76
- ) -> None:
77
- super().__init__()
78
-
79
- self._catalog = catalog
80
- self._confirmation = confirmation
81
-
82
- async def execute_tool_request(self, tr: mc.ToolExecRequest) -> mc.ToolExecResultMessage:
83
- tce = self._catalog.by_name[check.non_empty_str(tr.name)]
84
-
85
- await self._confirmation.confirm_tool_execution_or_raise(tr, tce)
86
-
87
- return await mc.execute_tool_request(
88
- mc.ToolContext(),
89
- tce.executor(),
90
- tr,
91
- )
@@ -1,44 +0,0 @@
1
- import dataclasses as dc
2
-
3
- from omlish import check
4
- from omlish import lang
5
-
6
- from .... import minichain as mc
7
- from ..base import Session
8
-
9
-
10
- ##
11
-
12
-
13
- DEFAULT_COMPLETION_MODEL_BACKEND = 'openai'
14
-
15
-
16
- class CompletionSession(Session['CompletionSession.Config']):
17
- @dc.dataclass(frozen=True)
18
- class Config(Session.Config):
19
- content: mc.Content
20
-
21
- _: dc.KW_ONLY
22
-
23
- backend: str | None = None
24
-
25
- def __init__(
26
- self,
27
- config: Config,
28
- *,
29
- backend_catalog: mc.BackendCatalog,
30
- ) -> None:
31
- super().__init__(config)
32
-
33
- self._backend_catalog = backend_catalog
34
-
35
- async def run(self) -> None:
36
- prompt = check.isinstance(self._config.content, str)
37
-
38
- mdl: mc.CompletionService
39
- with lang.maybe_managing(self._backend_catalog.get_backend(
40
- mc.CompletionService,
41
- self._config.backend or DEFAULT_COMPLETION_MODEL_BACKEND,
42
- )) as mdl:
43
- response = mdl.invoke(mc.CompletionRequest(prompt))
44
- print(response.v.strip())
@@ -1,42 +0,0 @@
1
- import dataclasses as dc
2
-
3
- from omlish import lang
4
- from omlish.formats import json
5
-
6
- from .... import minichain as mc
7
- from ..base import Session
8
-
9
-
10
- ##
11
-
12
-
13
- DEFAULT_EMBEDDING_MODEL_BACKEND = 'openai'
14
-
15
-
16
- class EmbeddingSession(Session['EmbeddingSession.Config']):
17
- @dc.dataclass(frozen=True)
18
- class Config(Session.Config):
19
- content: mc.Content
20
-
21
- _: dc.KW_ONLY
22
-
23
- backend: str | None = None
24
-
25
- def __init__(
26
- self,
27
- config: Config,
28
- *,
29
- backend_catalog: mc.BackendCatalog,
30
- ) -> None:
31
- super().__init__(config)
32
-
33
- self._backend_catalog = backend_catalog
34
-
35
- async def run(self) -> None:
36
- mdl: mc.EmbeddingService
37
- with lang.maybe_managing(self._backend_catalog.get_backend(
38
- mc.EmbeddingService,
39
- self._config.backend or DEFAULT_EMBEDDING_MODEL_BACKEND,
40
- )) as mdl:
41
- response = mdl.invoke(mc.EmbeddingRequest(self._config.content))
42
- print(json.dumps_compact(list(map(float, response.v))))
@@ -1,13 +0,0 @@
1
- from omlish import dataclasses as dc
2
-
3
-
4
- ##
5
-
6
-
7
- @dc.dataclass(frozen=True, kw_only=True)
8
- class ToolsConfig:
9
- enable_fs_tools: bool = False
10
-
11
- enable_unsafe_bash_tool: bool = False
12
-
13
- enable_test_weather_tool: bool = False
@@ -1,64 +0,0 @@
1
- import dataclasses as dc
2
- import typing as ta
3
-
4
- from omlish import inject as inj
5
- from omlish import lang
6
-
7
- from ... import minichain as mc
8
- from ..sessions.chat.inject import bind_chat_options
9
- from .config import ToolsConfig
10
- from .weather import WEATHER_TOOL
11
-
12
-
13
- ##
14
-
15
-
16
- @dc.dataclass(frozen=True, eq=False)
17
- class _InjectedTool:
18
- tce: mc.ToolCatalogEntry
19
-
20
-
21
- def bind_tool(tce: mc.ToolCatalogEntry) -> inj.Element | inj.Elements:
22
- return inj.as_elements(
23
- inj.bind_set_entry_const(ta.AbstractSet[_InjectedTool], _InjectedTool(tce)),
24
-
25
- bind_chat_options(mc.Tool(tce.spec)),
26
- )
27
-
28
-
29
- ##
30
-
31
-
32
- def bind_tools(tools_config: ToolsConfig) -> inj.Elements:
33
- els: list[inj.Elemental] = [
34
- inj.bind(tools_config),
35
-
36
- inj.bind(mc.ToolCatalog, singleton=True),
37
-
38
- inj.set_binder[_InjectedTool](),
39
- inj.bind(
40
- lang.typed_lambda(mc.ToolCatalogEntries, s=ta.AbstractSet[_InjectedTool])(
41
- lambda s: [it.tce for it in s],
42
- ),
43
- singleton=True,
44
- ),
45
- ]
46
-
47
- #
48
-
49
- if tools_config.enable_fs_tools:
50
- from ...minichain.lib.fs.ls.execution import ls_tool
51
-
52
- els.append(bind_tool(ls_tool()))
53
-
54
- if tools_config.enable_unsafe_bash_tool:
55
- from ...minichain.lib.bash import bash_tool
56
-
57
- els.append(bind_tool(bash_tool()))
58
-
59
- if tools_config.enable_test_weather_tool:
60
- els.append(bind_tool(WEATHER_TOOL))
61
-
62
- #
63
-
64
- return inj.as_elements(*els)
@@ -1,69 +0,0 @@
1
- import typing as ta
2
-
3
- from omlish import check
4
- from omlish import dataclasses as dc
5
-
6
- from ...services import Response
7
- from ..choices.services import ChatChoicesRequest
8
- from ..choices.services import static_check_is_chat_choices_service
9
- from ..choices.types import AiChoice
10
- from ..choices.types import AiChoices
11
- from ..messages import AiMessage
12
- from ..messages import ToolExecRequest
13
- from .services import ChatChoicesOutputs
14
- from .services import ChatChoicesStreamOutputs
15
- from .services import ChatChoicesStreamService
16
-
17
-
18
- ##
19
-
20
-
21
- @static_check_is_chat_choices_service
22
- @dc.dataclass(frozen=True)
23
- class ChatChoicesStreamServiceChatChoicesService:
24
- service: ChatChoicesStreamService
25
-
26
- class _Choice(ta.NamedTuple):
27
- parts: list[str]
28
- trs: list[ToolExecRequest]
29
-
30
- def invoke(self, request: ChatChoicesRequest) -> Response[
31
- AiChoices,
32
- ChatChoicesOutputs | ChatChoicesStreamOutputs,
33
- ]:
34
- lst: list[ChatChoicesStreamServiceChatChoicesService._Choice] = []
35
-
36
- resp = self.service.invoke(request)
37
- with resp.v as resp_v:
38
- i = -1 # noqa
39
- for i, cs in enumerate(resp_v):
40
- if i == 0:
41
- for c in cs:
42
- m = c.m
43
- lst.append(self._Choice(
44
- [check.isinstance(m.c, str)] if m.c is not None else [],
45
- # FIXME
46
- # list(m.tool_exec_requests or []),
47
- [],
48
- ))
49
-
50
- else:
51
- for ch, c in zip(lst, cs, strict=True):
52
- m = c.m
53
- if m.c is not None:
54
- ch.parts.append(check.isinstance(m.c, str))
55
- # FIXME
56
- # if m.tool_exec_requests:
57
- # ch.trs.extend(m.tool_exec_requests)
58
-
59
- check.state(resp_v.is_done)
60
-
61
- ret: list[AiChoice] = []
62
- for ch in lst:
63
- ret.append(AiChoice(AiMessage(
64
- ''.join(ch.parts) if ch.parts else None,
65
- ch.trs or None,
66
- )))
67
-
68
- # FIXME: outputs lol
69
- return Response(ret)
@@ -1,32 +0,0 @@
1
- from omlish import lang
2
-
3
- from ....tools.execution.catalog import ToolCatalogEntry
4
- from ....tools.execution.reflect import reflect_tool_catalog_entry
5
- from .rendering import LsLinesRenderer
6
- from .running import LsRunner
7
-
8
-
9
- ##
10
-
11
-
12
- def execute_ls_tool(
13
- base_path: str,
14
- ) -> str:
15
- """
16
- Recursively lists the directory contents of the given base path.
17
-
18
- Args:
19
- base_path: The path of the directory to list the contents of.
20
-
21
- Returns:
22
- A formatted string of the recursive directory contents.
23
- """
24
-
25
- root = LsRunner().run(base_path)
26
- lines = LsLinesRenderer().render(root)
27
- return '\n'.join(lines.lines)
28
-
29
-
30
- @lang.cached_function
31
- def ls_tool() -> ToolCatalogEntry:
32
- return reflect_tool_catalog_entry(execute_ls_tool)