diff --git a/ai-hub/add_knowledge.sh b/ai-hub/add_knowledge.sh deleted file mode 100644 index c7ab949..0000000 --- a/ai-hub/add_knowledge.sh +++ /dev/null @@ -1,87 +0,0 @@ -#!/bin/bash - -# ============================================================================== -# Script to scan for specific file types and upload their content to an API. -# Prerequisites: -# - The FastAPI application must be running locally on http://localhost:8000. -# - The 'jq' command-line JSON processor must be installed. -# - The 'curl' command-line tool must be installed. -# ============================================================================== - -# Define the API endpoint -API_URL="http://localhost:8000/documents" - -DEFAULT_MODEL="gemini" -CURRENT_MODEL="" # The model used in the last turn - -# --- 1. Check for Dependencies --- -if ! command -v jq &> /dev/null -then - echo "❌ 'jq' is not installed. Please install it to run this script." - exit 1 -fi - -# --- 2. Start the FastAPI Server in the Background --- -echo "--- Starting AI Hub Server ---" -uvicorn app.main:app --host 127.0.0.1 --port 8000 & -SERVER_PID=$! - -# Define a cleanup function to kill the server on exit -cleanup() { - echo "" - echo "--- Shutting Down Server (PID: $SERVER_PID) ---" - kill $SERVER_PID -} -# Register the cleanup function to run when the script exits (e.g., Ctrl+C or typing 'exit') -trap cleanup EXIT - -echo "Server started with PID: $SERVER_PID. Waiting for it to initialize..." -sleep 5 # Wait for the server to be ready - - -# Find all files with the specified extensions in the current directory and its subdirectories -# The -print0 option is used to handle filenames with spaces or special characters. -find . -type f \( -name "*.py" -o -name "*.txt" -o -name "*.md" -o -name "*.yaml" \) -print0 | while IFS= read -r -d $'\0' file_path; do - - # Get the file's basename (e.g., "my_file.md") to use as the title - file_title=$(basename -- "$file_path") - - # Get the file creation date. - # Note: 'stat' options differ between Linux and macOS. - # Linux: stat -c %w - # macOS: stat -f %B - # This script assumes a Linux-like stat output. You may need to adjust this. - file_created_at=$(stat -c %w "$file_path") - - # Read the entire file content into a variable. - # `cat` is used to get the content, and it's escaped for JSON. - file_content=$(cat "$file_path" | sed 's/\\/\\\\/g' | sed 's/"/\\"/g' | sed 's/`/\\`/g') - - # Construct the JSON payload using `jq` for robust formatting - json_payload=$(jq -n \ - --arg title "$file_title" \ - --arg text "$file_content" \ - --arg file_path "$file_path" \ - '{title: $title, text: $text, file_path: $file_path}') - - echo "Uploading file: $file_path" - - # Make the POST request to the API - response=$(curl -X POST \ - -s \ - -H "Content-Type: application/json" \ - -d "$json_payload" \ - "$API_URL") - - # Display the response from the API - if [[ "$response" == *"success"* ]]; then - echo "✅ Uploaded successfully. Response: $response" - else - echo "❌ Failed to upload. Response: $response" - fi - - echo "---" - -done - -echo "Script finished." diff --git a/ai-hub/run_chat.sh b/ai-hub/run_chat.sh deleted file mode 100644 index 695d2bc..0000000 --- a/ai-hub/run_chat.sh +++ /dev/null @@ -1,140 +0,0 @@ -#!/bin/bash - -# A script to automatically start the server and run an interactive chat session. -# It now tests the PATH_PREFIX functionality. - -# --- Configuration --- -# Set the desired path prefix for testing -TEST_PATH_PREFIX="/api/v1" -BASE_URL="http://127.0.0.1:8000" -DEFAULT_MODEL="deepseek" -CURRENT_MODEL="" # The model used in the last turn - -# --- 1. Check for Dependencies --- -if ! command -v jq &> /dev/null -then - echo "❌ 'jq' is not installed. Please install it to run this script." - exit 1 -fi - -# --- 2. Start the FastAPI Server in the Background with the PATH_PREFIX --- -echo "--- Starting AI Hub Server with PATH_PREFIX=$TEST_PATH_PREFIX ---" -# Export the PATH_PREFIX environment variable so the server can read it -export PATH_PREFIX="$TEST_PATH_PREFIX" -uvicorn app.main:app --host 127.0.0.1 --port 8000 & -SERVER_PID=$! - -# Define a cleanup function to kill the server on exit -cleanup() { - echo "" - echo "--- Shutting Down Server (PID: $SERVER_PID) ---" - kill $SERVER_PID -} -# Register the cleanup function to run when the script exits (e.g., Ctrl+C or typing 'exit') -trap cleanup EXIT - -echo "Server started with PID: $SERVER_PID. Waiting for it to initialize..." -sleep 5 # Wait for the server to be ready - -# --- 3. Create a New Conversation Session --- -echo "--- Starting a new conversation session... ---" -# Use the full URL with the test path prefix -SESSION_URL="$BASE_URL$TEST_PATH_PREFIX/sessions/" -SESSION_DATA=$(curl -s -X POST "$SESSION_URL" \ - -H "Content-Type: application/json" \ - -d '{"user_id": "local_user", "provider_name": "'"$DEFAULT_MODEL"'"}' \ - -w '\n%{http_code}') # Add a new line and the status code - -# Extract body and status code -HTTP_CODE=$(echo "$SESSION_DATA" | tail -n1) -SESSION_DATA_BODY=$(echo "$SESSION_DATA" | head -n-1) - -if [ "$HTTP_CODE" -ne 200 ]; then - echo "❌ Failed to create a session (HTTP $HTTP_CODE). Server might not have started correctly." - echo "Response body: $SESSION_DATA_BODY" - exit 1 -fi - -SESSION_ID=$(echo "$SESSION_DATA_BODY" | jq -r '.id') -if [ -z "$SESSION_ID" ] || [ "$SESSION_ID" == "null" ]; then - echo "❌ Failed to create a session. Server response did not contain an ID." - echo "Response body: $SESSION_DATA_BODY" - exit 1 -fi - -# Set the initial model -CURRENT_MODEL="$DEFAULT_MODEL" - -echo "✅ Session created with ID: $SESSION_ID. The initial model is '$CURRENT_MODEL'." -echo "--------------------------------------------------" -echo "To switch models, type your message like this: [gemini] " -echo "To enable the FAISS retriever, add the flag: [faiss] " -echo "You can combine them: [gemini] [faiss] " -echo "Type 'exit' or 'quit' to end." -echo "--------------------------------------------------" - -# --- 4. Start the Interactive Chat Loop --- -while true; do - read -p "You: " user_input - - if [[ "$user_input" == "exit" || "$user_input" == "quit" ]]; then - break - fi - - # Initialize variables for this turn - PROMPT_TEXT="$user_input" - MODEL_TO_USE="$CURRENT_MODEL" - LOAD_FAISS_RETRIEVER="false" - - # Check for and process the model switch - # This regex ensures we only match valid models and they must appear first - if [[ "$PROMPT_TEXT" =~ ^\[(deepseek|gemini)\]\ (.*)$ ]]; then - MODEL_TO_USE="${BASH_REMATCH[1]}" - PROMPT_TEXT="${BASH_REMATCH[2]}" - # Update the current model for the next prompt - CURRENT_MODEL="$MODEL_TO_USE" - fi - - # Check for and process the FAISS flag - # This check is separate to avoid misinterpreting "faiss" as a model - if [[ "$PROMPT_TEXT" =~ \[faiss\] ]]; then - LOAD_FAISS_RETRIEVER="true" - # Use sed to remove the [faiss] flag and trim any leading/trailing spaces - PROMPT_TEXT=$(echo "$PROMPT_TEXT" | sed 's/\[faiss\]//' | xargs) - fi - - # Check if the prompt is empty after processing flags and models - if [ -z "$PROMPT_TEXT" ]; then - echo "Please enter a message." - continue - fi - - # Construct the JSON payload with the model, prompt, and FAISS flag - # Note the use of --argjson to pass the boolean value correctly - json_payload=$(jq -n \ - --arg prompt "$PROMPT_TEXT" \ - --arg provider_name "$MODEL_TO_USE" \ - --argjson faiss_flag "$LOAD_FAISS_RETRIEVER" \ - '{"prompt": $prompt, "provider_name": $provider_name, "load_faiss_retriever": $faiss_flag}') - - echo "Payload: $json_payload" # Optional: for debugging - - # Use the full URL with the test path prefix - CHAT_URL="$BASE_URL$TEST_PATH_PREFIX/sessions/$SESSION_ID/chat" - ai_response_json=$(curl -s -X POST "$CHAT_URL" \ - -H "Content-Type: application/json" \ - -d "$json_payload") - - # Check if the response is valid JSON - if ! echo "$ai_response_json" | jq -e . >/dev/null; then - echo "❌ AI: An error occurred or the server returned an invalid response." - echo "Server response: $ai_response_json" - else - ai_answer=$(echo "$ai_response_json" | jq -r '.answer') - provider_used=$(echo "$ai_response_json" | jq -r '.provider_used') - echo "AI [$provider_used] [faiss_enabled: $LOAD_FAISS_RETRIEVER]: $ai_answer" - fi - -done - -# The 'trap' will automatically call the cleanup function when the loop breaks. \ No newline at end of file diff --git a/ai-hub/run_integration_tests.sh b/ai-hub/run_integration_tests.sh deleted file mode 100644 index a2102ac..0000000 --- a/ai-hub/run_integration_tests.sh +++ /dev/null @@ -1,112 +0,0 @@ -#!/bin/bash - -# A script to automate running tests locally. -# It starts the FastAPI server, runs the specified tests, and then shuts down the server. -# -# To run without starting the server, use the --skip-server flag: -# ./run_tests.sh --skip-server - -# --- Configuration --- -# You can define aliases for your test file paths here. -TEST_SUITES=( - "All tests" - "integration_tests/test_sessions_api.py" - "integration_tests/test_documents_api.py" - "integration_tests/test_misc_api.py" -) -TEST_PATHS=( - "integration_tests/" - "integration_tests/test_sessions_api.py" - "integration_tests/test_documents_api.py" - "integration_tests/test_misc_api.py" -) - -export DB_MODE=sqlite -export LOCAL_DB_PATH="data/integration_test_ai_hub.db" -export FAISS_INDEX_PATH="data/integration_test_faiss_index.bin" -export LOG_LEVEL="DEBUG" - -# Check for the --skip-server flag as an inline parameter. -# The user can pass this as the first argument to the script. -SKIP_SERVER=false -if [ "$1" == "--skip-server" ]; then - SKIP_SERVER=true - shift # Remove the --skip-server argument from the list -fi - -# --- User Interaction --- -echo "--- AI Hub Test Runner ---" -echo "Select a test suite to run:" - -# Display the menu options -for i in "${!TEST_SUITES[@]}"; do - echo "$((i+1)). ${TEST_SUITES[$i]}" -done - -# Prompt for user input -read -p "Enter the number of your choice (1-${#TEST_SUITES[@]}): " choice - -# Validate input and set the TEST_PATH -if [[ "$choice" =~ ^[0-9]+$ ]] && [ "$choice" -ge 1 ] && [ "$choice" -le "${#TEST_SUITES[@]}" ]; then - TEST_PATH=${TEST_PATHS[$((choice-1))]} - echo "You have selected: ${TEST_SUITES[$((choice-1))]}" -else - echo "Invalid choice. Running all tests by default." - TEST_PATH=${TEST_PATHS[0]} -fi - -# --- Conditional Server Startup and Cleanup --- -if [ "$SKIP_SERVER" = false ]; then - # --- Pre-test Cleanup --- - # Check for and remove old test files to ensure a clean test environment. - echo "--- Checking for and removing old test files ---" - if [ -f "$LOCAL_DB_PATH" ]; then - echo "Removing old database file: $LOCAL_DB_PATH" - rm "$LOCAL_DB_PATH" - fi - if [ -f "$FAISS_INDEX_PATH" ]; then - echo "Removing old FAISS index file: $FAISS_INDEX_PATH" - rm "$FAISS_INDEX_PATH" - fi - echo "Cleanup complete." - - echo "--- Starting AI Hub Server for Tests ---" - - # Start the uvicorn server in the background - # We bind it to 127.0.0.1 to ensure it's not accessible from outside the local machine. - uvicorn app.main:app --host 127.0.0.1 --port 8001 --reload & - - # Get the Process ID (PID) of the background server - SERVER_PID=$! - - # Define a cleanup function to be called on exit - cleanup() { - echo "" - echo "--- Shutting Down Server (PID: $SERVER_PID) ---" - kill $SERVER_PID - } - - # Register the cleanup function to run when the script exits - # This ensures the server is stopped even if tests fail or the script is interrupted (e.g., with Ctrl+C). - trap cleanup EXIT - - echo "Server started with PID: $SERVER_PID. Waiting for it to initialize..." - - # Wait a few seconds to ensure the server is fully up and running - sleep 5 -else - echo "--- Skipping server startup. Running tests against an existing server. ---" -fi - -echo "--- Running tests in: $TEST_PATH ---" - -# Execute the Python tests using pytest on the specified path -# The '-s' flag shows print statements from the tests. -pytest -s "$TEST_PATH" - -# Capture the exit code of the test script -TEST_EXIT_CODE=$? - -# The 'trap' will automatically call the cleanup function if it was set. -# Exit with the same code as the test script (0 for success, non-zero for failure). -exit $TEST_EXIT_CODE diff --git a/ai-hub/scripts/add_knowledge.sh b/ai-hub/scripts/add_knowledge.sh new file mode 100644 index 0000000..4f01434 --- /dev/null +++ b/ai-hub/scripts/add_knowledge.sh @@ -0,0 +1,91 @@ +#!/bin/bash + +# Resolve script directory and change to ai-hub root +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +cd "$SCRIPT_DIR/.." + +# ============================================================================== +# Script to scan for specific file types and upload their content to an API. +# Prerequisites: +# - The FastAPI application must be running locally on http://localhost:8000. +# - The 'jq' command-line JSON processor must be installed. +# - The 'curl' command-line tool must be installed. +# ============================================================================== + +# Define the API endpoint +API_URL="http://localhost:8000/documents" + +DEFAULT_MODEL="gemini" +CURRENT_MODEL="" # The model used in the last turn + +# --- 1. Check for Dependencies --- +if ! command -v jq &> /dev/null +then + echo "❌ 'jq' is not installed. Please install it to run this script." + exit 1 +fi + +# --- 2. Start the FastAPI Server in the Background --- +echo "--- Starting AI Hub Server ---" +uvicorn app.main:app --host 127.0.0.1 --port 8000 & +SERVER_PID=$! + +# Define a cleanup function to kill the server on exit +cleanup() { + echo "" + echo "--- Shutting Down Server (PID: $SERVER_PID) ---" + kill $SERVER_PID +} +# Register the cleanup function to run when the script exits (e.g., Ctrl+C or typing 'exit') +trap cleanup EXIT + +echo "Server started with PID: $SERVER_PID. Waiting for it to initialize..." +sleep 5 # Wait for the server to be ready + + +# Find all files with the specified extensions in the current directory and its subdirectories +# The -print0 option is used to handle filenames with spaces or special characters. +find . -type f \( -name "*.py" -o -name "*.txt" -o -name "*.md" -o -name "*.yaml" \) -print0 | while IFS= read -r -d $'\0' file_path; do + + # Get the file's basename (e.g., "my_file.md") to use as the title + file_title=$(basename -- "$file_path") + + # Get the file creation date. + # Note: 'stat' options differ between Linux and macOS. + # Linux: stat -c %w + # macOS: stat -f %B + # This script assumes a Linux-like stat output. You may need to adjust this. + file_created_at=$(stat -c %w "$file_path") + + # Read the entire file content into a variable. + # `cat` is used to get the content, and it's escaped for JSON. + file_content=$(cat "$file_path" | sed 's/\\/\\\\/g' | sed 's/"/\\"/g' | sed 's/`/\\`/g') + + # Construct the JSON payload using `jq` for robust formatting + json_payload=$(jq -n \ + --arg title "$file_title" \ + --arg text "$file_content" \ + --arg file_path "$file_path" \ + '{title: $title, text: $text, file_path: $file_path}') + + echo "Uploading file: $file_path" + + # Make the POST request to the API + response=$(curl -X POST \ + -s \ + -H "Content-Type: application/json" \ + -d "$json_payload" \ + "$API_URL") + + # Display the response from the API + if [[ "$response" == *"success"* ]]; then + echo "✅ Uploaded successfully. Response: $response" + else + echo "❌ Failed to upload. Response: $response" + fi + + echo "---" + +done + +echo "Script finished." diff --git a/ai-hub/scripts/run_chat.sh b/ai-hub/scripts/run_chat.sh new file mode 100644 index 0000000..879765c --- /dev/null +++ b/ai-hub/scripts/run_chat.sh @@ -0,0 +1,144 @@ +#!/bin/bash + +# Resolve script directory and change to ai-hub root +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +cd "$SCRIPT_DIR/.." + +# A script to automatically start the server and run an interactive chat session. +# It now tests the PATH_PREFIX functionality. + +# --- Configuration --- +# Set the desired path prefix for testing +TEST_PATH_PREFIX="/api/v1" +BASE_URL="http://127.0.0.1:8000" +DEFAULT_MODEL="deepseek" +CURRENT_MODEL="" # The model used in the last turn + +# --- 1. Check for Dependencies --- +if ! command -v jq &> /dev/null +then + echo "❌ 'jq' is not installed. Please install it to run this script." + exit 1 +fi + +# --- 2. Start the FastAPI Server in the Background with the PATH_PREFIX --- +echo "--- Starting AI Hub Server with PATH_PREFIX=$TEST_PATH_PREFIX ---" +# Export the PATH_PREFIX environment variable so the server can read it +export PATH_PREFIX="$TEST_PATH_PREFIX" +uvicorn app.main:app --host 127.0.0.1 --port 8000 & +SERVER_PID=$! + +# Define a cleanup function to kill the server on exit +cleanup() { + echo "" + echo "--- Shutting Down Server (PID: $SERVER_PID) ---" + kill $SERVER_PID +} +# Register the cleanup function to run when the script exits (e.g., Ctrl+C or typing 'exit') +trap cleanup EXIT + +echo "Server started with PID: $SERVER_PID. Waiting for it to initialize..." +sleep 5 # Wait for the server to be ready + +# --- 3. Create a New Conversation Session --- +echo "--- Starting a new conversation session... ---" +# Use the full URL with the test path prefix +SESSION_URL="$BASE_URL$TEST_PATH_PREFIX/sessions/" +SESSION_DATA=$(curl -s -X POST "$SESSION_URL" \ + -H "Content-Type: application/json" \ + -d '{"user_id": "local_user", "provider_name": "'"$DEFAULT_MODEL"'"}' \ + -w '\n%{http_code}') # Add a new line and the status code + +# Extract body and status code +HTTP_CODE=$(echo "$SESSION_DATA" | tail -n1) +SESSION_DATA_BODY=$(echo "$SESSION_DATA" | head -n-1) + +if [ "$HTTP_CODE" -ne 200 ]; then + echo "❌ Failed to create a session (HTTP $HTTP_CODE). Server might not have started correctly." + echo "Response body: $SESSION_DATA_BODY" + exit 1 +fi + +SESSION_ID=$(echo "$SESSION_DATA_BODY" | jq -r '.id') +if [ -z "$SESSION_ID" ] || [ "$SESSION_ID" == "null" ]; then + echo "❌ Failed to create a session. Server response did not contain an ID." + echo "Response body: $SESSION_DATA_BODY" + exit 1 +fi + +# Set the initial model +CURRENT_MODEL="$DEFAULT_MODEL" + +echo "✅ Session created with ID: $SESSION_ID. The initial model is '$CURRENT_MODEL'." +echo "--------------------------------------------------" +echo "To switch models, type your message like this: [gemini] " +echo "To enable the FAISS retriever, add the flag: [faiss] " +echo "You can combine them: [gemini] [faiss] " +echo "Type 'exit' or 'quit' to end." +echo "--------------------------------------------------" + +# --- 4. Start the Interactive Chat Loop --- +while true; do + read -p "You: " user_input + + if [[ "$user_input" == "exit" || "$user_input" == "quit" ]]; then + break + fi + + # Initialize variables for this turn + PROMPT_TEXT="$user_input" + MODEL_TO_USE="$CURRENT_MODEL" + LOAD_FAISS_RETRIEVER="false" + + # Check for and process the model switch + # This regex ensures we only match valid models and they must appear first + if [[ "$PROMPT_TEXT" =~ ^\[(deepseek|gemini)\]\ (.*)$ ]]; then + MODEL_TO_USE="${BASH_REMATCH[1]}" + PROMPT_TEXT="${BASH_REMATCH[2]}" + # Update the current model for the next prompt + CURRENT_MODEL="$MODEL_TO_USE" + fi + + # Check for and process the FAISS flag + # This check is separate to avoid misinterpreting "faiss" as a model + if [[ "$PROMPT_TEXT" =~ \[faiss\] ]]; then + LOAD_FAISS_RETRIEVER="true" + # Use sed to remove the [faiss] flag and trim any leading/trailing spaces + PROMPT_TEXT=$(echo "$PROMPT_TEXT" | sed 's/\[faiss\]//' | xargs) + fi + + # Check if the prompt is empty after processing flags and models + if [ -z "$PROMPT_TEXT" ]; then + echo "Please enter a message." + continue + fi + + # Construct the JSON payload with the model, prompt, and FAISS flag + # Note the use of --argjson to pass the boolean value correctly + json_payload=$(jq -n \ + --arg prompt "$PROMPT_TEXT" \ + --arg provider_name "$MODEL_TO_USE" \ + --argjson faiss_flag "$LOAD_FAISS_RETRIEVER" \ + '{"prompt": $prompt, "provider_name": $provider_name, "load_faiss_retriever": $faiss_flag}') + + echo "Payload: $json_payload" # Optional: for debugging + + # Use the full URL with the test path prefix + CHAT_URL="$BASE_URL$TEST_PATH_PREFIX/sessions/$SESSION_ID/chat" + ai_response_json=$(curl -s -X POST "$CHAT_URL" \ + -H "Content-Type: application/json" \ + -d "$json_payload") + + # Check if the response is valid JSON + if ! echo "$ai_response_json" | jq -e . >/dev/null; then + echo "❌ AI: An error occurred or the server returned an invalid response." + echo "Server response: $ai_response_json" + else + ai_answer=$(echo "$ai_response_json" | jq -r '.answer') + provider_used=$(echo "$ai_response_json" | jq -r '.provider_used') + echo "AI [$provider_used] [faiss_enabled: $LOAD_FAISS_RETRIEVER]: $ai_answer" + fi + +done + +# The 'trap' will automatically call the cleanup function when the loop breaks. \ No newline at end of file diff --git a/ai-hub/scripts/run_integration_tests.sh b/ai-hub/scripts/run_integration_tests.sh new file mode 100644 index 0000000..1835da6 --- /dev/null +++ b/ai-hub/scripts/run_integration_tests.sh @@ -0,0 +1,116 @@ +#!/bin/bash + +# Resolve script directory and change to ai-hub root +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +cd "$SCRIPT_DIR/.." + +# A script to automate running tests locally. +# It starts the FastAPI server, runs the specified tests, and then shuts down the server. +# +# To run without starting the server, use the --skip-server flag: +# ./run_tests.sh --skip-server + +# --- Configuration --- +# You can define aliases for your test file paths here. +TEST_SUITES=( + "All tests" + "integration_tests/test_sessions_api.py" + "integration_tests/test_documents_api.py" + "integration_tests/test_misc_api.py" +) +TEST_PATHS=( + "integration_tests/" + "integration_tests/test_sessions_api.py" + "integration_tests/test_documents_api.py" + "integration_tests/test_misc_api.py" +) + +export DB_MODE=sqlite +export LOCAL_DB_PATH="data/integration_test_ai_hub.db" +export FAISS_INDEX_PATH="data/integration_test_faiss_index.bin" +export LOG_LEVEL="DEBUG" + +# Check for the --skip-server flag as an inline parameter. +# The user can pass this as the first argument to the script. +SKIP_SERVER=false +if [ "$1" == "--skip-server" ]; then + SKIP_SERVER=true + shift # Remove the --skip-server argument from the list +fi + +# --- User Interaction --- +echo "--- AI Hub Test Runner ---" +echo "Select a test suite to run:" + +# Display the menu options +for i in "${!TEST_SUITES[@]}"; do + echo "$((i+1)). ${TEST_SUITES[$i]}" +done + +# Prompt for user input +read -p "Enter the number of your choice (1-${#TEST_SUITES[@]}): " choice + +# Validate input and set the TEST_PATH +if [[ "$choice" =~ ^[0-9]+$ ]] && [ "$choice" -ge 1 ] && [ "$choice" -le "${#TEST_SUITES[@]}" ]; then + TEST_PATH=${TEST_PATHS[$((choice-1))]} + echo "You have selected: ${TEST_SUITES[$((choice-1))]}" +else + echo "Invalid choice. Running all tests by default." + TEST_PATH=${TEST_PATHS[0]} +fi + +# --- Conditional Server Startup and Cleanup --- +if [ "$SKIP_SERVER" = false ]; then + # --- Pre-test Cleanup --- + # Check for and remove old test files to ensure a clean test environment. + echo "--- Checking for and removing old test files ---" + if [ -f "$LOCAL_DB_PATH" ]; then + echo "Removing old database file: $LOCAL_DB_PATH" + rm "$LOCAL_DB_PATH" + fi + if [ -f "$FAISS_INDEX_PATH" ]; then + echo "Removing old FAISS index file: $FAISS_INDEX_PATH" + rm "$FAISS_INDEX_PATH" + fi + echo "Cleanup complete." + + echo "--- Starting AI Hub Server for Tests ---" + + # Start the uvicorn server in the background + # We bind it to 127.0.0.1 to ensure it's not accessible from outside the local machine. + uvicorn app.main:app --host 127.0.0.1 --port 8001 --reload & + + # Get the Process ID (PID) of the background server + SERVER_PID=$! + + # Define a cleanup function to be called on exit + cleanup() { + echo "" + echo "--- Shutting Down Server (PID: $SERVER_PID) ---" + kill $SERVER_PID + } + + # Register the cleanup function to run when the script exits + # This ensures the server is stopped even if tests fail or the script is interrupted (e.g., with Ctrl+C). + trap cleanup EXIT + + echo "Server started with PID: $SERVER_PID. Waiting for it to initialize..." + + # Wait a few seconds to ensure the server is fully up and running + sleep 5 +else + echo "--- Skipping server startup. Running tests against an existing server. ---" +fi + +echo "--- Running tests in: $TEST_PATH ---" + +# Execute the Python tests using pytest on the specified path +# The '-s' flag shows print statements from the tests. +pytest -s "$TEST_PATH" + +# Capture the exit code of the test script +TEST_EXIT_CODE=$? + +# The 'trap' will automatically call the cleanup function if it was set. +# Exit with the same code as the test script (0 for success, non-zero for failure). +exit $TEST_EXIT_CODE diff --git a/ai-hub/scripts/test_stt.sh b/ai-hub/scripts/test_stt.sh new file mode 100644 index 0000000..69b6113 --- /dev/null +++ b/ai-hub/scripts/test_stt.sh @@ -0,0 +1,84 @@ +#!/bin/bash + +# Resolve script directory and change to ai-hub root +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +cd "$SCRIPT_DIR/.." + +# --- 0. Load environment variables from .env file --- +# This ensures any necessary credentials or configurations are loaded. +if [ -f .env ]; then + echo "Loading environment variables from .env" + export $(grep -v '^#' .env | xargs) +fi +export LOG_LEVEL=DEBUG + +# --- 1. Define variables and configurations --- +BASE_URL="http://127.0.0.1:8000" +STT_ENDPOINT="/stt/transcribe" +API_URL="${BASE_URL}${STT_ENDPOINT}" + +# --- 2. Start the FastAPI Server in the Background --- +echo "--- Starting AI Hub Server ---" +uvicorn app.main:app --host 127.0.0.1 --port 8000 & +SERVER_PID=$! + +# Define a function to shut down the server and clean up. +cleanup() { + echo "" + echo "--- Shutting Down Server (PID: $SERVER_PID) ---" + kill $SERVER_PID +} +trap cleanup EXIT + +# --- 3. Wait for the server to be ready --- +echo "Waiting for server to initialize..." +for i in {1..20}; do + if curl --fail --silent "$BASE_URL" &> /dev/null; then + echo "✅ Server is ready." + break + fi + sleep 1 + if [ "$i" -eq 20 ]; then + echo "❌ Error: Server failed to start in time. Exiting." + exit 1 + fi +done + +# --- 4. Prepare the audio file for testing --- +echo "" +echo "--- Preparing audio file for testing ---" +# Check if a file path was provided as an argument +if [ -z "$1" ]; then + echo "❌ Error: No audio file path provided." + echo "Usage: $0 /path/to/your/audio.wav" + exit 1 +fi + +TEMP_AUDIO_FILE="$1" +if [ ! -f "$TEMP_AUDIO_FILE" ]; then + echo "❌ Error: The specified file '$TEMP_AUDIO_FILE' does not exist." + exit 1 +fi +echo "✅ Using provided audio file: $TEMP_AUDIO_FILE" +echo "" + +# --- 5. Test a successful transcription --- +echo "--- Testing successful transcription with valid audio file ---" +# We now explicitly specify the MIME type for the file using the curl -F flag syntax. +# We also use the -f, --fail flag to ensure curl returns an error code on HTTP 4xx/5xx status. +curl -s -f -X POST "$API_URL" \ + -H "Content-Type: multipart/form-data" \ + -F "audio_file=@$TEMP_AUDIO_FILE;type=audio/wav" | jq '.' + +# Check the exit status of the curl command +# The return code is now more reliable thanks to the `-f` flag. +if [ ${PIPESTATUS[0]} -eq 0 ]; then + echo "" + echo "✅ Success! Received a valid transcription response." +else + echo "" + echo "❌ Failed to get a valid transcription response. Check the server logs for details." +fi +echo "" + +# --- Tests complete. --- diff --git a/ai-hub/scripts/test_tts.sh b/ai-hub/scripts/test_tts.sh new file mode 100644 index 0000000..5a469a5 --- /dev/null +++ b/ai-hub/scripts/test_tts.sh @@ -0,0 +1,74 @@ +#!/bin/bash + +# Resolve script directory and change to ai-hub root +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +cd "$SCRIPT_DIR/.." + +# --- 0. Load environment variables from .env file --- +if [ -f .env ]; then + echo "Loading environment variables from .env" + export $(grep -v '^#' .env | xargs) +fi +export LOG_LEVEL=DEBUG + +API_URL="http://localhost:8000/documents" +DEFAULT_MODEL="gemini" +CURRENT_MODEL="" + +# --- 1. Check for Dependencies --- +if ! command -v jq &> /dev/null; then + echo "❌ 'jq' is not installed. Please install it to run this script." + exit 1 +fi + +# --- 2. Start the FastAPI Server in the Background --- +echo "--- Starting AI Hub Server ---" +uvicorn app.main:app --host 127.0.0.1 --port 8000 & +SERVER_PID=$! + +cleanup() { + echo "" + echo "--- Shutting Down Server (PID: $SERVER_PID) ---" + kill $SERVER_PID +} +trap cleanup EXIT + +echo "Server started with PID: $SERVER_PID. Waiting for it to initialize..." +sleep 5 + +BASE_URL="http://localhost:8000" + +# --- 3. Get TEST_TEXT from CLI argument --- +if [ -z "$1" ]; then + echo "❌ No input text provided." + echo "Usage: $0 \"Your text to send to /speech\"" + exit 1 +fi +TEST_TEXT="$1" + +# Create a temporary file to store the JSON payload +TEMP_JSON_FILE=$(mktemp) +cat > "$TEMP_JSON_FILE" << EOF +{ + "text": "$TEST_TEXT" +} +EOF + +# --- Test streaming mode --- +echo "" +echo "--- Testing streaming mode for /speech endpoint ---" +STREAM_OUTPUT_FILE="data/speech_stream.wav" +curl -s -X POST "$BASE_URL/speech?stream=true" \ + -H "Content-Type: application/json" \ + --data "@$TEMP_JSON_FILE" \ + --output "$STREAM_OUTPUT_FILE" + +if [ -f "$STREAM_OUTPUT_FILE" ]; then + echo "✅ Success! Streaming audio saved to $STREAM_OUTPUT_FILE" +else + echo "❌ Failed to get streaming audio" +fi + +rm "$TEMP_JSON_FILE" +echo "" +echo "--- Tests complete. ---" diff --git a/ai-hub/test_stt.sh b/ai-hub/test_stt.sh deleted file mode 100644 index 6701225..0000000 --- a/ai-hub/test_stt.sh +++ /dev/null @@ -1,80 +0,0 @@ -#!/bin/bash - -# --- 0. Load environment variables from .env file --- -# This ensures any necessary credentials or configurations are loaded. -if [ -f .env ]; then - echo "Loading environment variables from .env" - export $(grep -v '^#' .env | xargs) -fi -export LOG_LEVEL=DEBUG - -# --- 1. Define variables and configurations --- -BASE_URL="http://127.0.0.1:8000" -STT_ENDPOINT="/stt/transcribe" -API_URL="${BASE_URL}${STT_ENDPOINT}" - -# --- 2. Start the FastAPI Server in the Background --- -echo "--- Starting AI Hub Server ---" -uvicorn app.main:app --host 127.0.0.1 --port 8000 & -SERVER_PID=$! - -# Define a function to shut down the server and clean up. -cleanup() { - echo "" - echo "--- Shutting Down Server (PID: $SERVER_PID) ---" - kill $SERVER_PID -} -trap cleanup EXIT - -# --- 3. Wait for the server to be ready --- -echo "Waiting for server to initialize..." -for i in {1..20}; do - if curl --fail --silent "$BASE_URL" &> /dev/null; then - echo "✅ Server is ready." - break - fi - sleep 1 - if [ "$i" -eq 20 ]; then - echo "❌ Error: Server failed to start in time. Exiting." - exit 1 - fi -done - -# --- 4. Prepare the audio file for testing --- -echo "" -echo "--- Preparing audio file for testing ---" -# Check if a file path was provided as an argument -if [ -z "$1" ]; then - echo "❌ Error: No audio file path provided." - echo "Usage: $0 /path/to/your/audio.wav" - exit 1 -fi - -TEMP_AUDIO_FILE="$1" -if [ ! -f "$TEMP_AUDIO_FILE" ]; then - echo "❌ Error: The specified file '$TEMP_AUDIO_FILE' does not exist." - exit 1 -fi -echo "✅ Using provided audio file: $TEMP_AUDIO_FILE" -echo "" - -# --- 5. Test a successful transcription --- -echo "--- Testing successful transcription with valid audio file ---" -# We now explicitly specify the MIME type for the file using the curl -F flag syntax. -# We also use the -f, --fail flag to ensure curl returns an error code on HTTP 4xx/5xx status. -curl -s -f -X POST "$API_URL" \ - -H "Content-Type: multipart/form-data" \ - -F "audio_file=@$TEMP_AUDIO_FILE;type=audio/wav" | jq '.' - -# Check the exit status of the curl command -# The return code is now more reliable thanks to the `-f` flag. -if [ ${PIPESTATUS[0]} -eq 0 ]; then - echo "" - echo "✅ Success! Received a valid transcription response." -else - echo "" - echo "❌ Failed to get a valid transcription response. Check the server logs for details." -fi -echo "" - -# --- Tests complete. --- diff --git a/ai-hub/test_tts.sh b/ai-hub/test_tts.sh deleted file mode 100644 index 14a0831..0000000 --- a/ai-hub/test_tts.sh +++ /dev/null @@ -1,70 +0,0 @@ -#!/bin/bash - -# --- 0. Load environment variables from .env file --- -if [ -f .env ]; then - echo "Loading environment variables from .env" - export $(grep -v '^#' .env | xargs) -fi -export LOG_LEVEL=DEBUG - -API_URL="http://localhost:8000/documents" -DEFAULT_MODEL="gemini" -CURRENT_MODEL="" - -# --- 1. Check for Dependencies --- -if ! command -v jq &> /dev/null; then - echo "❌ 'jq' is not installed. Please install it to run this script." - exit 1 -fi - -# --- 2. Start the FastAPI Server in the Background --- -echo "--- Starting AI Hub Server ---" -uvicorn app.main:app --host 127.0.0.1 --port 8000 & -SERVER_PID=$! - -cleanup() { - echo "" - echo "--- Shutting Down Server (PID: $SERVER_PID) ---" - kill $SERVER_PID -} -trap cleanup EXIT - -echo "Server started with PID: $SERVER_PID. Waiting for it to initialize..." -sleep 5 - -BASE_URL="http://localhost:8000" - -# --- 3. Get TEST_TEXT from CLI argument --- -if [ -z "$1" ]; then - echo "❌ No input text provided." - echo "Usage: $0 \"Your text to send to /speech\"" - exit 1 -fi -TEST_TEXT="$1" - -# Create a temporary file to store the JSON payload -TEMP_JSON_FILE=$(mktemp) -cat > "$TEMP_JSON_FILE" << EOF -{ - "text": "$TEST_TEXT" -} -EOF - -# --- Test streaming mode --- -echo "" -echo "--- Testing streaming mode for /speech endpoint ---" -STREAM_OUTPUT_FILE="data/speech_stream.wav" -curl -s -X POST "$BASE_URL/speech?stream=true" \ - -H "Content-Type: application/json" \ - --data "@$TEMP_JSON_FILE" \ - --output "$STREAM_OUTPUT_FILE" - -if [ -f "$STREAM_OUTPUT_FILE" ]; then - echo "✅ Success! Streaming audio saved to $STREAM_OUTPUT_FILE" -else - echo "❌ Failed to get streaming audio" -fi - -rm "$TEMP_JSON_FILE" -echo "" -echo "--- Tests complete. ---" diff --git a/deploy_local.sh b/deploy_local.sh new file mode 100644 index 0000000..f34c634 --- /dev/null +++ b/deploy_local.sh @@ -0,0 +1,61 @@ +#!/bin/bash + +# --- Deployment Script for AI Hub --- +# This script is designed to automate the deployment of the AI Hub application +# using Docker Compose. It's intended to be run on the production server. +# +# The script performs the following actions: +# 1. Defines project-specific configuration variables. +# 2. **Installs Docker Compose if it's not found on the system.** +# 3. Navigates to the correct project directory. +# 4. Stops and removes any currently running Docker containers for the project. +# 5. Pulls the latest Docker images from a registry (if applicable). +# 6. Builds the new Docker images from the source code. +# 7. Starts the new containers in detached mode, with production settings. +# 8. Performs cleanup of old, unused Docker images. + +# --- Configuration --- +# Set the project directory to the directory where this script is located. +PROJECT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" &> /dev/null && pwd)" + + +# --- Helper Function --- +# Find the correct docker-compose command (modern plugin or standalone v1) +if docker compose version &> /dev/null; then + DOCKER_CMD="docker compose" +else + DOCKER_CMD="docker-compose" +fi + +# --- Script Execution --- +echo "🚀 Starting AI Hub deployment process..." + +# Navigate to the project directory. Exit if the directory doesn't exist. +cd "$PROJECT_DIR" || { echo "Error: Project directory '$PROJECT_DIR' not found. Exiting."; exit 1; } + +# Stop and remove any existing containers to ensure a clean deployment. +echo "🛑 Stopping and removing old Docker containers and networks..." +sudo $DOCKER_CMD down || true + +# Pull the latest images if they are hosted on a registry. +# echo "📥 Pulling latest Docker images..." +# sudo $DOCKER_CMD pull + +# Build new images and start the services. The `--build` flag ensures +# the images are re-built from their respective Dockerfiles. +# The `--remove-orphans` flag ensures old service containers are cleaned up. +echo "🏗️ Building and starting new containers..." +sudo $DOCKER_CMD up -d --build --remove-orphans + +echo "✅ Containers started! Checking status..." +sudo docker ps --filter "name=ai_" + +echo "✅ Deployment complete! The AI Hub application is now running." + +# --- Post-Deployment Cleanup --- +echo "🧹 Cleaning up unused Docker resources..." + +# Remove dangling images (images without a tag). +sudo docker image prune -f || true + +echo "✨ Cleanup finished." \ No newline at end of file diff --git a/deploy_remote.sh b/deploy_remote.sh new file mode 100755 index 0000000..51154d6 --- /dev/null +++ b/deploy_remote.sh @@ -0,0 +1,53 @@ +#!/bin/bash +# Description: Automates deployment from the local environment to the production host 192.168.68.113 + +HOST="${REMOTE_HOST:-192.168.68.113}" +USER="${REMOTE_USER:-axieyangb}" +PASS="${REMOTE_PASS:-MySecurePassword}" +REMOTE_TMP="/tmp/cortex-hub/" +REMOTE_PROJ="/home/coder/project/cortex-hub" + +if [ "$PASS" = "MySecurePassword" ]; then + echo "Error: Please set the REMOTE_PASS environment variable before deploying." + echo "Example: REMOTE_PASS='your_password' ./remote_deploy.sh" + exit 1 +fi + +echo "Checking if sshpass is installed..." +if ! command -v sshpass &> /dev/null; then + echo "sshpass could not be found, installing..." + sudo apt-get update && sudo apt-get install -y sshpass +fi + +# 1. Sync local codebase to temporary directory on remote server +echo "Syncing local files to production..." +sshpass -p "$PASS" rsync -avz \ + --exclude '.git' \ + --exclude 'node_modules' \ + --exclude 'ui/client-app/node_modules' \ + --exclude 'ui/client-app/build' \ + --exclude 'ai-hub/__pycache__' \ + --exclude '.venv' \ + -e "ssh -o StrictHostKeyChecking=no" /app/ "$USER@$HOST:$REMOTE_TMP" + +if [ $? -ne 0 ]; then + echo "Rsync failed! Exiting." + exit 1 +fi + +# 2. Copy the synced files into the actual project directory replacing the old ones +echo "Overwriting production project files..." +sshpass -p "$PASS" ssh -o StrictHostKeyChecking=no "$USER@$HOST" << EOF + echo '$PASS' | sudo -S rm -rf $REMOTE_PROJ/nginx.conf + echo '$PASS' | sudo -S cp -r ${REMOTE_TMP}* $REMOTE_PROJ/ + echo '$PASS' | sudo -S chown -R $USER:$USER $REMOTE_PROJ +EOF + +# 3. Rebuild and restart services remotely +echo "Deploying on production server..." +sshpass -p "$PASS" ssh -o StrictHostKeyChecking=no "$USER@$HOST" << EOF + cd $REMOTE_PROJ + echo '$PASS' | sudo -S bash deploy_local.sh +EOF + +echo "Done! The new code is deployed to $HOST." diff --git a/local_deployment.sh b/local_deployment.sh deleted file mode 100644 index f34c634..0000000 --- a/local_deployment.sh +++ /dev/null @@ -1,61 +0,0 @@ -#!/bin/bash - -# --- Deployment Script for AI Hub --- -# This script is designed to automate the deployment of the AI Hub application -# using Docker Compose. It's intended to be run on the production server. -# -# The script performs the following actions: -# 1. Defines project-specific configuration variables. -# 2. **Installs Docker Compose if it's not found on the system.** -# 3. Navigates to the correct project directory. -# 4. Stops and removes any currently running Docker containers for the project. -# 5. Pulls the latest Docker images from a registry (if applicable). -# 6. Builds the new Docker images from the source code. -# 7. Starts the new containers in detached mode, with production settings. -# 8. Performs cleanup of old, unused Docker images. - -# --- Configuration --- -# Set the project directory to the directory where this script is located. -PROJECT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" &> /dev/null && pwd)" - - -# --- Helper Function --- -# Find the correct docker-compose command (modern plugin or standalone v1) -if docker compose version &> /dev/null; then - DOCKER_CMD="docker compose" -else - DOCKER_CMD="docker-compose" -fi - -# --- Script Execution --- -echo "🚀 Starting AI Hub deployment process..." - -# Navigate to the project directory. Exit if the directory doesn't exist. -cd "$PROJECT_DIR" || { echo "Error: Project directory '$PROJECT_DIR' not found. Exiting."; exit 1; } - -# Stop and remove any existing containers to ensure a clean deployment. -echo "🛑 Stopping and removing old Docker containers and networks..." -sudo $DOCKER_CMD down || true - -# Pull the latest images if they are hosted on a registry. -# echo "📥 Pulling latest Docker images..." -# sudo $DOCKER_CMD pull - -# Build new images and start the services. The `--build` flag ensures -# the images are re-built from their respective Dockerfiles. -# The `--remove-orphans` flag ensures old service containers are cleaned up. -echo "🏗️ Building and starting new containers..." -sudo $DOCKER_CMD up -d --build --remove-orphans - -echo "✅ Containers started! Checking status..." -sudo docker ps --filter "name=ai_" - -echo "✅ Deployment complete! The AI Hub application is now running." - -# --- Post-Deployment Cleanup --- -echo "🧹 Cleaning up unused Docker resources..." - -# Remove dangling images (images without a tag). -sudo docker image prune -f || true - -echo "✨ Cleanup finished." \ No newline at end of file diff --git a/remote_deploy.sh b/remote_deploy.sh deleted file mode 100755 index 78b2a71..0000000 --- a/remote_deploy.sh +++ /dev/null @@ -1,53 +0,0 @@ -#!/bin/bash -# Description: Automates deployment from the local environment to the production host 192.168.68.113 - -HOST="${REMOTE_HOST:-192.168.68.113}" -USER="${REMOTE_USER:-axieyangb}" -PASS="${REMOTE_PASS:-MySecurePassword}" -REMOTE_TMP="/tmp/cortex-hub/" -REMOTE_PROJ="/home/coder/project/cortex-hub" - -if [ "$PASS" = "MySecurePassword" ]; then - echo "Error: Please set the REMOTE_PASS environment variable before deploying." - echo "Example: REMOTE_PASS='your_password' ./remote_deploy.sh" - exit 1 -fi - -echo "Checking if sshpass is installed..." -if ! command -v sshpass &> /dev/null; then - echo "sshpass could not be found, installing..." - sudo apt-get update && sudo apt-get install -y sshpass -fi - -# 1. Sync local codebase to temporary directory on remote server -echo "Syncing local files to production..." -sshpass -p "$PASS" rsync -avz \ - --exclude '.git' \ - --exclude 'node_modules' \ - --exclude 'ui/client-app/node_modules' \ - --exclude 'ui/client-app/build' \ - --exclude 'ai-hub/__pycache__' \ - --exclude '.venv' \ - -e "ssh -o StrictHostKeyChecking=no" /app/ "$USER@$HOST:$REMOTE_TMP" - -if [ $? -ne 0 ]; then - echo "Rsync failed! Exiting." - exit 1 -fi - -# 2. Copy the synced files into the actual project directory replacing the old ones -echo "Overwriting production project files..." -sshpass -p "$PASS" ssh -o StrictHostKeyChecking=no "$USER@$HOST" << EOF - echo '$PASS' | sudo -S rm -rf $REMOTE_PROJ/nginx.conf - echo '$PASS' | sudo -S cp -r ${REMOTE_TMP}* $REMOTE_PROJ/ - echo '$PASS' | sudo -S chown -R $USER:$USER $REMOTE_PROJ -EOF - -# 3. Rebuild and restart services remotely -echo "Deploying on production server..." -sshpass -p "$PASS" ssh -o StrictHostKeyChecking=no "$USER@$HOST" << EOF - cd $REMOTE_PROJ - echo '$PASS' | sudo -S bash local_deployment.sh -EOF - -echo "Done! The new code is deployed to $HOST." diff --git a/run_web.sh b/run_web.sh new file mode 100644 index 0000000..d12c5f8 --- /dev/null +++ b/run_web.sh @@ -0,0 +1,88 @@ +#!/bin/bash + +# Enable strict mode +set -euo pipefail + +# Default to HTTP +USE_HTTPS=false + + + +# Parse arguments +for arg in "$@"; do + if [[ "$arg" == "--https" ]]; then + USE_HTTPS=true + fi +done + +# Resolve script directory +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +AI_HUB_DIR="$(realpath "$SCRIPT_DIR/ai-hub")" +CLIENT_DIR="$(realpath "$SCRIPT_DIR/ui/client-app")" + +AI_HUB_HOST="0.0.0.0" +AI_HUB_PORT="8001" +APP_MODULE="app.main:app" + +echo "--- Cleaning up existing processes ---" +# Kill existing uvicorn processes on the expected port +EXISTING_UVICORN_PID=$(lsof -ti tcp:${AI_HUB_PORT} || true) +if [ -n "$EXISTING_UVICORN_PID" ]; then + echo "Killing existing process on port ${AI_HUB_PORT} (PID: $EXISTING_UVICORN_PID)" + kill -9 "$EXISTING_UVICORN_PID" +fi + +# Kill existing React frontend on port 8000 +EXISTING_REACT_PID=$(lsof -ti tcp:8000 || true) +if [ -n "$EXISTING_REACT_PID" ]; then + echo "Killing existing frontend process on port 8000 (PID: $EXISTING_REACT_PID)" + kill -9 "$EXISTING_REACT_PID" +fi +pushd "$AI_HUB_DIR" > /dev/null + +pip install -e . + +SSL_ARGS="" +FRONTEND_ENV="" + +if [ "$USE_HTTPS" = true ]; then + echo "--- Generating self-signed SSL certificates ---" + + # Create a temporary directory for certs + SSL_TEMP_DIR=$(mktemp -d) + SSL_KEYFILE="${SSL_TEMP_DIR}/key.pem" + SSL_CERTFILE="${SSL_TEMP_DIR}/cert.pem" + + # Generate self-signed certificate + openssl req -x509 -nodes -days 1 -newkey rsa:2048 \ + -keyout "$SSL_KEYFILE" \ + -out "$SSL_CERTFILE" \ + -subj "/CN=localhost" + + # Cleanup function to remove certs on exit + cleanup() { + echo "--- Cleaning up SSL certificates ---" + rm -rf "$SSL_TEMP_DIR" + } + trap cleanup EXIT + + SSL_ARGS="--ssl-keyfile $SSL_KEYFILE --ssl-certfile $SSL_CERTFILE" + FRONTEND_ENV="HTTPS=true" +fi + +# New step: Install frontend dependencies +echo "--- Installing frontend dependencies ---" +pushd "$CLIENT_DIR" > /dev/null +npm install +popd > /dev/null + +echo "--- Starting AI Hub Server, React frontend, and backend proxy ---" + +# Run backend and frontend concurrently +npx concurrently \ + --prefix "[{name}]" \ + --names "aihub,tts-frontend" \ + "LOG_LEVEL=DEBUG uvicorn $APP_MODULE --host $AI_HUB_HOST --log-level debug --port $AI_HUB_PORT $SSL_ARGS --reload" \ + "cd $CLIENT_DIR && $FRONTEND_ENV GENERATE_SOURCEMAP=false HOST=0.0.0.0 PORT=8000 npm start" + +popd > /dev/null diff --git a/ui/run_web.sh b/ui/run_web.sh deleted file mode 100644 index 71944a4..0000000 --- a/ui/run_web.sh +++ /dev/null @@ -1,88 +0,0 @@ -#!/bin/bash - -# Enable strict mode -set -euo pipefail - -# Default to HTTP -USE_HTTPS=false - - - -# Parse arguments -for arg in "$@"; do - if [[ "$arg" == "--https" ]]; then - USE_HTTPS=true - fi -done - -# Resolve script directory -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -AI_HUB_DIR="$(realpath "$SCRIPT_DIR/../ai-hub")" -CLIENT_DIR="$SCRIPT_DIR/client-app" - -AI_HUB_HOST="0.0.0.0" -AI_HUB_PORT="8001" -APP_MODULE="app.main:app" - -echo "--- Cleaning up existing processes ---" -# Kill existing uvicorn processes on the expected port -EXISTING_UVICORN_PID=$(lsof -ti tcp:${AI_HUB_PORT} || true) -if [ -n "$EXISTING_UVICORN_PID" ]; then - echo "Killing existing process on port ${AI_HUB_PORT} (PID: $EXISTING_UVICORN_PID)" - kill -9 "$EXISTING_UVICORN_PID" -fi - -# Kill existing React frontend on port 8000 -EXISTING_REACT_PID=$(lsof -ti tcp:8000 || true) -if [ -n "$EXISTING_REACT_PID" ]; then - echo "Killing existing frontend process on port 8000 (PID: $EXISTING_REACT_PID)" - kill -9 "$EXISTING_REACT_PID" -fi -pushd "$AI_HUB_DIR" > /dev/null - -pip install -e . - -SSL_ARGS="" -FRONTEND_ENV="" - -if [ "$USE_HTTPS" = true ]; then - echo "--- Generating self-signed SSL certificates ---" - - # Create a temporary directory for certs - SSL_TEMP_DIR=$(mktemp -d) - SSL_KEYFILE="${SSL_TEMP_DIR}/key.pem" - SSL_CERTFILE="${SSL_TEMP_DIR}/cert.pem" - - # Generate self-signed certificate - openssl req -x509 -nodes -days 1 -newkey rsa:2048 \ - -keyout "$SSL_KEYFILE" \ - -out "$SSL_CERTFILE" \ - -subj "/CN=localhost" - - # Cleanup function to remove certs on exit - cleanup() { - echo "--- Cleaning up SSL certificates ---" - rm -rf "$SSL_TEMP_DIR" - } - trap cleanup EXIT - - SSL_ARGS="--ssl-keyfile $SSL_KEYFILE --ssl-certfile $SSL_CERTFILE" - FRONTEND_ENV="HTTPS=true" -fi - -# New step: Install frontend dependencies -echo "--- Installing frontend dependencies ---" -pushd "$CLIENT_DIR" > /dev/null -npm install -popd > /dev/null - -echo "--- Starting AI Hub Server, React frontend, and backend proxy ---" - -# Run backend and frontend concurrently -npx concurrently \ - --prefix "[{name}]" \ - --names "aihub,tts-frontend" \ - "LOG_LEVEL=DEBUG uvicorn $APP_MODULE --host $AI_HUB_HOST --log-level debug --port $AI_HUB_PORT $SSL_ARGS --reload" \ - "cd $CLIENT_DIR && $FRONTEND_ENV GENERATE_SOURCEMAP=false HOST=0.0.0.0 PORT=8000 npm start" - -popd > /dev/null