示例#1
0
        public void MigrateMediaFiles_Old(SmartObjectContext ctx)
        {
            var query = ctx.Set <MediaFile>();
            //.Where(x => x.Version == 0)
            //.Include(x => x.MediaStorage);

            var pager = new FastPager <MediaFile>(query, 1000);

            using (var scope = new DbContextScope(ctx,
                                                  hooksEnabled: false,
                                                  autoCommit: false,
                                                  proxyCreation: false,
                                                  validateOnSave: false,
                                                  lazyLoading: false))
            {
                while (pager.ReadNextPage(out var files))
                {
                    foreach (var file in files)
                    {
                        if (file.Version > 0)
                        {
                            continue;
                        }

                        if (file.Extension.IsEmpty())
                        {
                            file.Extension = MimeTypes.MapMimeTypeToExtension(file.MimeType);
                        }

                        var name = file.Name;
                        if (name.IsEmpty())
                        {
                            name = file.Id.ToString(System.Globalization.CultureInfo.InvariantCulture);
                        }
                        else
                        {
                            name = MediaHelper.NormalizeFileName(file.Name.Truncate(292));
                        }

                        file.Name         = name + "." + file.Extension;
                        file.CreatedOnUtc = file.UpdatedOnUtc;
                        file.Version      = 1;

                        ProcessMediaFile(file);
                    }

                    // Save to DB
                    int num = scope.Commit();

                    // Breathe
                    ctx.DetachEntities <MediaFile>(deep: true);
                }
            }
        }
示例#2
0
        public void MigrateMediaFiles(SmartObjectContext ctx)
        {
            var query = ctx.Set <MediaFile>()
                        //.Where(x => x.Version == 0)
                        .Include(x => x.MediaStorage);

            var pager = new FastPager <MediaFile>(query, 1000);

            using (var scope = new DbContextScope(ctx,
                                                  hooksEnabled: false,
                                                  autoCommit: false,
                                                  proxyCreation: false,
                                                  validateOnSave: false,
                                                  lazyLoading: false))
            {
                while (pager.ReadNextPage(out var files))
                {
                    foreach (var file in files)
                    {
                        if (file.Version > 0)
                        {
                            continue;
                        }

                        if (file.Extension.IsEmpty())
                        {
                            file.Extension = MimeTypes.MapMimeTypeToExtension(file.MimeType);
                        }

                        file.Name         = file.Name + "." + file.Extension;
                        file.CreatedOnUtc = file.UpdatedOnUtc;
                        file.Version      = 1;

                        ProcessMediaFile(file);
                    }

                    // Save to DB
                    int num = scope.Commit();

                    // Breathe
                    ctx.DetachEntities <MediaFile>(deep: true);
                }
            }
        }
示例#3
0
        public void MigrateUploadedFiles(SmartObjectContext ctx)
        {
            var fileSet   = ctx.Set <MediaFile>();
            var folderSet = ctx.Set <MediaFolder>();

            using (var scope = new DbContextScope(ctx,
                                                  hooksEnabled: false,
                                                  autoCommit: false,
                                                  validateOnSave: false,
                                                  lazyLoading: false,
                                                  autoDetectChanges: false))
            {
                var albumId    = _albumRegistry.GetAlbumByName(SystemAlbumProvider.Files)?.Id;
                var rootFolder = _mediaFileSystem.GetFolder("Uploaded");
                if (!rootFolder.Exists)
                {
                    return;
                }

                ProcessFolder(rootFolder, albumId.Value);

                void ProcessFolder(IFolder folder, int mediaFolderId)
                {
                    var newFiles = new List <FilePair>();

                    foreach (var uploadedFile in _mediaFileSystem.ListFiles(folder.Path))
                    {
                        var file = new MediaFile
                        {
                            CreatedOnUtc = uploadedFile.LastUpdated,
                            UpdatedOnUtc = uploadedFile.LastUpdated,
                            Extension    = uploadedFile.Extension.TrimStart('.'),
                            Name         = uploadedFile.Name,
                            MimeType     = MimeTypes.MapNameToMimeType(uploadedFile.Name),
                            Size         = Convert.ToInt32(uploadedFile.Size),
                            FolderId     = mediaFolderId,
                            Version      = 2
                        };

                        ProcessMediaFile(file);

                        newFiles.Add(new FilePair {
                            MediaFile = file, UploadedFile = uploadedFile
                        });
                        fileSet.Add(file);
                    }

                    // Process/save files of current folder
                    try
                    {
                        // Save files to DB
                        int num = scope.Commit();

                        // Copy/Move files
                        foreach (var newFile in newFiles)
                        {
                            if (_isFsProvider)
                            {
                                var newPath = GetStoragePath(newFile.MediaFile);
                                if (!_mediaFileSystem.FileExists(newPath))
                                {
                                    // TODO: (mm) (mc) should we actually MOVE the file?
                                    _mediaFileSystem.CopyFile(newFile.UploadedFile.Path, newPath);
                                }
                            }
                            else
                            {
                                _mediaStorageProvider.Save(newFile.MediaFile, MediaStorageItem.FromFile(newFile.UploadedFile));
                            }
                        }

                        if (!_isFsProvider)
                        {
                            // MediaFile.MediaStorageId has been updated, we need to save again.
                            num = scope.Commit();
                        }
                    }
                    catch
                    {
                        throw;
                    }
                    finally
                    {
                        newFiles.Clear();

                        // Breathe
                        ctx.DetachEntities <MediaFile>(deep: true);
                    }

                    foreach (var uploadedFolder in _mediaFileSystem.ListFolders(folder.Path))
                    {
                        var mediaFolder = new MediaFolder
                        {
                            Name     = uploadedFolder.Name,
                            ParentId = mediaFolderId
                        };

                        // Add folder and save ASAP, we need the folder id
                        folderSet.Add(mediaFolder);
                        ctx.SaveChanges();

                        ProcessFolder(uploadedFolder, mediaFolder.Id);
                    }
                }
            }
        }
示例#4
0
        public void MigrateMediaFiles(SmartObjectContext ctx)
        {
            string prevName  = null;
            int    fileIndex = 0;

            var query      = ctx.Set <MediaFile>().OrderBy(x => x.Name);
            var totalCount = query.Count();
            var pageSize   = Math.Max(1000, Math.Min(5000, totalCount / 200));
            var pageIndex  = 0;

            using (var scope = new DbContextScope(ctx,
                                                  hooksEnabled: false,
                                                  autoCommit: false,
                                                  proxyCreation: false,
                                                  validateOnSave: false,
                                                  lazyLoading: false))
            {
                while (true)
                {
                    var files = new PagedList <MediaFile>(query, pageIndex, pageSize);
                    if (files.Count == 0)
                    {
                        break;
                    }

                    foreach (var file in files)
                    {
                        if (file.Version > 0)
                        {
                            continue;
                        }

                        if (file.Extension.IsEmpty())
                        {
                            file.Extension = MimeTypes.MapMimeTypeToExtension(file.MimeType);
                        }

                        var name      = file.Name;
                        var fixedName = name;
                        if (name.IsEmpty())
                        {
                            name = fixedName = file.Id.ToString(System.Globalization.CultureInfo.InvariantCulture);
                        }
                        else
                        {
                            name = fixedName = MediaHelper.NormalizeFileName(file.Name.Truncate(292));
                            if (name == prevName)
                            {
                                // Make file name unique
                                fixedName = name + "-" + ++fileIndex;
                            }
                            else
                            {
                                fileIndex = 0;
                            }
                        }

                        prevName = name;

                        file.Name         = fixedName + "." + file.Extension;
                        file.CreatedOnUtc = file.UpdatedOnUtc;
                        file.Version      = 1;

                        ProcessMediaFile(file);
                    }

                    // Save to DB
                    int num = scope.Commit();

                    // Breathe
                    ctx.DetachEntities <MediaFile>(deep: true);

                    if (!files.HasNextPage)
                    {
                        break;
                    }

                    pageIndex++;
                }
            }
        }
示例#5
0
        public void MigrateDownloads(SmartObjectContext ctx)
        {
            var sql           = "SELECT * FROM [Download] WHERE [MediaFileId] IS NULL AND [UseDownloadUrl] = 0";
            var downloadStubs = ctx.SqlQuery <DownloadStub>(sql).ToDictionary(x => x.Id);

            var downloadsFolderId = _albumRegistry.GetAlbumByName(SystemAlbumProvider.Downloads)?.Id;
            var messagesFolderId  = _albumRegistry.GetAlbumByName(SystemAlbumProvider.Messages)?.Id;
            var newFiles          = new List <MediaFile>();

            using (var scope = new DbContextScope(ctx,
                                                  validateOnSave: false,
                                                  hooksEnabled: false,
                                                  autoCommit: false,
                                                  autoDetectChanges: false))
            {
                var messageTemplates = ctx.Set <MessageTemplate>()
                                       .Where(x => x.Attachment1FileId.HasValue || x.Attachment2FileId.HasValue || x.Attachment3FileId.HasValue)
                                       .ToList();

                // Key = Download.Id
                var messageTemplatesDict = new Dictionary <int, MessageTemplate>();
                foreach (var mt in messageTemplates)
                {
                    if (mt.Attachment1FileId.HasValue)
                    {
                        messageTemplatesDict[mt.Attachment1FileId.Value] = mt;
                    }
                    if (mt.Attachment2FileId.HasValue)
                    {
                        messageTemplatesDict[mt.Attachment2FileId.Value] = mt;
                    }
                    if (mt.Attachment3FileId.HasValue)
                    {
                        messageTemplatesDict[mt.Attachment3FileId.Value] = mt;
                    }
                }

                var hasPostProcessor = _isFsProvider || messageTemplatesDict.Count > 0;

                var query = ctx.Set <Download>().Where(x => x.MediaFileId == null);
                var pager = new FastPager <Download>(query, 1000);

                while (pager.ReadNextPage(out var downloads))
                {
                    foreach (var d in downloads)
                    {
                        var stub = downloadStubs.Get(d.Id);
                        if (stub == null)
                        {
                            continue;
                        }

                        if (stub.UseDownloadUrl || string.IsNullOrEmpty(stub.Extension))
                        {
                            // Something weird has happened in the past
                            continue;
                        }

                        if (stub.Filename == "undefined" || string.IsNullOrEmpty(stub.Filename))
                        {
                            stub.Filename = stub.Id.ToString(CultureInfo.InvariantCulture);
                        }

                        var isMailAttachment = false;
                        if (messageTemplatesDict.TryGetValue(stub.Id, out var mt))
                        {
                            isMailAttachment = true;
                        }

                        // Create and insert new MediaFile entity for the download
                        var file = new MediaFile
                        {
                            CreatedOnUtc   = stub.UpdatedOnUtc,
                            UpdatedOnUtc   = stub.UpdatedOnUtc,
                            Extension      = stub.Extension.TrimStart('.'),
                            Name           = stub.Filename.Truncate(292), // Extension appended later in MigrateFiles()
                            MimeType       = stub.ContentType,
                            MediaType      = MediaType.Image,             // Resolved later in MigrateFiles()
                            FolderId       = isMailAttachment ? messagesFolderId : downloadsFolderId,
                            IsTransient    = stub.IsTransient,
                            MediaStorageId = stub.MediaStorageId,
                            Version        = 0 // Ensure that this record gets processed by MigrateFiles()
                        };

                        // Assign new file to download
                        d.MediaFile = file;

                        // To be able to move files later
                        if (hasPostProcessor)
                        {
                            newFiles.Add(file);
                        }
                    }

                    // Save to DB
                    int num = scope.Commit();

                    if (hasPostProcessor)
                    {
                        var downloadsDict = downloads.ToDictionary(x => x.Id);

                        if (_isFsProvider)
                        {
                            // Copy files from "Media/Downloads" to "Media/Storage" folder
                            MoveDownloadFiles(newFiles.ToDictionary(x => x.Id), downloadsDict, downloadStubs);
                        }

                        // MessageTemplate attachments (Download > MediaFile)
                        if (messageTemplatesDict.Count > 0)
                        {
                            ReRefMessageTemplateAttachments(ctx, messageTemplatesDict, downloadsDict);
                        }

                        newFiles.Clear();
                    }

                    // Breathe
                    ctx.DetachEntities <MessageTemplate>();
                    ctx.DetachEntities <Download>(deep: true);
                }
            }
        }
        public void Migrate(IEnumerable <LocaleResourceEntry> entries, bool updateTouchedResources = false)
        {
            Guard.NotNull(entries, nameof(entries));

            if (!entries.Any() || !_languages.Any())
            {
                return;
            }

            using (var scope = new DbContextScope(_ctx, autoDetectChanges: false, hooksEnabled: false))
            {
                var langMap = _languages.ToDictionarySafe(x => x.LanguageCulture.EmptyNull().ToLower());

                var toDelete = new List <LocaleStringResource>();
                var toUpdate = new List <LocaleStringResource>();
                var toAdd    = new List <LocaleStringResource>();

                bool IsEntryValid(LocaleResourceEntry entry, Language targetLang)
                {
                    if (entry.Lang == null)
                    {
                        return(true);
                    }

                    var sourceLangCode = entry.Lang.ToLower();

                    if (targetLang != null)
                    {
                        var culture = targetLang.LanguageCulture;
                        if (culture == sourceLangCode || culture.StartsWith(sourceLangCode + "-"))
                        {
                            return(true);
                        }
                    }
                    else
                    {
                        if (langMap.ContainsKey(sourceLangCode))
                        {
                            return(true);
                        }

                        if (langMap.Keys.Any(k => k.StartsWith(sourceLangCode + "-", StringComparison.OrdinalIgnoreCase)))
                        {
                            return(true);
                        }
                    }

                    return(false);
                }

                // Remove all entries with invalid lang identifier
                var invalidEntries = entries.Where(x => !IsEntryValid(x, null));
                if (invalidEntries.Any())
                {
                    entries = entries.Except(invalidEntries).ToArray();
                }

                foreach (var lang in langMap)
                {
                    var validEntries = entries.Where(x => IsEntryValid(x, lang.Value)).ToArray();
                    foreach (var entry in validEntries)
                    {
                        var db = GetResource(entry.Key, lang.Value.Id, toAdd, out bool isLocal);

                        if (db == null && entry.Value.HasValue() && !entry.UpdateOnly)
                        {
                            // ADD action
                            toAdd.Add(new LocaleStringResource {
                                LanguageId = lang.Value.Id, ResourceName = entry.Key, ResourceValue = entry.Value
                            });
                        }

                        if (db == null)
                        {
                            continue;
                        }

                        if (entry.Value == null)
                        {
                            // DELETE action
                            if (isLocal)
                            {
                                toAdd.Remove(db);
                            }
                            else
                            {
                                toDelete.Add(db);
                            }
                        }
                        else
                        {
                            if (isLocal)
                            {
                                db.ResourceValue = entry.Value;
                                continue;
                            }

                            // UPDATE action
                            if (updateTouchedResources || !db.IsTouched.GetValueOrDefault())
                            {
                                db.ResourceValue = entry.Value;
                                toUpdate.Add(db);
                                if (toDelete.Contains(db))
                                {
                                    toDelete.Remove(db);
                                }
                            }
                        }
                    }
                }

                // add new resources to context
                _resources.AddRange(toAdd);

                // remove deleted resources
                _resources.RemoveRange(toDelete);

                // save now
                int affectedRows = _ctx.SaveChanges();

                _ctx.DetachEntities <Language>();
                _ctx.DetachEntities <LocaleStringResource>();
            }
        }
示例#7
0
        public void Migrate(IEnumerable <LocaleResourceEntry> entries, bool updateTouchedResources = false)
        {
            Guard.NotNull(entries, nameof(entries));

            if (!entries.Any() || !_languages.Any())
            {
                return;
            }

            using (var scope = new DbContextScope(_ctx, autoDetectChanges: false, hooksEnabled: false))
            {
                var langMap = _languages.ToDictionarySafe(x => x.UniqueSeoCode.EmptyNull().ToLower());

                var toDelete = new List <LocaleStringResource>();
                var toUpdate = new List <LocaleStringResource>();
                var toAdd    = new List <LocaleStringResource>();

                // remove all entries with invalid lang identifier
                var invalidEntries = entries.Where(x => x.Lang != null && !langMap.ContainsKey(x.Lang.ToLower()));
                if (invalidEntries.Any())
                {
                    entries = entries.Except(invalidEntries);
                }

                foreach (var lang in langMap)
                {
                    var validEntries = entries.Where(x => x.Lang == null || langMap[x.Lang.ToLower()].Id == lang.Value.Id);
                    foreach (var entry in validEntries)
                    {
                        var db = GetResource(entry.Key, lang.Value.Id, toAdd, out bool isLocal);

                        if (db == null && entry.Value.HasValue() && !entry.UpdateOnly)
                        {
                            // ADD action
                            toAdd.Add(new LocaleStringResource {
                                LanguageId = lang.Value.Id, ResourceName = entry.Key, ResourceValue = entry.Value
                            });
                        }

                        if (db == null)
                        {
                            continue;
                        }

                        if (entry.Value == null)
                        {
                            // DELETE action
                            if (isLocal)
                            {
                                toAdd.Remove(db);
                            }
                            else
                            {
                                toDelete.Add(db);
                            }
                        }
                        else
                        {
                            if (isLocal)
                            {
                                db.ResourceValue = entry.Value;
                                continue;
                            }

                            // UPDATE action
                            if (updateTouchedResources || !db.IsTouched.GetValueOrDefault())
                            {
                                db.ResourceValue = entry.Value;
                                toUpdate.Add(db);
                                if (toDelete.Contains(db))
                                {
                                    toDelete.Remove(db);
                                }
                            }
                        }
                    }
                }

                // add new resources to context
                _resources.AddRange(toAdd);

                // remove deleted resources
                _resources.RemoveRange(toDelete);

                // save now
                int affectedRows = _ctx.SaveChanges();

                _ctx.DetachEntities <LocaleStringResource>();
            }
        }