private async Task LoadConfigDataAsync(string tilde, bool isReload, CancellationToken cancellationToken)
        {
            var apiClient = this.apiClient.GetAsserted();

            var configTask = apiClient.FetchConfigAsync();
            var connectionsTask = apiClient.FetchConnectionsAsync();
            cancellationToken.ThrowIfCancellationRequested();

            await Task.WhenAll(configTask, connectionsTask);

            cancellationToken.ThrowIfCancellationRequested();

            // We can potentially see duplicate devices (if the user set their config file that way). Ignore them.
            var devices = configTask.Result.Devices.DistinctBy(x => x.DeviceID).Select(device =>
            {
                var deviceObj = new Device(device.DeviceID, device.Name);
                ItemConnectionData connectionData;
                if (connectionsTask.Result.DeviceConnections.TryGetValue(device.DeviceID, out connectionData))
                    deviceObj.SetConnected(connectionData.Address);
                return deviceObj;
            });
            this.devices = new ConcurrentDictionary<string, Device>(devices.Select(x => new KeyValuePair<string, Device>(x.DeviceId, x)));

            if (isReload)
                await this._folders.ReloadFoldersAsync(configTask.Result, tilde, cancellationToken);
            else
                await this._folders.LoadFoldersAsync(configTask.Result, tilde, cancellationToken);
        }
 public DeviceConnectedEventArgs(Device device)
 {
     this.Device = device;
 }
 public bool TryFetchDeviceById(string deviceId, out Device device)
 {
     return this.devices.TryGetValue(deviceId, out device);
 }
        private async Task LoadStartupDataAsync(CancellationToken cancellationToken)
        {
            logger.Debug("Startup Complete! Loading startup data");

            // There's a race where Syncthing died, and so we kill the API clients and set it to null,
            // but we still end up here, because threading.
            ISyncThingApiClient apiClient;
            lock (this.apiClientsLock)
            {
                cancellationToken.ThrowIfCancellationRequested();
                apiClient = this.apiClient.UnsynchronizedValue;
                if (apiClient == null)
                    throw new InvalidOperationException("ApiClient must not be null");
            }

            var configTask = apiClient.FetchConfigAsync();
            var systemTask = apiClient.FetchSystemInfoAsync();
            var versionTask = apiClient.FetchVersionAsync();
            var connectionsTask = apiClient.FetchConnectionsAsync();

            cancellationToken.ThrowIfCancellationRequested();
            await Task.WhenAll(configTask, systemTask, versionTask, connectionsTask);

            // We can potentially see duplicate devices (if the user set their config file that way). Ignore them.
            var devices = configTask.Result.Devices.DistinctBy(x => x.DeviceID).Select(device =>
            {
                var deviceObj = new Device(device.DeviceID, device.Name);
                ItemConnectionData connectionData;
                if (connectionsTask.Result.DeviceConnections.TryGetValue(device.DeviceID, out connectionData))
                    deviceObj.SetConnected(connectionData.Address);
                return deviceObj;
            });
            this.devices = new ConcurrentDictionary<string, Device>(devices.Select(x => new KeyValuePair<string, Device>(x.DeviceId, x)));

            await this._folders.LoadFoldersAsync(configTask.Result, systemTask.Result, cancellationToken);

            this.Version = versionTask.Result;

            cancellationToken.ThrowIfCancellationRequested();
            
            this.StartedTime = DateTime.UtcNow;
            this.IsDataLoaded = true;
            this.OnDataLoaded();
        }