Add standalone test script for mock services without Docker dependency

This commit is contained in:
openhands 2025-10-30 14:24:45 +00:00
parent d6635806f3
commit 7372c5a161
3 changed files with 862 additions and 0 deletions

View File

@ -0,0 +1,379 @@
#!/usr/bin/env python3
"""
Standalone test script for mock SCADA and optimizer services
This script can test the services without requiring Docker
"""
import subprocess
import sys
import time
import requests
import json
from datetime import datetime
def run_command(cmd, check=True):
"""Run a shell command and return output"""
try:
result = subprocess.run(cmd, shell=True, capture_output=True, text=True, check=check)
return result.stdout, result.stderr, result.returncode
except subprocess.CalledProcessError as e:
return e.stdout, e.stderr, e.returncode
def check_python_dependencies():
"""Check if required Python packages are installed"""
required_packages = ['flask', 'requests']
missing = []
for package in required_packages:
try:
__import__(package)
except ImportError:
missing.append(package)
if missing:
print(f"❌ Missing required packages: {', '.join(missing)}")
print("Install with: pip install flask requests")
return False
print("✅ All required Python packages are installed")
return True
def start_mock_services():
"""Start the mock services in background"""
print("🚀 Starting mock services...")
# Start SCADA service
scada_cmd = "cd tests/mock_services && python mock_scada_server.py > /tmp/scada.log 2>&1 &"
stdout, stderr, code = run_command(scada_cmd)
# Start Optimizer service
optimizer_cmd = "cd tests/mock_services && python mock_optimizer_server.py > /tmp/optimizer.log 2>&1 &"
stdout, stderr, code = run_command(optimizer_cmd)
print("✅ Mock services started in background")
print(" SCADA logs: /tmp/scada.log")
print(" Optimizer logs: /tmp/optimizer.log")
def wait_for_services():
"""Wait for services to be ready"""
print("⏳ Waiting for services to be ready...")
max_wait = 30
start_time = time.time()
while time.time() - start_time < max_wait:
try:
scada_ready = requests.get("http://localhost:8081/health", timeout=2).status_code == 200
optimizer_ready = requests.get("http://localhost:8082/health", timeout=2).status_code == 200
if scada_ready and optimizer_ready:
print("✅ All services are ready!")
return True
except:
pass
print(f" Waiting... ({int(time.time() - start_time)}/{max_wait} seconds)")
time.sleep(2)
print("❌ Services not ready within timeout period")
return False
def test_scada_service():
"""Test SCADA service functionality"""
print("\n📊 Testing SCADA Service...")
tests_passed = 0
total_tests = 0
try:
# Test health endpoint
total_tests += 1
response = requests.get("http://localhost:8081/health")
if response.status_code == 200 and response.json().get("status") == "healthy":
print(" ✅ Health check passed")
tests_passed += 1
else:
print(" ❌ Health check failed")
# Test data endpoint
total_tests += 1
response = requests.get("http://localhost:8081/api/v1/data")
if response.status_code == 200:
data = response.json()
if "data" in data and "equipment" in data:
print(" ✅ Data retrieval passed")
tests_passed += 1
else:
print(" ❌ Data structure invalid")
else:
print(" ❌ Data endpoint failed")
# Test specific data tag
total_tests += 1
response = requests.get("http://localhost:8081/api/v1/data/temperature")
if response.status_code == 200:
data = response.json()
if "value" in data and "unit" in data:
print(" ✅ Specific data tag passed")
tests_passed += 1
else:
print(" ❌ Specific data structure invalid")
else:
print(" ❌ Specific data endpoint failed")
# Test equipment control
total_tests += 1
response = requests.post(
"http://localhost:8081/api/v1/control/pump_1",
json={"command": "START"}
)
if response.status_code == 200:
data = response.json()
if "current_status" in data and data["current_status"] == "START":
print(" ✅ Equipment control passed")
tests_passed += 1
else:
print(" ❌ Equipment control response invalid")
else:
print(" ❌ Equipment control failed")
# Test alarms
total_tests += 1
response = requests.get("http://localhost:8081/api/v1/alarms")
if response.status_code == 200:
data = response.json()
if "alarms" in data:
print(" ✅ Alarms endpoint passed")
tests_passed += 1
else:
print(" ❌ Alarms structure invalid")
else:
print(" ❌ Alarms endpoint failed")
except Exception as e:
print(f" ❌ SCADA test error: {e}")
print(f" 📈 SCADA tests: {tests_passed}/{total_tests} passed")
return tests_passed, total_tests
def test_optimizer_service():
"""Test optimizer service functionality"""
print("\n🧠 Testing Optimizer Service...")
tests_passed = 0
total_tests = 0
try:
# Test health endpoint
total_tests += 1
response = requests.get("http://localhost:8082/health")
if response.status_code == 200 and response.json().get("status") == "healthy":
print(" ✅ Health check passed")
tests_passed += 1
else:
print(" ❌ Health check failed")
# Test models endpoint
total_tests += 1
response = requests.get("http://localhost:8082/api/v1/models")
if response.status_code == 200:
data = response.json()
if "models" in data and "energy_optimization" in data["models"]:
print(" ✅ Models endpoint passed")
tests_passed += 1
else:
print(" ❌ Models structure invalid")
else:
print(" ❌ Models endpoint failed")
# Test energy optimization
total_tests += 1
response = requests.post(
"http://localhost:8082/api/v1/optimize/energy_optimization",
json={"power_load": 450, "time_of_day": 14, "production_rate": 95}
)
if response.status_code == 200:
data = response.json()
if "result" in data and "optimization_id" in data:
print(" ✅ Energy optimization passed")
tests_passed += 1
else:
print(" ❌ Optimization response invalid")
else:
print(" ❌ Energy optimization failed")
# Test forecast
total_tests += 1
response = requests.post(
"http://localhost:8082/api/v1/forecast",
json={"hours": 12}
)
if response.status_code == 200:
data = response.json()
if "forecast" in data and len(data["forecast"]) == 12:
print(" ✅ Forecast passed")
tests_passed += 1
else:
print(" ❌ Forecast structure invalid")
else:
print(" ❌ Forecast failed")
# Test history
total_tests += 1
response = requests.get("http://localhost:8082/api/v1/history")
if response.status_code == 200:
data = response.json()
if "history" in data and "total_optimizations" in data:
print(" ✅ History endpoint passed")
tests_passed += 1
else:
print(" ❌ History structure invalid")
else:
print(" ❌ History endpoint failed")
except Exception as e:
print(f" ❌ Optimizer test error: {e}")
print(f" 📈 Optimizer tests: {tests_passed}/{total_tests} passed")
return tests_passed, total_tests
def test_end_to_end_workflow():
"""Test end-to-end workflow"""
print("\n🔄 Testing End-to-End Workflow...")
tests_passed = 0
total_tests = 0
try:
# Get SCADA data
total_tests += 1
scada_response = requests.get("http://localhost:8081/api/v1/data")
if scada_response.status_code == 200:
scada_data = scada_response.json()
power_value = scada_data["data"]["power"]["value"]
print(" ✅ SCADA data retrieved")
tests_passed += 1
else:
print(" ❌ SCADA data retrieval failed")
return tests_passed, total_tests
# Run optimization based on SCADA data
total_tests += 1
opt_response = requests.post(
"http://localhost:8082/api/v1/optimize/energy_optimization",
json={
"power_load": power_value,
"time_of_day": datetime.now().hour,
"production_rate": 95
}
)
if opt_response.status_code == 200:
opt_data = opt_response.json()
if "result" in opt_data and "recommended_actions" in opt_data["result"]:
print(" ✅ Optimization based on SCADA data passed")
tests_passed += 1
else:
print(" ❌ Optimization response invalid")
else:
print(" ❌ Optimization failed")
# Test control based on optimization
total_tests += 1
control_response = requests.post(
"http://localhost:8081/api/v1/control/compressor",
json={"command": "START"}
)
if control_response.status_code == 200:
control_data = control_response.json()
if "current_status" in control_data:
print(" ✅ Control based on workflow passed")
tests_passed += 1
else:
print(" ❌ Control response invalid")
else:
print(" ❌ Control failed")
except Exception as e:
print(f" ❌ End-to-end test error: {e}")
print(f" 📈 End-to-end tests: {tests_passed}/{total_tests} passed")
return tests_passed, total_tests
def stop_services():
"""Stop the mock services"""
print("\n🛑 Stopping mock services...")
# Find and kill the processes
run_command("pkill -f 'python mock_scada_server.py'", check=False)
run_command("pkill -f 'python mock_optimizer_server.py'", check=False)
print("✅ Mock services stopped")
def main():
"""Main test runner"""
print("🧪 Standalone Mock Services Test Runner")
print("=" * 50)
# Check dependencies
if not check_python_dependencies():
sys.exit(1)
# Create mock services directory if needed
import os
os.makedirs("tests/mock_services", exist_ok=True)
# Check if mock service files exist
if not os.path.exists("tests/mock_services/mock_scada_server.py"):
print("❌ Mock service files not found. Run setup script first:")
print(" ./scripts/setup-test-environment.sh")
sys.exit(1)
# Start services
start_mock_services()
# Wait for services
if not wait_for_services():
stop_services()
sys.exit(1)
# Run tests
total_passed = 0
total_tests = 0
# Test SCADA
passed, tests = test_scada_service()
total_passed += passed
total_tests += tests
# Test Optimizer
passed, tests = test_optimizer_service()
total_passed += passed
total_tests += tests
# Test End-to-End
passed, tests = test_end_to_end_workflow()
total_passed += passed
total_tests += tests
# Stop services
stop_services()
# Print summary
print("\n" + "=" * 50)
print("📊 TEST SUMMARY")
print("=" * 50)
print(f"Total Tests: {total_tests}")
print(f"Tests Passed: {total_passed}")
print(f"Tests Failed: {total_tests - total_passed}")
print(f"Success Rate: {(total_passed/total_tests)*100:.1f}%")
if total_passed == total_tests:
print("\n🎉 ALL TESTS PASSED!")
print("Mock services are working correctly!")
else:
print(f"\n{total_tests - total_passed} TESTS FAILED")
print("Check the logs above for details")
sys.exit(1)
if __name__ == "__main__":
main()

View File

@ -0,0 +1,280 @@
#!/usr/bin/env python3
"""
Mock Optimizer Server for testing
Simulates optimization service for industrial processes
"""
import json
import random
import time
from datetime import datetime, timedelta
from flask import Flask, jsonify, request
app = Flask(__name__)
# Mock optimization models
optimization_models = {
"energy_optimization": {
"name": "Energy Consumption Optimizer",
"description": "Optimizes energy usage while maintaining production targets",
"parameters": ["power_load", "time_of_day", "production_rate"],
"outputs": ["optimal_power_setpoint", "recommended_actions", "estimated_savings", "confidence"]
},
"production_optimization": {
"name": "Production Efficiency Optimizer",
"description": "Maximizes production efficiency and throughput",
"parameters": ["raw_material_quality", "machine_utilization", "operator_skill"],
"outputs": ["optimal_production_rate", "efficiency_gain", "recommended_adjustments"]
},
"cost_optimization": {
"name": "Cost Reduction Optimizer",
"description": "Minimizes operational costs while maintaining quality",
"parameters": ["energy_cost", "labor_cost", "maintenance_cost"],
"outputs": ["optimal_cost_structure", "cost_reduction", "implementation_plan"]
}
}
# Optimization history
optimization_history = []
def generate_optimization_id():
"""Generate unique optimization ID"""
return f"OPT_{datetime.now().strftime('%Y%m%d_%H%M%S')}_{random.randint(1000, 9999)}"
def run_energy_optimization(data):
"""Run energy optimization"""
power_load = data.get("power_load", 450.0)
time_of_day = data.get("time_of_day", 12)
production_rate = data.get("production_rate", 95.0)
# Mock optimization logic
if time_of_day >= 6 and time_of_day <= 18:
# Daytime optimization
optimal_power = power_load * 0.85 # Reduce power during peak hours
savings = power_load * 0.15 * 0.12 # 15% reduction at $0.12/kWh
else:
# Nighttime optimization
optimal_power = power_load * 0.95 # Slight reduction at night
savings = power_load * 0.05 * 0.08 # 5% reduction at $0.08/kWh
# Adjust based on production rate
if production_rate < 80:
optimal_power *= 0.9
savings *= 1.1
elif production_rate > 95:
optimal_power *= 1.05
savings *= 0.9
return {
"optimal_power_setpoint": round(optimal_power, 2),
"recommended_actions": [
"Adjust compressor speed to 85%",
"Optimize pump sequencing",
"Implement variable frequency drive"
],
"estimated_savings": round(savings, 2),
"confidence": random.uniform(0.85, 0.95)
}
def run_production_optimization(data):
"""Run production optimization"""
raw_material_quality = data.get("raw_material_quality", 85.0)
machine_utilization = data.get("machine_utilization", 92.0)
operator_skill = data.get("operator_skill", 88.0)
# Mock optimization logic
base_rate = 100.0
# Adjust based on factors
quality_factor = raw_material_quality / 100.0
utilization_factor = machine_utilization / 100.0
skill_factor = operator_skill / 100.0
optimal_rate = base_rate * quality_factor * utilization_factor * skill_factor
efficiency_gain = (optimal_rate - base_rate) / base_rate * 100
return {
"optimal_production_rate": round(optimal_rate, 2),
"efficiency_gain": round(efficiency_gain, 2),
"recommended_adjustments": [
"Increase raw material inspection frequency",
"Optimize machine maintenance schedule",
"Provide operator training on efficiency techniques"
]
}
def run_cost_optimization(data):
"""Run cost optimization"""
energy_cost = data.get("energy_cost", 55.0)
labor_cost = data.get("labor_cost", 30.0)
maintenance_cost = data.get("maintenance_cost", 15.0)
total_cost = energy_cost + labor_cost + maintenance_cost
# Mock optimization logic
optimal_energy = energy_cost * 0.9 # 10% reduction
optimal_labor = labor_cost * 0.95 # 5% reduction
optimal_maintenance = maintenance_cost * 1.05 # 5% increase for better maintenance
optimal_total = optimal_energy + optimal_labor + optimal_maintenance
cost_reduction = total_cost - optimal_total
return {
"optimal_cost_structure": {
"energy": round(optimal_energy, 2),
"labor": round(optimal_labor, 2),
"maintenance": round(optimal_maintenance, 2),
"total": round(optimal_total, 2)
},
"cost_reduction": round(cost_reduction, 2),
"implementation_plan": [
"Implement energy monitoring system",
"Optimize workforce scheduling",
"Increase preventive maintenance frequency"
]
}
def generate_forecast(hours=24):
"""Generate forecast data"""
forecast = []
base_time = datetime.now()
for i in range(hours):
timestamp = base_time + timedelta(hours=i)
hour = timestamp.hour
# Generate realistic forecast data
if hour >= 6 and hour <= 18:
# Daytime values
energy_consumption = random.uniform(450, 550)
production_rate = random.uniform(95, 105)
efficiency = random.uniform(85, 92)
cost = random.uniform(50, 60)
else:
# Nighttime values
energy_consumption = random.uniform(350, 450)
production_rate = random.uniform(80, 95)
efficiency = random.uniform(78, 85)
cost = random.uniform(40, 50)
forecast.append({
"timestamp": timestamp.isoformat(),
"energy_consumption": round(energy_consumption, 2),
"production_rate": round(production_rate, 2),
"efficiency": round(efficiency, 2),
"cost": round(cost, 2)
})
return forecast
@app.route('/health', methods=['GET'])
def health():
"""Health check endpoint"""
return jsonify({
"status": "healthy",
"service": "mock-optimizer",
"timestamp": datetime.now().isoformat(),
"models_available": len(optimization_models)
})
@app.route('/api/v1/models', methods=['GET'])
def get_models():
"""Get available optimization models"""
return jsonify({
"models": optimization_models,
"timestamp": datetime.now().isoformat()
})
@app.route('/api/v1/optimize/<model_name>', methods=['POST'])
def run_optimization(model_name):
"""Run optimization with specified model"""
if model_name not in optimization_models:
return jsonify({"error": f"Model '{model_name}' not found"}), 404
data = request.json
if not data:
return jsonify({"error": "No data provided"}), 400
start_time = time.time()
# Run appropriate optimization
if model_name == "energy_optimization":
result = run_energy_optimization(data)
elif model_name == "production_optimization":
result = run_production_optimization(data)
elif model_name == "cost_optimization":
result = run_cost_optimization(data)
else:
return jsonify({"error": "Model not implemented"}), 501
processing_time = round(time.time() - start_time, 3)
optimization_id = generate_optimization_id()
# Add to history
optimization_history.append({
"optimization_id": optimization_id,
"model": model_name,
"timestamp": datetime.now().isoformat(),
"processing_time": processing_time
})
return jsonify({
"optimization_id": optimization_id,
"model": model_name,
"result": result,
"processing_time": processing_time,
"timestamp": datetime.now().isoformat()
})
@app.route('/api/v1/history', methods=['GET'])
def get_history():
"""Get optimization history"""
return jsonify({
"history": optimization_history[-10:], # Last 10 optimizations
"total_optimizations": len(optimization_history),
"timestamp": datetime.now().isoformat()
})
@app.route('/api/v1/forecast', methods=['POST'])
def generate_optimization_forecast():
"""Generate optimization forecast"""
data = request.json or {}
hours = data.get("hours", 24)
if hours > 168: # Max 1 week
return jsonify({"error": "Forecast horizon too long. Maximum 168 hours (1 week)"}), 400
forecast = generate_forecast(hours)
return jsonify({
"forecast": forecast,
"generated_at": datetime.now().isoformat(),
"horizon_hours": hours
})
@app.route('/api/v1/status/<optimization_id>', methods=['GET'])
def get_optimization_status(optimization_id):
"""Get status of specific optimization"""
for opt in optimization_history:
if opt["optimization_id"] == optimization_id:
return jsonify({
"optimization_id": optimization_id,
"status": "completed",
"model": opt["model"],
"completed_at": opt["timestamp"],
"processing_time": opt["processing_time"]
})
return jsonify({"error": f"Optimization '{optimization_id}' not found"}), 404
if __name__ == '__main__':
print("🧠 Starting Mock Optimizer Server on port 8082...")
print("📊 Available endpoints:")
print(" GET /health")
print(" GET /api/v1/models")
print(" POST /api/v1/optimize/<model_name>")
print(" GET /api/v1/history")
print(" POST /api/v1/forecast")
print(" GET /api/v1/status/<optimization_id>")
app.run(host='0.0.0.0', port=8082, debug=False)

View File

@ -0,0 +1,203 @@
#!/usr/bin/env python3
"""
Mock SCADA Server for testing
Simulates industrial SCADA system with process data and equipment control
"""
import json
import random
import time
from datetime import datetime
from flask import Flask, jsonify, request
app = Flask(__name__)
# Mock SCADA data
current_data = {
"temperature": {"value": 75.5, "unit": "°C", "min": 50, "max": 100},
"pressure": {"value": 2.5, "unit": "bar", "min": 1, "max": 5},
"flow_rate": {"value": 120.0, "unit": "m³/h", "min": 50, "max": 200},
"level": {"value": 65.0, "unit": "%", "min": 0, "max": 100},
"power": {"value": 450.0, "unit": "kW", "min": 200, "max": 600},
"status": {"value": "RUNNING", "unit": "-"},
"efficiency": {"value": 87.5, "unit": "%", "min": 0, "max": 100}
}
# Equipment status
equipment_status = {
"pump_1": "RUNNING",
"pump_2": "STOPPED",
"valve_1": "OPEN",
"valve_2": "CLOSED",
"compressor": "RUNNING",
"heater": "STOPPED"
}
# Alarm status
alarms = []
def update_data():
"""Update mock data with realistic variations"""
global current_data
# Temperature variation
current_data["temperature"]["value"] += random.uniform(-0.5, 0.5)
current_data["temperature"]["value"] = max(50, min(100, current_data["temperature"]["value"]))
# Pressure variation
current_data["pressure"]["value"] += random.uniform(-0.1, 0.1)
current_data["pressure"]["value"] = max(1, min(5, current_data["pressure"]["value"]))
# Flow rate variation
current_data["flow_rate"]["value"] += random.uniform(-2, 2)
current_data["flow_rate"]["value"] = max(50, min(200, current_data["flow_rate"]["value"]))
# Level variation
current_data["level"]["value"] += random.uniform(-1, 1)
current_data["level"]["value"] = max(0, min(100, current_data["level"]["value"]))
# Power variation
current_data["power"]["value"] += random.uniform(-5, 5)
current_data["power"]["value"] = max(200, min(600, current_data["power"]["value"]))
# Efficiency variation
current_data["efficiency"]["value"] += random.uniform(-0.5, 0.5)
current_data["efficiency"]["value"] = max(0, min(100, current_data["efficiency"]["value"]))
# Check for alarm conditions
check_alarms()
def check_alarms():
"""Check for alarm conditions"""
global alarms
# Clear old alarms
alarms = [alarm for alarm in alarms if datetime.now().timestamp() - alarm["timestamp"] < 300]
# Check temperature alarm
if current_data["temperature"]["value"] > 95:
add_alarm("HIGH_TEMPERATURE", f"Temperature high: {current_data['temperature']['value']:.1f}°C")
elif current_data["temperature"]["value"] < 55:
add_alarm("LOW_TEMPERATURE", f"Temperature low: {current_data['temperature']['value']:.1f}°C")
# Check pressure alarm
if current_data["pressure"]["value"] > 4.5:
add_alarm("HIGH_PRESSURE", f"Pressure high: {current_data['pressure']['value']:.1f} bar")
elif current_data["pressure"]["value"] < 1.5:
add_alarm("LOW_PRESSURE", f"Pressure low: {current_data['pressure']['value']:.1f} bar")
# Check level alarm
if current_data["level"]["value"] > 90:
add_alarm("HIGH_LEVEL", f"Level high: {current_data['level']['value']:.1f}%")
elif current_data["level"]["value"] < 20:
add_alarm("LOW_LEVEL", f"Level low: {current_data['level']['value']:.1f}%")
def add_alarm(type, message):
"""Add a new alarm"""
global alarms
# Check if alarm already exists
for alarm in alarms:
if alarm["type"] == type:
return
alarms.append({
"type": type,
"message": message,
"timestamp": datetime.now().timestamp(),
"acknowledged": False
})
@app.route('/health', methods=['GET'])
def health():
"""Health check endpoint"""
return jsonify({
"status": "healthy",
"service": "mock-scada",
"timestamp": datetime.now().isoformat()
})
@app.route('/api/v1/data', methods=['GET'])
def get_all_data():
"""Get all SCADA data"""
update_data()
return jsonify({
"timestamp": datetime.now().isoformat(),
"data": current_data,
"equipment": equipment_status
})
@app.route('/api/v1/data/<tag>', methods=['GET'])
def get_specific_data(tag):
"""Get specific SCADA data tag"""
update_data()
if tag not in current_data:
return jsonify({"error": f"Tag '{tag}' not found"}), 404
return jsonify({
"tag": tag,
"value": current_data[tag]["value"],
"unit": current_data[tag]["unit"],
"timestamp": datetime.now().isoformat()
})
@app.route('/api/v1/control/<equipment>', methods=['POST'])
def control_equipment(equipment):
"""Control SCADA equipment"""
if equipment not in equipment_status:
return jsonify({"error": f"Equipment '{equipment}' not found"}), 404
command = request.json.get("command")
if not command:
return jsonify({"error": "Command is required"}), 400
valid_commands = ["START", "STOP", "OPEN", "CLOSE", "RESET"]
if command not in valid_commands:
return jsonify({"error": f"Invalid command. Valid commands: {valid_commands}"}), 400
previous_status = equipment_status[equipment]
equipment_status[equipment] = command
return jsonify({
"equipment": equipment,
"previous_status": previous_status,
"current_status": command,
"timestamp": datetime.now().isoformat(),
"message": f"Equipment {equipment} changed from {previous_status} to {command}"
})
@app.route('/api/v1/alarms', methods=['GET'])
def get_alarms():
"""Get current alarms"""
return jsonify({
"alarms": alarms,
"timestamp": datetime.now().isoformat()
})
@app.route('/api/v1/alarms/<alarm_type>/acknowledge', methods=['POST'])
def acknowledge_alarm(alarm_type):
"""Acknowledge an alarm"""
for alarm in alarms:
if alarm["type"] == alarm_type:
alarm["acknowledged"] = True
return jsonify({
"alarm": alarm_type,
"acknowledged": True,
"timestamp": datetime.now().isoformat()
})
return jsonify({"error": f"Alarm '{alarm_type}' not found"}), 404
if __name__ == '__main__':
print("🚀 Starting Mock SCADA Server on port 8081...")
print("📊 Available endpoints:")
print(" GET /health")
print(" GET /api/v1/data")
print(" GET /api/v1/data/<tag>")
print(" POST /api/v1/control/<equipment>")
print(" GET /api/v1/alarms")
print(" POST /api/v1/alarms/<type>/acknowledge")
app.run(host='0.0.0.0', port=8081, debug=False)