Skip to content

Commit

Permalink
integrate backup operation with new scriptable task (#440)
Browse files Browse the repository at this point in the history
* integrate backup operation with new scriptable task
  • Loading branch information
llali authored Aug 21, 2017
1 parent 1511f73 commit d94dda4
Show file tree
Hide file tree
Showing 12 changed files with 78 additions and 172 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -13,22 +13,19 @@
using Microsoft.SqlServer.Management.Smo;
using Microsoft.SqlTools.ServiceLayer.Admin;
using Microsoft.SqlTools.ServiceLayer.DisasterRecovery.Contracts;
using System.Globalization;
using System.Text;
using Microsoft.SqlTools.ServiceLayer.TaskServices;

namespace Microsoft.SqlTools.ServiceLayer.DisasterRecovery
{
/// <summary>
/// This class implements backup operations
/// </summary>
public class BackupOperation : IBackupOperation
public class BackupOperation : SmoScriptableTaskOperation, IBackupOperation
{
private CDataContainer dataContainer;
private ServerConnection serverConnection;
private CommonUtilities backupRestoreUtil = null;
private Backup backup = null;
private string scriptContent = "";

/// <summary>
/// Constants
Expand Down Expand Up @@ -151,40 +148,30 @@ public BackupConfigInfo CreateBackupConfigInfo(string databaseName)
return configInfo;
}

public string ScriptContent
/// <summary>
/// The error occurred during backup operation
/// </summary>
public override string ErrorMessage
{
get
{
return this.scriptContent;
}
set
{
this.scriptContent = value;
return string.Empty;
}
}

/// <summary>
/// The error occurred during backup operation
/// </summary>
public string ErrorMessage
public override Server Server
{
get
{
return string.Empty;
return this.dataContainer.Server;
}
}

public SqlTask SqlTask { get; set; }

/// <summary>
/// Execute backup
/// </summary>
public void Execute(TaskExecutionMode mode)
public override void Execute()
{
StringBuilder sb = new StringBuilder();
SqlExecutionModes oldExecutionMode = this.dataContainer.Server.ConnectionContext.SqlExecutionModes;
this.dataContainer.Server.ConnectionContext.SqlExecutionModes = (mode == TaskExecutionMode.Script) ? SqlExecutionModes.CaptureSql: SqlExecutionModes.ExecuteAndCaptureSql;
this.dataContainer.Server.ConnectionContext.CapturedSql.Clear();
this.backup = new Backup();
this.backup.Database = this.backupInfo.DatabaseName;
this.backup.Action = this.backupActionType;
Expand Down Expand Up @@ -322,24 +309,18 @@ public void Execute(TaskExecutionMode mode)
}
}

foreach (String s in this.dataContainer.Server.ConnectionContext.CapturedSql.Text)
{
sb.Append(s);
sb.Append(Environment.NewLine);
}
this.ScriptContent = sb.ToString();

}
finally
catch(Exception)
{
this.dataContainer.Server.ConnectionContext.CapturedSql.Clear();
this.dataContainer.Server.ConnectionContext.SqlExecutionModes = oldExecutionMode;
throw;
}
}

/// <summary>
/// Cancel backup
/// </summary>
public void Cancel()
public override void Cancel()
{
if (this.backup != null)
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,15 @@
//

using Microsoft.SqlTools.Hosting.Protocol.Contracts;
using Microsoft.SqlTools.ServiceLayer.TaskServices;
using Microsoft.SqlTools.ServiceLayer.Utility;

namespace Microsoft.SqlTools.ServiceLayer.DisasterRecovery.Contracts
{
/// <summary>
/// Backup parameters passed for execution and scripting
/// </summary>
public class BackupParams
public class BackupParams : IScriptableRequestParams
{
/// <summary>
/// Connection uri
Expand All @@ -23,9 +25,9 @@ public class BackupParams
public BackupInfo BackupInfo { get; set; }

/// <summary>
/// True for generating script, false for execution
///
/// </summary>
public bool IsScripting { get; set; }
public TaskExecutionMode TaskExecutionMode { get; set; }
}

/// <summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -147,20 +147,6 @@ internal IEnumerable<string> SelectedBackupSets
/// </summary>
public TaskExecutionMode TaskExecutionMode { get; set; }

/// <summary>
/// Same as Target Database name. Used by task manager to create task info
/// </summary>
public string DatabaseName
{
get
{
return TargetDatabaseName;
}
set
{
TargetDatabaseName = value;
}
}
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -225,6 +225,7 @@ internal async Task HandleRestoreRequest(
{
// create task metadata
TaskMetadata metadata = TaskMetadata.Create(restoreParams, SR.RestoreTaskName, restoreDataObject, ConnectionServiceInstance);
metadata.DatabaseName = restoreParams.TargetDatabaseName;

// create restore task and perform
SqlTask sqlTask = SqlTaskManagerInstance.CreateAndRun<SqlTask>(metadata);
Expand Down Expand Up @@ -277,23 +278,9 @@ internal async Task HandleBackupRequest(
SqlTask sqlTask = null;

// create task metadata
TaskMetadata metadata = new TaskMetadata();
metadata.ServerName = connInfo.ConnectionDetails.ServerName;
metadata.DatabaseName = connInfo.ConnectionDetails.DatabaseName;
metadata.TaskOperation = backupOperation;

if (backupParams.IsScripting)
{
metadata.Name = string.Format("{0} {1}", SR.BackupTaskName, SR.ScriptTaskName);
metadata.TaskExecutionMode = TaskExecutionMode.Script;
}
else
{
metadata.Name = SR.BackupTaskName;
metadata.TaskExecutionMode = TaskExecutionMode.ExecuteAndScript;
}

sqlTask = SqlTaskManagerInstance.CreateAndRun(metadata, this.PerformBackupTaskAsync, this.CancelBackupTaskAsync);
TaskMetadata metadata = TaskMetadata.Create(backupParams, SR.BackupTaskName, backupOperation, ConnectionServiceInstance);

sqlTask = SqlTaskManagerInstance.CreateAndRun<SqlTask>(metadata);
}
else
{
Expand Down Expand Up @@ -400,88 +387,5 @@ internal void ScriptBackup(BackupOperation backupOperation)
{
backupOperation.Execute(TaskExecutionMode.Script);
}

/// <summary>
/// Async task to execute backup
/// </summary>
/// <param name="sqlTask"></param>
/// <returns></returns>
internal async Task<TaskResult> PerformBackupTaskAsync(SqlTask sqlTask)
{
IBackupOperation backupOperation = sqlTask.TaskMetadata.TaskOperation as IBackupOperation;
TaskResult result = new TaskResult();

// Create a task to perform backup
await Task.Factory.StartNew(() =>
{
if (backupOperation != null)
{
try
{
sqlTask.AddMessage(SR.TaskInProgress, SqlTaskStatus.InProgress, true);

// Execute backup
backupOperation.Execute(sqlTask.TaskMetadata.TaskExecutionMode);

// Set result
result.TaskStatus = SqlTaskStatus.Succeeded;

// Send generated script to client
if (!String.IsNullOrEmpty(backupOperation.ScriptContent))
{
sqlTask.AddScript(result.TaskStatus, backupOperation.ScriptContent);
}
}
catch (Exception ex)
{
result.TaskStatus = SqlTaskStatus.Failed;
result.ErrorMessage = string.Format(CultureInfo.InvariantCulture, "error:{0} inner:{1} stacktrace:{2}",
ex.Message,
ex.InnerException != null ? ex.InnerException.Message : "",
ex.StackTrace);
}
}
else
{
result.TaskStatus = SqlTaskStatus.Failed;
}
});

return result;
}

/// <summary>
/// Async task to cancel backup
/// </summary>
/// <param name="sqlTask"></param>
/// <returns></returns>
internal async Task<TaskResult> CancelBackupTaskAsync(SqlTask sqlTask)
{
IBackupOperation backupOperation = sqlTask.TaskMetadata.TaskOperation as IBackupOperation;
TaskResult result = new TaskResult();

await Task.Factory.StartNew(() =>
{
if (backupOperation != null)
{
try
{
backupOperation.Cancel();
result.TaskStatus = SqlTaskStatus.Canceled;
}
catch (Exception ex)
{
result.TaskStatus = SqlTaskStatus.Failed;
result.ErrorMessage = ex.Message;
}
}
else
{
result.TaskStatus = SqlTaskStatus.Failed;
}
});

return result;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,8 @@ public interface IRestoreDatabaseTaskDataObject
string DefaultTargetDbName { get; }
string TargetDatabaseName { get; set; }

bool CanDropExistingConnections { get; }


}
/// <summary>
Expand Down Expand Up @@ -247,7 +249,6 @@ public string GetLastBackupTaken()
lastBackup = isTheLastOneSelected ?
string.Format(CultureInfo.CurrentCulture, SR.TheLastBackupTaken, (backupTimeStr)) : backupTimeStr;
}
//TODO: find the selected one
else if (GetFirstSelectedBackupSetIndex() == 0 && !this.RestorePlanner.RestoreToLastBackup)
{
lastBackup = this.CurrentRestorePointInTime.Value.ToLongDateString() +
Expand Down Expand Up @@ -1242,6 +1243,21 @@ internal bool DbFilesLocationAreValid()
return true;
}

/// <summary>
/// Returns true if can close eixisting connections for give database
/// </summary>
public bool CanDropExistingConnections
{
get
{
if (RestorePlan != null && RestorePlanner != null)
{
return RestorePlan.CanDropExistingConnections(RestorePlanner.DatabaseName);
}
return false;
}
}

/// <summary>
/// Cancels the restore operations
/// </summary>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -482,8 +482,7 @@ private RestoreOptionFactory()
{
return new OptionValidationResult()
{
//TODO: make the method public in SMO bool canDropExistingConnections = restoreDataObject.RestorePlan.CanDropExistingConnections(this.Data.RestorePlanner.DatabaseName);
IsReadOnly = false
IsReadOnly = !restoreDataObject.CanDropExistingConnections
};
},
SetValueFunction = (IRestoreDatabaseTaskDataObject restoreDataObject, object value) =>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,11 +67,7 @@ public static TaskMetadata Create(IRequestParams requestParam, string taskName,
taskMetadata.ServerName = connInfo.ConnectionDetails.ServerName;
}

if (!string.IsNullOrEmpty(requestParam.DatabaseName))
{
taskMetadata.DatabaseName = requestParam.DatabaseName;
}
else if (connInfo != null)
if (connInfo != null)
{
taskMetadata.DatabaseName = connInfo.ConnectionDetails.DatabaseName;
}
Expand Down
5 changes: 0 additions & 5 deletions src/Microsoft.SqlTools.ServiceLayer/Utility/IRequestParams.cs
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,5 @@ public interface IRequestParams
/// The Uri to find the connection to do the restore operations
/// </summary>
string OwnerUri { get; set; }

/// <summary>
/// Database name
/// </summary>
string DatabaseName { get; set; }
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -676,7 +676,7 @@ public async Task<string> CreateBackupFile()
{
OwnerUri = liveConnection.ConnectionInfo.OwnerUri,
BackupInfo = backupInfo,
IsScripting = false
TaskExecutionMode = TaskExecutionMode.Execute
};

// Backup the database
Expand Down
Loading

0 comments on commit d94dda4

Please sign in to comment.