using MediaBrowser.Common.Configuration; using MediaBrowser.Common.Net; using MediaBrowser.Controller.Library; using MediaBrowser.Controller.Notifications; using MediaBrowser.Controller.Plugins; using MediaBrowser.Model.Logging; using MediaBrowser.Model.Notifications; using MediaBrowser.Model.Serialization; using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Threading; using System.Threading.Tasks; namespace MediaBrowser.Server.Implementations.EntryPoints.Notifications { public class RemoteNotifications : IServerEntryPoint { private const string Url = "http://www.mb3admin.com/admin/service/MB3ServerNotifications.json"; private Timer _timer; private readonly IHttpClient _httpClient; private readonly IApplicationPaths _appPaths; private readonly ILogger _logger; private readonly IJsonSerializer _json; private readonly INotificationsRepository _notificationsRepo; private readonly IUserManager _userManager; private readonly TimeSpan _frequency = TimeSpan.FromHours(1); private readonly TimeSpan _maxAge = TimeSpan.FromDays(31); public RemoteNotifications(IApplicationPaths appPaths, ILogger logger, IHttpClient httpClient, IJsonSerializer json, INotificationsRepository notificationsRepo, IUserManager userManager) { _appPaths = appPaths; _logger = logger; _httpClient = httpClient; _json = json; _notificationsRepo = notificationsRepo; _userManager = userManager; } /// /// Runs this instance. /// public void Run() { _timer = new Timer(OnTimerFired, null, TimeSpan.FromMilliseconds(500), _frequency); } /// /// Called when [timer fired]. /// /// The state. private async void OnTimerFired(object state) { var dataPath = Path.Combine(_appPaths.DataPath, "remotenotifications.json"); var lastRunTime = File.Exists(dataPath) ? File.GetLastWriteTimeUtc(dataPath) : DateTime.MinValue; if ((DateTime.UtcNow - lastRunTime) >= _frequency) { try { await DownloadNotifications(dataPath, lastRunTime).ConfigureAwait(false); } catch (Exception ex) { _logger.ErrorException("Error downloading remote notifications", ex); } } } /// /// Downloads the notifications. /// /// The data path. /// The last run time. /// Task. private async Task DownloadNotifications(string dataPath, DateTime lastRunTime) { using (var stream = await _httpClient.Get(new HttpRequestOptions { Url = Url }).ConfigureAwait(false)) { var notifications = _json.DeserializeFromStream(stream); File.WriteAllText(dataPath, string.Empty); await CreateNotifications(notifications, lastRunTime).ConfigureAwait(false); } } /// /// Creates the notifications. /// /// The notifications. /// The last run time. /// Task. private async Task CreateNotifications(IEnumerable notifications, DateTime lastRunTime) { // Only show notifications that are active, new since last download, and not older than max age var notificationList = notifications .Where(i => string.Equals(i.active, "1") && i.date > lastRunTime && (DateTime.Now - i.date) <= _maxAge) .ToList(); foreach (var user in _userManager.Users.ToList()) { foreach (var notification in notificationList) { await _notificationsRepo.AddNotification(new Notification { Category = notification.category, Date = notification.date, Name = notification.name, Description = notification.description, Url = notification.url, UserId = user.Id }, CancellationToken.None).ConfigureAwait(false); } } } public void Dispose() { if (_timer != null) { _timer.Dispose(); _timer = null; } } private class RemoteNotification { public string id { get; set; } public DateTime date { get; set; } public string name { get; set; } public string description { get; set; } public string category { get; set; } public string url { get; set; } public object imageUrl { get; set; } public string active { get; set; } } } }