Files
Ilya Starchak d8061985d6 asdas
2025-12-10 02:27:35 +03:00

224 lines
7.2 KiB
Python

from fastapi import APIRouter, HTTPException, UploadFile, File
from pydantic import BaseModel
import json
from typing import List, Optional
from utils.models import StatusMessageModel
from routers import nfproxy, nfregex, porthijack, firewall
class ServiceConfig(BaseModel):
name: str
port: int
proto: str
ip_int: str
fail_open: bool = True
class PortHijackServiceConfig(BaseModel):
name: str
public_port: int
proxy_port: int
proto: str
ip_src: str
ip_dst: str
class FirewallRuleConfig(BaseModel):
mode: str
src: str
dst: str
in_int: str
out_int: str
proto: str
sport: str
dport: str
class SetupConfig(BaseModel):
services: Optional[List[ServiceConfig]] = []
porthijack: Optional[List[PortHijackServiceConfig]] = []
firewall: Optional[List[FirewallRuleConfig]] = []
class SetupResponse(BaseModel):
status: str
services_created: int = 0
porthijack_created: int = 0
firewall_created: int = 0
errors: List[str] = []
app = APIRouter()
@app.post("/import", response_model=SetupResponse)
async def import_setup(config: SetupConfig):
"""
Import services and rules from a setup configuration.
Creates basic services without filters or regex rules.
"""
errors = []
services_count = 0
porthijack_count = 0
firewall_count = 0
# Import Services
if config.services:
for service_config in config.services:
try:
# Determine which module to use based on protocol
# HTTP -> NFProxy, TCP/UDP -> can use either (prefer NFProxy)
if service_config.proto in ["tcp", "http", "udp"]:
# Create NFProxy service
try:
add_form = nfproxy.ServiceAddForm(
name=service_config.name,
port=service_config.port,
proto=service_config.proto,
ip_int=service_config.ip_int,
fail_open=service_config.fail_open
)
result = await nfproxy.add_service(add_form)
if result.status == "ok":
services_count += 1
else:
errors.append(f"Service '{service_config.name}': Failed to create")
except Exception as e:
errors.append(f"Service '{service_config.name}': {str(e)}")
else:
errors.append(f"Service '{service_config.name}': Unsupported protocol '{service_config.proto}'")
except Exception as e:
errors.append(f"Service '{service_config.name}': {str(e)}")
# Import PortHijack services
if config.porthijack:
for service_config in config.porthijack:
try:
add_form = porthijack.ServiceAddForm(
name=service_config.name,
public_port=service_config.public_port,
proxy_port=service_config.proxy_port,
proto=service_config.proto,
ip_src=service_config.ip_src,
ip_dst=service_config.ip_dst
)
result = await porthijack.add_service(add_form)
if result.status == "ok":
porthijack_count += 1
else:
errors.append(f"PortHijack service '{service_config.name}': Failed to create")
except Exception as e:
errors.append(f"PortHijack service '{service_config.name}': {str(e)}")
# Import Firewall rules
if config.firewall:
for rule_config in config.firewall:
try:
rule_form = firewall.RuleFormAdd(
mode=rule_config.mode,
src=rule_config.src,
dst=rule_config.dst,
in_int=rule_config.in_int,
out_int=rule_config.out_int,
proto=rule_config.proto,
sport=rule_config.sport,
dport=rule_config.dport
)
await firewall.add_rule(rule_form)
firewall_count += 1
except Exception as e:
errors.append(f"Firewall rule: {str(e)}")
return SetupResponse(
status="ok" if len(errors) == 0 else "partial",
services_created=services_count,
porthijack_created=porthijack_count,
firewall_created=firewall_count,
errors=errors
)
@app.post("/import/file")
async def import_setup_file(file: UploadFile = File(...)):
"""
Import services from an uploaded JSON file.
"""
try:
content = await file.read()
config_dict = json.loads(content.decode('utf-8'))
config = SetupConfig(**config_dict)
return await import_setup(config)
except json.JSONDecodeError as e:
raise HTTPException(status_code=400, detail=f"Invalid JSON: {str(e)}")
except Exception as e:
raise HTTPException(status_code=400, detail=f"Error processing file: {str(e)}")
@app.get("/export")
async def export_setup():
"""
Export all current services and rules as a JSON configuration.
Exports only service definitions without filters or regexes.
"""
config = {
"services": [],
"porthijack": [],
"firewall": []
}
# Export NFProxy services
try:
nfproxy_services = await nfproxy.get_services()
for service in nfproxy_services:
config["services"].append({
"name": service.name,
"port": service.port,
"proto": service.proto,
"ip_int": service.ip_int,
"fail_open": service.fail_open
})
except:
pass
# Export NFRegex services
try:
nfregex_services = await nfregex.get_services()
for service in nfregex_services:
config["services"].append({
"name": service.name,
"port": service.port,
"proto": service.proto,
"ip_int": service.ip_int,
"fail_open": service.fail_open
})
except:
pass
# Export PortHijack services
try:
porthijack_services = await porthijack.get_services()
for service in porthijack_services:
config["porthijack"].append({
"name": service.name,
"public_port": service.public_port,
"proxy_port": service.proxy_port,
"proto": service.proto,
"ip_src": service.ip_src,
"ip_dst": service.ip_dst
})
except:
pass
# Export Firewall rules
try:
fw_rules = await firewall.get_rules()
for rule in fw_rules:
config["firewall"].append({
"mode": rule.mode,
"src": rule.src,
"dst": rule.dst,
"in_int": rule.in_int,
"out_int": rule.out_int,
"proto": rule.proto,
"sport": rule.sport,
"dport": rule.dport
})
except:
pass
return config