Files
backend_vib360_laravel/app/Http/Controllers/APIS/CustomerApi/TimeseriesAlertMessageController.php

334 lines
13 KiB
PHP
Raw Normal View History

2025-04-01 16:53:04 +05:30
<?php
namespace App\Http\Controllers\APIS\CustomerApi;
use App\Http\Controllers\Controller;
use App\Models\Device;
use App\Services\CustomerInfoService;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Log;
use Illuminate\Support\Facades\Validator;
class TimeseriesAlertMessageController extends Controller
{
protected $customerInfoService;
public function __construct(CustomerInfoService $customerInfoService)
{
$this->customerInfoService = $customerInfoService;
}
// public function alertMessage(Request $request){
// $token = readHeaderToken();
// if (!$token) {
// return response()->json([
// 'success' => false,
// 'error' => 'Authorization token required'
// ], 401);
// }
// $validator = Validator::make($request->all(), [
// 'device_id' => 'required|string',
// 'startTs' => 'nullable|string',
// 'endTs' => 'nullable|string',
// ]);
// if ($validator->fails()) {
// return response()->json([
// 'success' => false,
// 'error' => $validator->errors()->first()
// ], 400);
// }
// $deviceId = $request->input('device_id');
// // $deviceWithTelemetry = Device::with([
// // 'deviceProfile',
// // 'timeseriesKeys' => function ($query) {
// // $query->where(function ($q) {
// // $q->where('display_on_dashboard', true)
// // ->orWhere('display_on_popup', true);
// // })
// // ->select('id','device_profile_xid', 'display_name')
// // ->with(['timeseriesAlert' => function($query) { // Use singular name to match model
// // $query->select('id', 'timeseries_key_master_xid', 'min_value', 'max_value', 'color_code', 'alert_msg');
// // }]);
// // }
// // ])
// // ->where('id', $deviceId)
// // ->firstOrFail();
// }
// public function alertMessage(Request $request)
// {
// try {
// // Authentication
// $token = readHeaderToken();
// if (!$token) {
// return response()->json([
// 'success' => false,
// 'message' => 'Authorization token required'
// ], 401);
// }
// // Validation
// $validator = Validator::make($request->all(), [
// 'device_id' => 'required|string|exists:devices,id',
// 'startTs' => 'nullable|numeric',
// 'endTs' => 'nullable|numeric|gte:startTs',
// ]);
// if ($validator->fails()) {
// return response()->json([
// 'success' => false,
// 'message' => $validator->errors()->first()
// ], 400);
// }
// // Fetch device with relationships
// $device = Device::with([
// 'deviceProfile',
// 'timeseriesKeys' => function ($query) {
// $query->where(function ($q) {
// $q->where('display_on_dashboard', true)
// ->orWhere('display_on_popup', true);
// })
// ->select('id', 'device_profile_xid', 'key_name', 'display_name')
// ->with(['timeseriesAlert' => function ($query) {
// $query->select('id', 'timeseries_key_master_xid', 'min_value', 'max_value', 'color_code', 'alert_msg');
// }]);
// }
// ])->findOrFail($request->device_id);
// // Get telemetry data
// $telemetryData = $this->customerInfoService->getTelemetryDataDevice(
// $device,
// $device->timeseriesKeys->pluck('key_name')->toArray(),
// $request->startTs,
// $request->endTs
// );
// if (isset($telemetryData['error'])) {
// throw new \Exception($telemetryData['error']);
// }
// // Process data
// $result = [
// 'alerts' => [],
// 'normal_telemetry' => []
// ];
// foreach ($device->timeseriesKeys as $key) {
// if (!isset($telemetryData[$key->key_name])) continue;
// $dataPoint = $telemetryData[$key->key_name][0] ?? null;
// if (!$dataPoint || !isset($dataPoint['value'])) continue;
// $item = [
// 'key' => $key->key_name,
// 'display_name' => $key->display_name,
// 'value' => $dataPoint['value'],
// 'timestamp' => $dataPoint['ts'] ?? null
// ];
// // Check alerts
// // Inside your alertMessage controller method, modify the alert check:
// foreach ($key->timeseriesAlert as $alert) {
// $isBelowMin = $alert->min_value !== null && $dataPoint['value'] < $alert->min_value;
// $isAboveMax = $alert->max_value !== null && $dataPoint['value'] > $alert->max_value;
// if ($isBelowMin || $isAboveMax) {
// Log::warning("Alert triggered", [
// 'device' => $device->id,
// 'key' => $key->key_name,
// 'value' => $dataPoint['value'],
// 'threshold_min' => $alert->min_value,
// 'threshold_max' => $alert->max_value,
// 'condition' => $isBelowMin ? 'below_min' : 'above_max'
// ]);
// $item['alert'] = [
// 'message' => $alert->alert_msg,
// 'color_code' => $alert->color_code,
// 'thresholds' => [
// 'min' => $alert->min_value,
// 'max' => $alert->max_value
// ]
// ];
// $result['alerts'][] = $item;
// continue 2;
// }
// }
// $result['normal_telemetry'][] = $item;
// }
// return response()->json([
// 'success' => true,
// 'device' => [
// 'id' => $device->id,
// 'name' => $device->name,
// 'profile' => $device->deviceProfile
// ],
// 'data' => $result
// ]);
// } catch (\Exception $e) {
// Log::error("Alert processing failed: {$e->getMessage()}", [
// 'device_id' => $request->device_id ?? null,
// 'trace' => $e->getTraceAsString()
// ]);
// return response()->json([
// 'success' => false,
// 'message' => 'Failed to process alerts: ' . $e->getMessage()
// ], 500);
// }
// }
public function alertMessage(Request $request)
{
try {
// Authentication
$token = readHeaderToken();
if (!$token) {
return response()->json([
'success' => false,
'message' => 'Authorization token required'
], 401);
}
// Validation
$validator = Validator::make($request->all(), [
'device_id' => 'required|string|exists:devices,id',
'startTs' => 'nullable|numeric',
'endTs' => 'nullable|numeric|gte:startTs',
]);
if ($validator->fails()) {
return response()->json([
'success' => false,
'message' => $validator->errors()->first()
], 400);
}
// Fetch device with relationships
$device = Device::with([
'deviceProfile',
'timeseriesKeys' => function ($query) {
$query->where(function ($q) {
$q->where('display_on_dashboard', true)
->orWhere('display_on_popup', true);
})
->select('id', 'device_profile_xid', 'key_name', 'display_name')
->with(['timeseriesAlert' => function ($query) {
$query->select('id', 'timeseries_key_master_xid', 'min_value', 'max_value', 'color_code', 'alert_msg');
}]);
}
])->findOrFail($request->device_id);
// Get telemetry data FIRST
$telemetryData = $this->customerInfoService->getTelemetryDataDevice(
$device,
$device->timeseriesKeys->pluck('key_name')->toArray(),
$request->startTs,
$request->endTs
);
if (isset($telemetryData['error'])) {
throw new \Exception($telemetryData['error']);
}
// Get only the keys that actually exist in ThingsBoard response
$existingKeys = array_keys($telemetryData);
// Process data
$result = [
'alerts' => [],
'normal_telemetry' => []
];
foreach ($device->timeseriesKeys as $key) {
// Skip if this key doesn't exist in ThingsBoard response
if (!in_array($key->key_name, $existingKeys)) {
continue;
}
$dataPoint = $telemetryData[$key->key_name][0] ?? null;
if (!$dataPoint || !isset($dataPoint['value'])) {
continue;
}
// Convert values to float for proper comparison
$currentValue = (float)$dataPoint['value'];
$item = [
'key' => $key->key_name,
'display_name' => $key->display_name,
'value' => $currentValue,
'timestamp' => $dataPoint['ts'] ?? null
];
$alertTriggered = false;
foreach ($key->timeseriesAlert as $alert) {
// Convert thresholds to float
$minValue = $alert->min_value !== null ? (float)$alert->min_value : null;
$maxValue = $alert->max_value !== null ? (float)$alert->max_value : null;
$isBelowMin = $minValue !== null && $currentValue < $minValue;
$isAboveMax = $maxValue !== null && $currentValue > $maxValue;
if ($isBelowMin || $isAboveMax) {
Log::warning("Alert triggered", [
'device' => $device->id,
'key' => $key->key_name,
'value' => $currentValue,
'threshold_min' => $minValue,
'threshold_max' => $maxValue,
'condition' => $isBelowMin ? 'below_min' : 'above_max'
]);
$item['alert'] = [
'message' => $alert->alert_msg,
'color_code' => $alert->color_code,
'thresholds' => [
'min' => $minValue,
'max' => $maxValue
]
];
$result['alerts'][] = $item;
$alertTriggered = true;
break;
}
}
if (!$alertTriggered) {
$result['normal_telemetry'][] = $item;
}
}
return response()->json([
'success' => true,
'device' => [
'id' => $device->id,
'name' => $device->name,
'profile' => $device->deviceProfile
],
'data' => $result
]);
} catch (\Exception $e) {
Log::error("Alert processing failed: {$e->getMessage()}", [
'device_id' => $request->device_id ?? null,
'trace' => $e->getTraceAsString()
]);
return response()->json([
'success' => false,
'message' => 'Failed to process alerts: ' . $e->getMessage()
], 500);
}
}
}