using Application.Domain.Entities; using Hangfire; using Hangfire.Storage; using Infrastructure.Application.Entites.Settings; using Infrastructure.Data; using Infrastructure.Events; using Infrastructure.Extensions; using IoT.Shared.Services; using IoTNode.DeviceServices.Onvif; using Jint; using Jint.Native; using Microsoft.EntityFrameworkCore; using Microsoft.Extensions.Logging; using System; using System.Linq; using System.Threading.Tasks; namespace IoTNode.Services { public class IoTNodeEventHandler : IEventHander>, IEventHander>, IEventHander>, IEventHander>, IEventHander> { private readonly ILogger _logger; private readonly ISceneTiggerService _sceneTiggerService; private readonly OnvifService _onvifService; private readonly IoTNodeClient _ioTNodeClient; private readonly IRepository _sceneTimerRepo; private readonly IRepository _sceneTiggerRepo; public IoTNodeEventHandler(ILogger logger, ISceneTiggerService sceneTiggerService, OnvifService onvifService, IoTNodeClient ioTNodeClient, IRepository sceneTimerRepo, IRepository sceneTiggerRepo) { this._logger = logger; this._sceneTiggerService = sceneTiggerService; this._onvifService = onvifService; this._ioTNodeClient = ioTNodeClient; this._sceneTimerRepo = sceneTimerRepo; this._sceneTiggerRepo = sceneTiggerRepo; } public void Handle(EntityInsertedEvent message) { RecurringJob.AddOrUpdate(message.Data.Id.ToString(), () => Handle(message.Data.Id), message.Data.Cron, TimeZoneInfo.Local); } public void Handle(EntityUpdatedEvent message) { RecurringJob.AddOrUpdate(message.Data.Id.ToString(), () => Handle(message.Data.Id), message.Data.Cron, TimeZoneInfo.Local); } public void Handle(EntityDeletedEvent message) { RecurringJob.RemoveIfExists(message.Data.Id.ToString()); } public void UpdateTimer() { using var conn = JobStorage.Current.GetConnection(); var jobs = conn.GetRecurringJobs(); foreach (var job in jobs) { RecurringJob.RemoveIfExists(job.Id); } var list = this._sceneTimerRepo.ReadOnlyTable().ToList(); foreach (var timer in list) { try { RecurringJob.AddOrUpdate(timer.Id.ToString(), () => Handle(timer.Id), timer.Cron, TimeZoneInfo.Local); } catch (Exception ex) { ex.PrintStack(); this._logger.LogError(ex.ToString()); } } } public void Handle(Guid id) { this._logger.LogInformation($"node timer exec:{id}"); var commands = this._sceneTimerRepo.ReadOnlyTable() .Include(o => o.Scene).ThenInclude(o => o.SceneCommands).ThenInclude(o => o.Command).ThenInclude(o => o.Api) .Include(o => o.Scene).ThenInclude(o => o.SceneCommands).ThenInclude(o => o.Command).ThenInclude(o => o.Device) .Where(o => o.Id == id) .SelectMany(o => o.Scene.SceneCommands) .Select(o => o.Command) .ToList(); this._ioTNodeClient.ExecCommands(commands); } public void Handle(EntityUpdatedEvent message) { this.TiggerHandle(message); } public void Handle(EntityUpdatedEvent message) { if (message.Data.Name == "stream.rtmp" || message.Data.Name == "ffmpeg.args") { Task.Delay(1000); this._onvifService.StopPushToServer(); this._onvifService.StartPushToServer(); } else if (message.Data.Name == "notify:host") { this._ioTNodeClient.Close(); this._ioTNodeClient.Connect(); } else if (message.Data.Name == "code") { this._ioTNodeClient.Close(); this._ioTNodeClient.Connect(); } } private void TiggerHandle(BaseEvent message) { try { foreach (var tigger in this._sceneTiggerService.GetSceneTiggers()) { var data = message.Data; if (tigger.DataId == data.Id) { try { var condition = tigger.Condition; var value = data.Value; var engine = new Engine().Execute($"function valid(value){{return {condition};}}"); var result = engine.Invoke("valid", value); if (result == JsValue.True) { this.TiggerHandle(tigger.Id); } } catch (Exception ex) { this._logger.LogError(ex.ToString()); } } } } catch (Exception ex) { this._logger.LogError(ex.ToString()); } } private void TiggerHandle(Guid tiggerId) { this._logger.LogDebug($"node tigger exec:{tiggerId}"); var commands = this._sceneTiggerRepo.ReadOnlyTable() .Include(o => o.Scene).ThenInclude(o => o.SceneCommands).ThenInclude(o => o.Command).ThenInclude(o => o.Api) .Include(o => o.Scene).ThenInclude(o => o.SceneCommands).ThenInclude(o => o.Command).ThenInclude(o => o.Device) .Where(o => o.Id == tiggerId) .SelectMany(o => o.Scene.SceneCommands) .Select(o => o.Command) .ToList(); this._ioTNodeClient.ExecCommands(commands); } } }