Skip to content

Commit ede1b7a

Browse files
committed
updated main command line with more params + cleaning
1 parent 74ae0c4 commit ede1b7a

File tree

11 files changed

+253
-76
lines changed

11 files changed

+253
-76
lines changed

ExecutionAgent.sh

Lines changed: 75 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,51 +1,115 @@
11
#!/bin/bash
22

3+
# Default value for the number parameter
4+
num=40
5+
36
# Function to extract project name from GitHub URL
47
# Extracts the last component of the URL, which is usually the project name
58
extract_project_name() {
69
local url="$1"
710
echo "$url" | awk -F '/' '{print $(NF)}'
811
}
912

13+
# Function to run the command and handle retries
14+
run_with_retries() {
15+
local command="$1"
16+
local project_name="$2"
17+
local max_retries=2
18+
local attempt=1
19+
20+
while [[ $attempt -le $max_retries ]]; do
21+
echo "======================================================================"
22+
echo "STARTING ITERATION $attempt:"
23+
echo "PROJECT: $project_name"
24+
echo "======================================================================"
25+
26+
eval "$command"
27+
result=$(python3.10 post_process.py "$project_name")
28+
29+
if [[ "$result" == "SUCCESS" ]]; then
30+
echo "Post-process succeeded."
31+
return
32+
fi
33+
34+
echo "Attempt $attempt failed with FAILURE. Retrying..."
35+
((attempt++))
36+
done
37+
38+
while true; do
39+
echo "======================================================================"
40+
echo "PROMPTING USER FOR ADDITIONAL RETRY:"
41+
echo "PROJECT: $project_name"
42+
echo "======================================================================"
43+
44+
read -p "Post-process failed after $max_retries attempts. Do you want to retry again? (yes/no): " user_input
45+
case "$user_input" in
46+
[Yy]* ) eval "$command"; result=$(python3.10 post_process.py "$project_name");
47+
if [[ "$result" == "SUCCESS" ]]; then
48+
echo "Post-process succeeded."
49+
return
50+
fi
51+
;;
52+
[Nn]* ) echo "Exiting retry loop."; break;;
53+
* ) echo "Please answer yes or no.";;
54+
esac
55+
done
56+
}
57+
58+
# Parse command-line arguments
59+
while [[ $# -gt 0 ]]; do
60+
case "$1" in
61+
--repo)
62+
repo_url="$2"
63+
shift 2
64+
;;
65+
-l)
66+
num="$2"
67+
shift 2
68+
;;
69+
*)
70+
shift
71+
;;
72+
esac
73+
done
74+
1075
# Set up API key, increment experiment, and prepare AI settings
1176
python3.10 setup_api_key.py # Sets up the API key required for the scripts
1277
python3.10 experimental_setups/increment_experiment.py # Updates experimental parameters
1378
python3.10 prepare_ai_settings.py # Prepares the AI settings configuration
1479

1580
# Check for the --repo argument or file path
16-
if [[ "$1" == "--repo" ]]; then
81+
if [[ -n "$repo_url" ]]; then
1782
# Ensure the user provided a GitHub URL with the --repo argument
18-
if [[ -z "$2" ]]; then
83+
if [[ -z "$repo_url" ]]; then
1984
echo "Error: --repo argument requires a GitHub URL."
2085
echo "Usage: ./script_name.sh --repo <github_repo_url>"
2186
exit 1
2287
fi
2388

2489
# Extract the project name from the provided GitHub URL
25-
github_url="$2"
26-
project_name=$(extract_project_name "$github_url")
90+
project_name=$(extract_project_name "$repo_url")
2791

2892
# Call get_main_language.py to determine the main language of the repository
2993
# The Python script is expected to return a string like "Primary language: <language>"
30-
primary_language=$(python3.10 get_main_language.py "$github_url")
94+
primary_language=$(python3.10 get_main_language.py "$repo_url")
3195
echo "$primary_language"
3296

3397
# Continue processing for a single repository
3498
echo "$project_name" # Print the project name
35-
echo "$github_url" # Print the GitHub URL
99+
echo "$repo_url" # Print the GitHub URL
36100

37101
# Initialize an empty Docker configuration file
38102
echo "{}" > ~/.docker/config.json
39103

40104
# Call the Python script to clone the repo and set metadata
41-
python3.10 clone_and_set_metadata.py "$project_name" "$github_url" "$primary_language"
105+
python3.10 clone_and_set_metadata.py "$project_name" "$repo_url" "$primary_language"
42106

43107
# Run the main script with specific AI settings and experiment parameters
44-
./run.sh --ai-settings ai_settings.yaml -c -l 40 -m json_file --experiment-file "project_meta_data.json"
108+
run_with_retries "./run.sh --ai-settings ai_settings.yaml -c -l \"$num\" -m json_file --experiment-file \"project_meta_data.json\"" "$project_name"
45109

46-
elif [[ -f "$1" ]]; then
110+
elif [[ -f "$repo_url" ]]; then
47111
# Handle the case where the input is a file containing multiple repositories
48-
file_path="$1"
112+
file_path="$repo_url"
49113
echo "Using file path: $file_path" # Print the file path being processed
50114

51115
# Read the file line by line
@@ -66,7 +130,7 @@ elif [[ -f "$1" ]]; then
66130
python3.10 clone_and_set_metadata.py "$project_name" "$github_url" "$language"
67131

68132
# Run the main script with specific AI settings and experiment parameters
69-
./run.sh --ai-settings ai_settings.yaml -c -l 40 -m json_file --experiment-file "project_meta_data.json"
133+
run_with_retries "./run.sh --ai-settings ai_settings.yaml -c -l \"$num\" -m json_file --experiment-file \"project_meta_data.json\"" "$project_name"
70134
done < "$file_path"
71135

72136
else

README.md

Lines changed: 22 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -29,11 +29,11 @@ To get started in a VSCode Dev Container:
2929
### 1️⃣ Single Repository Mode
3030
You can directly process a single GitHub repository using the `--repo` option:
3131
```bash
32-
./ExecutionAgent.sh --repo <github_repo_url>
32+
./ExecutionAgent.sh --repo <github_repo_url> -l <num_value>
3333
```
3434
Example:
3535
```bash
36-
./ExecutionAgent.sh --repo https://github.com/pytest-dev/pytest
36+
./ExecutionAgent.sh --repo https://github.com/pytest-dev/pytest -l 50
3737
```
3838

3939
When this mode is used, ExecutionAgent will:
@@ -42,6 +42,8 @@ When this mode is used, ExecutionAgent will:
4242
3. Clone the repository and set up metadata.
4343
4. Launch the main loop of ExecutionAgent to build the project and run its test cases.
4444

45+
The `-l` option allows you to specify the number of cycles which corresponds to the number of actions the agent can execute. By default, if `-l` is not provided, it will be set to 40. If you want to set a different number, simply pass the desired value after `-l`. For example, `-l 50` will use 50 instead of the default value.
46+
4547
### 2️⃣ Batch File Mode
4648
Prepare a batch file listing projects to process in the format:
4749
`<project_name> <github_url> <language>`
@@ -51,14 +53,13 @@ Example (notice how for now we leave one empty line after each entry):
5153
scipy https://github.com/scipy/scipy Python
5254
5355
pytest https://github.com/pytest-dev/pytest Python
54-
5556
```
5657

5758
Run ExecutionAgent with the batch file:
5859
```bash
5960
./ExecutionAgent.sh /path/to/batch_file.txt
6061
```
61-
ExecutionAgent will process each project listed in the file, performing the same steps as the single repository mode.
62+
ExecutionAgent will process each project listed in the file, performing the same steps as the single repository mode. The `-l` option can also be applied here by adding it to the command when running the script.
6263

6364
---
6465

@@ -77,6 +78,23 @@ ExecutionAgent will process each project listed in the file, performing the same
7778

7879
Results are logged under `experimental_setups/experiment_XX`, where `XX` is an incremented number for each invocation of ExecutionAgent.
7980

81+
## 📁 Output Folder Structure Explanation
82+
83+
The folder structure under `experimental_setups/experiment_XX` is organized to keep track of the various outputs and logs generated during the execution of the `ExecutionAgent`. Below is a breakdown of the key directories and their contents:
84+
85+
- **files**: Contains files generated by the ExecutionAgent, such as `Dockerfile`, installation scripts, or any configuration files necessary for setting up the container environment.
86+
- Example: `Dockerfile`, `INSTALL.sh`
87+
88+
- **logs**: Stores raw logs capturing the input prompts and the corresponding outputs from the model during execution. These logs are essential for troubleshooting and understanding the behavior of the agent.
89+
- Example: `cycles_list_marshmallow`, `prompt_history_marshmallow`
90+
91+
- **responses**: Holds the responses generated by the model during the execution process in a structured JSON format. These responses include details about the generated build or test configurations and results.
92+
- Example: `model_responses_marshmallow`
93+
94+
- **saved_contexts**: Contains the saved states of the agent object at each iteration of the execution process. These snapshots are useful for debugging, tracking changes, and extracting subcomponents of the prompt across different cycles.
95+
- Example: `cycle_1`, `cycle_10`, etc.
96+
97+
This structure helps in managing the various data generated throughout the experimentation, ensuring easy access to logs, model responses, and agent states.
8098
---
8199

82100
## 📜 Research Paper

autogpt/app/main.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -295,6 +295,7 @@ def graceful_agent_interrupt(signum: int, frame: Optional[FrameType]) -> None:
295295
if cycles_remaining == 1: # Last cycle
296296
stop_and_remove(agent.container)
297297
os.system("docker system prune -f")
298+
exit()
298299
user_feedback, user_input, new_cycles_remaining = get_user_feedback(
299300
config,
300301
ai_config,

autogpt/commands/system.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,4 +63,6 @@ def task_complete(reason: str, agent: Agent) -> NoReturn:
6363
logger.info(title="Shutting down...\n", message=reason)
6464
stop_and_remove(agent.container)
6565
os.system("docker system prune -f")
66+
with open(os.path.join("experimental_setups", agent.exp_number, "saved_contexts", "SUCCESS"), "w") as ssf:
67+
ssf.write("SUCCESS")
6668
quit()

clean.sh

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,4 +2,5 @@ rm -rf experimental_setups/experiment_*
22
rm -rf logs/*
33
rm -rf execution_agent_workspace/*
44
touch execution_agent_workspace/readme
5-
python3.10 remove_api_token.py
5+
python3.10 remove_api_token.py
6+
rm model_logging_temp.txt

post_process.py

Lines changed: 113 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,113 @@
1+
import os
2+
import json
3+
import sys
4+
import argparse
5+
6+
import warnings
7+
warnings.filterwarnings("ignore")
8+
9+
import openai
10+
11+
def ask_chatgpt(query, system_message, model="gpt-4"):
12+
# Read the OpenAI API token from a file
13+
with open("openai_token.txt") as opt:
14+
token = opt.read().strip()
15+
16+
# Set up the OpenAI API key
17+
openai.api_key = token
18+
19+
# Construct the messages for the Chat Completion API
20+
messages = [
21+
{"role": "system", "content": system_message},
22+
{"role": "user", "content": query}
23+
]
24+
25+
# Call the OpenAI API for chat completion
26+
response = openai.ChatCompletion.create(
27+
model=model,
28+
messages=messages
29+
)
30+
31+
# Extract and return the content of the assistant's response
32+
return response["choices"][0]["message"]["content"]
33+
34+
def main():
35+
if len(sys.argv) != 2:
36+
print("Usage: python post_process.py <project_name>")
37+
sys.exit(1)
38+
39+
project_name = sys.argv[1]
40+
41+
# Read the last line of experiments_list.txt
42+
experiments_file = "experimental_setups/experiments_list.txt"
43+
if not os.path.exists(experiments_file):
44+
print(f"Error: {experiments_file} does not exist.")
45+
sys.exit(1)
46+
47+
with open(experiments_file, 'r') as f:
48+
lines = f.readlines()
49+
if not lines:
50+
print(f"Error: {experiments_file} is empty.")
51+
sys.exit(1)
52+
last_line = lines[-1].strip()
53+
54+
# Build paths
55+
success_file = f"experimental_setups/{last_line}/saved_contexts/{project_name}/SUCCESS"
56+
57+
if os.path.exists(success_file):
58+
print("SUCCESS")
59+
return
60+
61+
# Find the cycle_XX file with the highest XX
62+
contexts_dir = f"experimental_setups/{last_line}/saved_contexts/{project_name}"
63+
if not os.path.exists(contexts_dir):
64+
print(f"Error: {contexts_dir} does not exist.")
65+
sys.exit(1)
66+
67+
cycle_files = [f for f in os.listdir(contexts_dir) if f.startswith("cycle_") and f[6:].isdigit()]
68+
if not cycle_files:
69+
print(f"Error: No cycle files found in {contexts_dir}.")
70+
sys.exit(1)
71+
72+
latest_cycle_file = max(cycle_files, key=lambda x: int(x[6:]))
73+
latest_cycle_path = os.path.join(contexts_dir, latest_cycle_file)
74+
75+
# Read the JSON content of the latest cycle file
76+
with open(latest_cycle_path, 'r') as f:
77+
try:
78+
file_content = json.load(f)
79+
except json.JSONDecodeError:
80+
print(f"Error: Failed to decode JSON from {latest_cycle_path}.")
81+
sys.exit(1)
82+
83+
# Extract the desired content
84+
try:
85+
extracted_content = file_content["steps_object"]["1"]["result_of_step"]
86+
except KeyError as e:
87+
print(f"Error: Missing key in JSON structure: {e}")
88+
sys.exit(1)
89+
90+
# Prepare the query for ask_chatgpt
91+
query = (
92+
"the following would represent the sequence of commands and reasoning made by an LLM trying to install \"webpack\" project from source code and execute test cases. "
93+
"I want you to summarize the encountered problems and give advice for next attempt. Be precise and concise. Address the most important and critical issues (ignore non critical warnings and so). Your response should have one header: ### Feedback from previous installation attempts\n"
94+
f"+ {extracted_content}"
95+
)
96+
97+
system_message = (
98+
"You are a helpful software engineering assistant with capabilities of installing, building, configuring, and testing software projects."
99+
)
100+
101+
# Call ask_chatgpt
102+
response = ask_chatgpt(query, system_message)
103+
104+
# Save the response to problems_memory/{project_name}
105+
problems_memory = f"problems_memory/{project_name}"
106+
with open(problems_memory, 'w') as f:
107+
f.write(response)
108+
109+
# Print FAILURE
110+
print("FAILURE")
111+
112+
if __name__ == "__main__":
113+
main()

problems_memory/marshmallow

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
### Feedback from previous installation attempts
2+
3+
All provided reports suggest that the installation worked as expected; though, it's unclear if the "webpack" project is used at all since the contents of the reports all mention the 'marshmallow' project. 'tox' is used, which is a test runner, so it's assumed that the tests have been executed without stating any issues.
4+
5+
If "webpack" should be installed and tested, the steps might have been unclear or misreported. "Webpack" is not a Python project, so Python-specific instructions or tools such as 'tox', 'venv', or 'pip' are not applicable. Webpack is a static module bundler for modern JavaScript applications and needs Node.js environment.
6+
7+
Advice for next installation and test execution attempt:
8+
9+
1. Check the scope of the project. Make sure you work on the correct software project ("webpack" vs. "marshmallow").
10+
2. If the objective is to install and test "webpack", Node.js and npm (node package manager) are required. Webpack can be installed globally with `npm install --global webpack`. For testing, use the included scripts in the project's `package.json` file, often it's as simple as running `npm test`.
11+
3. If working with the Python 'marshmallow' project, continue using Python environment setup with venv and pip. Use tox for executing the provided tests.

problems_memory/pytest

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
### Feedback from previous installation attempts
2+
3+
1. The initial setup and installation of the 'pytest' project seem to be successful with all the important dependencies correctly extracted. However, it is important to note that there is confusion between 'webpack' and 'pytest'. As per the request, the 'webpack' project was to be installed but all actions and results are related to 'pytest'.
4+
5+
2. Another issue is running pip as the root user, which is considered a bad practice. The warning suggests using a virtual environment, which helps in isolating the environment to prevent conflicts between different version of packages.
6+
7+
3. In the later stages, the 'tox' command was not found which indicates that it may not have been installed or is not available in the current environment. This was corrected in a subsequent step by installing 'tox'.
8+
9+
For the next attempt, ensure that:
10+
11+
- The correct project ('webpack' vs 'pytest') is being installed.
12+
- Utilize a virtual environment to manage Python dependencies
13+
- Verify that all necessary testing tools like 'tox' are installed before running test cases.

run.sh

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ if $PYTHON_CMD -c "import sys; sys.exit(sys.version_info < (3, 10))"; then
2525
$PYTHON_CMD -m pip install -r requirements.txt
2626
fi
2727
$PYTHON_CMD -m autogpt --skip-news "$@"
28-
read -p "Press any key to continue..."
28+
#read -p "Press any key to continue..."
2929
else
3030
echo "Python 3.10 or higher is required to run Auto GPT."
3131
fi

0 commit comments

Comments
 (0)