示例#1
0
        public void CanBackupToDirectory_MultipleBackups()
        {
            var backupPath = NewDataPath("BackupFolder");

            using (var store = NewDocumentStore())
            {
                using (var session = store.OpenSession())
                {
                    session.Store(new User {
                        Name = "oren"
                    });
                    var periodicBackupSetup = new PeriodicBackupSetup
                    {
                        LocalFolderName      = backupPath,
                        IntervalMilliseconds = 25
                    };
                    session.Store(periodicBackupSetup, PeriodicBackupSetup.RavenDocumentKey);

                    session.SaveChanges();
                }
                SpinWait.SpinUntil(() =>
                {
                    var jsonDocument = store.DatabaseCommands.Get(PeriodicBackupStatus.RavenDocumentKey);
                    if (jsonDocument == null)
                    {
                        return(false);
                    }
                    var periodicBackupStatus = jsonDocument.DataAsJson.JsonDeserialization <PeriodicBackupStatus>();
                    return(periodicBackupStatus.LastDocsEtag != Etag.Empty && periodicBackupStatus.LastDocsEtag != null);
                });

                var etagForBackups = store.DatabaseCommands.Get(PeriodicBackupStatus.RavenDocumentKey).Etag;
                using (var session = store.OpenSession())
                {
                    session.Store(new User {
                        Name = "ayende"
                    });
                    session.SaveChanges();
                }
                SpinWait.SpinUntil(() =>
                                   store.DatabaseCommands.Get(PeriodicBackupStatus.RavenDocumentKey).Etag != etagForBackups);
            }

            using (var store = NewDocumentStore())
            {
                var smugglerOptions = new SmugglerOptions
                {
                    BackupPath = backupPath
                };
                var dataDumper = new DataDumper(store.DocumentDatabase, smugglerOptions);
                dataDumper.ImportData(smugglerOptions, true).Wait();

                using (var session = store.OpenSession())
                {
                    Assert.Equal("oren", session.Load <User>(1).Name);
                    Assert.Equal("ayende", session.Load <User>(2).Name);
                }
            }
            IOExtensions.DeleteDirectory(backupPath);
        }
        public override void CheckForChanges()
        {
            if (HasUnsavedChanges)
            {
                return;
            }

            if (PeriodicBackupSettings.Equals(OriginalPeriodicBackupSettings) == false)
            {
                HasUnsavedChanges = true;
                return;
            }
            if (PeriodicBackupSetup == null)
            {
                if (OriginalPeriodicBackupSetup == null)
                {
                    return;
                }
                HasUnsavedChanges = true;
                return;
            }

            if (PeriodicBackupSetup.Equals(OriginalPeriodicBackupSetup) == false)
            {
                HasUnsavedChanges = true;
            }
        }
示例#3
0
        private void UploadToGlacier(string backupPath, PeriodicBackupSetup localBackupConfigs)
        {
            var awsRegion = RegionEndpoint.GetBySystemName(localBackupConfigs.AwsRegionEndpoint) ?? RegionEndpoint.USEast1;
            var manager   = new ArchiveTransferManager(awsAccessKey, awsSecretKey, awsRegion);
            var archiveId = manager.Upload(localBackupConfigs.GlacierVaultName, GetArchiveDescription(), backupPath).ArchiveId;

            logger.Info(string.Format("Successfully uploaded backup {0} to Glacier, archive ID: {1}", Path.GetFileName(backupPath),
                                      archiveId));
        }
示例#4
0
        public void CanBackupToDirectory_MultipleBackups()
        {
            var backupPath = GetPath("BackupFolder");

            using (var store = NewDocumentStore())
            {
                Guid?etagForBackups;
                using (var session = store.OpenSession())
                {
                    session.Store(new User {
                        Name = "oren"
                    });
                    var periodicBackupSetup = new PeriodicBackupSetup
                    {
                        LocalFolderName      = backupPath,
                        IntervalMilliseconds = 25
                    };
                    session.Store(periodicBackupSetup, PeriodicBackupSetup.RavenDocumentKey);

                    session.SaveChanges();

                    etagForBackups = session.Advanced.GetEtagFor(periodicBackupSetup);
                }
                SpinWait.SpinUntil(() =>
                                   store.DatabaseCommands.Get(PeriodicBackupSetup.RavenDocumentKey).Etag != etagForBackups);

                etagForBackups = store.DatabaseCommands.Get(PeriodicBackupSetup.RavenDocumentKey).Etag;
                using (var session = store.OpenSession())
                {
                    session.Store(new User {
                        Name = "ayende"
                    });
                    session.SaveChanges();
                }
                SpinWait.SpinUntil(() =>
                                   store.DatabaseCommands.Get(PeriodicBackupSetup.RavenDocumentKey).Etag != etagForBackups);
            }

            using (var store = NewDocumentStore())
            {
                var smugglerOptions = new SmugglerOptions
                {
                    BackupPath = backupPath
                };
                var dataDumper = new DataDumper(store.DocumentDatabase, smugglerOptions);
                dataDumper.ImportData(smugglerOptions, true);

                using (var session = store.OpenSession())
                {
                    Assert.Equal("oren", session.Load <User>(1).Name);
                    Assert.Equal("ayende", session.Load <User>(2).Name);
                }
            }
            IOExtensions.DeleteDirectory(backupPath);
        }
示例#5
0
 private void UploadToServer(string backupPath, PeriodicBackupSetup localBackupConfigs)
 {
     if (!string.IsNullOrWhiteSpace(localBackupConfigs.GlacierVaultName))
     {
         UploadToGlacier(backupPath, localBackupConfigs);
     }
     else if (!string.IsNullOrWhiteSpace(localBackupConfigs.S3BucketName))
     {
         UploadToS3(backupPath, localBackupConfigs);
     }
 }
示例#6
0
        private void ReadSetupValuesFromDocument()
        {
            using (LogContext.WithDatabase(Database.Name))
            {
                try
                {
                    // Not having a setup doc means this DB isn't enabled for periodic backups
                    var document = Database.Get(PeriodicBackupSetup.RavenDocumentKey, null);
                    if (document == null)
                    {
                        backupConfigs = null;
                        backupStatus  = null;
                        return;
                    }

                    var status = Database.Get(PeriodicBackupStatus.RavenDocumentKey, null);

                    backupStatus  = status == null ? new PeriodicBackupStatus() : status.DataAsJson.JsonDeserialization <PeriodicBackupStatus>();
                    backupConfigs = document.DataAsJson.JsonDeserialization <PeriodicBackupSetup>();
                    if (backupConfigs.IntervalMilliseconds <= 0)
                    {
                        logger.Warn("Periodic backup interval is set to zero or less, periodic backup is now disabled");
                        return;
                    }

                    awsAccessKey        = Database.Configuration.Settings["Raven/AWSAccessKey"];
                    awsSecretKey        = Database.Configuration.Settings["Raven/AWSSecretKey"];
                    azureStorageAccount = Database.Configuration.Settings["Raven/AzureStorageAccount"];
                    azureStorageKey     = Database.Configuration.Settings["Raven/AzureStorageKey"];

                    var interval = TimeSpan.FromMilliseconds(backupConfigs.IntervalMilliseconds);
                    logger.Info("Periodic backups started, will backup every" + interval.TotalMinutes + "minutes");

                    var timeSinceLastBackup = DateTime.UtcNow - backupStatus.LastBackup;
                    var nextBackup          = timeSinceLastBackup >= interval ? TimeSpan.Zero : interval - timeSinceLastBackup;
                    timer = new Timer(TimerCallback, null, nextBackup, interval);
                }
                catch (Exception ex)
                {
                    logger.ErrorException("Could not read periodic backup config", ex);
                    Database.AddAlert(new Alert
                    {
                        AlertLevel = AlertLevel.Error,
                        CreatedAt  = SystemTime.UtcNow,
                        Message    = ex.Message,
                        Title      = "Could not read periodic backup config",
                        Exception  = ex.ToString(),
                        UniqueKey  = "Periodic Backup Config Error"
                    });
                }
            }
        }
示例#7
0
        private void ReadSetupValuesFromDocument()
        {
            using (LogManager.OpenMappedContext("database", Database.Name ?? Constants.SystemDatabase))
                using (new DisposableAction(() => LogContext.DatabaseName.Value = null))
                {
                    LogContext.DatabaseName.Value = Database.Name;

                    try
                    {
                        // Not having a setup doc means this DB isn't enabled for periodic backups
                        var document = Database.Get(PeriodicBackupSetup.RavenDocumentKey, null);
                        if (document == null)
                        {
                            backupConfigs = null;
                            return;
                        }

                        backupConfigs = document.DataAsJson.JsonDeserialization <PeriodicBackupSetup>();
                        if (backupConfigs.IntervalMilliseconds <= 0)
                        {
                            logger.Warn("Peridoic backup interval is set to zero or less, periodic backup is now disabled");
                            return;
                        }

                        awsAccessKey = Database.Configuration.Settings["Raven/AWSAccessKey"];
                        awsSecretKey = Database.Configuration.Settings["Raven/AWSSecretKey"];

                        var interval = TimeSpan.FromMilliseconds(backupConfigs.IntervalMilliseconds);
                        logger.Info("Periodic backups started, will backup every" + interval.TotalMinutes + "minutes");
                        timer = new Timer(TimerCallback, null, TimeSpan.Zero, interval);
                    }
                    catch (Exception ex)
                    {
                        logger.ErrorException("Could not read periodic backup config", ex);
                        Database.AddAlert(new Alert
                        {
                            AlertLevel = AlertLevel.Error,
                            CreatedAt  = SystemTime.UtcNow,
                            Message    = ex.Message,
                            Title      = "Error in Periodic Backup",
                            Exception  = ex
                        });
                    }
                }
        }
示例#8
0
        private void UploadToS3(string backupPath, PeriodicBackupSetup localBackupConfigs)
        {
            var awsRegion = RegionEndpoint.GetBySystemName(localBackupConfigs.AwsRegionEndpoint) ?? RegionEndpoint.USEast1;

            using (var client = new Amazon.S3.AmazonS3Client(awsAccessKey, awsSecretKey, awsRegion))
                using (var fileStream = File.OpenRead(backupPath))
                {
                    var key     = Path.GetFileName(backupPath);
                    var request = new PutObjectRequest();
                    request.WithMetaData("Description", GetArchiveDescription());
                    request.WithInputStream(fileStream);
                    request.WithBucketName(localBackupConfigs.S3BucketName);
                    request.WithKey(key);

                    using (client.PutObject(request))
                    {
                        logger.Info(string.Format("Successfully uploaded backup {0} to S3 bucket {1}, with key {2}",
                                                  Path.GetFileName(backupPath), localBackupConfigs.S3BucketName, key));
                    }
                }
        }
示例#9
0
        public void CanBackupToDirectory()
        {
            var backupPath = NewDataPath("BackupFolder");

            using (var store = NewDocumentStore())
            {
                using (var session = store.OpenSession())
                {
                    session.Store(new User {
                        Name = "oren"
                    });
                    var periodicBackupSetup = new PeriodicBackupSetup
                    {
                        LocalFolderName      = backupPath,
                        IntervalMilliseconds = 25
                    };
                    session.Store(periodicBackupSetup, PeriodicBackupSetup.RavenDocumentKey);

                    session.SaveChanges();
                }
                SpinWait.SpinUntil(() =>
                                   store.DatabaseCommands.Get(PeriodicBackupStatus.RavenDocumentKey) != null, 10000);
            }

            using (var store = NewDocumentStore())
            {
                var smugglerOptions = new SmugglerOptions
                {
                    BackupPath = backupPath
                };
                var dataDumper = new DataDumper(store.DocumentDatabase, smugglerOptions);
                dataDumper.ImportData(smugglerOptions, true).Wait();

                using (var session = store.OpenSession())
                {
                    Assert.Equal("oren", session.Load <User>(1).Name);
                }
            }
            IOExtensions.DeleteDirectory(backupPath);
        }
示例#10
0
        public static void ConfigurePeriodicBackup(this IDocumentStore store, ErrorditeConfiguration configuration, string databaseName)
        {
            using (var session = store.OpenSession(databaseName))
            {
                session.Advanced.UseOptimisticConcurrency = true;

                var backupDoc = session.Load <PeriodicBackupSetup>(PeriodicBackupSetup.RavenDocumentKey);

                if (backupDoc == null)
                {
                    backupDoc = new PeriodicBackupSetup
                    {
                        IntervalMilliseconds = configuration.RavenBackupInterval,
                        AwsRegionEndpoint    = RegionEndpoint.EUWest1.SystemName,
                        S3BucketName         = databaseName,
                    };

                    session.Store(backupDoc, PeriodicBackupSetup.RavenDocumentKey);
                    session.SaveChanges();
                }
            }
        }
示例#11
0
        private void DoUpload(string backupPath, PeriodicBackupSetup backupConfigs)
        {
            var AWSRegion = RegionEndpoint.GetBySystemName(backupConfigs.AwsRegionEndpoint) ?? RegionEndpoint.USEast1;

            var desc = string.Format("Raven.Database.Backup {0} {1}", Database.Name,
                                     DateTimeOffset.UtcNow.ToString("u"));

            if (!string.IsNullOrWhiteSpace(backupConfigs.GlacierVaultName))
            {
                var manager   = new ArchiveTransferManager(awsAccessKey, awsSecretKey, AWSRegion);
                var archiveId = manager.Upload(backupConfigs.GlacierVaultName, desc, backupPath).ArchiveId;
                logger.Info(string.Format("Successfully uploaded backup {0} to Glacier, archive ID: {1}", Path.GetFileName(backupPath),
                                          archiveId));
                return;
            }

            if (!string.IsNullOrWhiteSpace(backupConfigs.S3BucketName))
            {
                var client = new Amazon.S3.AmazonS3Client(awsAccessKey, awsSecretKey, AWSRegion);

                using (var fileStream = File.OpenRead(backupPath))
                {
                    var key     = Path.GetFileName(backupPath);
                    var request = new PutObjectRequest();
                    request.WithMetaData("Description", desc);
                    request.WithInputStream(fileStream);
                    request.WithBucketName(backupConfigs.S3BucketName);
                    request.WithKey(key);

                    using (S3Response _ = client.PutObject(request))
                    {
                        logger.Info(string.Format("Successfully uploaded backup {0} to S3 bucket {1}, with key {2}",
                                                  Path.GetFileName(backupPath), backupConfigs.S3BucketName, key));
                        return;
                    }
                }
            }
        }
示例#12
0
        private void UploadToAzure(string backupPath, PeriodicBackupSetup localBackupConfigs)
        {
            StorageCredentials  storageCredentials = new StorageCredentials(azureStorageAccount, azureStorageKey);
            CloudStorageAccount storageAccount     = new CloudStorageAccount(storageCredentials, true);
            CloudBlobClient     blobClient         = new CloudBlobClient(storageAccount.BlobEndpoint, storageCredentials);
            CloudBlobContainer  backupContainer    = blobClient.GetContainerReference(localBackupConfigs.AzureStorageContainer);

            backupContainer.CreateIfNotExists();
            using (var fileStream = File.OpenRead(backupPath))
            {
                var            key        = Path.GetFileName(backupPath);
                CloudBlockBlob backupBlob = backupContainer.GetBlockBlobReference(key);
                backupBlob.Metadata.Add("Description", this.GetArchiveDescription());
                backupBlob.UploadFromStream(fileStream);
                backupBlob.SetMetadata();

                this.logger.Info(string.Format(
                                     "Successfully uploaded backup {0} to Azure container {1}, with key {2}",
                                     Path.GetFileName(backupPath),
                                     localBackupConfigs.AzureStorageContainer,
                                     key));
            }
        }
        public override void LoadFor(DatabaseDocument document)
        {
            PeriodicBackupSettings = new PeriodicBackupSettings();
            var session = ApplicationModel.Current.Server.Value.DocumentStore
                          .OpenAsyncSession(ApplicationModel.Current.Server.Value.SelectedDatabase.Value.Name);

            if (document.Settings.ContainsKey("Raven/AWSAccessKey") && document.SecuredSettings.ContainsKey("Raven/AWSSecretKey"))
            {
                PeriodicBackupSettings.AwsAccessKey = document.Settings["Raven/AWSAccessKey"];
                PeriodicBackupSettings.AwsSecretKey = document.SecuredSettings["Raven/AWSSecretKey"];
            }

            if (document.Settings.ContainsKey("Raven/AzureStorageAccount") && document.SecuredSettings.ContainsKey("Raven/AzureStorageKey"))
            {
                PeriodicBackupSettings.AzureStorageAccount = document.Settings["Raven/AzureStorageAccount"];
                PeriodicBackupSettings.AzureStorageKey     = document.SecuredSettings["Raven/AzureStorageKey"];
            }

            OriginalPeriodicBackupSettings = new PeriodicBackupSettings
            {
                AwsAccessKey        = PeriodicBackupSettings.AwsAccessKey,
                AwsSecretKey        = PeriodicBackupSettings.AwsSecretKey,
                AzureStorageAccount = PeriodicBackupSettings.AzureStorageAccount,
                AzureStorageKey     = PeriodicBackupSettings.AzureStorageKey
            };

            session.LoadAsync <PeriodicBackupSetup>(PeriodicBackupSetup.RavenDocumentKey).ContinueWith(task =>
            {
                PeriodicBackupSetup = task.Result;

                if (PeriodicBackupSetup == null)
                {
                    return;
                }

                OriginalPeriodicBackupSetup = new PeriodicBackupSetup
                {
                    AwsRegionEndpoint     = PeriodicBackupSetup.AwsRegionEndpoint,
                    AzureStorageContainer = PeriodicBackupSetup.AzureStorageContainer,
                    GlacierVaultName      = PeriodicBackupSetup.GlacierVaultName,
                    IntervalMilliseconds  = PeriodicBackupSetup.IntervalMilliseconds,
                    LocalFolderName       = PeriodicBackupSetup.LocalFolderName,
                    S3BucketName          = PeriodicBackupSetup.S3BucketName
                };

                HasDocument = true;
                if (string.IsNullOrWhiteSpace(PeriodicBackupSetup.LocalFolderName) == false)
                {
                    SelectedOption.Value = 0;
                }
                else if (string.IsNullOrWhiteSpace(PeriodicBackupSetup.GlacierVaultName) == false)
                {
                    SelectedOption.Value = 1;
                }
                else if (string.IsNullOrWhiteSpace(PeriodicBackupSetup.S3BucketName) == false)
                {
                    SelectedOption.Value = 2;
                }
                else if (string.IsNullOrWhiteSpace(PeriodicBackupSetup.AzureStorageContainer) == false)
                {
                    SelectedOption.Value = 3;
                }
                OnPropertyChanged(() => HasDocument);
                OnPropertyChanged(() => PeriodicBackupSetup);
            });
        }