/// <summary> /// Synchronize the media object library, starting with the root album. Optionally specify that only the /// specified album is synchronized. If <see cref="IsRecursive" /> = true, then child albums are recursively synchronized; /// otherwise, only the root album (or the specified album if that overload is used) is synchronized. /// </summary> /// <param name="synchId">A GUID that uniquely identifies the synchronization. If another synchronization is in /// progress, a <see cref="GalleryServerPro.Events.CustomExceptions.SynchronizationInProgressException" /> exception is thrown.</param> /// <param name="userName">The user name for the logged on user. This is used for the audit fields in the album /// and media objects.</param> /// <param name="album">The album to synchronize.</param> /// <exception cref="GalleryServerPro.Events.CustomExceptions.SynchronizationInProgressException"> /// Thrown if another synchronization is in progress.</exception> /// <exception cref="ArgumentNullException">Thrown when <paramref name="album" /> is null.</exception> public void Synchronize(string synchId, IAlbum album, string userName) { if (album == null) { throw new ArgumentNullException("album"); } try { Initialize(synchId, album, userName); // Will throw SynchronizationInProgressException if another is in progress. Will be caught be upstream code. var albumDirectory = new DirectoryInfo(album.FullPhysicalPathOnDisk); // Synchronize the files in this album. No recursive action. SynchronizeMediaObjectFiles(albumDirectory, album); if (IsRecursive) { // Synchronize the child directories and their files. Acts recursively. SynchronizeChildDirectories(albumDirectory, album); } Album.AssignAlbumThumbnail(album, false, true, UserName); album.SortAsync(true, UserName, true); if (_synchStatus != null) { _synchStatus.Finish(); } } catch (SynchronizationTerminationRequestedException) { // The user has canceled the synchronization. Swallow the exception and return. return; } catch (SynchronizationInProgressException) { // Another sync is in progress. We don't want the generic catch below to change the sync state, so we intercept it here. throw; } catch { if (_synchStatus != null) { UpdateStatus(0, syncState: SynchronizationState.Error, persistToDatabase: true); } throw; } finally { HelperFunctions.PurgeCache(); } }
/// <summary> /// Synchronize the media object library, starting with the root album. Optionally specify that only the /// specified album is synchronized. If <see cref="IsRecursive" /> = true, then child albums are recursively synchronized; /// otherwise, only the root album (or the specified album if that overload is used) is synchronized. /// </summary> /// <param name="synchId">A GUID that uniquely identifies the synchronization. If another synchronization is in /// progress, a <see cref="GalleryServerPro.Events.CustomExceptions.SynchronizationInProgressException" /> exception is thrown.</param> /// <param name="userName">The user name for the logged on user. This is used for the audit fields in the album /// and media objects.</param> /// <param name="album">The album to synchronize.</param> /// <exception cref="GalleryServerPro.Events.CustomExceptions.SynchronizationInProgressException"> /// Thrown if another synchronization is in progress.</exception> /// <exception cref="ArgumentNullException">Thrown when <paramref name="album" /> is null.</exception> public void Synchronize(string synchId, IAlbum album, string userName) { if (album == null) throw new ArgumentNullException("album"); try { Initialize(synchId, album, userName); // Will throw SynchronizationInProgressException if another is in progress. Will be caught be upstream code. var albumDirectory = new DirectoryInfo(album.FullPhysicalPathOnDisk); // Synchronize the files in this album. No recursive action. SynchronizeMediaObjectFiles(albumDirectory, album); if (IsRecursive) { // Synchronize the child directories and their files. Acts recursively. SynchronizeChildDirectories(albumDirectory, album); } Album.AssignAlbumThumbnail(album, false, true, UserName); album.SortAsync(true, UserName, true); if (_synchStatus != null) _synchStatus.Finish(); } catch (SynchronizationTerminationRequestedException) { // The user has canceled the synchronization. Swallow the exception and return. return; } catch (SynchronizationInProgressException) { // Another sync is in progress. We don't want the generic catch below to change the sync state, so we intercept it here. throw; } catch { if (_synchStatus != null) UpdateStatus(0, syncState: SynchronizationState.Error, persistToDatabase: true); throw; } finally { HelperFunctions.PurgeCache(); } }
/// <summary> /// Creates the media object from the file specified in <paramref name="options" />. /// </summary> /// <param name="options">The options.</param> /// <returns>List{ActionResult}.</returns> /// <exception cref="Events.CustomExceptions.GallerySecurityException">Thrown when user is not authorized to add a media object to the album.</exception> /// <remarks>This function can be invoked from a thread that does not have access to the current HTTP context (for example, when /// uploading ZIP files). Therefore, be sure nothing in this body (or the functions it calls) uses HttpContext.Current, or at /// least check it for null first.</remarks> private static List <ActionResult> CreateMediaObjectFromFile(AddMediaObjectSettings options) { string sourceFilePath = Path.Combine(AppSetting.Instance.PhysicalApplicationPath, GlobalConstants.TempUploadDirectory, options.FileNameOnServer); try { IAlbum album = AlbumController.LoadAlbumInstance(options.AlbumId, true, true); if (HttpContext.Current != null) { SecurityManager.ThrowIfUserNotAuthorized(SecurityActions.AddMediaObject, RoleController.GetGalleryServerRolesForUser(), album.Id, album.GalleryId, Utils.IsAuthenticated, album.IsPrivate, album.IsVirtualAlbum); } else { // We are extracting files from a zip archive (we know this because this is the only scenario that happens on a background // thread where HttpContext.Current is null). Tweak the security check slightly to ensure the HTTP context isn't used. // The changes are still secure because options.CurrentUserName is assigned in the server's API method. SecurityManager.ThrowIfUserNotAuthorized(SecurityActions.AddMediaObject, RoleController.GetGalleryServerRolesForUser(options.CurrentUserName), album.Id, album.GalleryId, !String.IsNullOrWhiteSpace(options.CurrentUserName), album.IsPrivate, album.IsVirtualAlbum); } var extension = Path.GetExtension(options.FileName); if (extension != null && ((extension.Equals(".zip", StringComparison.OrdinalIgnoreCase)) && (options.ExtractZipFile))) { List <ActionResult> result; // Extract the files from the zipped file. using (var zip = new ZipUtility(options.CurrentUserName, RoleController.GetGalleryServerRolesForUser(options.CurrentUserName))) { using (var fs = new FileStream(sourceFilePath, FileMode.Open, FileAccess.Read)) { result = zip.ExtractZipFile(fs, album, options.DiscardOriginalFile); } } album.SortAsync(true, options.CurrentUserName, true); return(result); } else { string albumPhysicalPath = album.FullPhysicalPathOnDisk; string filename = HelperFunctions.ValidateFileName(albumPhysicalPath, options.FileName); string filepath = Path.Combine(albumPhysicalPath, filename); MoveFile(filepath, sourceFilePath); ActionResult result = CreateMediaObject(filepath, album, options); album.Sort(true, options.CurrentUserName); return(new List <ActionResult> { result }); } } catch (Exception ex) { AppEventController.LogError(ex); return(new List <ActionResult> { new ActionResult { Title = options.FileName, Status = ActionResultStatus.Error.ToString(), Message = "The event log may have additional details." } }); } finally { try { // If the file still exists in the temp directory, delete it. Typically this happens when we've // extracted the contents of a zip file (since other files will have already been moved to the dest album.) if (File.Exists(sourceFilePath)) { File.Delete(sourceFilePath); } } catch (IOException) { } // Ignore an error; not a big deal if it continues to exist in the temp directory catch (UnauthorizedAccessException) { } // Ignore an error; not a big deal if it continues to exist in the temp directory } }