support save/script/report operations for table designer (#1348)

* save changes

* rename

* new version of dacfx
This commit is contained in:
Alan Ren
2021-12-21 15:31:44 -08:00
committed by GitHub
parent 8d7976dd14
commit 5ca4054582
7 changed files with 88 additions and 32 deletions

View File

@@ -20,7 +20,7 @@
<PackageReference Update="Microsoft.Data.SqlClient.AlwaysEncrypted.AzureKeyVaultProvider" Version="1.1.1" /> <PackageReference Update="Microsoft.Data.SqlClient.AlwaysEncrypted.AzureKeyVaultProvider" Version="1.1.1" />
<PackageReference Update="Microsoft.Data.SqlClient" Version="3.0.0"/> <PackageReference Update="Microsoft.Data.SqlClient" Version="3.0.0"/>
<PackageReference Update="Microsoft.SqlServer.SqlManagementObjects" Version="161.46367.54" /> <PackageReference Update="Microsoft.SqlServer.SqlManagementObjects" Version="161.46367.54" />
<PackageReference Update="Microsoft.SqlServer.DACFx" Version="160.5339.7-preview" GeneratePathProperty="true" /> <PackageReference Update="Microsoft.SqlServer.DACFx" Version="160.5371.2-preview" GeneratePathProperty="true" />
<PackageReference Update="Microsoft.Azure.Kusto.Data" Version="9.0.4" /> <PackageReference Update="Microsoft.Azure.Kusto.Data" Version="9.0.4" />
<PackageReference Update="Microsoft.Azure.Kusto.Language" Version="9.0.4"/> <PackageReference Update="Microsoft.Azure.Kusto.Language" Version="9.0.4"/>
<PackageReference Update="Microsoft.SqlServer.Assessment" Version="[1.0.305]" /> <PackageReference Update="Microsoft.SqlServer.Assessment" Version="[1.0.305]" />

View File

@@ -0,0 +1,21 @@
//
// Copyright (c) Microsoft. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
//
using Microsoft.SqlTools.Hosting.Protocol.Contracts;
using Microsoft.SqlTools.Utility;
namespace Microsoft.SqlTools.ServiceLayer.TableDesigner.Contracts
{
/// <summary>
/// The service request to generate report for the changes.
/// </summary>
public class GenerateReportRequest
{
/// <summary>
/// Request definition
/// </summary>
public static readonly RequestType<TableInfo, string> Type = RequestType<TableInfo, string>.Create("tabledesigner/report");
}
}

View File

@@ -0,0 +1,21 @@
//
// Copyright (c) Microsoft. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
//
using Microsoft.SqlTools.Hosting.Protocol.Contracts;
using Microsoft.SqlTools.Utility;
namespace Microsoft.SqlTools.ServiceLayer.TableDesigner.Contracts
{
/// <summary>
/// The service request to generate script for the changes.
/// </summary>
public class GenerateScriptRequest
{
/// <summary>
/// Request definition
/// </summary>
public static readonly RequestType<TableInfo, string> Type = RequestType<TableInfo, string>.Create("tabledesigner/script");
}
}

View File

@@ -8,13 +8,13 @@ using Microsoft.SqlTools.Hosting.Protocol.Contracts;
namespace Microsoft.SqlTools.ServiceLayer.TableDesigner.Contracts namespace Microsoft.SqlTools.ServiceLayer.TableDesigner.Contracts
{ {
/// <summary> /// <summary>
/// The service request to get the designer information about a table. /// The service request to initialize a table designer.
/// </summary> /// </summary>
public class GetTableDesignerInfoRequest public class InitializeTableDesignerRequest
{ {
/// <summary> /// <summary>
/// Request definition /// Request definition
/// </summary> /// </summary>
public static readonly RequestType<TableInfo, TableDesignerInfo> Type = RequestType<TableInfo, TableDesignerInfo>.Create("tabledesigner/gettabledesignerinfo"); public static readonly RequestType<TableInfo, TableDesignerInfo> Type = RequestType<TableInfo, TableDesignerInfo>.Create("tabledesigner/initialize");
} }
} }

View File

@@ -13,8 +13,6 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner.Contracts
public TableInfo TableInfo { get; set; } public TableInfo TableInfo { get; set; }
public TableDesignerChangeInfo TableChangeInfo { get; set; } public TableDesignerChangeInfo TableChangeInfo { get; set; }
public TableViewModel ViewModel { get; set; }
} }
public class ProcessTableDesignerEditResponse public class ProcessTableDesignerEditResponse

View File

@@ -8,13 +8,6 @@ using Microsoft.SqlTools.Utility;
namespace Microsoft.SqlTools.ServiceLayer.TableDesigner.Contracts namespace Microsoft.SqlTools.ServiceLayer.TableDesigner.Contracts
{ {
public class SaveTableChangesRequestParams : GeneralRequestDetails
{
public TableInfo TableInfo { get; set; }
public TableViewModel ViewModel { get; set; }
}
public class SaveTableChangesResponse public class SaveTableChangesResponse
{ {
} }
@@ -27,6 +20,6 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner.Contracts
/// <summary> /// <summary>
/// Request definition /// Request definition
/// </summary> /// </summary>
public static readonly RequestType<SaveTableChangesRequestParams, SaveTableChangesResponse> Type = RequestType<SaveTableChangesRequestParams, SaveTableChangesResponse>.Create("tabledesigner/savechanges"); public static readonly RequestType<TableInfo, SaveTableChangesResponse> Type = RequestType<TableInfo, SaveTableChangesResponse>.Create("tabledesigner/save");
} }
} }

View File

@@ -20,7 +20,7 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
/// </summary> /// </summary>
public sealed class TableDesignerService : IDisposable public sealed class TableDesignerService : IDisposable
{ {
private Dictionary<string, Dac.TableDesignerViewModel> idTableMap = new Dictionary<string, Dac.TableDesignerViewModel>(); private Dictionary<string, Dac.TableDesigner> idTableMap = new Dictionary<string, Dac.TableDesigner>();
private bool disposed = false; private bool disposed = false;
private static readonly Lazy<TableDesignerService> instance = new Lazy<TableDesignerService>(() => new TableDesignerService()); private static readonly Lazy<TableDesignerService> instance = new Lazy<TableDesignerService>(() => new TableDesignerService());
@@ -51,9 +51,11 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
this.ServiceHost = serviceHost; this.ServiceHost = serviceHost;
this.ServiceHost.SetRequestHandler(GetTableDesignerInfoRequest.Type, HandleGetTableDesignerInfoRequest); this.ServiceHost.SetRequestHandler(InitializeTableDesignerRequest.Type, HandleInitializeTableDesignerRequest);
this.ServiceHost.SetRequestHandler(ProcessTableDesignerEditRequest.Type, HandleProcessTableDesignerEditRequest); this.ServiceHost.SetRequestHandler(ProcessTableDesignerEditRequest.Type, HandleProcessTableDesignerEditRequest);
this.ServiceHost.SetRequestHandler(SaveTableChangesRequest.Type, HandleSaveTableChangesRequest); this.ServiceHost.SetRequestHandler(SaveTableChangesRequest.Type, HandleSaveTableChangesRequest);
this.ServiceHost.SetRequestHandler(GenerateScriptRequest.Type, HandleGenerateScriptRequest);
this.ServiceHost.SetRequestHandler(GenerateReportRequest.Type, HandleGenerateReportRequest);
this.ServiceHost.SetRequestHandler(DisposeTableDesignerRequest.Type, HandleDisposeTableDesignerRequest); this.ServiceHost.SetRequestHandler(DisposeTableDesignerRequest.Type, HandleDisposeTableDesignerRequest);
} }
private Task HandleRequest<T>(RequestContext<T> requestContext, Func<Task> action) private Task HandleRequest<T>(RequestContext<T> requestContext, Func<Task> action)
@@ -74,14 +76,14 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
return Task.CompletedTask; return Task.CompletedTask;
} }
private Task HandleGetTableDesignerInfoRequest(TableInfo tableInfo, RequestContext<TableDesignerInfo> requestContext) private Task HandleInitializeTableDesignerRequest(TableInfo tableInfo, RequestContext<TableDesignerInfo> requestContext)
{ {
return this.HandleRequest<TableDesignerInfo>(requestContext, async () => return this.HandleRequest<TableDesignerInfo>(requestContext, async () =>
{ {
var connectinStringbuilder = new SqlConnectionStringBuilder(tableInfo.ConnectionString); var connectinStringbuilder = new SqlConnectionStringBuilder(tableInfo.ConnectionString);
connectinStringbuilder.InitialCatalog = tableInfo.Database; connectinStringbuilder.InitialCatalog = tableInfo.Database;
var connectionString = connectinStringbuilder.ToString(); var connectionString = connectinStringbuilder.ToString();
var table = new Dac.TableDesignerViewModel(connectionString, tableInfo.Schema, tableInfo.Name, tableInfo.IsNewTable); var table = new Dac.TableDesigner(connectionString, tableInfo.Schema, tableInfo.Name, tableInfo.IsNewTable);
this.idTableMap.Add(tableInfo.Id, table); this.idTableMap.Add(tableInfo.Id, table);
var viewModel = this.GetTableViewModel(tableInfo); var viewModel = this.GetTableViewModel(tableInfo);
var view = this.GetDesignerViewInfo(tableInfo); var view = this.GetDesignerViewInfo(tableInfo);
@@ -122,15 +124,35 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
}); });
} }
private Task HandleSaveTableChangesRequest(SaveTableChangesRequestParams requestParams, RequestContext<SaveTableChangesResponse> requestContext) private Task HandleSaveTableChangesRequest(TableInfo tableInfo, RequestContext<SaveTableChangesResponse> requestContext)
{ {
return this.HandleRequest<SaveTableChangesResponse>(requestContext, async () => return this.HandleRequest<SaveTableChangesResponse>(requestContext, async () =>
{ {
// TODO: Handle the save changes request. var tableDesigner = this.GetTableDesigner(tableInfo);
tableDesigner.CommitChanges();
await requestContext.SendResult(new SaveTableChangesResponse()); await requestContext.SendResult(new SaveTableChangesResponse());
}); });
} }
private Task HandleGenerateScriptRequest(TableInfo tableInfo, RequestContext<string> requestContext)
{
return this.HandleRequest<string>(requestContext, async () =>
{
var table = this.GetTableDesigner(tableInfo);
var script = table.GenerateScript();
await requestContext.SendResult(script);
});
}
private Task HandleGenerateReportRequest(TableInfo tableInfo, RequestContext<string> requestContext)
{
return this.HandleRequest<string>(requestContext, async () =>
{
var table = this.GetTableDesigner(tableInfo);
var report = table.GenerateReport();
await requestContext.SendResult(report);
});
}
private Task HandleDisposeTableDesignerRequest(TableInfo tableInfo, RequestContext<DisposeTableDesignerResponse> requestContext) private Task HandleDisposeTableDesignerRequest(TableInfo tableInfo, RequestContext<DisposeTableDesignerResponse> requestContext)
{ {
@@ -143,7 +165,7 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
private void HandleAddItemRequest(ProcessTableDesignerEditRequestParams requestParams) private void HandleAddItemRequest(ProcessTableDesignerEditRequestParams requestParams)
{ {
var table = this.GetTable(requestParams.TableInfo); var table = this.GetTableDesigner(requestParams.TableInfo).TableViewModel;
var path = requestParams.TableChangeInfo.Path; var path = requestParams.TableChangeInfo.Path;
// Handle the add item request on top level table properties, e.g. Columns, Indexes. // Handle the add item request on top level table properties, e.g. Columns, Indexes.
if (path.Length == 1) if (path.Length == 1)
@@ -166,7 +188,7 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
private void HandleRemoveItemRequest(ProcessTableDesignerEditRequestParams requestParams) private void HandleRemoveItemRequest(ProcessTableDesignerEditRequestParams requestParams)
{ {
var table = this.GetTable(requestParams.TableInfo); var table = this.GetTableDesigner(requestParams.TableInfo).TableViewModel;
var path = requestParams.TableChangeInfo.Path; var path = requestParams.TableChangeInfo.Path;
// Handle the add item request on top level table properties, e.g. Columns, Indexes. // Handle the add item request on top level table properties, e.g. Columns, Indexes.
if (path.Length == 2) if (path.Length == 2)
@@ -175,7 +197,7 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
switch (propertyName) switch (propertyName)
{ {
case TablePropertyNames.Columns: case TablePropertyNames.Columns:
table.Columns.Items.RemoveAt(Convert.ToInt32(path[1])); table.Columns.RemoveAt(Convert.ToInt32(path[1]));
break; break;
default: default:
break; break;
@@ -189,7 +211,7 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
private void HandleUpdateItemRequest(ProcessTableDesignerEditRequestParams requestParams) private void HandleUpdateItemRequest(ProcessTableDesignerEditRequestParams requestParams)
{ {
var table = this.GetTable(requestParams.TableInfo); var table = this.GetTableDesigner(requestParams.TableInfo).TableViewModel;
var path = requestParams.TableChangeInfo.Path; var path = requestParams.TableChangeInfo.Path;
if (path.Length == 3) if (path.Length == 3)
@@ -232,7 +254,8 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
private TableViewModel GetTableViewModel(TableInfo tableInfo) private TableViewModel GetTableViewModel(TableInfo tableInfo)
{ {
var table = this.GetTable(tableInfo); var tableDesigner = this.GetTableDesigner(tableInfo);
var table = tableDesigner.TableViewModel;
var tableViewModel = new TableViewModel(); var tableViewModel = new TableViewModel();
tableViewModel.Name.Value = table.Name; tableViewModel.Name.Value = table.Name;
tableViewModel.Schema.Value = table.Schema; tableViewModel.Schema.Value = table.Schema;
@@ -276,7 +299,7 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
foreignKeyViewModel.OnUpdateAction.Value = SqlForeignKeyActionUtil.GetName(foreignKey.OnUpdateAction); foreignKeyViewModel.OnUpdateAction.Value = SqlForeignKeyActionUtil.GetName(foreignKey.OnUpdateAction);
foreignKeyViewModel.OnUpdateAction.Values = SqlForeignKeyActionUtil.ActionNames; foreignKeyViewModel.OnUpdateAction.Values = SqlForeignKeyActionUtil.ActionNames;
foreignKeyViewModel.PrimaryKeyTable.Value = foreignKey.PrimaryKeyTable; foreignKeyViewModel.PrimaryKeyTable.Value = foreignKey.PrimaryKeyTable;
foreignKeyViewModel.PrimaryKeyTable.Values = table.AllTables.ToList(); foreignKeyViewModel.PrimaryKeyTable.Values = tableDesigner.AllTables.ToList();
foreignKeyViewModel.IsNotForReplication.Checked = foreignKey.IsNotForReplication; foreignKeyViewModel.IsNotForReplication.Checked = foreignKey.IsNotForReplication;
for (int i = 0; i < foreignKey.ForeignKeyColumns.Count; i++) for (int i = 0; i < foreignKey.ForeignKeyColumns.Count; i++)
{ {
@@ -286,7 +309,7 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
mapping.ForeignKeyColumn.Value = foreignKeyColumn; mapping.ForeignKeyColumn.Value = foreignKeyColumn;
mapping.ForeignKeyColumn.Values = table.Columns.Items.Select(c => c.Name).ToList(); mapping.ForeignKeyColumn.Values = table.Columns.Items.Select(c => c.Name).ToList();
mapping.PrimaryKeyColumn.Value = primaryKeyColumn; mapping.PrimaryKeyColumn.Value = primaryKeyColumn;
mapping.PrimaryKeyColumn.Values = table.GetColumnsForTable(foreignKey.PrimaryKeyTable).ToList(); mapping.PrimaryKeyColumn.Values = tableDesigner.GetColumnsForTable(foreignKey.PrimaryKeyTable).ToList();
foreignKeyViewModel.Columns.Data.Add(mapping); foreignKeyViewModel.Columns.Data.Add(mapping);
} }
tableViewModel.ForeignKeys.Data.Add(foreignKeyViewModel); tableViewModel.ForeignKeys.Data.Add(foreignKeyViewModel);
@@ -302,7 +325,7 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
} }
tableViewModel.Script.Enabled = false; tableViewModel.Script.Enabled = false;
tableViewModel.Script.Value = table.Script; tableViewModel.Script.Value = tableDesigner.Script;
// TODO: set other properties of the table // TODO: set other properties of the table
return tableViewModel; return tableViewModel;
} }
@@ -384,12 +407,12 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
return view; return view;
} }
private Dac.TableDesignerViewModel GetTable(TableInfo tableInfo) private Dac.TableDesigner GetTableDesigner(TableInfo tableInfo)
{ {
Dac.TableDesignerViewModel table; Dac.TableDesigner tableDesigner;
if (this.idTableMap.TryGetValue(tableInfo.Id, out table)) if (this.idTableMap.TryGetValue(tableInfo.Id, out tableDesigner))
{ {
return table; return tableDesigner;
} }
else else
{ {