public async Task <bool> DeleteEGSResource(int taskID, RoutedItem routedItem, LITEConnection connection, IHttpManager httpManager) { Connection = connection; var taskInfo = $"task: {taskID} connection: {Connection.name}"; HttpResponseMessage response = null; //string resourceURL = Connection.URL + "/api/File/" + routedItem.box + "/" + routedItem.resource; string resourceURL = Connection.URL + FileAgentConstants.GetDeleteUrl(routedItem); var httpClient = _liteHttpClient.GetClient(Connection); try { var stopWatch = new Stopwatch(); stopWatch.Start(); //set the URL _logger.Log(LogLevel.Debug, $"{taskInfo} URL: {resourceURL}"); // issue the POST Task <HttpResponseMessage> task; task = httpClient.DeleteAsync(resourceURL, _taskManager.cts.Token); response = await task.ConfigureAwait(false); // output the result _logger.LogHttpResponseAndHeaders(response, taskInfo); stopWatch.Stop(); _logger.Log(LogLevel.Information, $"{taskInfo} elapsed: {stopWatch.Elapsed}"); switch (response.StatusCode) { case HttpStatusCode.NoContent: return(true); default: if (response.StatusCode == HttpStatusCode.Unauthorized) { httpManager.loginNeeded = true; } _logger.Log(LogLevel.Warning, $"Deletion of {resourceURL} failed with {response.StatusCode}"); _liteHttpClient.DumpHttpClientDetails(); return(false); } } catch (TaskCanceledException) { _logger.Log(LogLevel.Information, $"Task was canceled."); } catch (HttpRequestException e) { _logger.Log(LogLevel.Warning, $"{taskInfo} Exception: {e.Message} {e.StackTrace}"); if (e.InnerException != null) { _logger.Log(LogLevel.Warning, $"Inner Exception: {e.InnerException}"); } _liteHttpClient.DumpHttpClientDetails(); } catch (FileNotFoundException e) { _logger.Log(LogLevel.Warning, $"{taskInfo} {e.Message} {e.StackTrace}"); } catch (IOException e) { _logger.Log(LogLevel.Warning, $"{taskInfo} {e.Message} {e.StackTrace}"); } catch (Exception e) { _logger.LogFullException(e, taskInfo); _liteHttpClient.DumpHttpClientDetails(); } finally { if (response != null) { response.Dispose(); } } return(false); }
/// <summary> /// wado downloads studies from liCloud. ImagingStudy is required while Series and Instance are optional. RAM utilization remains low regardless of download size. /// </summary> /// <param name="taskID"></param> /// <param name="routedItem"></param> /// <param name="connection"></param> /// <param name="httpManager"></param> /// <param name="compress"></param> /// <returns></returns> public async Task DownloadViaHttp(int taskID, RoutedItem routedItem, LITEConnection connection, IHttpManager httpManager, bool compress = true) { Connection = connection; var taskInfo = $"task: {taskID} connection: {Connection.name} resource: {routedItem.resource}"; var profile = _profileStorage.Current; var stopWatch = new Stopwatch(); stopWatch.Start(); //string url = Connection.URL + $"/api/File/{routedItem.box}/{routedItem.resource}"; string url = Connection.URL + FileAgentConstants.GetDownloadUrl(routedItem); string dir = profile.tempPath + Path.DirectorySeparatorChar + Connection.name + Path.DirectorySeparatorChar + Constants.Dirs.ToRules + Path.DirectorySeparatorChar + Guid.NewGuid(); Directory.CreateDirectory(dir); long fileSize = 0; HttpResponseMessage response = null; MultipartFileStreamProvider streamProvider = null; MultipartFileStreamProvider contents = null; var httpClient = _liteHttpClient.GetClient(connection); try { _logger.Log(LogLevel.Debug, $"{taskInfo} download dir will be {dir}"); _logger.Log(LogLevel.Debug, $"{taskInfo} url: {url} attempt: {routedItem.attempts}"); var cookies = _liteHttpClient.GetCookies(url); _logger.LogCookies(cookies, taskInfo); // issue the GET var task = httpClient.GetAsync(url, HttpCompletionOption.ResponseHeadersRead, _taskManager.cts.Token); try { response = await task.ConfigureAwait(false); } catch (TaskCanceledException) { _logger.Log(LogLevel.Information, $"{taskInfo} Task Canceled"); } // output the result _logger.LogHttpResponseAndHeaders(response, taskInfo); //if(Logger.logger.FileTraceLevel == "Verbose") _logger.Log(LogLevel.Debug,$"{taskInfo} await response.Content.ReadAsStringAsync(): {await response.Content.ReadAsStringAsync()}"); switch (response.StatusCode) { case HttpStatusCode.OK: break; case HttpStatusCode.NotFound: routedItem.Error = HttpStatusCode.NotFound.ToString(); _routedItemManager.Init(routedItem); _routedItemManager.Dequeue(Connection, Connection.fromEGS, nameof(Connection.fromEGS), error: true); return; case HttpStatusCode.Unauthorized: httpManager.loginNeeded = true; _liteHttpClient.DumpHttpClientDetails(); return; default: _liteHttpClient.DumpHttpClientDetails(); return; } if (!_util.IsDiskAvailable(dir, profile, routedItem.length)) { _logger.Log(LogLevel.Debug, $"{taskInfo} Insufficient disk to write {url} to {dir} guessing it could be 16GB"); return; } streamProvider = new MultipartFileStreamProvider(dir, 1024000); try { contents = await response.Content.ReadAsMultipartAsync(streamProvider, _taskManager.cts.Token).ConfigureAwait(false); } catch (Exception e) { //MIME is corrupt such as Unexpected end of MIME multipart stream. MIME multipart message is not complete. //This usually happens if the upload does not complete. Catch as "normal" and remove resource as if success //since retrying will not help this condition. _logger.LogFullException(e, taskInfo); _liteHttpClient.DumpHttpClientDetails(); if (await _deleteEGSResourceService.DeleteEGSResource(taskID, routedItem, connection, httpManager).ConfigureAwait(false)) { _routedItemManager.Init(routedItem); _routedItemManager.Dequeue(Connection, Connection.fromEGS, nameof(Connection.fromEGS), error: false); } else { routedItem.Error = "Unable to delete EGS resource"; _routedItemManager.Init(routedItem); _routedItemManager.Dequeue(Connection, Connection.fromEGS, nameof(Connection.fromEGS), error: true); } return; } int index = 0; _logger.Log(LogLevel.Debug, $"{taskInfo} Splitting {contents?.FileData.Count} files into RoutedItems."); foreach (var part in contents.FileData) { try { index++; fileSize += new FileInfo(part.LocalFileName).Length; _logger.Log(LogLevel.Debug, $"{taskInfo} downloaded file: {part.LocalFileName}"); RoutedItem ri = new RoutedItem(fromConnection: Connection.name, sourceFileName: part.LocalFileName, taskID: taskID, fileIndex: index, fileCount: contents.FileData.Count) { type = RoutedItem.Type.FILE }; _logger.Log(LogLevel.Debug, $"{taskInfo} Enqueuing RoutedItem {routedItem.sourceFileName}"); _routedItemManager.Init(ri); _routedItemManager.Enqueue(Connection, Connection.toRules, nameof(Connection.toRules)); } catch (Exception e) { _logger.LogFullException(e, taskInfo); } } if (await _deleteEGSResourceService.DeleteEGSResource(taskID, routedItem, connection, httpManager).ConfigureAwait(false)) { _routedItemManager.Init(routedItem); _routedItemManager.Dequeue(Connection, Connection.fromEGS, nameof(Connection.fromEGS), error: false); } else { routedItem.Error = "Unable to delete EGS resource"; _routedItemManager.Init(routedItem); _routedItemManager.Dequeue(Connection, Connection.fromEGS, nameof(Connection.fromEGS), error: true); } } catch (TaskCanceledException) { _logger.Log(LogLevel.Information, $"Task was canceled."); } catch (NullReferenceException e) { _logger.Log(LogLevel.Warning, $"{taskInfo} Exception: {e.Message} {e.StackTrace}"); //throw e; } catch (HttpRequestException e) { _logger.Log(LogLevel.Warning, $"{taskInfo} Exception: {e.Message} {e.StackTrace}"); if (e.InnerException != null) { _logger.Log(LogLevel.Warning, $"Inner Exception: {e.InnerException}"); } _liteHttpClient.DumpHttpClientDetails(); } catch (Exception e) { _logger.LogFullException(e, taskInfo); _liteHttpClient.DumpHttpClientDetails(); } finally { if (response != null) { response.Dispose(); } _taskManager.Stop($"{Connection.name}.DownloadViaHttp"); } stopWatch.Stop(); _logger.Log(LogLevel.Information, $"{taskInfo} elapsed: {stopWatch.Elapsed} size: {fileSize} rate: {(float)fileSize / stopWatch.Elapsed.TotalMilliseconds * 1000 / 1000000} MB/s"); }