git+docker improvements

version, build branch

frdel committed Nov 19, 2024 at 20:46 UTC 020c16ef8636e995c9022216a8f961084de8b0f7
11 files changed +129 -36
docker/run/Dockerfile
+13 -12
@@ -1,12 +1,14 @@
1 # Use the latest slim version of Debian
2 FROM debian:bookworm-slim
3
4 +# Check if the argument is provided, else throw an error
5 +ARG BRANCH
6 +RUN if [ -z "$BRANCH" ]; then echo "ERROR: BRANCH is not set!" >&2; exit 1; fi
7 +
8 # Update and install necessary packages
9 RUN apt-get update && apt-get install -y \
10 python3 \
11 python3-pip \
8 - python3-dev \
9 - python3-babel \
12 python3-venv \
13 nodejs \
14 npm \
@@ -15,13 +17,8 @@ RUN apt-get update && apt-get install -y \
17 curl \
18 wget \
19 git \
18 - build-essential \
20 ffmpeg
21
21 -# Cleanup package list
22 -RUN rm -rf /var/lib/apt/lists/*
23 -RUN apt-get clean
24 -
22 # Set up SSH
23 RUN mkdir /var/run/sshd && \
24 echo 'root:toor' | chpasswd && \
@@ -33,12 +30,16 @@ COPY ./fs/ /
30 # install additional software
31 RUN bash /ins/install_searxng.sh
32
36 -# install a0 with caching
37 -RUN bash /ins/install_A0.sh
33 +# install A0
34 +RUN bash /ins/install_A0.sh $BRANCH
35
39 -# cleanup repo and install a0 without caching, this speeds up builds
40 -ARG CACHE_DATE=unknown
41 -RUN echo "cache buster $CACHE_DATE" && bash /ins/install_A02.sh
36 +# cleanup repo and install A0 without caching, this speeds up builds
37 +ARG CACHE_DATE=none
38 +RUN echo "cache buster $CACHE_DATE" && bash /ins/install_A02.sh $BRANCH
39 +
40 +# Cleanup package list
41 +RUN rm -rf /var/lib/apt/lists/*
42 +RUN apt-get clean
43
44 # Expose ports
45 # EXPOSE 22
docker/run/build.txt
+15 -4
@@ -1,7 +1,18 @@
1 # local image with smart cache
2 -docker build -t agent-zero-run:local --build-arg CACHE_DATE=$(date +%Y-%m-%d:%H:%M:%S) .
2 +docker build -t agent-zero-run:local --build-arg BRANCH=development --build-arg CACHE_DATE=$(date +%Y-%m-%d:%H:%M:%S) .
3 +
4 +# local image without cache
5 +docker build -t agent-zero-run:local --build-arg BRANCH=development --no-cache .
6 +
7 +# dockerhub push:
8
4 -# dockerhub push with and without caching
9 docker login
6 -docker buildx build --platform linux/amd64,linux/arm64 -t frdel/agent-zero-run:testing --push --build-arg CACHE_DATE=$(date +%Y-%m-%d:%H:%M:%S) .
7 -docker buildx build --platform linux/amd64,linux/arm64 -t frdel/agent-zero-run:testing --push --no-cache .
\ No newline at end of file
10 +
11 +# development:
12 +docker buildx build --build-arg BRANCH=development -t frdel/agent-zero-run:development --platform linux/amd64,linux/arm64 --push --build-arg CACHE_DATE=$(date +%Y-%m-%d:%H:%M:%S) .
13 +
14 +# testing:
15 +docker buildx build --build-arg BRANCH=testing -t frdel/agent-zero-run:testing --platform linux/amd64,linux/arm64 --push --build-arg CACHE_DATE=$(date +%Y-%m-%d:%H:%M:%S) .
16 +
17 +# main
18 +docker buildx build --build-arg BRANCH=testing -t frdel/agent-zero-run:testing --platform linux/amd64,linux/arm64 --push --no-cache .
docker/run/fs/exe/node_eval.js
+24 -4
@@ -2,11 +2,29 @@
2
3 const vm = require('vm');
4 const path = require('path');
5 +const Module = require('module');
6
6 -// Create a comprehensive context with all important global objects
7 +// Enhance `require` to search CWD first, then globally
8 +function customRequire(moduleName) {
9 + try {
10 + // Try resolving from CWD's node_modules
11 + const cwdPath = path.resolve(process.cwd(), 'node_modules', moduleName);
12 + return require(cwdPath);
13 + } catch (cwdErr) {
14 + try {
15 + // Try resolving as a global module
16 + return require(moduleName);
17 + } catch (globalErr) {
18 + console.error(`Cannot find module: ${moduleName}`);
19 + throw globalErr;
20 + }
21 + }
22 +}
23 +
24 +// Create the VM context
25 const context = vm.createContext({
26 ...global,
9 - require: require,
27 + require: customRequire, // Use the custom require
28 __filename: path.join(process.cwd(), 'eval.js'),
29 __dirname: process.cwd(),
30 module: { exports: {} },
@@ -19,10 +37,12 @@ const context = vm.createContext({
37 setImmediate: setImmediate,
38 clearTimeout: clearTimeout,
39 clearInterval: clearInterval,
22 - clearImmediate: clearImmediate
40 + clearImmediate: clearImmediate,
41 });
42
43 +// Retrieve the code from the command-line argument
44 const code = process.argv[2];
45 +
46 const wrappedCode = `
47 (async function() {
48 try {
@@ -38,4 +58,4 @@ vm.runInContext(wrappedCode, context, {
58 filename: 'eval.js',
59 lineOffset: -2,
60 columnOffset: 0,
41 -}).catch(console.error);
\ No newline at end of file
61 +}).catch(console.error);
docker/run/fs/ins/install_A0.sh
+8 -1
@@ -1,9 +1,16 @@
1 #!/bin/bash
2
3 -BRANCH="development"
3 +# branch from parameter
4 +if [ -z "$1" ]; then
5 + echo "Error: Branch parameter is empty. Please provide a valid branch name."
6 + exit 1
7 +fi
8 +BRANCH="$1"
9 +
10
11 git clone -b "$BRANCH" "https://github.com/frdel/agent-zero" "/git/agent-zero"
12
13 +
14 # Create and activate Python virtual environment
15 python3 -m venv /opt/venv
16 source /opt/venv/bin/activate
docker/run/fs/ins/install_A02.sh
+1 -1
@@ -4,7 +4,7 @@
4 rm -rf /git/agent-zero
5
6 # run the original install script again
7 -bash /ins/install_A0.sh
7 +bash /ins/install_A0.sh "$@"
8
9 # remove python packages cache
10 source /opt/venv/bin/activate
docker/run/fs/ins/install_searxng2.sh
+3
@@ -28,3 +28,6 @@ pip install -U pyyaml
28 # jump to SearXNG's working tree and install SearXNG into virtualenv
29 cd "/usr/local/searxng/searxng-src"
30 pip install --use-pep517 --no-build-isolation -e .
31 +
32 +# cleanup cache
33 +pip cache purge
\ No newline at end of file
python/helpers/git.py new
+48
@@ -0,0 +1,48 @@
1 +from git import Repo
2 +from datetime import datetime
3 +import os
4 +from python.helpers import files
5 +
6 +def get_git_info():
7 + # Get the current working directory (assuming the repo is in the same folder as the script)
8 + repo_path = files.get_base_dir()
9 +
10 + # Open the Git repository
11 + repo = Repo(repo_path)
12 +
13 + # Ensure the repository is not bare
14 + if repo.bare:
15 + raise ValueError(f"Repository at {repo_path} is bare and cannot be used.")
16 +
17 + # Get the current branch name
18 + branch = repo.active_branch.name if repo.head.is_detached is False else ""
19 +
20 + # Get the latest commit hash
21 + commit_hash = repo.head.commit.hexsha
22 +
23 + # Get the commit date (ISO 8601 format)
24 + commit_time = datetime.fromtimestamp(repo.head.commit.committed_date).strftime('%y-%m-%d %H:%M')
25 +
26 + # Get the latest tag description (if available)
27 + short_tag = ""
28 + try:
29 + tag = repo.git.describe(tags=True)
30 + tag_split = tag.split('-')
31 + if len(tag_split) >= 3:
32 + short_tag = "-".join(tag_split[:-1])
33 + except:
34 + tag = ""
35 +
36 + version = branch[0].upper() + " " + ( short_tag or commit_hash[:7] )
37 +
38 + # Create the dictionary with collected information
39 + git_info = {
40 + "branch": branch,
41 + "commit_hash": commit_hash,
42 + "commit_time": commit_time,
43 + "tag": tag,
44 + "short_tag": short_tag,
45 + "version": version
46 + }
47 +
48 + return git_info
\ No newline at end of file
python/helpers/persist_chat.py
+1 -1
@@ -165,7 +165,7 @@ def _deserialize_history(history: list[dict[str, Any]]):
165 def _deserialize_log(data: dict[str, Any]) -> "Log":
166 log = Log()
167 log.guid = data.get("guid", str(uuid.uuid4()))
168 - log.progress = data.get("progress", "")
168 + log.progress = "" #data.get("progress", "")
169 log.progress_no = data.get("progress_no", 0)
170
171 # Deserialize the list of LogItem objects
requirements.txt
+1
@@ -5,6 +5,7 @@ duckduckgo-search==6.1.12
5 faiss-cpu==1.8.0.post1
6 flask[async]==3.0.3
7 flask-basicauth==0.2.0
8 +GitPython==3.1.43
9 inputimeout==1.0.4
10 langchain-anthropic==0.1.19
11 langchain-community==0.2.7
run_ui.py
+14 -12
@@ -8,7 +8,7 @@ from flask import Flask, request, jsonify, Response
8 from flask_basicauth import BasicAuth
9 from agent import AgentContext
10 from initialize import initialize
11 -from python.helpers import files
11 +from python.helpers import files, git
12 from python.helpers.files import get_abs_path
13 from python.helpers.print_style import PrintStyle
14 from python.helpers.dotenv import load_dotenv
@@ -48,12 +48,9 @@ def requires_auth(f):
48 async def decorated(*args, **kwargs):
49 user = dotenv.get_dotenv_value("AUTH_LOGIN")
50 password = dotenv.get_dotenv_value("AUTH_PASSWORD")
51 - if user and password:
51 + if user and password:
52 auth = request.authorization
53 - if not auth or not (
54 - auth.username == user
55 - and auth.password == password
56 - ):
53 + if not auth or not (auth.username == user and auth.password == password):
54 return Response(
55 "Could not verify your access level for that URL.\n"
56 "You have to login with proper credentials",
@@ -87,6 +84,8 @@ async def upload_file():
84
85
86 ALLOWED_EXTENSIONS = {"png", "jpg", "jpeg", "txt", "pdf", "csv", "html", "json", "md"}
87 +
88 +
89 def allowed_file(filename):
90 return "." in filename and filename.rsplit(".", 1)[1].lower() in ALLOWED_EXTENSIONS
91
@@ -131,17 +130,20 @@ async def browse_work_dir():
130 )
131
132
134 -# handle default address, show demo html page from ./test_form.html
133 +# handle default address, load index
134 @app.route("/", methods=["GET"])
135 @requires_auth
137 -async def test_form():
138 - return Path(get_abs_path("./webui/index.html")).read_text()
136 +async def serve_index():
137 + gitinfo = git.get_git_info()
138 + return files.read_file("./webui/index.html", version_no=gitinfo["version"])
139
140
141 # simple health check, just return OK to see the server is running
142 @app.route("/ok", methods=["GET", "POST"])
143 async def health_check():
144 - return "OK"
144 + gitinfo = git.get_git_info()
145 + return jsonify({"ok": True, "gitinfo": gitinfo})
146 +
147
148 # send message to agent (async UI)
149 @app.route("/msg", methods=["POST"])
@@ -530,7 +532,7 @@ async def transcribe():
532 "message": str(e),
533 }
534 PrintStyle.error(str(e))
533 -
535 +
536 # respond with json
537 return jsonify(response)
538
@@ -550,7 +552,7 @@ async def handle_rfc():
552 "ok": True,
553 "result": result,
554 }
553 -
555 +
556 return jsonify(response)
557 except Exception as e:
558 response = {
webui/index.html
+1 -1
@@ -159,7 +159,7 @@
159 </div>
160 <!-- Version Info -->
161 <div class="version-info">
162 - <span id="a0version">Agent Zero 0.7.2<br>built on 2024-11-04</span>
162 + <span id="a0version">Version {{version_no}} {{version_time}}</span>
163 </div>
164 </div>
165 </div>