code-puppy 0.0.154__py3-none-any.whl → 0.0.156__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.
- code_puppy/agent.py +26 -5
- code_puppy/agents/agent_creator_agent.py +65 -13
- code_puppy/agents/json_agent.py +8 -0
- code_puppy/agents/runtime_manager.py +12 -4
- code_puppy/command_line/command_handler.py +83 -0
- code_puppy/command_line/mcp/install_command.py +50 -1
- code_puppy/command_line/mcp/wizard_utils.py +88 -17
- code_puppy/command_line/prompt_toolkit_completion.py +18 -2
- code_puppy/config.py +8 -2
- code_puppy/main.py +17 -4
- code_puppy/mcp/__init__.py +2 -2
- code_puppy/mcp/config_wizard.py +1 -1
- code_puppy/messaging/spinner/console_spinner.py +1 -1
- code_puppy/model_factory.py +13 -12
- code_puppy/models.json +26 -0
- code_puppy/round_robin_model.py +35 -18
- code_puppy/summarization_agent.py +1 -3
- code_puppy/tools/agent_tools.py +41 -138
- code_puppy/tools/file_operations.py +116 -96
- code_puppy/tui/app.py +1 -1
- {code_puppy-0.0.154.data → code_puppy-0.0.156.data}/data/code_puppy/models.json +26 -0
- {code_puppy-0.0.154.dist-info → code_puppy-0.0.156.dist-info}/METADATA +4 -3
- {code_puppy-0.0.154.dist-info → code_puppy-0.0.156.dist-info}/RECORD +26 -48
- code_puppy/token_utils.py +0 -67
- code_puppy/tools/token_check.py +0 -32
- code_puppy/tui/tests/__init__.py +0 -1
- code_puppy/tui/tests/test_agent_command.py +0 -79
- code_puppy/tui/tests/test_chat_message.py +0 -28
- code_puppy/tui/tests/test_chat_view.py +0 -88
- code_puppy/tui/tests/test_command_history.py +0 -89
- code_puppy/tui/tests/test_copy_button.py +0 -191
- code_puppy/tui/tests/test_custom_widgets.py +0 -27
- code_puppy/tui/tests/test_disclaimer.py +0 -27
- code_puppy/tui/tests/test_enums.py +0 -15
- code_puppy/tui/tests/test_file_browser.py +0 -60
- code_puppy/tui/tests/test_help.py +0 -38
- code_puppy/tui/tests/test_history_file_reader.py +0 -107
- code_puppy/tui/tests/test_input_area.py +0 -33
- code_puppy/tui/tests/test_settings.py +0 -44
- code_puppy/tui/tests/test_sidebar.py +0 -33
- code_puppy/tui/tests/test_sidebar_history.py +0 -153
- code_puppy/tui/tests/test_sidebar_history_navigation.py +0 -132
- code_puppy/tui/tests/test_status_bar.py +0 -54
- code_puppy/tui/tests/test_timestamped_history.py +0 -52
- code_puppy/tui/tests/test_tools.py +0 -82
- {code_puppy-0.0.154.dist-info → code_puppy-0.0.156.dist-info}/WHEEL +0 -0
- {code_puppy-0.0.154.dist-info → code_puppy-0.0.156.dist-info}/entry_points.txt +0 -0
- {code_puppy-0.0.154.dist-info → code_puppy-0.0.156.dist-info}/licenses/LICENSE +0 -0
|
@@ -1,43 +1,42 @@
|
|
|
1
1
|
code_puppy/__init__.py,sha256=ehbM1-wMjNmOXk_DBhhJECFyBv2dRHwwo7ucjHeM68E,107
|
|
2
2
|
code_puppy/__main__.py,sha256=pDVssJOWP8A83iFkxMLY9YteHYat0EyWDQqMkKHpWp4,203
|
|
3
|
-
code_puppy/agent.py,sha256=
|
|
3
|
+
code_puppy/agent.py,sha256=hZOrJJJDwtLtb82b6Zyt5CZb8RbzDtvHMIBUPVYsgOM,8133
|
|
4
4
|
code_puppy/callbacks.py,sha256=6wYB6K_fGSCkKKEFaYOYkJT45WaV5W_NhUIzcvVH_nU,5060
|
|
5
|
-
code_puppy/config.py,sha256=
|
|
5
|
+
code_puppy/config.py,sha256=nD-1Ftwzd1LgZIi5Pi0P4_8DvPkZiOwFXQ5UuYFMO6E,16207
|
|
6
6
|
code_puppy/http_utils.py,sha256=BAvt4hed7fVMXglA7eS9gOb08h2YTuOyai6VmQq09fg,3432
|
|
7
|
-
code_puppy/main.py,sha256=
|
|
7
|
+
code_puppy/main.py,sha256=tYLfhUjPTJ-4S1r-pr-jSbn6kIU1iYvt2Z8lxI7zDFY,22220
|
|
8
8
|
code_puppy/message_history_processor.py,sha256=aV-vcRcOQJPZPlrokB4CaLMxEU3Y4nDiabb9Ov_sJeU,15933
|
|
9
|
-
code_puppy/model_factory.py,sha256
|
|
10
|
-
code_puppy/models.json,sha256=
|
|
9
|
+
code_puppy/model_factory.py,sha256=0tJWwmKHSqNGEiakk1aGdUrlZyQy0QM4yShxHqxmXpA,11758
|
|
10
|
+
code_puppy/models.json,sha256=jNLDAGhbASNAhul64H4SMS5V4Y6QKW09WcNej4I_4oc,4034
|
|
11
11
|
code_puppy/reopenable_async_client.py,sha256=4UJRaMp5np8cbef9F0zKQ7TPKOfyf5U-Kv-0zYUWDho,8274
|
|
12
|
-
code_puppy/round_robin_model.py,sha256=
|
|
12
|
+
code_puppy/round_robin_model.py,sha256=SEN3VSwTgC5wHjx2sZsHQLPWOycf4jGwzB-EydgqkdY,5643
|
|
13
13
|
code_puppy/state_management.py,sha256=o4mNBCPblRyVrNBH-992-1YqffgH6AKHU7iZRqgP1LI,5925
|
|
14
14
|
code_puppy/status_display.py,sha256=F6eEAkGePDp4StM2BWj-uLLQTDGtJrf0IufzCeP1rRg,8336
|
|
15
|
-
code_puppy/summarization_agent.py,sha256
|
|
16
|
-
code_puppy/token_utils.py,sha256=inLo-S2YERGA-JmV-nrSFN7KMswSfHxpawAuK6YiDHc,1982
|
|
15
|
+
code_puppy/summarization_agent.py,sha256=kos4_YK-l_YjYRq4Fs4X5YoTUbmAcDhhPqefL-rdenI,3197
|
|
17
16
|
code_puppy/version_checker.py,sha256=bjLDmgGPrl7XnYwX1u13O8uFlsfikV90PK6nbA9Z9QU,1150
|
|
18
17
|
code_puppy/agents/__init__.py,sha256=SwtHGNG1GIgDBv7y3EGIXOXEWrG_Ou7fEknNgFbrHv8,594
|
|
19
18
|
code_puppy/agents/agent_code_puppy.py,sha256=sbuQxLzlkMbPOyLbILbXOAHecRsxbFdQt13HJ_GEqQo,7972
|
|
20
|
-
code_puppy/agents/agent_creator_agent.py,sha256=
|
|
19
|
+
code_puppy/agents/agent_creator_agent.py,sha256=jyOfqCa4d3Tqlv0ZODjK1J6cRwJjBxKyNa9RQSdsB44,23256
|
|
21
20
|
code_puppy/agents/agent_manager.py,sha256=nXvro6fpX8KA-NedRoVJuhJW966trrePOrH4eAnqq40,17034
|
|
22
21
|
code_puppy/agents/agent_orchestrator.json,sha256=Iqnc0p6ICoAlUTMkEsi1XXMXJi4pdxVnWZUMaih6s5o,1267
|
|
23
22
|
code_puppy/agents/base_agent.py,sha256=XYSff6IQX9Z6C7hPVbN_YXC2xfjwd268e2jtG3ZGnVk,3450
|
|
24
|
-
code_puppy/agents/json_agent.py,sha256=
|
|
25
|
-
code_puppy/agents/runtime_manager.py,sha256=
|
|
23
|
+
code_puppy/agents/json_agent.py,sha256=y6AYE3Fx9LhmemcPzt46d7359MNnkGIjU83YBGNer2g,4533
|
|
24
|
+
code_puppy/agents/runtime_manager.py,sha256=fUOBpmETo3wTyLc5wWBfGKSX1HFRQWSpuwxYAOyA-_8,10059
|
|
26
25
|
code_puppy/command_line/__init__.py,sha256=y7WeRemfYppk8KVbCGeAIiTuiOszIURCDjOMZv_YRmU,45
|
|
27
|
-
code_puppy/command_line/command_handler.py,sha256=
|
|
26
|
+
code_puppy/command_line/command_handler.py,sha256=KVZySqUMJwrRadKSUCcWa62FZ_lge5XjxD0Hebzr2EE,24520
|
|
28
27
|
code_puppy/command_line/file_path_completion.py,sha256=gw8NpIxa6GOpczUJRyh7VNZwoXKKn-yvCqit7h2y6Gg,2931
|
|
29
28
|
code_puppy/command_line/load_context_completion.py,sha256=6eZxV6Bs-EFwZjN93V8ZDZUC-6RaWxvtZk-04Wtikyw,2240
|
|
30
29
|
code_puppy/command_line/meta_command_handler.py,sha256=80aK5JQOaqjt149qBmSsM02uy2Cikkee8zaQnu5u2KQ,5712
|
|
31
30
|
code_puppy/command_line/model_picker_completion.py,sha256=adxp3NZaDV67YqaGv0SG7WVvOTXN0UwkkLqxTsknAvs,4126
|
|
32
31
|
code_puppy/command_line/motd.py,sha256=PEdkp3ZnydVfvd7mNJylm8YyFNUKg9jmY6uwkA1em8c,2152
|
|
33
|
-
code_puppy/command_line/prompt_toolkit_completion.py,sha256=
|
|
32
|
+
code_puppy/command_line/prompt_toolkit_completion.py,sha256=saq1ZRjcxK8s2M-SKy-7I62xGC4Cpxdw02bvxbMwTxA,10010
|
|
34
33
|
code_puppy/command_line/utils.py,sha256=7eyxDHjPjPB9wGDJQQcXV_zOsGdYsFgI0SGCetVmTqE,1251
|
|
35
34
|
code_puppy/command_line/mcp/__init__.py,sha256=0-OQuwjq_pLiTVJ1_NrirVwdRerghyKs_MTZkwPC7YY,315
|
|
36
35
|
code_puppy/command_line/mcp/add_command.py,sha256=RghGmOCjwwYJfrbLiV5UZojMA4-FNPlM04LKci0rpAw,6415
|
|
37
36
|
code_puppy/command_line/mcp/base.py,sha256=nIDv0S5LmGuYtYjVAa9yw3NuSvldxDB17YEEvhbEL1s,889
|
|
38
37
|
code_puppy/command_line/mcp/handler.py,sha256=ZPWNfJEwGurNQh4KUCRRRsHXuB0kHlaGG4oLN1sFhBg,4412
|
|
39
38
|
code_puppy/command_line/mcp/help_command.py,sha256=Z55-ObpUQFMdqMWAkSJkRi_v2uZhDFVxg6DcIdjVY6Q,5250
|
|
40
|
-
code_puppy/command_line/mcp/install_command.py,sha256=
|
|
39
|
+
code_puppy/command_line/mcp/install_command.py,sha256=AgrEp-MynkbLsrOZL54dod5jUsc0Zw_VbHcS3EFz8N4,8826
|
|
41
40
|
code_puppy/command_line/mcp/list_command.py,sha256=9ggXgoqMyzCp9_XGMLbA0WOdIDTynRfJC0VRxnjG7uk,3178
|
|
42
41
|
code_puppy/command_line/mcp/logs_command.py,sha256=x_QsVGPpI5XY7RCZtiNFegc6R3csiwF_IEB_Rh2575w,4453
|
|
43
42
|
code_puppy/command_line/mcp/remove_command.py,sha256=MrWmXQ9jZTq1wrohFDO3ls0a1faTHCqRZocN-ynTzh8,2753
|
|
@@ -50,13 +49,13 @@ code_puppy/command_line/mcp/stop_all_command.py,sha256=-HbIE-WXzfWEMFVZhFtxf7pfe
|
|
|
50
49
|
code_puppy/command_line/mcp/stop_command.py,sha256=zuZO8pIP2Ix11LATf-cwwX3fPFIGAbRDaZ6qnfPTqLY,2594
|
|
51
50
|
code_puppy/command_line/mcp/test_command.py,sha256=Pjod77DYRcA9WDZcxaCe6AUgpEXKJr42QRkxMhSjXhM,3689
|
|
52
51
|
code_puppy/command_line/mcp/utils.py,sha256=FqaeJMPEp39suMq_R3_xb-e8zcNpw1Rcluwvdgum3Uo,3624
|
|
53
|
-
code_puppy/command_line/mcp/wizard_utils.py,sha256=
|
|
54
|
-
code_puppy/mcp/__init__.py,sha256=
|
|
52
|
+
code_puppy/command_line/mcp/wizard_utils.py,sha256=HabnT3y6EWLP6w1llRwVO_P25Wi15bYFddTM_2kxAq8,11073
|
|
53
|
+
code_puppy/mcp/__init__.py,sha256=UZ6ZYEIN8At3Jq88ZTkrVQHswNMxHyIBz4hbOn71osk,1444
|
|
55
54
|
code_puppy/mcp/async_lifecycle.py,sha256=pTQrwQCVgjad8EJeRTSHtIeSQRgT_8r5BeLv-1SgKog,7772
|
|
56
55
|
code_puppy/mcp/blocking_startup.py,sha256=bgYln3j12kuHoBsoCUzCjVcTdcoSIAx8kSaOJVwUaRg,13484
|
|
57
56
|
code_puppy/mcp/captured_stdio_server.py,sha256=ubINgtKdd5-oOLR7MRuavUqd40iQFJk2YCNtTFYeI5Q,8948
|
|
58
57
|
code_puppy/mcp/circuit_breaker.py,sha256=a83YwXux9h4R6zBWBUrCIqtp2ffyl7JZEoK2tErG_0I,8601
|
|
59
|
-
code_puppy/mcp/config_wizard.py,sha256=
|
|
58
|
+
code_puppy/mcp/config_wizard.py,sha256=SIsm8uhDInfRYy_2W8wPIZcmoxk24680ikhMT93VuvQ,16481
|
|
60
59
|
code_puppy/mcp/dashboard.py,sha256=y6t6trrBZU-mr8W1_29VN5DeZI8VYvOsKNz1EXxlvUg,9022
|
|
61
60
|
code_puppy/mcp/error_isolation.py,sha256=mpPBiH17zTXPsOEAn9WmkbwQwnt4gmgiaWv87JBJbUo,12426
|
|
62
61
|
code_puppy/mcp/health_monitor.py,sha256=n5R6EeYOYbUucUFe74qGWCU3g6Mep5UEQbLF0wbT0dU,19688
|
|
@@ -73,20 +72,19 @@ code_puppy/messaging/message_queue.py,sha256=CDVpstLee_RbCBeJWv2eON3c3qhlEISf2i9
|
|
|
73
72
|
code_puppy/messaging/queue_console.py,sha256=L4QFUsR_emAFsIRan3-rnL-F1LODF4DG6je-IlUTxNc,10864
|
|
74
73
|
code_puppy/messaging/renderers.py,sha256=9VOpVmu7emyyg1CXgm17u4IzMNcLHvueBl7G14pLQho,16123
|
|
75
74
|
code_puppy/messaging/spinner/__init__.py,sha256=9mkXPYojafydBOAMh9ZUrB4X6uH5Iqz_-E-Obpd72ko,1365
|
|
76
|
-
code_puppy/messaging/spinner/console_spinner.py,sha256=
|
|
75
|
+
code_puppy/messaging/spinner/console_spinner.py,sha256=DhEXjD37_FuJwcNNfIP2D0y1ruGlFmuCCuaUW4DFrNg,6932
|
|
77
76
|
code_puppy/messaging/spinner/spinner_base.py,sha256=474qMrTYpNfWcprFzmhaOJEOC-2rRHpTFCLsnl54bXA,1689
|
|
78
77
|
code_puppy/messaging/spinner/textual_spinner.py,sha256=Omx9A-FSPkxYDMYgBXgYMBQnK-DMlyqLOgkFVG8cmo4,3465
|
|
79
78
|
code_puppy/plugins/__init__.py,sha256=fksDqMUiXPJ5WNuMsYsVR8ulueQRCXPlvECEyicHPtQ,1312
|
|
80
79
|
code_puppy/tools/__init__.py,sha256=YiiXRqxU1BEJ5t0Oe163lSqOneI9sKtwDW0swCPgBt4,2119
|
|
81
|
-
code_puppy/tools/agent_tools.py,sha256=
|
|
80
|
+
code_puppy/tools/agent_tools.py,sha256=bHMrFIbYRhuubR41G_XdLsk3cUKWfIPl2O4bVzo2pE0,5591
|
|
82
81
|
code_puppy/tools/command_runner.py,sha256=GVNsgwjTFD9tkNlycgMNmMoVPdmMkZkbAcHH5y6iMww,26070
|
|
83
82
|
code_puppy/tools/common.py,sha256=pL-9xcRs3rxU7Fl9X9EUgbDp2-csh2LLJ5DHH_KAHKY,10596
|
|
84
83
|
code_puppy/tools/file_modifications.py,sha256=oeNEQItqwMhGOeEN2TzGR7TjmgLsfFFdPaVMzWbfXIQ,30398
|
|
85
|
-
code_puppy/tools/file_operations.py,sha256=
|
|
86
|
-
code_puppy/tools/token_check.py,sha256=cNrGOOKahXsnWsvh5xnMkL1NS9FjYur9QIRZGQFW-pE,1189
|
|
84
|
+
code_puppy/tools/file_operations.py,sha256=dfG1MDmpvbxsdapSAyo-FJoctC1XM6_AO8HM1PlxUIE,30894
|
|
87
85
|
code_puppy/tools/tools_content.py,sha256=bsBqW-ppd1XNAS_g50B3UHDQBWEALC1UneH6-afz1zo,2365
|
|
88
86
|
code_puppy/tui/__init__.py,sha256=XesAxIn32zLPOmvpR2wIDxDAnnJr81a5pBJB4cZp1Xs,321
|
|
89
|
-
code_puppy/tui/app.py,sha256=
|
|
87
|
+
code_puppy/tui/app.py,sha256=nPOzwlusjdWzBfu__EbC3Q0etkPrqRq-2g-mk4IcfG4,39378
|
|
90
88
|
code_puppy/tui/messages.py,sha256=zQoToWI0eWdT36NEsY6RdCFzcDfAmfvoPlHv8jiCbgo,720
|
|
91
89
|
code_puppy/tui/components/__init__.py,sha256=uj5pnk3s6SEN3SbFI0ZnzaA2KK1NNg8TfUj6U-Z732U,455
|
|
92
90
|
code_puppy/tui/components/chat_view.py,sha256=wKdrCWgoo8p_f9rL9lB6PDuW4eVdMSZe88TVo--sGF0,18547
|
|
@@ -106,29 +104,9 @@ code_puppy/tui/screens/help.py,sha256=eJuPaOOCp7ZSUlecearqsuX6caxWv7NQszUh0tZJjB
|
|
|
106
104
|
code_puppy/tui/screens/mcp_install_wizard.py,sha256=xqwN5omltMkfxWZwXj3D2PbXbtrxUi1dT0XT77oxOKk,27685
|
|
107
105
|
code_puppy/tui/screens/settings.py,sha256=GMpv-qa08rorAE9mj3AjmqjZFPhmeJ_GWd-DBHG6iAA,10671
|
|
108
106
|
code_puppy/tui/screens/tools.py,sha256=3pr2Xkpa9Js6Yhf1A3_wQVRzFOui-KDB82LwrsdBtyk,1715
|
|
109
|
-
code_puppy/
|
|
110
|
-
code_puppy/
|
|
111
|
-
code_puppy/
|
|
112
|
-
code_puppy/
|
|
113
|
-
code_puppy/
|
|
114
|
-
code_puppy
|
|
115
|
-
code_puppy/tui/tests/test_custom_widgets.py,sha256=kRsbnWDe0o8yz-3bWYlvX13fzlQeVp5zt4SgwIjag9k,640
|
|
116
|
-
code_puppy/tui/tests/test_disclaimer.py,sha256=x83pkEldP-oCtoNgq8Tq-9hmPymxJETRwbIMoU1bxtg,921
|
|
117
|
-
code_puppy/tui/tests/test_enums.py,sha256=UJ-F-ssqLiBHdvTMM6I7eOwiY8bthr7_wZPpmGjSvyo,430
|
|
118
|
-
code_puppy/tui/tests/test_file_browser.py,sha256=MxFZXPV6wX5Zu22k78i4cO2_3Y86jDxdpWtIJjD4uYY,2006
|
|
119
|
-
code_puppy/tui/tests/test_help.py,sha256=FeuhSOKkrZ41e6oM6T3d7IBFLxY8H4CXI-sf-EZ3hr4,1116
|
|
120
|
-
code_puppy/tui/tests/test_history_file_reader.py,sha256=xALYU9BKH4ZpsLT2Vt1nn5uj6cF05GRq4swKkoO62SI,3610
|
|
121
|
-
code_puppy/tui/tests/test_input_area.py,sha256=Loic1TDs-0ae7V551UHCxAxkMI4ltIiXGs6dKucEFHs,938
|
|
122
|
-
code_puppy/tui/tests/test_settings.py,sha256=uP7mGRy2vslQqAQCeG66eDiCVivG0wzKN5fwkG2Y3zw,1330
|
|
123
|
-
code_puppy/tui/tests/test_sidebar.py,sha256=GrnslL6V9e-q5Vm3Kq4ajp3YFtGehLY0i6Xa1KjjKdE,909
|
|
124
|
-
code_puppy/tui/tests/test_sidebar_history.py,sha256=Va57Ww2nwMXgHrsnZAObMyLPU5a8-WbRjMqhzi_UgMc,5875
|
|
125
|
-
code_puppy/tui/tests/test_sidebar_history_navigation.py,sha256=JGiyua8A2B8dLfwiEzyJjl7AWuzajVmStFIZe3OlW50,5157
|
|
126
|
-
code_puppy/tui/tests/test_status_bar.py,sha256=nYT_FZGdmqnnbn6o0ZuOkLtNUtJzLSmtX8P72liQ5Vo,1797
|
|
127
|
-
code_puppy/tui/tests/test_timestamped_history.py,sha256=nVXt9hExZZ_8MFP-AZj4L4bB_1Eo_mc-ZhVICzTuw3I,1799
|
|
128
|
-
code_puppy/tui/tests/test_tools.py,sha256=kgzzAkK4r0DPzQwHHD4cePpVNgrHor6cFr05Pg6DBWg,2687
|
|
129
|
-
code_puppy-0.0.154.data/data/code_puppy/models.json,sha256=dAfpMMI2EEeOMv0ynHSmMuJAYDLcZrs5gCLX3voC4-A,3252
|
|
130
|
-
code_puppy-0.0.154.dist-info/METADATA,sha256=r4J6tLEqJwVVG7j5eMrQRI1zMENfwZKdNo2KrOI_pBQ,19516
|
|
131
|
-
code_puppy-0.0.154.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
|
|
132
|
-
code_puppy-0.0.154.dist-info/entry_points.txt,sha256=d8YkBvIUxF-dHNJAj-x4fPEqizbY5d_TwvYpc01U5kw,58
|
|
133
|
-
code_puppy-0.0.154.dist-info/licenses/LICENSE,sha256=31u8x0SPgdOq3izJX41kgFazWsM43zPEF9eskzqbJMY,1075
|
|
134
|
-
code_puppy-0.0.154.dist-info/RECORD,,
|
|
107
|
+
code_puppy-0.0.156.data/data/code_puppy/models.json,sha256=jNLDAGhbASNAhul64H4SMS5V4Y6QKW09WcNej4I_4oc,4034
|
|
108
|
+
code_puppy-0.0.156.dist-info/METADATA,sha256=-z0wFe40Q3FDRWzi1Z5vv-2VmPBu2fwa_57kwZHYhJg,19567
|
|
109
|
+
code_puppy-0.0.156.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
|
|
110
|
+
code_puppy-0.0.156.dist-info/entry_points.txt,sha256=d8YkBvIUxF-dHNJAj-x4fPEqizbY5d_TwvYpc01U5kw,58
|
|
111
|
+
code_puppy-0.0.156.dist-info/licenses/LICENSE,sha256=31u8x0SPgdOq3izJX41kgFazWsM43zPEF9eskzqbJMY,1075
|
|
112
|
+
code_puppy-0.0.156.dist-info/RECORD,,
|
code_puppy/token_utils.py
DELETED
|
@@ -1,67 +0,0 @@
|
|
|
1
|
-
import json
|
|
2
|
-
|
|
3
|
-
import pydantic
|
|
4
|
-
from pydantic_ai.messages import ModelMessage
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
def estimate_token_count(text: str) -> int:
|
|
8
|
-
"""
|
|
9
|
-
Simple token estimation using len(message) - 4.
|
|
10
|
-
This replaces tiktoken with a much simpler approach.
|
|
11
|
-
"""
|
|
12
|
-
return max(1, len(text) - 4)
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
def stringify_message_part(part) -> str:
|
|
16
|
-
"""
|
|
17
|
-
Convert a message part to a string representation for token estimation or other uses.
|
|
18
|
-
|
|
19
|
-
Args:
|
|
20
|
-
part: A message part that may contain content or be a tool call
|
|
21
|
-
|
|
22
|
-
Returns:
|
|
23
|
-
String representation of the message part
|
|
24
|
-
"""
|
|
25
|
-
result = ""
|
|
26
|
-
if hasattr(part, "part_kind"):
|
|
27
|
-
result += part.part_kind + ": "
|
|
28
|
-
else:
|
|
29
|
-
result += str(type(part)) + ": "
|
|
30
|
-
|
|
31
|
-
# Handle content
|
|
32
|
-
if hasattr(part, "content") and part.content:
|
|
33
|
-
# Handle different content types
|
|
34
|
-
if isinstance(part.content, str):
|
|
35
|
-
result = part.content
|
|
36
|
-
elif isinstance(part.content, pydantic.BaseModel):
|
|
37
|
-
result = json.dumps(part.content.model_dump())
|
|
38
|
-
elif isinstance(part.content, dict):
|
|
39
|
-
result = json.dumps(part.content)
|
|
40
|
-
else:
|
|
41
|
-
result = str(part.content)
|
|
42
|
-
|
|
43
|
-
# Handle tool calls which may have additional token costs
|
|
44
|
-
# If part also has content, we'll process tool calls separately
|
|
45
|
-
if hasattr(part, "tool_name") and part.tool_name:
|
|
46
|
-
# Estimate tokens for tool name and parameters
|
|
47
|
-
tool_text = part.tool_name
|
|
48
|
-
if hasattr(part, "args"):
|
|
49
|
-
tool_text += f" {str(part.args)}"
|
|
50
|
-
result += tool_text
|
|
51
|
-
|
|
52
|
-
return result
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
def estimate_tokens_for_message(message: ModelMessage) -> int:
|
|
56
|
-
"""
|
|
57
|
-
Estimate the number of tokens in a message using len(message) - 4.
|
|
58
|
-
Simple and fast replacement for tiktoken.
|
|
59
|
-
"""
|
|
60
|
-
total_tokens = 0
|
|
61
|
-
|
|
62
|
-
for part in message.parts:
|
|
63
|
-
part_str = stringify_message_part(part)
|
|
64
|
-
if part_str:
|
|
65
|
-
total_tokens += estimate_token_count(part_str)
|
|
66
|
-
|
|
67
|
-
return max(1, total_tokens)
|
code_puppy/tools/token_check.py
DELETED
|
@@ -1,32 +0,0 @@
|
|
|
1
|
-
try:
|
|
2
|
-
from code_puppy.token_utils import estimate_tokens_for_message
|
|
3
|
-
from code_puppy.tools.common import get_model_context_length
|
|
4
|
-
except ImportError:
|
|
5
|
-
# Fallback if these modules aren't available in the internal version
|
|
6
|
-
def get_model_context_length():
|
|
7
|
-
return 128000 # Default context length
|
|
8
|
-
|
|
9
|
-
def estimate_tokens_for_message(msg):
|
|
10
|
-
# Simple fallback estimation
|
|
11
|
-
return len(str(msg)) // 4 # Rough estimate: 4 chars per token
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
def token_guard(num_tokens: int):
|
|
15
|
-
try:
|
|
16
|
-
from code_puppy import state_management
|
|
17
|
-
|
|
18
|
-
current_history = state_management.get_message_history()
|
|
19
|
-
message_hist_tokens = sum(
|
|
20
|
-
estimate_tokens_for_message(msg) for msg in current_history
|
|
21
|
-
)
|
|
22
|
-
|
|
23
|
-
if message_hist_tokens + num_tokens > (get_model_context_length() * 0.9):
|
|
24
|
-
raise ValueError(
|
|
25
|
-
"Tokens produced by this tool call would exceed model capacity"
|
|
26
|
-
)
|
|
27
|
-
except ImportError:
|
|
28
|
-
# Fallback: simple check against a reasonable limit
|
|
29
|
-
if num_tokens > 10000:
|
|
30
|
-
raise ValueError(
|
|
31
|
-
f"Token count {num_tokens} exceeds safety limit of 10,000 tokens"
|
|
32
|
-
)
|
code_puppy/tui/tests/__init__.py
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
# Test package for tui
|
|
@@ -1,79 +0,0 @@
|
|
|
1
|
-
"""Tests for the /agent command handling in TUI mode."""
|
|
2
|
-
|
|
3
|
-
from unittest.mock import MagicMock, patch
|
|
4
|
-
|
|
5
|
-
from code_puppy.tui.app import CodePuppyTUI
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
class TestTUIAgentCommand:
|
|
9
|
-
"""Test the TUI's handling of /agent commands."""
|
|
10
|
-
|
|
11
|
-
@patch("code_puppy.tui.app.get_runtime_agent_manager")
|
|
12
|
-
@patch("code_puppy.tui.app.handle_command")
|
|
13
|
-
def test_tui_handles_agent_command(self, mock_handle_command, mock_get_manager):
|
|
14
|
-
"""Test that TUI properly delegates /agent commands to command handler."""
|
|
15
|
-
# Create a TUI app instance
|
|
16
|
-
app = CodePuppyTUI()
|
|
17
|
-
|
|
18
|
-
# Mock the agent manager and agent
|
|
19
|
-
mock_agent_instance = MagicMock()
|
|
20
|
-
mock_manager = MagicMock()
|
|
21
|
-
mock_manager.get_agent.return_value = mock_agent_instance
|
|
22
|
-
mock_get_manager.return_value = mock_manager
|
|
23
|
-
|
|
24
|
-
# Mock handle_command to simulate successful processing
|
|
25
|
-
mock_handle_command.return_value = True
|
|
26
|
-
|
|
27
|
-
# Simulate processing an /agent command
|
|
28
|
-
message = "/agent code-puppy"
|
|
29
|
-
app.agent = mock_agent_instance
|
|
30
|
-
|
|
31
|
-
# Call the method that processes messages
|
|
32
|
-
# We'll need to mock some UI elements to avoid complex setup
|
|
33
|
-
with (
|
|
34
|
-
patch.object(app, "add_user_message"),
|
|
35
|
-
patch.object(app, "_update_submit_cancel_button"),
|
|
36
|
-
patch.object(app, "start_agent_progress"),
|
|
37
|
-
patch.object(app, "stop_agent_progress"),
|
|
38
|
-
patch.object(app, "refresh_history_display"),
|
|
39
|
-
):
|
|
40
|
-
import asyncio
|
|
41
|
-
|
|
42
|
-
# Create an event loop for the async test
|
|
43
|
-
loop = asyncio.get_event_loop()
|
|
44
|
-
loop.run_until_complete(app.process_message(message))
|
|
45
|
-
|
|
46
|
-
# Verify that handle_command was called with the correct argument
|
|
47
|
-
mock_handle_command.assert_called_once_with(message)
|
|
48
|
-
|
|
49
|
-
# Verify that agent manager's get_agent was called to refresh the agent instance
|
|
50
|
-
mock_manager.get_agent.assert_called()
|
|
51
|
-
|
|
52
|
-
@patch("code_puppy.tui.app.get_runtime_agent_manager")
|
|
53
|
-
def test_tui_refreshes_agent_after_command(self, mock_get_manager):
|
|
54
|
-
"""Test that TUI refreshes its agent instance after processing /agent command."""
|
|
55
|
-
# Create a TUI app instance
|
|
56
|
-
app = CodePuppyTUI()
|
|
57
|
-
|
|
58
|
-
# Mock the agent manager
|
|
59
|
-
mock_manager = MagicMock()
|
|
60
|
-
initial_agent = MagicMock()
|
|
61
|
-
new_agent = MagicMock()
|
|
62
|
-
|
|
63
|
-
# Set initial agent
|
|
64
|
-
app.agent = initial_agent
|
|
65
|
-
app.agent_manager = mock_manager
|
|
66
|
-
|
|
67
|
-
# Mock manager to return a new agent instance
|
|
68
|
-
mock_manager.get_agent.return_value = new_agent
|
|
69
|
-
mock_get_manager.return_value = mock_manager
|
|
70
|
-
|
|
71
|
-
# Simulate that an /agent command was processed
|
|
72
|
-
with patch("code_puppy.tui.app.handle_command"):
|
|
73
|
-
import asyncio
|
|
74
|
-
|
|
75
|
-
loop = asyncio.get_event_loop()
|
|
76
|
-
loop.run_until_complete(app.process_message("/agent code-puppy"))
|
|
77
|
-
|
|
78
|
-
# Verify that the agent was refreshed through the manager
|
|
79
|
-
mock_manager.get_agent.assert_called()
|
|
@@ -1,28 +0,0 @@
|
|
|
1
|
-
import unittest
|
|
2
|
-
from datetime import datetime
|
|
3
|
-
|
|
4
|
-
from code_puppy.tui.models.chat_message import ChatMessage
|
|
5
|
-
from code_puppy.tui.models.enums import MessageType
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
class TestChatMessage(unittest.TestCase):
|
|
9
|
-
def test_chat_message_defaults(self):
|
|
10
|
-
msg = ChatMessage(
|
|
11
|
-
id="1", type=MessageType.USER, content="hi", timestamp=datetime.now()
|
|
12
|
-
)
|
|
13
|
-
self.assertEqual(msg.metadata, {})
|
|
14
|
-
|
|
15
|
-
def test_chat_message_with_metadata(self):
|
|
16
|
-
meta = {"foo": "bar"}
|
|
17
|
-
msg = ChatMessage(
|
|
18
|
-
id="2",
|
|
19
|
-
type=MessageType.AGENT,
|
|
20
|
-
content="hello",
|
|
21
|
-
timestamp=datetime.now(),
|
|
22
|
-
metadata=meta,
|
|
23
|
-
)
|
|
24
|
-
self.assertEqual(msg.metadata, meta)
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
if __name__ == "__main__":
|
|
28
|
-
unittest.main()
|
|
@@ -1,88 +0,0 @@
|
|
|
1
|
-
import unittest
|
|
2
|
-
from datetime import datetime
|
|
3
|
-
from unittest.mock import patch
|
|
4
|
-
|
|
5
|
-
from code_puppy.tui.components.chat_view import ChatView
|
|
6
|
-
from code_puppy.tui.models.chat_message import ChatMessage
|
|
7
|
-
from code_puppy.tui.models.enums import MessageType
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
class TestChatView(unittest.TestCase):
|
|
11
|
-
def setUp(self):
|
|
12
|
-
self.chat_view = ChatView()
|
|
13
|
-
|
|
14
|
-
@patch.object(ChatView, "mount")
|
|
15
|
-
def test_add_message_user(self, mock_mount):
|
|
16
|
-
msg = ChatMessage(
|
|
17
|
-
id="test-user-1",
|
|
18
|
-
type=MessageType.USER,
|
|
19
|
-
content="Hello",
|
|
20
|
-
timestamp=datetime.now(),
|
|
21
|
-
)
|
|
22
|
-
self.chat_view.add_message(msg)
|
|
23
|
-
self.assertIn(msg, self.chat_view.messages)
|
|
24
|
-
mock_mount.assert_called_once()
|
|
25
|
-
|
|
26
|
-
@patch.object(ChatView, "mount")
|
|
27
|
-
def test_add_message_agent(self, mock_mount):
|
|
28
|
-
msg = ChatMessage(
|
|
29
|
-
id="test-agent-1",
|
|
30
|
-
type=MessageType.AGENT,
|
|
31
|
-
content="Hi there!",
|
|
32
|
-
timestamp=datetime.now(),
|
|
33
|
-
)
|
|
34
|
-
self.chat_view.add_message(msg)
|
|
35
|
-
self.assertIn(msg, self.chat_view.messages)
|
|
36
|
-
mock_mount.assert_called_once()
|
|
37
|
-
|
|
38
|
-
@patch.object(ChatView, "mount")
|
|
39
|
-
def test_add_message_system(self, mock_mount):
|
|
40
|
-
msg = ChatMessage(
|
|
41
|
-
id="test-system-1",
|
|
42
|
-
type=MessageType.SYSTEM,
|
|
43
|
-
content="System message",
|
|
44
|
-
timestamp=datetime.now(),
|
|
45
|
-
)
|
|
46
|
-
self.chat_view.add_message(msg)
|
|
47
|
-
self.assertIn(msg, self.chat_view.messages)
|
|
48
|
-
mock_mount.assert_called_once()
|
|
49
|
-
|
|
50
|
-
@patch.object(ChatView, "mount")
|
|
51
|
-
def test_add_message_error(self, mock_mount):
|
|
52
|
-
msg = ChatMessage(
|
|
53
|
-
id="test-error-1",
|
|
54
|
-
type=MessageType.ERROR,
|
|
55
|
-
content="Error occurred",
|
|
56
|
-
timestamp=datetime.now(),
|
|
57
|
-
)
|
|
58
|
-
self.chat_view.add_message(msg)
|
|
59
|
-
self.assertIn(msg, self.chat_view.messages)
|
|
60
|
-
mock_mount.assert_called_once()
|
|
61
|
-
|
|
62
|
-
@patch.object(ChatView, "mount")
|
|
63
|
-
@patch.object(ChatView, "query")
|
|
64
|
-
def test_clear_messages(self, mock_query, mock_mount):
|
|
65
|
-
# Mock the query method to return empty iterables
|
|
66
|
-
mock_query.return_value = []
|
|
67
|
-
|
|
68
|
-
msg = ChatMessage(
|
|
69
|
-
id="test-clear-1",
|
|
70
|
-
type=MessageType.USER,
|
|
71
|
-
content="Hello",
|
|
72
|
-
timestamp=datetime.now(),
|
|
73
|
-
)
|
|
74
|
-
self.chat_view.add_message(msg)
|
|
75
|
-
self.chat_view.clear_messages()
|
|
76
|
-
self.assertEqual(len(self.chat_view.messages), 0)
|
|
77
|
-
# Verify that query was called to find widgets to remove
|
|
78
|
-
self.assertTrue(mock_query.called)
|
|
79
|
-
|
|
80
|
-
def test_render_agent_message_with_syntax(self):
|
|
81
|
-
prefix = "Agent: "
|
|
82
|
-
content = "Some text\n```python\nprint('hi')\n```"
|
|
83
|
-
group = self.chat_view._render_agent_message_with_syntax(prefix, content)
|
|
84
|
-
self.assertIsNotNone(group)
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
if __name__ == "__main__":
|
|
88
|
-
unittest.main()
|
|
@@ -1,89 +0,0 @@
|
|
|
1
|
-
import re
|
|
2
|
-
import unittest
|
|
3
|
-
from unittest.mock import MagicMock, patch
|
|
4
|
-
|
|
5
|
-
from code_puppy.config import COMMAND_HISTORY_FILE
|
|
6
|
-
from code_puppy.tui.app import CodePuppyTUI
|
|
7
|
-
from code_puppy.tui.components.custom_widgets import CustomTextArea
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
class TestCommandHistory(unittest.TestCase):
|
|
11
|
-
def setUp(self):
|
|
12
|
-
self.app = CodePuppyTUI()
|
|
13
|
-
|
|
14
|
-
@patch("builtins.open", new_callable=unittest.mock.mock_open)
|
|
15
|
-
def test_action_send_message_saves_to_history(self, mock_open):
|
|
16
|
-
# Setup test mocks
|
|
17
|
-
self.app.query_one = MagicMock()
|
|
18
|
-
input_field_mock = MagicMock(spec=CustomTextArea)
|
|
19
|
-
input_field_mock.text = "test command"
|
|
20
|
-
self.app.query_one.return_value = input_field_mock
|
|
21
|
-
|
|
22
|
-
# Mock other methods to prevent full execution
|
|
23
|
-
self.app.add_user_message = MagicMock()
|
|
24
|
-
self.app._update_submit_cancel_button = MagicMock()
|
|
25
|
-
self.app.run_worker = MagicMock()
|
|
26
|
-
|
|
27
|
-
# Execute
|
|
28
|
-
self.app.action_send_message()
|
|
29
|
-
|
|
30
|
-
# Assertions
|
|
31
|
-
mock_open.assert_called_once_with(COMMAND_HISTORY_FILE, "a")
|
|
32
|
-
# Check that write was called with timestamped format
|
|
33
|
-
write_calls = mock_open().write.call_args_list
|
|
34
|
-
self.assertEqual(len(write_calls), 1)
|
|
35
|
-
written_content = write_calls[0][0][0]
|
|
36
|
-
# Should match pattern: \n# YYYY-MM-DDTHH:MM:SS\ntest command\n
|
|
37
|
-
self.assertTrue(
|
|
38
|
-
re.match(
|
|
39
|
-
r"^\n# \d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\ntest command\n$",
|
|
40
|
-
written_content,
|
|
41
|
-
)
|
|
42
|
-
)
|
|
43
|
-
self.app.add_user_message.assert_called_once_with("test command")
|
|
44
|
-
|
|
45
|
-
@patch("builtins.open", new_callable=unittest.mock.mock_open)
|
|
46
|
-
def test_action_send_message_empty_command(self, mock_open):
|
|
47
|
-
# Setup test mocks
|
|
48
|
-
self.app.query_one = MagicMock()
|
|
49
|
-
input_field_mock = MagicMock(spec=CustomTextArea)
|
|
50
|
-
input_field_mock.text = " " # Empty or whitespace-only command
|
|
51
|
-
self.app.query_one.return_value = input_field_mock
|
|
52
|
-
|
|
53
|
-
# Mock other methods
|
|
54
|
-
self.app.add_user_message = MagicMock()
|
|
55
|
-
|
|
56
|
-
# Execute
|
|
57
|
-
self.app.action_send_message()
|
|
58
|
-
|
|
59
|
-
# Assertions - nothing should happen with empty commands
|
|
60
|
-
mock_open.assert_not_called()
|
|
61
|
-
self.app.add_user_message.assert_not_called()
|
|
62
|
-
|
|
63
|
-
@patch("builtins.open")
|
|
64
|
-
def test_action_send_message_handles_error(self, mock_open):
|
|
65
|
-
# Setup test mocks
|
|
66
|
-
self.app.query_one = MagicMock()
|
|
67
|
-
input_field_mock = MagicMock(spec=CustomTextArea)
|
|
68
|
-
input_field_mock.text = "test command"
|
|
69
|
-
self.app.query_one.return_value = input_field_mock
|
|
70
|
-
|
|
71
|
-
# Mock other methods to prevent full execution
|
|
72
|
-
self.app.add_user_message = MagicMock()
|
|
73
|
-
self.app._update_submit_cancel_button = MagicMock()
|
|
74
|
-
self.app.run_worker = MagicMock()
|
|
75
|
-
self.app.add_error_message = MagicMock()
|
|
76
|
-
|
|
77
|
-
# Make open throw an exception
|
|
78
|
-
mock_open.side_effect = Exception("File error")
|
|
79
|
-
|
|
80
|
-
# Execute
|
|
81
|
-
self.app.action_send_message()
|
|
82
|
-
|
|
83
|
-
# Assertions - error is printed to stdout, not added to UI
|
|
84
|
-
# Message should still be processed despite error saving to history
|
|
85
|
-
self.app.add_user_message.assert_called_once_with("test command")
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
if __name__ == "__main__":
|
|
89
|
-
unittest.main()
|