add_llm_to_agent.sh
1 #!/bin/bash 2 3 # Script to add LLM integration to an ECHO agent 4 # Usage: ./add_llm_to_agent.sh <agent_name> <agent_role> 5 # Example: ./add_llm_to_agent.sh chro chro 6 7 set -e 8 9 if [ "$#" -ne 2 ]; then 10 echo "Usage: $0 <agent_name> <agent_role>" 11 echo "Example: $0 chro chro" 12 exit 1 13 fi 14 15 AGENT_NAME=$1 16 AGENT_ROLE=$2 17 AGENT_DIR="../agents/${AGENT_NAME}" 18 AGENT_FILE="${AGENT_DIR}/lib/${AGENT_NAME}.ex" 19 20 if [ ! -f "$AGENT_FILE" ]; then 21 echo "Error: Agent file not found: $AGENT_FILE" 22 exit 1 23 fi 24 25 echo "Adding LLM integration to ${AGENT_NAME} agent..." 26 27 # Create backup 28 cp "$AGENT_FILE" "${AGENT_FILE}.backup" 29 30 # The integration will be done manually via Elixir since shell scripting for complex edits is error-prone 31 # Instead, we'll create an Elixir script to do the modifications 32 33 cat > /tmp/add_llm_integration.exs << 'EOF' 34 [agent_file, agent_role] = System.argv() 35 36 content = File.read!(agent_file) 37 38 # Step 1: Add DecisionHelper alias after Repo alias 39 if String.contains?(content, "alias EchoShared.LLM.DecisionHelper") do 40 IO.puts("✓ DecisionHelper alias already present") 41 else 42 content = String.replace( 43 content, 44 ~r/(alias EchoShared\.Repo)/, 45 "\\1\n alias EchoShared.LLM.DecisionHelper" 46 ) 47 IO.puts("✓ Added DecisionHelper alias") 48 end 49 50 # Step 2: Add ai_consult tool before closing the tools list 51 if String.contains?(content, ~s("ai_consult")) do 52 IO.puts("✓ ai_consult tool already present") 53 else 54 # Find the last tool in the array and add ai_consult after it 55 ai_consult_tool = """ 56 }, 57 %{ 58 name: "ai_consult", 59 description: "Consult AI advisor for insights and analysis", 60 inputSchema: %{ 61 type: "object", 62 properties: %{ 63 query_type: %{ 64 type: "string", 65 enum: ["decision_analysis", "question", "option_evaluation"], 66 description: "Type of AI consultation" 67 }, 68 question: %{ 69 type: "string", 70 description: "The question or decision to analyze" 71 }, 72 context: %{ 73 type: "object", 74 description: "Additional context" 75 } 76 }, 77 required: ["query_type", "question"] 78 } 79 } 80 ] 81 end 82 """ 83 84 content = String.replace( 85 content, 86 ~r/\}\n \]\n end\n\n @impl true\n def execute_tool/, 87 ai_consult_tool <> "\n\n @impl true\n def execute_tool" 88 ) 89 IO.puts("✓ Added ai_consult tool") 90 end 91 92 # Step 3: Add execute_tool for ai_consult 93 if String.contains?(content, ~s(def execute_tool("ai_consult")) do 94 IO.puts("✓ ai_consult execute_tool already present") 95 else 96 ai_consult_impl = """ 97 98 def execute_tool("ai_consult", args) do 99 with {:ok, query_type} <- validate_required_string(args, "query_type"), 100 {:ok, question} <- validate_required_string(args, "question") do 101 102 context = args["context"] || %{} 103 104 result = case query_type do 105 "decision_analysis" -> 106 decision_context = Map.merge(context, %{ 107 decision_type: context["decision_type"] || "general", 108 context: question 109 }) 110 DecisionHelper.analyze_decision(:#{agent_role}, decision_context) 111 112 "option_evaluation" -> 113 evaluation_context = %{ 114 question: question, 115 options: context["options"] || [], 116 criteria: context["criteria"] 117 } 118 DecisionHelper.evaluate_options(:#{agent_role}, evaluation_context) 119 120 "question" -> 121 DecisionHelper.consult(:#{agent_role}, question, context["additional_context"]) 122 123 _ -> 124 {:error, "Unknown query type: #{query_type}"} 125 end 126 127 case result do 128 {:ok, response} -> 129 {:ok, "AI Consultation Result:\\n\\n" <> response <> "\\n\\n---\\nNote: AI-generated advice."} 130 {:error, :llm_disabled} -> 131 {:ok, "AI consultation is currently disabled. Enable with #{String.upcase(agent_role)}_LLM_ENABLED=true"} 132 {:error, reason} -> 133 {:error, "AI consultation failed: #{inspect(reason)}"} 134 end 135 end 136 end 137 """ 138 139 content = String.replace( 140 content, 141 ~r/\n def execute_tool\(name, _args\) do\n \{:error, "Unknown tool: #\{name\}"\}\n end/, 142 ai_consult_impl <> "\n\n def execute_tool(name, _args) do\n {:error, \"Unknown tool: \#{name}\"}\n end" 143 ) 144 IO.puts("✓ Added ai_consult execute_tool implementation") 145 end 146 147 # Step 4: Add LLM helper functions before final end 148 if String.contains?(content, "## LLM Consultation Helpers") do 149 IO.puts("✓ LLM helper functions already present") 150 else 151 llm_helpers = """ 152 153 ## LLM Consultation Helpers 154 155 defp consult_llm_for_decision(decision_context) do 156 DecisionHelper.analyze_decision(:#{agent_role}, decision_context) 157 end 158 159 defp consult_llm_for_evaluation(evaluation_context) do 160 DecisionHelper.evaluate_options(:#{agent_role}, evaluation_context) 161 end 162 163 defp consult_llm_simple(question, context) do 164 DecisionHelper.consult(:#{agent_role}, question, context) 165 end 166 """ 167 168 content = String.replace( 169 content, 170 ~r/end\n$/, 171 llm_helpers <> "end\n" 172 ) 173 IO.puts("✓ Added LLM helper functions") 174 end 175 176 File.write!(agent_file, content) 177 IO.puts("✅ Successfully integrated LLM into #{agent_role} agent!") 178 EOF 179 180 # Run the Elixir script 181 elixir /tmp/add_llm_integration.exs "$AGENT_FILE" "$AGENT_ROLE" 182 183 echo "Done! Backup created at ${AGENT_FILE}.backup"