diff --git a/services/orchestrator/a2a_protocol.py b/services/orchestrator/a2a_protocol.py index 5cef1a4..bff2a8f 100644 --- a/services/orchestrator/a2a_protocol.py +++ b/services/orchestrator/a2a_protocol.py @@ -442,20 +442,18 @@ async def discover_agents( "WHERE " + " AND ".join(where_conditions) if where_conditions else "" ) - results = await conn.fetch( - f""" - SELECT card_data FROM a2a_agent_cards + _query = f""" + SELECT card_data FROM a2a_agent_cards {where_clause} - ORDER BY - CASE availability_status - WHEN 'available' THEN 1 - WHEN 'busy' THEN 2 - ELSE 3 + ORDER BY + CASE availability_status + WHEN 'available' THEN 1 + WHEN 'busy' THEN 2 + ELSE 3 END, current_task_count ASC - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + results = await conn.fetch(_query, *params) return [AgentCard(**result["card_data"]) for result in results] @@ -740,16 +738,13 @@ async def get_agent_tasks( where_clause = " AND ".join(where_conditions) - results = await conn.fetch( - f""" - SELECT task_data FROM a2a_tasks + _query = f""" + SELECT task_data FROM a2a_tasks WHERE {where_clause} ORDER BY created_at DESC LIMIT ${param_count} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - limit, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + results = await conn.fetch(_query, *params, limit) return [A2ATask(**result["task_data"]) for result in results] @@ -770,15 +765,12 @@ async def get_agent_messages( where_clause = " AND ".join(where_conditions) - results = await conn.fetch( - f""" - SELECT message_data FROM a2a_messages + _query = f""" + SELECT message_data FROM a2a_messages WHERE {where_clause} ORDER BY created_at DESC LIMIT ${param_count} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - limit, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + results = await conn.fetch(_query, *params, limit) return [A2AMessage(**result["message_data"]) for result in results] diff --git a/services/orchestrator/claude_code_wrapper.py b/services/orchestrator/claude_code_wrapper.py index c9525e8..f09abaf 100644 --- a/services/orchestrator/claude_code_wrapper.py +++ b/services/orchestrator/claude_code_wrapper.py @@ -1,7 +1,7 @@ import asyncio import json import os -import subprocess +import subprocess # nosec B404 -- subprocess used only for running known test runners import tempfile import time from pathlib import Path @@ -440,7 +440,7 @@ def _run_tests(self, tmpdir: str, language: str) -> Optional[Dict[str, Any]]: try: if language == "python": # Try to run pytest - result = subprocess.run( + result = subprocess.run( # nosec B603 B607 -- fixed command list, no shell, no user input ["python", "-m", "pytest", tmpdir, "-v"], capture_output=True, text=True, @@ -458,7 +458,7 @@ def _run_tests(self, tmpdir: str, language: str) -> Optional[Dict[str, Any]]: # Try to run with node test_files = [f for f in os.listdir(tmpdir) if f.startswith("test_")] if test_files: - result = subprocess.run( + result = subprocess.run( # nosec B603 B607 -- fixed command list, no shell, no user input ["node", test_files[0]], capture_output=True, text=True, diff --git a/services/orchestrator/claude_sdk_manager.py b/services/orchestrator/claude_sdk_manager.py index 2663963..3e8a6b2 100644 --- a/services/orchestrator/claude_sdk_manager.py +++ b/services/orchestrator/claude_sdk_manager.py @@ -10,7 +10,7 @@ import logging import os import re -import subprocess +import subprocess # nosec B404 -- subprocess used only for running Claude SDK processes import time from dataclasses import dataclass from datetime import datetime diff --git a/services/orchestrator/container_manager.py b/services/orchestrator/container_manager.py index 4c20b92..6dd09b7 100644 --- a/services/orchestrator/container_manager.py +++ b/services/orchestrator/container_manager.py @@ -534,7 +534,7 @@ async def _get_container_status(self, container) -> ContainerStatus: started = datetime.fromisoformat( state["StartedAt"].replace("Z", "+00:00") ) - except: + except: # nosec B110 -- intentional bare except for datetime parsing of Docker timestamps pass if state.get("FinishedAt"): @@ -542,7 +542,7 @@ async def _get_container_status(self, container) -> ContainerStatus: finished = datetime.fromisoformat( state["FinishedAt"].replace("Z", "+00:00") ) - except: + except: # nosec B110 -- intentional bare except for datetime parsing of Docker timestamps pass # Get resource usage (if available) @@ -586,7 +586,7 @@ async def _get_container_status(self, container) -> ContainerStatus: if host_bindings: for binding in host_bindings: ports[container_port] = ( - f"{binding.get('HostIp', '0.0.0.0')}:{binding.get('HostPort')}" + f"{binding.get('HostIp', '0.0.0.0')}:{binding.get('HostPort')}" # nosec B104 -- container port mapping from Docker API, not user input ) # Get health status diff --git a/services/orchestrator/conversation_manager.py b/services/orchestrator/conversation_manager.py index 507aa26..de696ad 100644 --- a/services/orchestrator/conversation_manager.py +++ b/services/orchestrator/conversation_manager.py @@ -366,15 +366,13 @@ async def get_conversation_history( params.append(limit) async with get_db_connection() as conn: - rows = await conn.fetch( - f""" + _query = f""" SELECT * FROM claude_conversations WHERE {where_clause} ORDER BY created_at ASC {limit_clause} - """, # nosec B608 -- where/limit clauses are fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where/limit clauses are fixed fragments with $N placeholders; all values bound as query params + rows = await conn.fetch(_query, *params) return [dict(row) for row in rows] @@ -469,14 +467,12 @@ async def get_code_generations( where_clause = " AND ".join(conditions) async with get_db_connection() as conn: - rows = await conn.fetch( - f""" + _query = f""" SELECT * FROM code_generations WHERE {where_clause} ORDER BY generated_at ASC - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + rows = await conn.fetch(_query, *params) return [dict(row) for row in rows] @@ -518,14 +514,12 @@ async def get_agent_performance_metrics( where_clause = "WHERE " + " AND ".join(conditions) if conditions else "" async with get_db_connection() as conn: - rows = await conn.fetch( - f""" + _query = f""" SELECT * FROM agent_performance_metrics {where_clause} ORDER BY measured_at DESC - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values (incl. interval multiplier) bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values (incl. interval multiplier) bound as query params + rows = await conn.fetch(_query, *params) return [dict(row) for row in rows] diff --git a/services/orchestrator/git_workflow_manager.py b/services/orchestrator/git_workflow_manager.py index dac499f..e720c95 100644 --- a/services/orchestrator/git_workflow_manager.py +++ b/services/orchestrator/git_workflow_manager.py @@ -14,7 +14,7 @@ import json import logging import os -import subprocess +import subprocess # nosec B404 -- subprocess used only for git commands with fixed args import tempfile from dataclasses import dataclass from datetime import datetime diff --git a/services/orchestrator/goal_conversation_service.py b/services/orchestrator/goal_conversation_service.py index 15fc167..3280b66 100644 --- a/services/orchestrator/goal_conversation_service.py +++ b/services/orchestrator/goal_conversation_service.py @@ -623,8 +623,7 @@ async def get_goal_conversations( where_clause = " AND ".join(where_conditions) - conversations = await conn.fetch( - """ + _query = f""" SELECT id, conversation_type, conversation_title, conversation_summary, status, last_activity_at, created_at, COALESCE(array_length(string_to_array(messages::text, '}}'), 1), 0) as message_count, @@ -633,12 +632,8 @@ async def get_goal_conversations( WHERE {where_clause} ORDER BY last_activity_at DESC, created_at DESC LIMIT ${param_idx} - """.format( # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - where_clause=where_clause, param_idx=param_idx - ), - *params, - limit, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + conversations = await conn.fetch(_query, *params, limit) return [dict(conv) for conv in conversations] diff --git a/services/orchestrator/goals_management_service.py b/services/orchestrator/goals_management_service.py index e8e0b17..60d0384 100644 --- a/services/orchestrator/goals_management_service.py +++ b/services/orchestrator/goals_management_service.py @@ -371,16 +371,13 @@ async def list_organization_goals( where_clause = " AND ".join(where_conditions) - rows = await conn.fetch( - f""" - SELECT * FROM organization_goals + _query = f""" + SELECT * FROM organization_goals WHERE {where_clause} ORDER BY priority_level DESC, created_at DESC LIMIT ${param_idx} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - limit, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + rows = await conn.fetch(_query, *params, limit) return [self._row_to_goal(row) for row in rows] @@ -423,14 +420,12 @@ async def update_goal_progress( if update_fields: update_fields.append("updated_at = NOW()") - await conn.execute( - f""" + _query = f""" UPDATE organization_goals SET {', '.join(update_fields)} WHERE id = $1 - """, # nosec B608 -- SET built only from fixed column fragments; all values bound as $N params - *params, - ) + """ # nosec B608 -- SET built only from fixed column fragments; all values bound as $N params + await conn.execute(_query, *params) # Record progress tracking entry await conn.execute( diff --git a/services/orchestrator/knowledge_analytics_service.py b/services/orchestrator/knowledge_analytics_service.py index 09f74ae..e8ee3da 100644 --- a/services/orchestrator/knowledge_analytics_service.py +++ b/services/orchestrator/knowledge_analytics_service.py @@ -232,9 +232,8 @@ async def analyze_knowledge_effectiveness( where_clause = " AND ".join(where_conditions) - knowledge_items = await conn.fetch( - f""" - SELECT + _query = f""" + SELECT kb.id, kb.title, kb.knowledge_category, @@ -243,25 +242,22 @@ async def analyze_knowledge_effectiveness( kb.quality_score, kb.created_at, kb.updated_at, - -- Calculate agent adoption rate COALESCE(agent_usage.adoption_rate, 0.0) as agent_adoption_rate, - -- Calculate team adoption rate COALESCE(team_usage.adoption_rate, 0.0) as team_adoption_rate, - -- Calculate average relevance from recent usage COALESCE(recent_relevance.avg_relevance, 0.0) as average_relevance FROM organization_knowledge_base kb LEFT JOIN ( - SELECT + SELECT knowledge_id, COUNT(DISTINCT agent_id)::float / NULLIF(total_agents.count, 0) as adoption_rate FROM agent_memory am - JOIN (SELECT COUNT(*) as count FROM agents WHERE team_id IN + JOIN (SELECT COUNT(*) as count FROM agents WHERE team_id IN (SELECT id FROM teams WHERE organization_id = $1)) total_agents ON true WHERE knowledge_id IS NOT NULL GROUP BY knowledge_id ) agent_usage ON kb.id::text = agent_usage.knowledge_id LEFT JOIN ( - SELECT + SELECT source_knowledge_id, COUNT(DISTINCT team_id)::float / NULLIF(total_teams.count, 0) as adoption_rate FROM team_knowledge_base tkb @@ -270,7 +266,7 @@ async def analyze_knowledge_effectiveness( GROUP BY source_knowledge_id ) team_usage ON kb.id::text = team_usage.source_knowledge_id LEFT JOIN ( - SELECT + SELECT knowledge_id, AVG(relevance_score) as avg_relevance FROM agent_memory am @@ -280,9 +276,8 @@ async def analyze_knowledge_effectiveness( ) recent_relevance ON kb.id::text = recent_relevance.knowledge_id WHERE {where_clause} ORDER BY kb.usage_count DESC, kb.success_correlation DESC - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + knowledge_items = await conn.fetch(_query, *params) effectiveness_metrics = [] diff --git a/services/orchestrator/knowledge_notification_service.py b/services/orchestrator/knowledge_notification_service.py index 66d1251..018c9ad 100644 --- a/services/orchestrator/knowledge_notification_service.py +++ b/services/orchestrator/knowledge_notification_service.py @@ -435,12 +435,11 @@ async def get_notifications_for_recipient( where_clause = "WHERE " + " AND ".join(where_conditions) - notifications = await conn.fetch( - f""" + _query = f""" SELECT * FROM knowledge_notifications {where_clause} - ORDER BY - CASE priority + ORDER BY + CASE priority WHEN 'urgent' THEN 4 WHEN 'high' THEN 3 WHEN 'medium' THEN 2 @@ -448,10 +447,8 @@ async def get_notifications_for_recipient( END DESC, created_at DESC LIMIT ${param_idx} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - limit, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + notifications = await conn.fetch(_query, *params, limit) return [self._row_to_notification(row) for row in notifications] @@ -485,14 +482,12 @@ async def mark_notification_status( params.append(json.dumps(action_taken)) param_idx += 1 - result = await conn.execute( - f""" + _query = f""" UPDATE knowledge_notifications SET {', '.join(update_fields)} WHERE id = $1 - """, # nosec B608 -- SET built only from fixed column fragments; all values bound as $N params - *params, - ) + """ # nosec B608 -- SET built only from fixed column fragments; all values bound as $N params + result = await conn.execute(_query, *params) return result == "UPDATE 1" @@ -534,9 +529,8 @@ async def get_notification_statistics( where_clause = "WHERE " + " AND ".join(where_conditions) - basic_stats = await conn.fetchrow( - f""" - SELECT + _basic_query = f""" + SELECT COUNT(*) as total_notifications, COUNT(CASE WHEN status = 'unread' THEN 1 END) as unread, COUNT(CASE WHEN status = 'read' THEN 1 END) as read, @@ -546,14 +540,12 @@ async def get_notification_statistics( COUNT(CASE WHEN requires_action = true THEN 1 END) as requiring_action FROM knowledge_notifications {where_clause} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + basic_stats = await conn.fetchrow(_basic_query, *params) # Notification type breakdown - type_stats = await conn.fetch( - f""" - SELECT + _type_query = f""" + SELECT notification_type, COUNT(*) as count, COUNT(CASE WHEN status = 'acted_upon' THEN 1 END) as acted_upon_count, @@ -562,30 +554,27 @@ async def get_notification_statistics( {where_clause} GROUP BY notification_type ORDER BY count DESC - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + type_stats = await conn.fetch(_type_query, *params) # Priority distribution - priority_stats = await conn.fetch( - f""" - SELECT + _priority_query = f""" + SELECT priority, COUNT(*) as count, AVG(CASE WHEN read_at IS NOT NULL THEN EXTRACT(EPOCH FROM read_at - created_at) END) / 3600 as avg_time_to_read_hours FROM knowledge_notifications {where_clause} GROUP BY priority - ORDER BY - CASE priority + ORDER BY + CASE priority WHEN 'urgent' THEN 4 WHEN 'high' THEN 3 WHEN 'medium' THEN 2 ELSE 1 END DESC - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + priority_stats = await conn.fetch(_priority_query, *params) return { "time_period_days": days_back, diff --git a/services/orchestrator/knowledge_propagation_engine.py b/services/orchestrator/knowledge_propagation_engine.py index 056b6f5..415ae02 100644 --- a/services/orchestrator/knowledge_propagation_engine.py +++ b/services/orchestrator/knowledge_propagation_engine.py @@ -495,9 +495,8 @@ async def get_propagation_statistics( where_clause = "WHERE " + " AND ".join(where_conditions) # Basic statistics - stats = await conn.fetchrow( - f""" - SELECT + _stats_query = f""" + SELECT COUNT(*) as total_propagations, COUNT(CASE WHEN propagation_status = 'completed' THEN 1 END) as completed, COUNT(CASE WHEN propagation_status = 'failed' THEN 1 END) as failed, @@ -507,14 +506,12 @@ async def get_propagation_statistics( AVG(confidence_score) as avg_confidence FROM knowledge_propagation_log {where_clause} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + stats = await conn.fetchrow(_stats_query, *params) # Propagation flow statistics - flow_stats = await conn.fetch( - f""" - SELECT + _flow_query = f""" + SELECT source_type || ' → ' || target_type as flow_type, COUNT(*) as count, AVG(confidence_score) as avg_confidence, @@ -523,14 +520,12 @@ async def get_propagation_statistics( {where_clause} GROUP BY source_type, target_type ORDER BY count DESC - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + flow_stats = await conn.fetch(_flow_query, *params) # Trigger analysis - trigger_stats = await conn.fetch( - f""" - SELECT + _trigger_query = f""" + SELECT propagation_trigger, COUNT(*) as count, AVG(confidence_score) as avg_confidence @@ -538,9 +533,8 @@ async def get_propagation_statistics( {where_clause} GROUP BY propagation_trigger ORDER BY count DESC - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + trigger_stats = await conn.fetch(_trigger_query, *params) return { "time_period_days": days_back, diff --git a/services/orchestrator/main.py b/services/orchestrator/main.py index 0ea6bef..a14b7f4 100644 --- a/services/orchestrator/main.py +++ b/services/orchestrator/main.py @@ -5343,12 +5343,12 @@ async def stream_agent_container_logs(websocket: WebSocket, agent_id: str): logger.error(f"Error in log stream for agent {agent_id}: {e}") try: await websocket.send_json({"error": str(e)}) - except: + except: # nosec B110 -- best-effort error send; WebSocket may already be closed pass finally: try: await websocket.close() - except: + except: # nosec B110 -- best-effort close; WebSocket may already be closed pass @@ -5695,7 +5695,7 @@ async def websocket_agent_conversation( for conn in active_conversations.get(conversation_id, []): try: await conn.send_json(message_data) - except: + except: # nosec B110 -- best-effort broadcast; individual connections may be closed pass # Connection might be closed # TODO: Here we would trigger agent response generation @@ -5717,7 +5717,7 @@ async def websocket_agent_conversation( for conn in active_conversations.get(conversation_id, []): try: await conn.send_json(agent_response) - except: + except: # nosec B110 -- best-effort broadcast; individual connections may be closed pass # Store agent response in database diff --git a/services/orchestrator/main_with_hierarchy.py b/services/orchestrator/main_with_hierarchy.py index 7abaf64..c8f52b1 100644 --- a/services/orchestrator/main_with_hierarchy.py +++ b/services/orchestrator/main_with_hierarchy.py @@ -1409,4 +1409,4 @@ async def demo_endpoint(): if __name__ == "__main__": import uvicorn - uvicorn.run(app, host="0.0.0.0", port=8000) + uvicorn.run(app, host="0.0.0.0", port=8000) # nosec B104 -- intentional bind-all for containerized deployment diff --git a/services/orchestrator/model_configuration.py b/services/orchestrator/model_configuration.py index 7d7f2ee..077ee01 100644 --- a/services/orchestrator/model_configuration.py +++ b/services/orchestrator/model_configuration.py @@ -125,7 +125,7 @@ def __init__(self): def _get_or_create_encryption_key(self) -> bytes: """Get or create encryption key for API credentials""" - key_file = "/tmp/fuzeagent_encryption.key" + key_file = "/tmp/fuzeagent_encryption.key" # nosec B108 -- tmp path for ephemeral container key storage if os.path.exists(key_file): with open(key_file, "rb") as f: diff --git a/services/orchestrator/organization_rag_manager.py b/services/orchestrator/organization_rag_manager.py index cc4698e..01ff428 100644 --- a/services/orchestrator/organization_rag_manager.py +++ b/services/orchestrator/organization_rag_manager.py @@ -270,16 +270,12 @@ async def search_knowledge( where_clause = "WHERE " + " AND ".join(where_conditions) # Execute search - knowledge_results = await conn.fetch( - f""" + _search_query = f""" SELECT * FROM search_organization_knowledge( $2, $1, null, ${param_idx}, ${param_idx} ) - """, # nosec B608 -- only $N placeholder indices are interpolated; all values bound as query params - *params, - limit, - min_similarity, - ) + """ # nosec B608 -- only $N placeholder indices are interpolated; all values bound as query params + knowledge_results = await conn.fetch(_search_query, *params, limit, min_similarity) # Convert to result objects results = [] @@ -405,14 +401,12 @@ async def update_knowledge_quality( params.append(knowledge_id) async with self.pool.acquire() as conn: - result = await conn.execute( - f""" + _query = f""" UPDATE organization_knowledge_base SET {', '.join(updates)} WHERE id = ${param_idx} - """, # nosec B608 -- SET built only from fixed column fragments; all values bound as $N params - *params, - ) + """ # nosec B608 -- SET built only from fixed column fragments; all values bound as $N params + result = await conn.execute(_query, *params) return result == "UPDATE 1" diff --git a/services/orchestrator/rag_manager.py b/services/orchestrator/rag_manager.py index 2f5a160..1299d97 100644 --- a/services/orchestrator/rag_manager.py +++ b/services/orchestrator/rag_manager.py @@ -361,21 +361,17 @@ async def search_conversation_history( else: param_offset = 3 - messages = await conn.fetch( - f""" - SELECT + _msg_query = f""" + SELECT id, session_id, message_type, content, metadata, created_at, 1 - (embedding <=> $1) as similarity - FROM agent_conversations + FROM agent_conversations {where_clause} AND 1 - (embedding <=> $1) > ${param_offset} ORDER BY similarity DESC LIMIT ${param_offset + 1} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - similarity_threshold, - limit, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + messages = await conn.fetch(_msg_query, *params, similarity_threshold, limit) results = [] for msg in messages: @@ -394,21 +390,17 @@ async def search_conversation_history( # Search conversation summaries if requested if include_summaries: - summaries = await conn.fetch( - f""" - SELECT + _summary_query = f""" + SELECT id, session_id, summary_text, message_count, time_range, created_at, 1 - (summary_embedding <=> $1) as similarity - FROM conversation_summaries + FROM conversation_summaries {where_clause} AND 1 - (summary_embedding <=> $1) > ${param_offset} ORDER BY similarity DESC LIMIT ${param_offset + 1} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - similarity_threshold, - limit // 2, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + summaries = await conn.fetch(_summary_query, *params, similarity_threshold, limit // 2) for summary in summaries: results.append( @@ -496,20 +488,17 @@ async def search_knowledge_base( where_clause = "WHERE " + " AND ".join(where_conditions) - results = await conn.fetch( - f""" - SELECT - id, content, content_type, source_type, metadata, tags, + _kb_query = f""" + SELECT + id, content, content_type, source_type, metadata, tags, access_count, created_at, 1 - (embedding <=> $1) as similarity - FROM agent_knowledge_base + FROM agent_knowledge_base {where_clause} ORDER BY similarity DESC LIMIT ${param_count} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - limit, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + results = await conn.fetch(_kb_query, *params, limit) # Update access count for retrieved items if results: diff --git a/services/orchestrator/sandbox_manager.py b/services/orchestrator/sandbox_manager.py index 99eab0e..af55c12 100644 --- a/services/orchestrator/sandbox_manager.py +++ b/services/orchestrator/sandbox_manager.py @@ -397,7 +397,7 @@ async def _create_container(self, sandbox: Sandbox, config: SandboxConfig): "cap_drop": config.capabilities["drop"], "cap_add": config.capabilities["add"], "read_only": False, # Need write access for development - "tmpfs": {"/tmp": "rw,noexec,nosuid,size=1g"}, + "tmpfs": {"/tmp": "rw,noexec,nosuid,size=1g"}, # nosec B108 -- /tmp is the Docker tmpfs mount for sandbox containers "labels": { "fuzeagent.sandbox": "true", "fuzeagent.agent_id": sandbox.agent_id, diff --git a/services/orchestrator/simple_main.py b/services/orchestrator/simple_main.py index 86e9d48..dbedd06 100644 --- a/services/orchestrator/simple_main.py +++ b/services/orchestrator/simple_main.py @@ -459,4 +459,4 @@ async def get_agent_documents(agent_id: str): if __name__ == "__main__": import uvicorn - uvicorn.run(app, host="0.0.0.0", port=8000) + uvicorn.run(app, host="0.0.0.0", port=8000) # nosec B104 -- intentional bind-all for containerized deployment diff --git a/services/orchestrator/team_knowledge_manager.py b/services/orchestrator/team_knowledge_manager.py index a20741b..e8c690d 100644 --- a/services/orchestrator/team_knowledge_manager.py +++ b/services/orchestrator/team_knowledge_manager.py @@ -504,19 +504,16 @@ async def _search_team_specific_knowledge( where_clause = "WHERE " + " AND ".join(where_conditions) - results = await conn.fetch( - f""" - SELECT + _query = f""" + SELECT *, (1 - (embedding <=> $1)) as similarity_score - FROM team_knowledge_base + FROM team_knowledge_base {where_clause} ORDER BY similarity_score DESC, effectiveness_score DESC LIMIT ${param_idx} - """, # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params - *params, - limit, - ) + """ # nosec B608 -- where clause is fixed fragments with $N placeholders; all values bound as query params + results = await conn.fetch(_query, *params, limit) search_results = [] for row in results: diff --git a/services/orchestrator/tests/test_auth_authz.py b/services/orchestrator/tests/test_auth_authz.py index 376b71d..6c1578e 100644 --- a/services/orchestrator/tests/test_auth_authz.py +++ b/services/orchestrator/tests/test_auth_authz.py @@ -27,7 +27,7 @@ # Configure verification material before importing the auth module so that # get_current_user runs in its prod-like (fail-closed) mode. -os.environ["JWT_SECRET"] = "test-secret-for-issue-6-authz" +os.environ["JWT_SECRET"] = "test-secret-for-issue-6-authz" # nosec B105 -- test-only secret, never used in production os.environ["JWT_ALGORITHM"] = "HS256" os.environ.pop("AUTH_DISABLED", None) os.environ.pop("JWT_AUDIENCE", None) diff --git a/services/orchestrator/tests/test_claude_code_wrapper.py b/services/orchestrator/tests/test_claude_code_wrapper.py index 85ddabc..a7ba5d6 100644 --- a/services/orchestrator/tests/test_claude_code_wrapper.py +++ b/services/orchestrator/tests/test_claude_code_wrapper.py @@ -90,12 +90,12 @@ def test_wrapper_initialization(self, mock_anthropic_client): def test_constructor_accepts_agent_context(self, mock_anthropic_client): """Optional agent/task/workspace context is stored on the instance.""" wrapper = ClaudeCodeWrapper( - workspace_path="/tmp/does-not-need-to-exist", + workspace_path="/tmp/does-not-need-to-exist", # nosec B108 -- test-only tmp path agent_id="agent-123", task_id="task-456", ) - assert wrapper.workspace_path == "/tmp/does-not-need-to-exist" + assert wrapper.workspace_path == "/tmp/does-not-need-to-exist" # nosec B108 -- test-only tmp path assert wrapper.agent_id == "agent-123" assert wrapper.task_id == "task-456" # repository_context is initialised as a fresh dict per instance. diff --git a/services/orchestrator/tests/test_hierarchy_ws_authz.py b/services/orchestrator/tests/test_hierarchy_ws_authz.py index 73a5978..32d157b 100644 --- a/services/orchestrator/tests/test_hierarchy_ws_authz.py +++ b/services/orchestrator/tests/test_hierarchy_ws_authz.py @@ -34,7 +34,7 @@ # Environment — set BEFORE importing auth/hierarchy_endpoints so the module # evaluates with the correct JWT config (fail-closed, no bypass). # --------------------------------------------------------------------------- -os.environ["JWT_SECRET"] = "test-secret-hierarchy-ws-authz" +os.environ["JWT_SECRET"] = "test-secret-hierarchy-ws-authz" # nosec B105 -- test-only secret, never used in production os.environ["JWT_ALGORITHM"] = "HS256" os.environ.pop("AUTH_DISABLED", None) os.environ.pop("JWT_AUDIENCE", None) diff --git a/services/orchestrator/tests/test_residual_authz.py b/services/orchestrator/tests/test_residual_authz.py index b001df5..0f7ce75 100644 --- a/services/orchestrator/tests/test_residual_authz.py +++ b/services/orchestrator/tests/test_residual_authz.py @@ -31,7 +31,7 @@ import pytest # Configure verification material BEFORE importing auth so it runs fail-closed. -os.environ["JWT_SECRET"] = "test-secret-for-issue-6-authz" +os.environ["JWT_SECRET"] = "test-secret-for-issue-6-authz" # nosec B105 -- test-only secret, never used in production os.environ["JWT_ALGORITHM"] = "HS256" os.environ.pop("AUTH_DISABLED", None) os.environ.pop("JWT_AUDIENCE", None)