chatmcp-cli 0.1.0__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.
- aider/__init__.py +20 -0
- aider/__main__.py +4 -0
- aider/_version.py +21 -0
- aider/analytics.py +250 -0
- aider/args.py +926 -0
- aider/args_formatter.py +228 -0
- aider/coders/__init__.py +34 -0
- aider/coders/architect_coder.py +48 -0
- aider/coders/architect_prompts.py +40 -0
- aider/coders/ask_coder.py +9 -0
- aider/coders/ask_prompts.py +35 -0
- aider/coders/base_coder.py +2483 -0
- aider/coders/base_prompts.py +60 -0
- aider/coders/chat_chunks.py +64 -0
- aider/coders/context_coder.py +53 -0
- aider/coders/context_prompts.py +75 -0
- aider/coders/editblock_coder.py +657 -0
- aider/coders/editblock_fenced_coder.py +10 -0
- aider/coders/editblock_fenced_prompts.py +143 -0
- aider/coders/editblock_func_coder.py +141 -0
- aider/coders/editblock_func_prompts.py +27 -0
- aider/coders/editblock_prompts.py +174 -0
- aider/coders/editor_diff_fenced_coder.py +9 -0
- aider/coders/editor_diff_fenced_prompts.py +11 -0
- aider/coders/editor_editblock_coder.py +8 -0
- aider/coders/editor_editblock_prompts.py +18 -0
- aider/coders/editor_whole_coder.py +8 -0
- aider/coders/editor_whole_prompts.py +10 -0
- aider/coders/help_coder.py +16 -0
- aider/coders/help_prompts.py +46 -0
- aider/coders/patch_coder.py +706 -0
- aider/coders/patch_prompts.py +161 -0
- aider/coders/search_replace.py +757 -0
- aider/coders/shell.py +37 -0
- aider/coders/single_wholefile_func_coder.py +102 -0
- aider/coders/single_wholefile_func_prompts.py +27 -0
- aider/coders/udiff_coder.py +429 -0
- aider/coders/udiff_prompts.py +115 -0
- aider/coders/udiff_simple.py +14 -0
- aider/coders/udiff_simple_prompts.py +25 -0
- aider/coders/wholefile_coder.py +144 -0
- aider/coders/wholefile_func_coder.py +134 -0
- aider/coders/wholefile_func_prompts.py +27 -0
- aider/coders/wholefile_prompts.py +67 -0
- aider/commands.py +1665 -0
- aider/copypaste.py +72 -0
- aider/deprecated.py +126 -0
- aider/diffs.py +128 -0
- aider/dump.py +29 -0
- aider/editor.py +147 -0
- aider/exceptions.py +107 -0
- aider/format_settings.py +26 -0
- aider/gui.py +545 -0
- aider/help.py +163 -0
- aider/help_pats.py +19 -0
- aider/history.py +143 -0
- aider/io.py +1175 -0
- aider/linter.py +304 -0
- aider/llm.py +47 -0
- aider/main.py +1267 -0
- aider/mdstream.py +243 -0
- aider/models.py +1286 -0
- aider/onboarding.py +428 -0
- aider/openrouter.py +128 -0
- aider/prompts.py +64 -0
- aider/queries/tree-sitter-language-pack/README.md +7 -0
- aider/queries/tree-sitter-language-pack/arduino-tags.scm +5 -0
- aider/queries/tree-sitter-language-pack/c-tags.scm +9 -0
- aider/queries/tree-sitter-language-pack/chatito-tags.scm +16 -0
- aider/queries/tree-sitter-language-pack/commonlisp-tags.scm +122 -0
- aider/queries/tree-sitter-language-pack/cpp-tags.scm +15 -0
- aider/queries/tree-sitter-language-pack/csharp-tags.scm +26 -0
- aider/queries/tree-sitter-language-pack/d-tags.scm +26 -0
- aider/queries/tree-sitter-language-pack/dart-tags.scm +92 -0
- aider/queries/tree-sitter-language-pack/elisp-tags.scm +5 -0
- aider/queries/tree-sitter-language-pack/elixir-tags.scm +54 -0
- aider/queries/tree-sitter-language-pack/elm-tags.scm +19 -0
- aider/queries/tree-sitter-language-pack/gleam-tags.scm +41 -0
- aider/queries/tree-sitter-language-pack/go-tags.scm +42 -0
- aider/queries/tree-sitter-language-pack/java-tags.scm +20 -0
- aider/queries/tree-sitter-language-pack/javascript-tags.scm +88 -0
- aider/queries/tree-sitter-language-pack/lua-tags.scm +34 -0
- aider/queries/tree-sitter-language-pack/ocaml-tags.scm +115 -0
- aider/queries/tree-sitter-language-pack/ocaml_interface-tags.scm +98 -0
- aider/queries/tree-sitter-language-pack/pony-tags.scm +39 -0
- aider/queries/tree-sitter-language-pack/properties-tags.scm +5 -0
- aider/queries/tree-sitter-language-pack/python-tags.scm +14 -0
- aider/queries/tree-sitter-language-pack/r-tags.scm +21 -0
- aider/queries/tree-sitter-language-pack/racket-tags.scm +12 -0
- aider/queries/tree-sitter-language-pack/ruby-tags.scm +64 -0
- aider/queries/tree-sitter-language-pack/rust-tags.scm +60 -0
- aider/queries/tree-sitter-language-pack/solidity-tags.scm +43 -0
- aider/queries/tree-sitter-language-pack/swift-tags.scm +51 -0
- aider/queries/tree-sitter-language-pack/udev-tags.scm +20 -0
- aider/queries/tree-sitter-languages/README.md +23 -0
- aider/queries/tree-sitter-languages/c-tags.scm +9 -0
- aider/queries/tree-sitter-languages/c_sharp-tags.scm +46 -0
- aider/queries/tree-sitter-languages/cpp-tags.scm +15 -0
- aider/queries/tree-sitter-languages/dart-tags.scm +91 -0
- aider/queries/tree-sitter-languages/elisp-tags.scm +8 -0
- aider/queries/tree-sitter-languages/elixir-tags.scm +54 -0
- aider/queries/tree-sitter-languages/elm-tags.scm +19 -0
- aider/queries/tree-sitter-languages/go-tags.scm +30 -0
- aider/queries/tree-sitter-languages/hcl-tags.scm +77 -0
- aider/queries/tree-sitter-languages/java-tags.scm +20 -0
- aider/queries/tree-sitter-languages/javascript-tags.scm +88 -0
- aider/queries/tree-sitter-languages/kotlin-tags.scm +27 -0
- aider/queries/tree-sitter-languages/ocaml-tags.scm +115 -0
- aider/queries/tree-sitter-languages/ocaml_interface-tags.scm +98 -0
- aider/queries/tree-sitter-languages/php-tags.scm +26 -0
- aider/queries/tree-sitter-languages/python-tags.scm +12 -0
- aider/queries/tree-sitter-languages/ql-tags.scm +26 -0
- aider/queries/tree-sitter-languages/ruby-tags.scm +64 -0
- aider/queries/tree-sitter-languages/rust-tags.scm +60 -0
- aider/queries/tree-sitter-languages/scala-tags.scm +65 -0
- aider/queries/tree-sitter-languages/typescript-tags.scm +41 -0
- aider/reasoning_tags.py +82 -0
- aider/repo.py +623 -0
- aider/repomap.py +847 -0
- aider/report.py +200 -0
- aider/resources/__init__.py +3 -0
- aider/resources/model-metadata.json +468 -0
- aider/resources/model-settings.yml +1767 -0
- aider/run_cmd.py +132 -0
- aider/scrape.py +284 -0
- aider/sendchat.py +61 -0
- aider/special.py +203 -0
- aider/urls.py +17 -0
- aider/utils.py +338 -0
- aider/versioncheck.py +113 -0
- aider/voice.py +187 -0
- aider/waiting.py +221 -0
- aider/watch.py +318 -0
- aider/watch_prompts.py +12 -0
- aider/website/Gemfile +8 -0
- aider/website/_includes/blame.md +162 -0
- aider/website/_includes/get-started.md +22 -0
- aider/website/_includes/help-tip.md +5 -0
- aider/website/_includes/help.md +24 -0
- aider/website/_includes/install.md +5 -0
- aider/website/_includes/keys.md +4 -0
- aider/website/_includes/model-warnings.md +67 -0
- aider/website/_includes/multi-line.md +22 -0
- aider/website/_includes/python-m-aider.md +5 -0
- aider/website/_includes/recording.css +228 -0
- aider/website/_includes/recording.md +34 -0
- aider/website/_includes/replit-pipx.md +9 -0
- aider/website/_includes/works-best.md +1 -0
- aider/website/_sass/custom/custom.scss +103 -0
- aider/website/docs/config/adv-model-settings.md +1881 -0
- aider/website/docs/config/aider_conf.md +527 -0
- aider/website/docs/config/api-keys.md +90 -0
- aider/website/docs/config/dotenv.md +478 -0
- aider/website/docs/config/editor.md +127 -0
- aider/website/docs/config/model-aliases.md +103 -0
- aider/website/docs/config/options.md +843 -0
- aider/website/docs/config/reasoning.md +209 -0
- aider/website/docs/config.md +44 -0
- aider/website/docs/faq.md +378 -0
- aider/website/docs/git.md +76 -0
- aider/website/docs/index.md +47 -0
- aider/website/docs/install/codespaces.md +39 -0
- aider/website/docs/install/docker.md +57 -0
- aider/website/docs/install/optional.md +100 -0
- aider/website/docs/install/replit.md +8 -0
- aider/website/docs/install.md +115 -0
- aider/website/docs/languages.md +264 -0
- aider/website/docs/legal/contributor-agreement.md +111 -0
- aider/website/docs/legal/privacy.md +104 -0
- aider/website/docs/llms/anthropic.md +77 -0
- aider/website/docs/llms/azure.md +48 -0
- aider/website/docs/llms/bedrock.md +132 -0
- aider/website/docs/llms/cohere.md +34 -0
- aider/website/docs/llms/deepseek.md +32 -0
- aider/website/docs/llms/gemini.md +49 -0
- aider/website/docs/llms/github.md +105 -0
- aider/website/docs/llms/groq.md +36 -0
- aider/website/docs/llms/lm-studio.md +39 -0
- aider/website/docs/llms/ollama.md +75 -0
- aider/website/docs/llms/openai-compat.md +39 -0
- aider/website/docs/llms/openai.md +58 -0
- aider/website/docs/llms/openrouter.md +78 -0
- aider/website/docs/llms/other.md +103 -0
- aider/website/docs/llms/vertex.md +50 -0
- aider/website/docs/llms/warnings.md +10 -0
- aider/website/docs/llms/xai.md +53 -0
- aider/website/docs/llms.md +54 -0
- aider/website/docs/more/analytics.md +122 -0
- aider/website/docs/more/edit-formats.md +116 -0
- aider/website/docs/more/infinite-output.md +137 -0
- aider/website/docs/more-info.md +8 -0
- aider/website/docs/recordings/auto-accept-architect.md +31 -0
- aider/website/docs/recordings/dont-drop-original-read-files.md +35 -0
- aider/website/docs/recordings/index.md +21 -0
- aider/website/docs/recordings/model-accepts-settings.md +69 -0
- aider/website/docs/recordings/tree-sitter-language-pack.md +80 -0
- aider/website/docs/repomap.md +112 -0
- aider/website/docs/scripting.md +100 -0
- aider/website/docs/troubleshooting/aider-not-found.md +24 -0
- aider/website/docs/troubleshooting/edit-errors.md +76 -0
- aider/website/docs/troubleshooting/imports.md +62 -0
- aider/website/docs/troubleshooting/models-and-keys.md +54 -0
- aider/website/docs/troubleshooting/support.md +79 -0
- aider/website/docs/troubleshooting/token-limits.md +96 -0
- aider/website/docs/troubleshooting/warnings.md +12 -0
- aider/website/docs/troubleshooting.md +11 -0
- aider/website/docs/usage/browser.md +57 -0
- aider/website/docs/usage/caching.md +49 -0
- aider/website/docs/usage/commands.md +132 -0
- aider/website/docs/usage/conventions.md +119 -0
- aider/website/docs/usage/copypaste.md +121 -0
- aider/website/docs/usage/images-urls.md +48 -0
- aider/website/docs/usage/lint-test.md +118 -0
- aider/website/docs/usage/modes.md +211 -0
- aider/website/docs/usage/not-code.md +179 -0
- aider/website/docs/usage/notifications.md +87 -0
- aider/website/docs/usage/tips.md +79 -0
- aider/website/docs/usage/tutorials.md +30 -0
- aider/website/docs/usage/voice.md +121 -0
- aider/website/docs/usage/watch.md +294 -0
- aider/website/docs/usage.md +92 -0
- aider/website/share/index.md +101 -0
- chatmcp_cli-0.1.0.dist-info/METADATA +502 -0
- chatmcp_cli-0.1.0.dist-info/RECORD +228 -0
- chatmcp_cli-0.1.0.dist-info/WHEEL +5 -0
- chatmcp_cli-0.1.0.dist-info/entry_points.txt +3 -0
- chatmcp_cli-0.1.0.dist-info/licenses/LICENSE.txt +202 -0
- chatmcp_cli-0.1.0.dist-info/top_level.txt +1 -0
@@ -0,0 +1,143 @@
|
|
1
|
+
# flake8: noqa: E501
|
2
|
+
|
3
|
+
from .editblock_prompts import EditBlockPrompts
|
4
|
+
|
5
|
+
|
6
|
+
class EditBlockFencedPrompts(EditBlockPrompts):
|
7
|
+
example_messages = [
|
8
|
+
dict(
|
9
|
+
role="user",
|
10
|
+
content="Change get_factorial() to use math.factorial",
|
11
|
+
),
|
12
|
+
dict(
|
13
|
+
role="assistant",
|
14
|
+
content="""To make this change we need to modify `mathweb/flask/app.py` to:
|
15
|
+
|
16
|
+
1. Import the math package.
|
17
|
+
2. Remove the existing factorial() function.
|
18
|
+
3. Update get_factorial() to call math.factorial instead.
|
19
|
+
|
20
|
+
Here are the *SEARCH/REPLACE* blocks:
|
21
|
+
|
22
|
+
{fence[0]}python
|
23
|
+
mathweb/flask/app.py
|
24
|
+
<<<<<<< SEARCH
|
25
|
+
from flask import Flask
|
26
|
+
=======
|
27
|
+
import math
|
28
|
+
from flask import Flask
|
29
|
+
>>>>>>> REPLACE
|
30
|
+
{fence[1]}
|
31
|
+
|
32
|
+
{fence[0]}python
|
33
|
+
mathweb/flask/app.py
|
34
|
+
<<<<<<< SEARCH
|
35
|
+
def factorial(n):
|
36
|
+
"compute factorial"
|
37
|
+
|
38
|
+
if n == 0:
|
39
|
+
return 1
|
40
|
+
else:
|
41
|
+
return n * factorial(n-1)
|
42
|
+
|
43
|
+
=======
|
44
|
+
>>>>>>> REPLACE
|
45
|
+
{fence[1]}
|
46
|
+
|
47
|
+
{fence[0]}python
|
48
|
+
mathweb/flask/app.py
|
49
|
+
<<<<<<< SEARCH
|
50
|
+
return str(factorial(n))
|
51
|
+
=======
|
52
|
+
return str(math.factorial(n))
|
53
|
+
>>>>>>> REPLACE
|
54
|
+
{fence[1]}
|
55
|
+
<<<<<<< HEAD
|
56
|
+
""",
|
57
|
+
),
|
58
|
+
dict(
|
59
|
+
role="user",
|
60
|
+
content="Refactor hello() into its own file.",
|
61
|
+
),
|
62
|
+
dict(
|
63
|
+
role="assistant",
|
64
|
+
content="""To make this change we need to modify `main.py` and make a new file `hello.py`:
|
65
|
+
|
66
|
+
1. Make a new hello.py file with hello() in it.
|
67
|
+
2. Remove hello() from main.py and replace it with an import.
|
68
|
+
|
69
|
+
Here are the *SEARCH/REPLACE* blocks:
|
70
|
+
|
71
|
+
{fence[0]}python
|
72
|
+
hello.py
|
73
|
+
<<<<<<< SEARCH
|
74
|
+
=======
|
75
|
+
def hello():
|
76
|
+
"print a greeting"
|
77
|
+
|
78
|
+
print("hello")
|
79
|
+
>>>>>>> REPLACE
|
80
|
+
{fence[1]}
|
81
|
+
|
82
|
+
{fence[0]}python
|
83
|
+
main.py
|
84
|
+
<<<<<<< SEARCH
|
85
|
+
def hello():
|
86
|
+
"print a greeting"
|
87
|
+
|
88
|
+
print("hello")
|
89
|
+
=======
|
90
|
+
from hello import hello
|
91
|
+
>>>>>>> REPLACE
|
92
|
+
{fence[1]}
|
93
|
+
""",
|
94
|
+
),
|
95
|
+
]
|
96
|
+
|
97
|
+
system_reminder = """
|
98
|
+
# *SEARCH/REPLACE block* Rules:
|
99
|
+
|
100
|
+
Every *SEARCH/REPLACE block* must use this format:
|
101
|
+
1. The opening fence and code language, eg: {fence[0]}python
|
102
|
+
2. The *FULL* file path alone on a line, verbatim. No bold asterisks, no quotes around it, no escaping of characters, etc.
|
103
|
+
3. The start of search block: <<<<<<< SEARCH
|
104
|
+
4. A contiguous chunk of lines to search for in the existing source code
|
105
|
+
5. The dividing line: =======
|
106
|
+
6. The lines to replace into the source code
|
107
|
+
7. The end of the replace block: >>>>>>> REPLACE
|
108
|
+
8. The closing fence: {fence[1]}
|
109
|
+
|
110
|
+
Use the *FULL* file path, as shown to you by the user.
|
111
|
+
{quad_backtick_reminder}
|
112
|
+
Every *SEARCH* section must *EXACTLY MATCH* the existing file content, character for character, including all comments, docstrings, etc.
|
113
|
+
If the file contains code or other data wrapped/escaped in json/xml/quotes or other containers, you need to propose edits to the literal contents of the file, including the container markup.
|
114
|
+
|
115
|
+
*SEARCH/REPLACE* blocks will *only* replace the first match occurrence.
|
116
|
+
Including multiple unique *SEARCH/REPLACE* blocks if needed.
|
117
|
+
Include enough lines in each SEARCH section to uniquely match each set of lines that need to change.
|
118
|
+
|
119
|
+
Keep *SEARCH/REPLACE* blocks concise.
|
120
|
+
Break large *SEARCH/REPLACE* blocks into a series of smaller blocks that each change a small portion of the file.
|
121
|
+
Include just the changing lines, and a few surrounding lines if needed for uniqueness.
|
122
|
+
Do not include long runs of unchanging lines in *SEARCH/REPLACE* blocks.
|
123
|
+
|
124
|
+
Only create *SEARCH/REPLACE* blocks for files that the user has added to the chat!
|
125
|
+
|
126
|
+
To move code within a file, use 2 *SEARCH/REPLACE* blocks: 1 to delete it from its current location, 1 to insert it in the new location.
|
127
|
+
|
128
|
+
Pay attention to which filenames the user wants you to edit, especially if they are asking you to create a new file.
|
129
|
+
|
130
|
+
If you want to put code in a new file, use a *SEARCH/REPLACE block* with:
|
131
|
+
- A new file path, including dir name if needed
|
132
|
+
- An empty `SEARCH` section
|
133
|
+
- The new file's contents in the `REPLACE` section
|
134
|
+
|
135
|
+
To rename files which have been added to the chat, use shell commands at the end of your response.
|
136
|
+
|
137
|
+
If the user just says something like "ok" or "go ahead" or "do that" they probably want you to make SEARCH/REPLACE blocks for the code changes you just proposed.
|
138
|
+
The user will say when they've applied your edits. If they haven't explicitly confirmed the edits have been applied, they probably want proper SEARCH/REPLACE blocks.
|
139
|
+
|
140
|
+
{final_reminders}
|
141
|
+
ONLY EVER RETURN CODE IN A *SEARCH/REPLACE BLOCK*!
|
142
|
+
{shell_cmd_reminder}
|
143
|
+
"""
|
@@ -0,0 +1,141 @@
|
|
1
|
+
import json
|
2
|
+
|
3
|
+
from ..dump import dump # noqa: F401
|
4
|
+
from .base_coder import Coder
|
5
|
+
from .editblock_coder import do_replace
|
6
|
+
from .editblock_func_prompts import EditBlockFunctionPrompts
|
7
|
+
|
8
|
+
|
9
|
+
class EditBlockFunctionCoder(Coder):
|
10
|
+
functions = [
|
11
|
+
dict(
|
12
|
+
name="replace_lines",
|
13
|
+
description="create or update one or more files",
|
14
|
+
parameters=dict(
|
15
|
+
type="object",
|
16
|
+
required=["explanation", "edits"],
|
17
|
+
properties=dict(
|
18
|
+
explanation=dict(
|
19
|
+
type="string",
|
20
|
+
description=(
|
21
|
+
"Step by step plan for the changes to be made to the code (future"
|
22
|
+
" tense, markdown format)"
|
23
|
+
),
|
24
|
+
),
|
25
|
+
edits=dict(
|
26
|
+
type="array",
|
27
|
+
items=dict(
|
28
|
+
type="object",
|
29
|
+
required=["path", "original_lines", "updated_lines"],
|
30
|
+
properties=dict(
|
31
|
+
path=dict(
|
32
|
+
type="string",
|
33
|
+
description="Path of file to edit",
|
34
|
+
),
|
35
|
+
original_lines=dict(
|
36
|
+
type="array",
|
37
|
+
items=dict(
|
38
|
+
type="string",
|
39
|
+
),
|
40
|
+
description=(
|
41
|
+
"A unique stretch of lines from the original file,"
|
42
|
+
" including all whitespace, without skipping any lines"
|
43
|
+
),
|
44
|
+
),
|
45
|
+
updated_lines=dict(
|
46
|
+
type="array",
|
47
|
+
items=dict(
|
48
|
+
type="string",
|
49
|
+
),
|
50
|
+
description="New content to replace the `original_lines` with",
|
51
|
+
),
|
52
|
+
),
|
53
|
+
),
|
54
|
+
),
|
55
|
+
),
|
56
|
+
),
|
57
|
+
),
|
58
|
+
]
|
59
|
+
|
60
|
+
def __init__(self, code_format, *args, **kwargs):
|
61
|
+
raise RuntimeError("Deprecated, needs to be refactored to support get_edits/apply_edits")
|
62
|
+
self.code_format = code_format
|
63
|
+
|
64
|
+
if code_format == "string":
|
65
|
+
original_lines = dict(
|
66
|
+
type="string",
|
67
|
+
description=(
|
68
|
+
"A unique stretch of lines from the original file, including all"
|
69
|
+
" whitespace and newlines, without skipping any lines"
|
70
|
+
),
|
71
|
+
)
|
72
|
+
updated_lines = dict(
|
73
|
+
type="string",
|
74
|
+
description="New content to replace the `original_lines` with",
|
75
|
+
)
|
76
|
+
|
77
|
+
self.functions[0]["parameters"]["properties"]["edits"]["items"]["properties"][
|
78
|
+
"original_lines"
|
79
|
+
] = original_lines
|
80
|
+
self.functions[0]["parameters"]["properties"]["edits"]["items"]["properties"][
|
81
|
+
"updated_lines"
|
82
|
+
] = updated_lines
|
83
|
+
|
84
|
+
self.gpt_prompts = EditBlockFunctionPrompts()
|
85
|
+
super().__init__(*args, **kwargs)
|
86
|
+
|
87
|
+
def render_incremental_response(self, final=False):
|
88
|
+
if self.partial_response_content:
|
89
|
+
return self.partial_response_content
|
90
|
+
|
91
|
+
args = self.parse_partial_args()
|
92
|
+
res = json.dumps(args, indent=4)
|
93
|
+
return res
|
94
|
+
|
95
|
+
def _update_files(self):
|
96
|
+
name = self.partial_response_function_call.get("name")
|
97
|
+
|
98
|
+
if name and name != "replace_lines":
|
99
|
+
raise ValueError(f'Unknown function_call name="{name}", use name="replace_lines"')
|
100
|
+
|
101
|
+
args = self.parse_partial_args()
|
102
|
+
if not args:
|
103
|
+
return
|
104
|
+
|
105
|
+
edits = args.get("edits", [])
|
106
|
+
|
107
|
+
edited = set()
|
108
|
+
for edit in edits:
|
109
|
+
path = get_arg(edit, "path")
|
110
|
+
original = get_arg(edit, "original_lines")
|
111
|
+
updated = get_arg(edit, "updated_lines")
|
112
|
+
|
113
|
+
# gpt-3.5 returns lists even when instructed to return a string!
|
114
|
+
if self.code_format == "list" or type(original) is list:
|
115
|
+
original = "\n".join(original)
|
116
|
+
if self.code_format == "list" or type(updated) is list:
|
117
|
+
updated = "\n".join(updated)
|
118
|
+
|
119
|
+
if original and not original.endswith("\n"):
|
120
|
+
original += "\n"
|
121
|
+
if updated and not updated.endswith("\n"):
|
122
|
+
updated += "\n"
|
123
|
+
|
124
|
+
full_path = self.allowed_to_edit(path)
|
125
|
+
if not full_path:
|
126
|
+
continue
|
127
|
+
content = self.io.read_text(full_path)
|
128
|
+
content = do_replace(full_path, content, original, updated)
|
129
|
+
if content:
|
130
|
+
self.io.write_text(full_path, content)
|
131
|
+
edited.add(path)
|
132
|
+
continue
|
133
|
+
self.io.tool_error(f"Failed to apply edit to {path}")
|
134
|
+
|
135
|
+
return edited
|
136
|
+
|
137
|
+
|
138
|
+
def get_arg(edit, arg):
|
139
|
+
if arg not in edit:
|
140
|
+
raise ValueError(f"Missing `{arg}` parameter: {edit}")
|
141
|
+
return edit[arg]
|
@@ -0,0 +1,27 @@
|
|
1
|
+
# flake8: noqa: E501
|
2
|
+
|
3
|
+
from .base_prompts import CoderPrompts
|
4
|
+
|
5
|
+
|
6
|
+
class EditBlockFunctionPrompts(CoderPrompts):
|
7
|
+
main_system = """Act as an expert software developer.
|
8
|
+
Take requests for changes to the supplied code.
|
9
|
+
If the request is ambiguous, ask questions.
|
10
|
+
|
11
|
+
Once you understand the request you MUST use the `replace_lines` function to edit the files to make the needed changes.
|
12
|
+
"""
|
13
|
+
|
14
|
+
system_reminder = """
|
15
|
+
ONLY return code using the `replace_lines` function.
|
16
|
+
NEVER return code outside the `replace_lines` function.
|
17
|
+
"""
|
18
|
+
|
19
|
+
files_content_prefix = "Here is the current content of the files:\n"
|
20
|
+
files_no_full_files = "I am not sharing any files yet."
|
21
|
+
|
22
|
+
redacted_edit_message = "No changes are needed."
|
23
|
+
|
24
|
+
repo_content_prefix = (
|
25
|
+
"Below here are summaries of other files! Do not propose changes to these *read-only*"
|
26
|
+
" files without asking me first.\n"
|
27
|
+
)
|
@@ -0,0 +1,174 @@
|
|
1
|
+
# flake8: noqa: E501
|
2
|
+
|
3
|
+
from . import shell
|
4
|
+
from .base_prompts import CoderPrompts
|
5
|
+
|
6
|
+
|
7
|
+
class EditBlockPrompts(CoderPrompts):
|
8
|
+
main_system = """Act as an expert software developer.
|
9
|
+
Always use best practices when coding.
|
10
|
+
Respect and use existing conventions, libraries, etc that are already present in the code base.
|
11
|
+
{final_reminders}
|
12
|
+
Take requests for changes to the supplied code.
|
13
|
+
If the request is ambiguous, ask questions.
|
14
|
+
|
15
|
+
Always reply to the user in {language}.
|
16
|
+
|
17
|
+
Once you understand the request you MUST:
|
18
|
+
|
19
|
+
1. Decide if you need to propose *SEARCH/REPLACE* edits to any files that haven't been added to the chat. You can create new files without asking!
|
20
|
+
|
21
|
+
But if you need to propose edits to existing files not already added to the chat, you *MUST* tell the user their full path names and ask them to *add the files to the chat*.
|
22
|
+
End your reply and wait for their approval.
|
23
|
+
You can keep asking if you then decide you need to edit more files.
|
24
|
+
|
25
|
+
2. Think step-by-step and explain the needed changes in a few short sentences.
|
26
|
+
|
27
|
+
3. Describe each change with a *SEARCH/REPLACE block* per the examples below.
|
28
|
+
|
29
|
+
All changes to files must use this *SEARCH/REPLACE block* format.
|
30
|
+
ONLY EVER RETURN CODE IN A *SEARCH/REPLACE BLOCK*!
|
31
|
+
{shell_cmd_prompt}
|
32
|
+
"""
|
33
|
+
example_messages = [
|
34
|
+
dict(
|
35
|
+
role="user",
|
36
|
+
content="Change get_factorial() to use math.factorial",
|
37
|
+
),
|
38
|
+
dict(
|
39
|
+
role="assistant",
|
40
|
+
content="""To make this change we need to modify `mathweb/flask/app.py` to:
|
41
|
+
|
42
|
+
1. Import the math package.
|
43
|
+
2. Remove the existing factorial() function.
|
44
|
+
3. Update get_factorial() to call math.factorial instead.
|
45
|
+
|
46
|
+
Here are the *SEARCH/REPLACE* blocks:
|
47
|
+
|
48
|
+
mathweb/flask/app.py
|
49
|
+
{fence[0]}python
|
50
|
+
<<<<<<< SEARCH
|
51
|
+
from flask import Flask
|
52
|
+
=======
|
53
|
+
import math
|
54
|
+
from flask import Flask
|
55
|
+
>>>>>>> REPLACE
|
56
|
+
{fence[1]}
|
57
|
+
|
58
|
+
mathweb/flask/app.py
|
59
|
+
{fence[0]}python
|
60
|
+
<<<<<<< SEARCH
|
61
|
+
def factorial(n):
|
62
|
+
"compute factorial"
|
63
|
+
|
64
|
+
if n == 0:
|
65
|
+
return 1
|
66
|
+
else:
|
67
|
+
return n * factorial(n-1)
|
68
|
+
|
69
|
+
=======
|
70
|
+
>>>>>>> REPLACE
|
71
|
+
{fence[1]}
|
72
|
+
|
73
|
+
mathweb/flask/app.py
|
74
|
+
{fence[0]}python
|
75
|
+
<<<<<<< SEARCH
|
76
|
+
return str(factorial(n))
|
77
|
+
=======
|
78
|
+
return str(math.factorial(n))
|
79
|
+
>>>>>>> REPLACE
|
80
|
+
{fence[1]}
|
81
|
+
""",
|
82
|
+
),
|
83
|
+
dict(
|
84
|
+
role="user",
|
85
|
+
content="Refactor hello() into its own file.",
|
86
|
+
),
|
87
|
+
dict(
|
88
|
+
role="assistant",
|
89
|
+
content="""To make this change we need to modify `main.py` and make a new file `hello.py`:
|
90
|
+
|
91
|
+
1. Make a new hello.py file with hello() in it.
|
92
|
+
2. Remove hello() from main.py and replace it with an import.
|
93
|
+
|
94
|
+
Here are the *SEARCH/REPLACE* blocks:
|
95
|
+
|
96
|
+
hello.py
|
97
|
+
{fence[0]}python
|
98
|
+
<<<<<<< SEARCH
|
99
|
+
=======
|
100
|
+
def hello():
|
101
|
+
"print a greeting"
|
102
|
+
|
103
|
+
print("hello")
|
104
|
+
>>>>>>> REPLACE
|
105
|
+
{fence[1]}
|
106
|
+
|
107
|
+
main.py
|
108
|
+
{fence[0]}python
|
109
|
+
<<<<<<< SEARCH
|
110
|
+
def hello():
|
111
|
+
"print a greeting"
|
112
|
+
|
113
|
+
print("hello")
|
114
|
+
=======
|
115
|
+
from hello import hello
|
116
|
+
>>>>>>> REPLACE
|
117
|
+
{fence[1]}
|
118
|
+
""",
|
119
|
+
),
|
120
|
+
]
|
121
|
+
|
122
|
+
system_reminder = """# *SEARCH/REPLACE block* Rules:
|
123
|
+
|
124
|
+
Every *SEARCH/REPLACE block* must use this format:
|
125
|
+
1. The *FULL* file path alone on a line, verbatim. No bold asterisks, no quotes around it, no escaping of characters, etc.
|
126
|
+
2. The opening fence and code language, eg: {fence[0]}python
|
127
|
+
3. The start of search block: <<<<<<< SEARCH
|
128
|
+
4. A contiguous chunk of lines to search for in the existing source code
|
129
|
+
5. The dividing line: =======
|
130
|
+
6. The lines to replace into the source code
|
131
|
+
7. The end of the replace block: >>>>>>> REPLACE
|
132
|
+
8. The closing fence: {fence[1]}
|
133
|
+
|
134
|
+
Use the *FULL* file path, as shown to you by the user.
|
135
|
+
{quad_backtick_reminder}
|
136
|
+
Every *SEARCH* section must *EXACTLY MATCH* the existing file content, character for character, including all comments, docstrings, etc.
|
137
|
+
If the file contains code or other data wrapped/escaped in json/xml/quotes or other containers, you need to propose edits to the literal contents of the file, including the container markup.
|
138
|
+
|
139
|
+
*SEARCH/REPLACE* blocks will *only* replace the first match occurrence.
|
140
|
+
Including multiple unique *SEARCH/REPLACE* blocks if needed.
|
141
|
+
Include enough lines in each SEARCH section to uniquely match each set of lines that need to change.
|
142
|
+
|
143
|
+
Keep *SEARCH/REPLACE* blocks concise.
|
144
|
+
Break large *SEARCH/REPLACE* blocks into a series of smaller blocks that each change a small portion of the file.
|
145
|
+
Include just the changing lines, and a few surrounding lines if needed for uniqueness.
|
146
|
+
Do not include long runs of unchanging lines in *SEARCH/REPLACE* blocks.
|
147
|
+
|
148
|
+
Only create *SEARCH/REPLACE* blocks for files that the user has added to the chat!
|
149
|
+
|
150
|
+
To move code within a file, use 2 *SEARCH/REPLACE* blocks: 1 to delete it from its current location, 1 to insert it in the new location.
|
151
|
+
|
152
|
+
Pay attention to which filenames the user wants you to edit, especially if they are asking you to create a new file.
|
153
|
+
|
154
|
+
If you want to put code in a new file, use a *SEARCH/REPLACE block* with:
|
155
|
+
- A new file path, including dir name if needed
|
156
|
+
- An empty `SEARCH` section
|
157
|
+
- The new file's contents in the `REPLACE` section
|
158
|
+
|
159
|
+
{rename_with_shell}{go_ahead_tip}{final_reminders}ONLY EVER RETURN CODE IN A *SEARCH/REPLACE BLOCK*!
|
160
|
+
{shell_cmd_reminder}
|
161
|
+
"""
|
162
|
+
|
163
|
+
rename_with_shell = """To rename files which have been added to the chat, use shell commands at the end of your response.
|
164
|
+
|
165
|
+
"""
|
166
|
+
|
167
|
+
go_ahead_tip = """If the user just says something like "ok" or "go ahead" or "do that" they probably want you to make SEARCH/REPLACE blocks for the code changes you just proposed.
|
168
|
+
The user will say when they've applied your edits. If they haven't explicitly confirmed the edits have been applied, they probably want proper SEARCH/REPLACE blocks.
|
169
|
+
|
170
|
+
"""
|
171
|
+
|
172
|
+
shell_cmd_prompt = shell.shell_cmd_prompt
|
173
|
+
no_shell_cmd_prompt = shell.no_shell_cmd_prompt
|
174
|
+
shell_cmd_reminder = shell.shell_cmd_reminder
|
@@ -0,0 +1,9 @@
|
|
1
|
+
from .editblock_fenced_coder import EditBlockFencedCoder
|
2
|
+
from .editor_diff_fenced_prompts import EditorDiffFencedPrompts
|
3
|
+
|
4
|
+
|
5
|
+
class EditorDiffFencedCoder(EditBlockFencedCoder):
|
6
|
+
"A coder that uses search/replace blocks, focused purely on editing files."
|
7
|
+
|
8
|
+
edit_format = "editor-diff-fenced"
|
9
|
+
gpt_prompts = EditorDiffFencedPrompts()
|
@@ -0,0 +1,11 @@
|
|
1
|
+
# flake8: noqa: E501
|
2
|
+
|
3
|
+
from .editblock_fenced_prompts import EditBlockFencedPrompts
|
4
|
+
|
5
|
+
|
6
|
+
class EditorDiffFencedPrompts(EditBlockFencedPrompts):
|
7
|
+
shell_cmd_prompt = ""
|
8
|
+
no_shell_cmd_prompt = ""
|
9
|
+
shell_cmd_reminder = ""
|
10
|
+
go_ahead_tip = ""
|
11
|
+
rename_with_shell = ""
|
@@ -0,0 +1,8 @@
|
|
1
|
+
from .editblock_coder import EditBlockCoder
|
2
|
+
from .editor_editblock_prompts import EditorEditBlockPrompts
|
3
|
+
|
4
|
+
|
5
|
+
class EditorEditBlockCoder(EditBlockCoder):
|
6
|
+
"A coder that uses search/replace blocks, focused purely on editing files."
|
7
|
+
edit_format = "editor-diff"
|
8
|
+
gpt_prompts = EditorEditBlockPrompts()
|
@@ -0,0 +1,18 @@
|
|
1
|
+
# flake8: noqa: E501
|
2
|
+
|
3
|
+
from .editblock_prompts import EditBlockPrompts
|
4
|
+
|
5
|
+
|
6
|
+
class EditorEditBlockPrompts(EditBlockPrompts):
|
7
|
+
main_system = """Act as an expert software developer who edits source code.
|
8
|
+
{final_reminders}
|
9
|
+
Describe each change with a *SEARCH/REPLACE block* per the examples below.
|
10
|
+
All changes to files must use this *SEARCH/REPLACE block* format.
|
11
|
+
ONLY EVER RETURN CODE IN A *SEARCH/REPLACE BLOCK*!
|
12
|
+
"""
|
13
|
+
|
14
|
+
shell_cmd_prompt = ""
|
15
|
+
no_shell_cmd_prompt = ""
|
16
|
+
shell_cmd_reminder = ""
|
17
|
+
go_ahead_tip = ""
|
18
|
+
rename_with_shell = ""
|
@@ -0,0 +1,8 @@
|
|
1
|
+
from .editor_whole_prompts import EditorWholeFilePrompts
|
2
|
+
from .wholefile_coder import WholeFileCoder
|
3
|
+
|
4
|
+
|
5
|
+
class EditorWholeFileCoder(WholeFileCoder):
|
6
|
+
"A coder that operates on entire files, focused purely on editing files."
|
7
|
+
edit_format = "editor-whole"
|
8
|
+
gpt_prompts = EditorWholeFilePrompts()
|
@@ -0,0 +1,10 @@
|
|
1
|
+
# flake8: noqa: E501
|
2
|
+
|
3
|
+
from .wholefile_prompts import WholeFilePrompts
|
4
|
+
|
5
|
+
|
6
|
+
class EditorWholeFilePrompts(WholeFilePrompts):
|
7
|
+
main_system = """Act as an expert software developer and make changes to source code.
|
8
|
+
{final_reminders}
|
9
|
+
Output a copy of each file that needs changes.
|
10
|
+
"""
|
@@ -0,0 +1,16 @@
|
|
1
|
+
from ..dump import dump # noqa: F401
|
2
|
+
from .base_coder import Coder
|
3
|
+
from .help_prompts import HelpPrompts
|
4
|
+
|
5
|
+
|
6
|
+
class HelpCoder(Coder):
|
7
|
+
"""Interactive help and documentation about aider."""
|
8
|
+
|
9
|
+
edit_format = "help"
|
10
|
+
gpt_prompts = HelpPrompts()
|
11
|
+
|
12
|
+
def get_edits(self, mode="update"):
|
13
|
+
return []
|
14
|
+
|
15
|
+
def apply_edits(self, edits):
|
16
|
+
pass
|
@@ -0,0 +1,46 @@
|
|
1
|
+
# flake8: noqa: E501
|
2
|
+
|
3
|
+
from .base_prompts import CoderPrompts
|
4
|
+
|
5
|
+
|
6
|
+
class HelpPrompts(CoderPrompts):
|
7
|
+
main_system = """You are an expert on the AI coding tool called Aider.
|
8
|
+
Answer the user's questions about how to use aider.
|
9
|
+
|
10
|
+
The user is currently chatting with you using aider, to write and edit code.
|
11
|
+
|
12
|
+
Use the provided aider documentation *if it is relevant to the user's question*.
|
13
|
+
|
14
|
+
Include a bulleted list of urls to the aider docs that might be relevant for the user to read.
|
15
|
+
Include *bare* urls. *Do not* make [markdown links](http://...).
|
16
|
+
For example:
|
17
|
+
- https://aider.chat/docs/usage.html
|
18
|
+
- https://aider.chat/docs/faq.html
|
19
|
+
|
20
|
+
If you don't know the answer, say so and suggest some relevant aider doc urls.
|
21
|
+
|
22
|
+
If asks for something that isn't possible with aider, be clear about that.
|
23
|
+
Don't suggest a solution that isn't supported.
|
24
|
+
|
25
|
+
Be helpful but concise.
|
26
|
+
|
27
|
+
Unless the question indicates otherwise, assume the user wants to use aider as a CLI tool.
|
28
|
+
|
29
|
+
Keep this info about the user's system in mind:
|
30
|
+
{platform}
|
31
|
+
"""
|
32
|
+
|
33
|
+
example_messages = []
|
34
|
+
system_reminder = ""
|
35
|
+
|
36
|
+
files_content_prefix = """These are some files we have been discussing that we may want to edit after you answer my questions:
|
37
|
+
"""
|
38
|
+
|
39
|
+
files_no_full_files = "I am not sharing any files with you."
|
40
|
+
|
41
|
+
files_no_full_files_with_repo_map = ""
|
42
|
+
files_no_full_files_with_repo_map_reply = ""
|
43
|
+
|
44
|
+
repo_content_prefix = """Here are summaries of some files present in my git repository.
|
45
|
+
We may look at these in more detail after you answer my questions.
|
46
|
+
"""
|