Re-enable parallel message processing (#1741)

* add flag to handler

* cleanup

* concurrency control

* add flag for handler setters

* update service flags

* fix event handlers

* more handlers

* make sure behavior is unchanged if flag is off

* cleanup

* add test case for parallel processing

* comments

* stop dispatcher in test

* add log for request lifespan

* cleanup and add comments

* correctly release semaphore

* remove deleted file from merge

* use await for semaphore release

* move handler invocation to await and adjust test

* cleanup exception handling and wrapper

* space

* loose assertion condition to make test stable
This commit is contained in:
Hai Cao
2022-12-11 00:05:33 -08:00
committed by GitHub
parent c304f54ca2
commit f86ebae9b8
37 changed files with 350 additions and 245 deletions

View File

@@ -23,7 +23,7 @@ namespace Microsoft.SqlTools.Hosting.Protocol.Channel
/// <summary> /// <summary>
/// Gets the MessageReader for reading messages from the channel. /// Gets the MessageReader for reading messages from the channel.
/// </summary> /// </summary>
public MessageReader MessageReader { get; protected set; } public virtual MessageReader MessageReader { get; protected set; } // mark as virtual for mocking ChannelBase in UT
/// <summary> /// <summary>
/// Gets the MessageWriter for writing messages to the channel. /// Gets the MessageWriter for writing messages to the channel.

View File

@@ -16,17 +16,43 @@ namespace Microsoft.SqlTools.Hosting.Protocol
/// </summary> /// </summary>
public interface IProtocolEndpoint : IEventSender, IRequestSender public interface IProtocolEndpoint : IEventSender, IRequestSender
{ {
/// <summary>
/// Set a request handler
/// </summary>
/// <typeparam name="TParams">type of parameter</typeparam>
/// <typeparam name="TResult">type of result</typeparam>
/// <param name="requestType">request type</param>
/// <param name="requestHandler">request handler</param>
/// <param name="isParallelProcessingSupported">whether this handler supports parallel processing</param>
void SetRequestHandler<TParams, TResult>( void SetRequestHandler<TParams, TResult>(
RequestType<TParams, TResult> requestType, RequestType<TParams, TResult> requestType,
Func<TParams, RequestContext<TResult>, Task> requestHandler); Func<TParams, RequestContext<TResult>, Task> requestHandler,
bool isParallelProcessingSupported = false);
void SetEventHandler<TParams>(
EventType<TParams> eventType,
Func<TParams, EventContext, Task> eventHandler);
/// <summary>
/// Set an request handler
/// </summary>
/// <typeparam name="TParams">type of parameter</typeparam>
/// <param name="eventType">type of event</param>
/// <param name="eventHandler">event handler</param>
/// <param name="isParallelProcessingSupported">whether this handler supports parallel processing</param>
void SetEventHandler<TParams>( void SetEventHandler<TParams>(
EventType<TParams> eventType, EventType<TParams> eventType,
Func<TParams, EventContext, Task> eventHandler, Func<TParams, EventContext, Task> eventHandler,
bool overrideExisting); bool isParallelProcessingSupported = false);
/// <summary>
/// Set an request handler
/// </summary>
/// <typeparam name="TParams">type of parameter</typeparam>
/// <param name="eventType">type of event</param>
/// <param name="eventHandler">event handler</param>
/// <param name="overrideExisting">whether to override the existing handler for the same event type</param>
/// <param name="isParallelProcessingSupported">whether this handler supports parallel processing</param>
void SetEventHandler<TParams>(
EventType<TParams> eventType,
Func<TParams, EventContext, Task> eventHandler,
bool overrideExisting,
bool isParallelProcessingSupported = false);
} }
} }

View File

@@ -27,14 +27,22 @@ namespace Microsoft.SqlTools.Hosting.Protocol
internal Dictionary<string, Func<Message, MessageWriter, Task>> requestHandlers = internal Dictionary<string, Func<Message, MessageWriter, Task>> requestHandlers =
new Dictionary<string, Func<Message, MessageWriter, Task>>(); new Dictionary<string, Func<Message, MessageWriter, Task>>();
internal Dictionary<string, bool> requestHandlerParallelismMap =
new Dictionary<string, bool>();
internal Dictionary<string, Func<Message, MessageWriter, Task>> eventHandlers = internal Dictionary<string, Func<Message, MessageWriter, Task>> eventHandlers =
new Dictionary<string, Func<Message, MessageWriter, Task>>(); new Dictionary<string, Func<Message, MessageWriter, Task>>();
internal Dictionary<string, bool> eventHandlerParallelismMap =
new Dictionary<string, bool>();
private Action<Message> responseHandler; private Action<Message> responseHandler;
private CancellationTokenSource messageLoopCancellationToken = private CancellationTokenSource messageLoopCancellationToken =
new CancellationTokenSource(); new CancellationTokenSource();
private SemaphoreSlim semaphore = new SemaphoreSlim(10); // Limit to 10 threads to begin with, ideally there shouldn't be any limitation
#endregion #endregion
#region Properties #region Properties
@@ -112,7 +120,8 @@ namespace Microsoft.SqlTools.Hosting.Protocol
public void SetRequestHandler<TParams, TResult>( public void SetRequestHandler<TParams, TResult>(
RequestType<TParams, TResult> requestType, RequestType<TParams, TResult> requestType,
Func<TParams, RequestContext<TResult>, Task> requestHandler, Func<TParams, RequestContext<TResult>, Task> requestHandler,
bool overrideExisting) bool overrideExisting,
bool isParallelProcessingSupported = false)
{ {
if (overrideExisting) if (overrideExisting)
{ {
@@ -120,10 +129,12 @@ namespace Microsoft.SqlTools.Hosting.Protocol
this.requestHandlers.Remove(requestType.MethodName); this.requestHandlers.Remove(requestType.MethodName);
} }
this.requestHandlerParallelismMap.Add(requestType.MethodName, isParallelProcessingSupported);
this.requestHandlers.Add( this.requestHandlers.Add(
requestType.MethodName, requestType.MethodName,
async (requestMessage, messageWriter) => async (requestMessage, messageWriter) =>
{ {
Logger.Write(TraceEventType.Verbose, $"Processing message with id[{requestMessage.Id}], of type[{requestMessage.MessageType}] and method[{requestMessage.Method}]");
var requestContext = var requestContext =
new RequestContext<TResult>( new RequestContext<TResult>(
requestMessage, requestMessage,
@@ -144,6 +155,7 @@ namespace Microsoft.SqlTools.Hosting.Protocol
} }
await requestHandler(typedParams, requestContext); await requestHandler(typedParams, requestContext);
Logger.Write(TraceEventType.Verbose, $"Finished processing message with id[{requestMessage.Id}], of type[{requestMessage.MessageType}] and method[{requestMessage.Method}]");
} }
catch (Exception ex) catch (Exception ex)
{ {
@@ -166,7 +178,8 @@ namespace Microsoft.SqlTools.Hosting.Protocol
public void SetEventHandler<TParams>( public void SetEventHandler<TParams>(
EventType<TParams> eventType, EventType<TParams> eventType,
Func<TParams, EventContext, Task> eventHandler, Func<TParams, EventContext, Task> eventHandler,
bool overrideExisting) bool overrideExisting,
bool isParallelProcessingSupported = false)
{ {
if (overrideExisting) if (overrideExisting)
{ {
@@ -174,10 +187,12 @@ namespace Microsoft.SqlTools.Hosting.Protocol
this.eventHandlers.Remove(eventType.MethodName); this.eventHandlers.Remove(eventType.MethodName);
} }
this.eventHandlerParallelismMap.Add(eventType.MethodName, isParallelProcessingSupported);
this.eventHandlers.Add( this.eventHandlers.Add(
eventType.MethodName, eventType.MethodName,
async (eventMessage, messageWriter) => async (eventMessage, messageWriter) =>
{ {
Logger.Write(TraceEventType.Verbose, $"Processing message with id[{eventMessage.Id}], of type[{eventMessage.MessageType}] and method[{eventMessage.Method}]");
var eventContext = new EventContext(messageWriter); var eventContext = new EventContext(messageWriter);
TParams typedParams = default(TParams); TParams typedParams = default(TParams);
try try
@@ -194,6 +209,7 @@ namespace Microsoft.SqlTools.Hosting.Protocol
} }
} }
await eventHandler(typedParams, eventContext); await eventHandler(typedParams, eventContext);
Logger.Write(TraceEventType.Verbose, $"Finished processing message with id[{eventMessage.Id}], of type[{eventMessage.MessageType}] and method[{eventMessage.Method}]");
} }
catch (Exception ex) catch (Exception ex)
{ {
@@ -284,19 +300,13 @@ namespace Microsoft.SqlTools.Hosting.Protocol
Message messageToDispatch, Message messageToDispatch,
MessageWriter messageWriter) MessageWriter messageWriter)
{ {
Task handlerToAwait = null; Func<Message, MessageWriter, Task> handlerToAwait = null;
bool isParallelProcessingSupported = false;
if (messageToDispatch.MessageType == MessageType.Request) if (messageToDispatch.MessageType == MessageType.Request)
{ {
Func<Message, MessageWriter, Task> requestHandler = null; this.requestHandlers.TryGetValue(messageToDispatch.Method, out handlerToAwait);
if (this.requestHandlers.TryGetValue(messageToDispatch.Method, out requestHandler)) this.requestHandlerParallelismMap.TryGetValue(messageToDispatch.Method, out isParallelProcessingSupported);
{
handlerToAwait = requestHandler(messageToDispatch, messageWriter);
}
// else
// {
// // TODO: Message not supported error
// }
} }
else if (messageToDispatch.MessageType == MessageType.Response) else if (messageToDispatch.MessageType == MessageType.Response)
{ {
@@ -307,15 +317,8 @@ namespace Microsoft.SqlTools.Hosting.Protocol
} }
else if (messageToDispatch.MessageType == MessageType.Event) else if (messageToDispatch.MessageType == MessageType.Event)
{ {
Func<Message, MessageWriter, Task> eventHandler = null; this.eventHandlers.TryGetValue(messageToDispatch.Method, out handlerToAwait);
if (this.eventHandlers.TryGetValue(messageToDispatch.Method, out eventHandler)) this.eventHandlerParallelismMap.TryGetValue(messageToDispatch.Method, out isParallelProcessingSupported);
{
handlerToAwait = eventHandler(messageToDispatch, messageWriter);
}
else
{
// TODO: Message not supported error
}
} }
// else // else
// { // {
@@ -324,39 +327,37 @@ namespace Microsoft.SqlTools.Hosting.Protocol
if (handlerToAwait != null) if (handlerToAwait != null)
{ {
if (this.ParallelMessageProcessing) try
{
if (this.ParallelMessageProcessing && isParallelProcessingSupported)
{ {
// Run the task in a separate thread so that the main // Run the task in a separate thread so that the main
// thread is not blocked. // thread is not blocked. Use semaphore to limit the degree of parallelism.
_ = Task.Run(() => await semaphore.WaitAsync();
_ = Task.Run(async () =>
{ {
_ = RunTask(handlerToAwait); await handlerToAwait(messageToDispatch, messageWriter);
semaphore.Release();
}); });
} }
else else
{ {
await RunTask(handlerToAwait); await handlerToAwait(messageToDispatch, messageWriter);
} }
} }
} catch (TaskCanceledException e)
private async Task RunTask(Task task)
{
try
{
await task;
}
catch (TaskCanceledException)
{ {
// Some tasks may be cancelled due to legitimate // Some tasks may be cancelled due to legitimate
// timeouts so don't let those exceptions go higher. // timeouts so don't let those exceptions go higher.
Logger.Write(TraceEventType.Verbose, string.Format("A TaskCanceledException occurred in the request handler: {0}", e.ToString()));
} }
catch (Exception e) catch (Exception e)
{ {
if (!(e is AggregateException && ((AggregateException)e).InnerExceptions[0] is TaskCanceledException)) if (!(e is AggregateException && ((AggregateException)e).InnerExceptions[0] is TaskCanceledException))
{ {
// Log the error but don't rethrow it to prevent any errors in the handler from crashing the service // Log the error but don't rethrow it to prevent any errors in the handler from crashing the service
Logger.Write(TraceEventType.Error, string.Format("An unexpected error occured in the request handler: {0}", e.ToString())); Logger.Write(TraceEventType.Error, string.Format("An unexpected error occurred in the request handler: {0}", e.ToString()));
}
} }
} }
} }

View File

@@ -49,6 +49,7 @@ namespace Microsoft.SqlTools.Hosting.Protocol
#endregion #endregion
#region Constructors #region Constructors
public MessageReader() {} // added for mocking MessageReader in UT
public MessageReader( public MessageReader(
Stream inputStream, Stream inputStream,
@@ -74,7 +75,7 @@ namespace Microsoft.SqlTools.Hosting.Protocol
#region Public Methods #region Public Methods
public async Task<Message> ReadMessage() public virtual async Task<Message> ReadMessage() // mark as virtual for mocking MessageReader in UT
{ {
string messageContent = null; string messageContent = null;

View File

@@ -272,32 +272,39 @@ namespace Microsoft.SqlTools.Hosting.Protocol
public void SetRequestHandler<TParams, TResult>( public void SetRequestHandler<TParams, TResult>(
RequestType<TParams, TResult> requestType, RequestType<TParams, TResult> requestType,
Func<TParams, RequestContext<TResult>, Task> requestHandler) Func<TParams, RequestContext<TResult>, Task> requestHandler,
bool isParallelProcessingSupported = false)
{ {
this.MessageDispatcher.SetRequestHandler( this.MessageDispatcher.SetRequestHandler(
requestType, requestType,
requestHandler); requestHandler,
} false,
isParallelProcessingSupported);
public void SetEventHandler<TParams>(
EventType<TParams> eventType,
Func<TParams, EventContext, Task> eventHandler)
{
this.MessageDispatcher.SetEventHandler(
eventType,
eventHandler,
false);
} }
public void SetEventHandler<TParams>( public void SetEventHandler<TParams>(
EventType<TParams> eventType, EventType<TParams> eventType,
Func<TParams, EventContext, Task> eventHandler, Func<TParams, EventContext, Task> eventHandler,
bool overrideExisting) bool isParallelProcessingSupported = false)
{ {
this.MessageDispatcher.SetEventHandler( this.MessageDispatcher.SetEventHandler(
eventType, eventType,
eventHandler, eventHandler,
overrideExisting); false,
isParallelProcessingSupported);
}
public void SetEventHandler<TParams>(
EventType<TParams> eventType,
Func<TParams, EventContext, Task> eventHandler,
bool overrideExisting,
bool isParallelProcessingSupported = false)
{
this.MessageDispatcher.SetEventHandler(
eventType,
eventHandler,
overrideExisting,
isParallelProcessingSupported);
} }
private void HandleResponse(Message responseMessage) private void HandleResponse(Message responseMessage)

View File

@@ -65,10 +65,10 @@ namespace Microsoft.SqlTools.ServiceLayer.Admin
/// </summary> /// </summary>
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(CreateDatabaseRequest.Type, HandleCreateDatabaseRequest); serviceHost.SetRequestHandler(CreateDatabaseRequest.Type, HandleCreateDatabaseRequest, true);
serviceHost.SetRequestHandler(CreateLoginRequest.Type, HandleCreateLoginRequest); serviceHost.SetRequestHandler(CreateLoginRequest.Type, HandleCreateLoginRequest, true);
serviceHost.SetRequestHandler(DefaultDatabaseInfoRequest.Type, HandleDefaultDatabaseInfoRequest); serviceHost.SetRequestHandler(DefaultDatabaseInfoRequest.Type, HandleDefaultDatabaseInfoRequest, true);
serviceHost.SetRequestHandler(GetDatabaseInfoRequest.Type, HandleGetDatabaseInfoRequest); serviceHost.SetRequestHandler(GetDatabaseInfoRequest.Type, HandleGetDatabaseInfoRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -79,56 +79,56 @@ namespace Microsoft.SqlTools.ServiceLayer.Agent
this.ServiceHost = serviceHost; this.ServiceHost = serviceHost;
// Jobs request handlers // Jobs request handlers
this.ServiceHost.SetRequestHandler(AgentJobsRequest.Type, HandleAgentJobsRequest); this.ServiceHost.SetRequestHandler(AgentJobsRequest.Type, HandleAgentJobsRequest, true);
this.ServiceHost.SetRequestHandler(AgentJobHistoryRequest.Type, HandleJobHistoryRequest); this.ServiceHost.SetRequestHandler(AgentJobHistoryRequest.Type, HandleJobHistoryRequest, true);
this.ServiceHost.SetRequestHandler(AgentJobActionRequest.Type, HandleJobActionRequest); this.ServiceHost.SetRequestHandler(AgentJobActionRequest.Type, HandleJobActionRequest, true);
this.ServiceHost.SetRequestHandler(CreateAgentJobRequest.Type, HandleCreateAgentJobRequest); this.ServiceHost.SetRequestHandler(CreateAgentJobRequest.Type, HandleCreateAgentJobRequest, true);
this.ServiceHost.SetRequestHandler(UpdateAgentJobRequest.Type, HandleUpdateAgentJobRequest); this.ServiceHost.SetRequestHandler(UpdateAgentJobRequest.Type, HandleUpdateAgentJobRequest, true);
this.ServiceHost.SetRequestHandler(DeleteAgentJobRequest.Type, HandleDeleteAgentJobRequest); this.ServiceHost.SetRequestHandler(DeleteAgentJobRequest.Type, HandleDeleteAgentJobRequest, true);
this.ServiceHost.SetRequestHandler(AgentJobDefaultsRequest.Type, HandleAgentJobDefaultsRequest); this.ServiceHost.SetRequestHandler(AgentJobDefaultsRequest.Type, HandleAgentJobDefaultsRequest, true);
// Job Steps request handlers // Job Steps request handlers
this.ServiceHost.SetRequestHandler(CreateAgentJobStepRequest.Type, HandleCreateAgentJobStepRequest); this.ServiceHost.SetRequestHandler(CreateAgentJobStepRequest.Type, HandleCreateAgentJobStepRequest, true);
this.ServiceHost.SetRequestHandler(UpdateAgentJobStepRequest.Type, HandleUpdateAgentJobStepRequest); this.ServiceHost.SetRequestHandler(UpdateAgentJobStepRequest.Type, HandleUpdateAgentJobStepRequest, true);
this.ServiceHost.SetRequestHandler(DeleteAgentJobStepRequest.Type, HandleDeleteAgentJobStepRequest); this.ServiceHost.SetRequestHandler(DeleteAgentJobStepRequest.Type, HandleDeleteAgentJobStepRequest, true);
// Alerts request handlers // Alerts request handlers
this.ServiceHost.SetRequestHandler(AgentAlertsRequest.Type, HandleAgentAlertsRequest); this.ServiceHost.SetRequestHandler(AgentAlertsRequest.Type, HandleAgentAlertsRequest, true);
this.ServiceHost.SetRequestHandler(CreateAgentAlertRequest.Type, HandleCreateAgentAlertRequest); this.ServiceHost.SetRequestHandler(CreateAgentAlertRequest.Type, HandleCreateAgentAlertRequest, true);
this.ServiceHost.SetRequestHandler(UpdateAgentAlertRequest.Type, HandleUpdateAgentAlertRequest); this.ServiceHost.SetRequestHandler(UpdateAgentAlertRequest.Type, HandleUpdateAgentAlertRequest, true);
this.ServiceHost.SetRequestHandler(DeleteAgentAlertRequest.Type, HandleDeleteAgentAlertRequest); this.ServiceHost.SetRequestHandler(DeleteAgentAlertRequest.Type, HandleDeleteAgentAlertRequest, true);
// Operators request handlers // Operators request handlers
this.ServiceHost.SetRequestHandler(AgentOperatorsRequest.Type, HandleAgentOperatorsRequest); this.ServiceHost.SetRequestHandler(AgentOperatorsRequest.Type, HandleAgentOperatorsRequest, true);
this.ServiceHost.SetRequestHandler(CreateAgentOperatorRequest.Type, HandleCreateAgentOperatorRequest); this.ServiceHost.SetRequestHandler(CreateAgentOperatorRequest.Type, HandleCreateAgentOperatorRequest, true);
this.ServiceHost.SetRequestHandler(UpdateAgentOperatorRequest.Type, HandleUpdateAgentOperatorRequest); this.ServiceHost.SetRequestHandler(UpdateAgentOperatorRequest.Type, HandleUpdateAgentOperatorRequest, true);
this.ServiceHost.SetRequestHandler(DeleteAgentOperatorRequest.Type, HandleDeleteAgentOperatorRequest); this.ServiceHost.SetRequestHandler(DeleteAgentOperatorRequest.Type, HandleDeleteAgentOperatorRequest, true);
// Proxy Accounts request handlers // Proxy Accounts request handlers
this.ServiceHost.SetRequestHandler(AgentProxiesRequest.Type, HandleAgentProxiesRequest); this.ServiceHost.SetRequestHandler(AgentProxiesRequest.Type, HandleAgentProxiesRequest, true);
this.ServiceHost.SetRequestHandler(CreateAgentProxyRequest.Type, HandleCreateAgentProxyRequest); this.ServiceHost.SetRequestHandler(CreateAgentProxyRequest.Type, HandleCreateAgentProxyRequest, true);
this.ServiceHost.SetRequestHandler(UpdateAgentProxyRequest.Type, HandleUpdateAgentProxyRequest); this.ServiceHost.SetRequestHandler(UpdateAgentProxyRequest.Type, HandleUpdateAgentProxyRequest, true);
this.ServiceHost.SetRequestHandler(DeleteAgentProxyRequest.Type, HandleDeleteAgentProxyRequest); this.ServiceHost.SetRequestHandler(DeleteAgentProxyRequest.Type, HandleDeleteAgentProxyRequest, true);
// Schedule request handlers // Schedule request handlers
this.ServiceHost.SetRequestHandler(AgentSchedulesRequest.Type, HandleAgentSchedulesRequest); this.ServiceHost.SetRequestHandler(AgentSchedulesRequest.Type, HandleAgentSchedulesRequest, true);
this.ServiceHost.SetRequestHandler(CreateAgentScheduleRequest.Type, HandleCreateAgentScheduleRequest); this.ServiceHost.SetRequestHandler(CreateAgentScheduleRequest.Type, HandleCreateAgentScheduleRequest, true);
this.ServiceHost.SetRequestHandler(UpdateAgentScheduleRequest.Type, HandleUpdateAgentScheduleRequest); this.ServiceHost.SetRequestHandler(UpdateAgentScheduleRequest.Type, HandleUpdateAgentScheduleRequest, true);
this.ServiceHost.SetRequestHandler(DeleteAgentScheduleRequest.Type, HandleDeleteAgentScheduleRequest); this.ServiceHost.SetRequestHandler(DeleteAgentScheduleRequest.Type, HandleDeleteAgentScheduleRequest, true);
// Notebook request handlers // Notebook request handlers
this.ServiceHost.SetRequestHandler(AgentNotebooksRequest.Type, HandleAgentNotebooksRequest); this.ServiceHost.SetRequestHandler(AgentNotebooksRequest.Type, HandleAgentNotebooksRequest, true);
this.ServiceHost.SetRequestHandler(AgentNotebookHistoryRequest.Type, HandleAgentNotebookHistoryRequest); this.ServiceHost.SetRequestHandler(AgentNotebookHistoryRequest.Type, HandleAgentNotebookHistoryRequest, true);
this.ServiceHost.SetRequestHandler(AgentNotebookMaterializedRequest.Type, HandleAgentNotebookMaterializedRequest); this.ServiceHost.SetRequestHandler(AgentNotebookMaterializedRequest.Type, HandleAgentNotebookMaterializedRequest, true);
this.ServiceHost.SetRequestHandler(AgentNotebookTemplateRequest.Type, HandleAgentNotebookTemplateRequest); this.ServiceHost.SetRequestHandler(AgentNotebookTemplateRequest.Type, HandleAgentNotebookTemplateRequest, true);
this.ServiceHost.SetRequestHandler(CreateAgentNotebookRequest.Type, HandleCreateAgentNotebookRequest); this.ServiceHost.SetRequestHandler(CreateAgentNotebookRequest.Type, HandleCreateAgentNotebookRequest, true);
this.ServiceHost.SetRequestHandler(DeleteAgentNotebookRequest.Type, HandleDeleteAgentNotebooksRequest); this.ServiceHost.SetRequestHandler(DeleteAgentNotebookRequest.Type, HandleDeleteAgentNotebooksRequest, true);
this.ServiceHost.SetRequestHandler(UpdateAgentNotebookRequest.Type, HandleUpdateAgentNotebookRequest); this.ServiceHost.SetRequestHandler(UpdateAgentNotebookRequest.Type, HandleUpdateAgentNotebookRequest, true);
this.ServiceHost.SetRequestHandler(UpdateAgentNotebookRunPinRequest.Type, HandleUpdateAgentNotebookRunPinRequest); this.ServiceHost.SetRequestHandler(UpdateAgentNotebookRunPinRequest.Type, HandleUpdateAgentNotebookRunPinRequest, true);
this.ServiceHost.SetRequestHandler(UpdateAgentNotebookRunNameRequest.Type, HandleUpdateAgentNotebookRunNameRequest); this.ServiceHost.SetRequestHandler(UpdateAgentNotebookRunNameRequest.Type, HandleUpdateAgentNotebookRunNameRequest, true);
this.ServiceHost.SetRequestHandler(DeleteNotebookMaterializedRequest.Type, HandleDeleteNotebookMaterializedRequest); this.ServiceHost.SetRequestHandler(DeleteNotebookMaterializedRequest.Type, HandleDeleteNotebookMaterializedRequest, true);
serviceHost.RegisterShutdownTask((_, _) => serviceHost.RegisterShutdownTask((_, _) =>
{ {
@@ -1194,7 +1194,7 @@ namespace Microsoft.SqlTools.ServiceLayer.Agent
parameters.OwnerUri, parameters.OwnerUri,
out connInfo); out connInfo);
result.Success = true; result.Success = true;
result.Notebooks = AgentNotebookHelper.GetAgentNotebooks(connInfo).Result; result.Notebooks = await AgentNotebookHelper.GetAgentNotebooks(connInfo);
} }
catch (Exception e) catch (Exception e)
{ {
@@ -1243,7 +1243,7 @@ namespace Microsoft.SqlTools.ServiceLayer.Agent
ConnectionServiceInstance.TryFindConnection( ConnectionServiceInstance.TryFindConnection(
parameters.OwnerUri, parameters.OwnerUri,
out connInfo); out connInfo);
result.NotebookMaterialized = AgentNotebookHelper.GetMaterializedNotebook(connInfo, parameters.NotebookMaterializedId, parameters.TargetDatabase).Result; result.NotebookMaterialized = await AgentNotebookHelper.GetMaterializedNotebook(connInfo, parameters.NotebookMaterializedId, parameters.TargetDatabase);
result.Success = true; result.Success = true;
} }
catch (Exception e) catch (Exception e)

View File

@@ -35,7 +35,7 @@ namespace Microsoft.SqlTools.ServiceLayer.AzureBlob
public void InitializeService(IProtocolEndpoint serviceHost) public void InitializeService(IProtocolEndpoint serviceHost)
{ {
serviceHost.SetRequestHandler(CreateSasRequest.Type, HandleCreateSasRequest); serviceHost.SetRequestHandler(CreateSasRequest.Type, HandleCreateSasRequest, true);
} }
internal async Task HandleCreateSasRequest( internal async Task HandleCreateSasRequest(

View File

@@ -32,8 +32,8 @@ namespace Microsoft.SqlTools.ServiceLayer.AzureFunctions
/// <param name="serviceHost"></param> /// <param name="serviceHost"></param>
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(AddSqlBindingRequest.Type, this.HandleAddSqlBindingRequest); serviceHost.SetRequestHandler(AddSqlBindingRequest.Type, this.HandleAddSqlBindingRequest, true);
serviceHost.SetRequestHandler(GetAzureFunctionsRequest.Type, this.HandleGetAzureFunctionsRequest); serviceHost.SetRequestHandler(GetAzureFunctionsRequest.Type, this.HandleGetAzureFunctionsRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -43,12 +43,12 @@ namespace Microsoft.SqlTools.ServiceLayer.Cms
/// <param name="serviceHost"></param> /// <param name="serviceHost"></param>
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(CreateCentralManagementServerRequest.Type, this.HandleCreateCentralManagementServerRequest); serviceHost.SetRequestHandler(CreateCentralManagementServerRequest.Type, this.HandleCreateCentralManagementServerRequest, true);
serviceHost.SetRequestHandler(ListRegisteredServersRequest.Type, this.HandleListRegisteredServersRequest); serviceHost.SetRequestHandler(ListRegisteredServersRequest.Type, this.HandleListRegisteredServersRequest, true);
serviceHost.SetRequestHandler(AddRegisteredServerRequest.Type, this.HandleAddRegisteredServerRequest); serviceHost.SetRequestHandler(AddRegisteredServerRequest.Type, this.HandleAddRegisteredServerRequest, true);
serviceHost.SetRequestHandler(RemoveRegisteredServerRequest.Type, this.HandleRemoveRegisteredServerRequest); serviceHost.SetRequestHandler(RemoveRegisteredServerRequest.Type, this.HandleRemoveRegisteredServerRequest, true);
serviceHost.SetRequestHandler(AddServerGroupRequest.Type, this.HandleAddServerGroupRequest); serviceHost.SetRequestHandler(AddServerGroupRequest.Type, this.HandleAddServerGroupRequest, true);
serviceHost.SetRequestHandler(RemoveServerGroupRequest.Type, this.HandleRemoveServerGroupRequest); serviceHost.SetRequestHandler(RemoveServerGroupRequest.Type, this.HandleRemoveServerGroupRequest, true);
} }
public async Task HandleCreateCentralManagementServerRequest(CreateCentralManagementServerParams createCmsParams, RequestContext<ListRegisteredServersResult> requestContext) public async Task HandleCreateCentralManagementServerRequest(CreateCentralManagementServerParams createCmsParams, RequestContext<ListRegisteredServersResult> requestContext)

View File

@@ -1059,14 +1059,14 @@ namespace Microsoft.SqlTools.ServiceLayer.Connection
this.ServiceHost = serviceHost; this.ServiceHost = serviceHost;
// Register request and event handlers with the Service Host // Register request and event handlers with the Service Host
serviceHost.SetRequestHandler(ConnectionRequest.Type, HandleConnectRequest); serviceHost.SetRequestHandler(ConnectionRequest.Type, HandleConnectRequest, true);
serviceHost.SetRequestHandler(CancelConnectRequest.Type, HandleCancelConnectRequest); serviceHost.SetRequestHandler(CancelConnectRequest.Type, HandleCancelConnectRequest, true);
serviceHost.SetRequestHandler(ChangePasswordRequest.Type, HandleChangePasswordRequest); serviceHost.SetRequestHandler(ChangePasswordRequest.Type, HandleChangePasswordRequest, true);
serviceHost.SetRequestHandler(DisconnectRequest.Type, HandleDisconnectRequest); serviceHost.SetRequestHandler(DisconnectRequest.Type, HandleDisconnectRequest, true);
serviceHost.SetRequestHandler(ListDatabasesRequest.Type, HandleListDatabasesRequest); serviceHost.SetRequestHandler(ListDatabasesRequest.Type, HandleListDatabasesRequest, true);
serviceHost.SetRequestHandler(ChangeDatabaseRequest.Type, HandleChangeDatabaseRequest); serviceHost.SetRequestHandler(ChangeDatabaseRequest.Type, HandleChangeDatabaseRequest, true);
serviceHost.SetRequestHandler(GetConnectionStringRequest.Type, HandleGetConnectionStringRequest); serviceHost.SetRequestHandler(GetConnectionStringRequest.Type, HandleGetConnectionStringRequest, true);
serviceHost.SetRequestHandler(BuildConnectionInfoRequest.Type, HandleBuildConnectionInfoRequest); serviceHost.SetRequestHandler(BuildConnectionInfoRequest.Type, HandleBuildConnectionInfoRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -46,18 +46,18 @@ namespace Microsoft.SqlTools.ServiceLayer.DacFx
/// <param name="serviceHost"></param> /// <param name="serviceHost"></param>
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(ExportRequest.Type, this.HandleExportRequest); serviceHost.SetRequestHandler(ExportRequest.Type, this.HandleExportRequest, true);
serviceHost.SetRequestHandler(ImportRequest.Type, this.HandleImportRequest); serviceHost.SetRequestHandler(ImportRequest.Type, this.HandleImportRequest, true);
serviceHost.SetRequestHandler(ExtractRequest.Type, this.HandleExtractRequest); serviceHost.SetRequestHandler(ExtractRequest.Type, this.HandleExtractRequest, true);
serviceHost.SetRequestHandler(DeployRequest.Type, this.HandleDeployRequest); serviceHost.SetRequestHandler(DeployRequest.Type, this.HandleDeployRequest, true);
serviceHost.SetRequestHandler(GenerateDeployScriptRequest.Type, this.HandleGenerateDeployScriptRequest); serviceHost.SetRequestHandler(GenerateDeployScriptRequest.Type, this.HandleGenerateDeployScriptRequest, true);
serviceHost.SetRequestHandler(GenerateDeployPlanRequest.Type, this.HandleGenerateDeployPlanRequest); serviceHost.SetRequestHandler(GenerateDeployPlanRequest.Type, this.HandleGenerateDeployPlanRequest, true);
serviceHost.SetRequestHandler(GetOptionsFromProfileRequest.Type, this.HandleGetOptionsFromProfileRequest); serviceHost.SetRequestHandler(GetOptionsFromProfileRequest.Type, this.HandleGetOptionsFromProfileRequest, true);
serviceHost.SetRequestHandler(ValidateStreamingJobRequest.Type, this.HandleValidateStreamingJobRequest); serviceHost.SetRequestHandler(ValidateStreamingJobRequest.Type, this.HandleValidateStreamingJobRequest, true);
serviceHost.SetRequestHandler(GetDefaultPublishOptionsRequest.Type, this.HandleGetDefaultPublishOptionsRequest); serviceHost.SetRequestHandler(GetDefaultPublishOptionsRequest.Type, this.HandleGetDefaultPublishOptionsRequest, true);
serviceHost.SetRequestHandler(ParseTSqlScriptRequest.Type, this.HandleParseTSqlScriptRequest); serviceHost.SetRequestHandler(ParseTSqlScriptRequest.Type, this.HandleParseTSqlScriptRequest, true);
serviceHost.SetRequestHandler(GenerateTSqlModelRequest.Type, this.HandleGenerateTSqlModelRequest); serviceHost.SetRequestHandler(GenerateTSqlModelRequest.Type, this.HandleGenerateTSqlModelRequest, true);
serviceHost.SetRequestHandler(GetObjectsFromTSqlModelRequest.Type, this.HandleGetObjectsFromTSqlModelRequest); serviceHost.SetRequestHandler(GetObjectsFromTSqlModelRequest.Type, this.HandleGetObjectsFromTSqlModelRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -96,22 +96,22 @@ namespace Microsoft.SqlTools.ServiceLayer.DisasterRecovery
public void InitializeService(IProtocolEndpoint serviceHost) public void InitializeService(IProtocolEndpoint serviceHost)
{ {
// Get database info // Get database info
serviceHost.SetRequestHandler(BackupConfigInfoRequest.Type, HandleBackupConfigInfoRequest); serviceHost.SetRequestHandler(BackupConfigInfoRequest.Type, HandleBackupConfigInfoRequest, true);
// Create backup // Create backup
serviceHost.SetRequestHandler(BackupRequest.Type, HandleBackupRequest); serviceHost.SetRequestHandler(BackupRequest.Type, HandleBackupRequest, true);
// Create restore task // Create restore task
serviceHost.SetRequestHandler(RestoreRequest.Type, HandleRestoreRequest); serviceHost.SetRequestHandler(RestoreRequest.Type, HandleRestoreRequest, true);
// Create restore plan // Create restore plan
serviceHost.SetRequestHandler(RestorePlanRequest.Type, HandleRestorePlanRequest); serviceHost.SetRequestHandler(RestorePlanRequest.Type, HandleRestorePlanRequest, true);
// Cancel restore plan // Cancel restore plan
serviceHost.SetRequestHandler(CancelRestorePlanRequest.Type, HandleCancelRestorePlanRequest); serviceHost.SetRequestHandler(CancelRestorePlanRequest.Type, HandleCancelRestorePlanRequest, true);
// Create restore config // Create restore config
serviceHost.SetRequestHandler(RestoreConfigInfoRequest.Type, HandleRestoreConfigInfoRequest); serviceHost.SetRequestHandler(RestoreConfigInfoRequest.Type, HandleRestoreConfigInfoRequest, true);
// Register file path validation callbacks // Register file path validation callbacks
FileBrowserServiceInstance.RegisterValidatePathsCallback(FileValidationServiceConstants.Backup, DisasterRecoveryFileValidator.ValidatePaths); FileBrowserServiceInstance.RegisterValidatePathsCallback(FileValidationServiceConstants.Backup, DisasterRecoveryFileValidator.ValidatePaths);

View File

@@ -75,15 +75,15 @@ namespace Microsoft.SqlTools.ServiceLayer.EditData
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
// Register handlers for requests // Register handlers for requests
serviceHost.SetRequestHandler(EditCreateRowRequest.Type, HandleCreateRowRequest); serviceHost.SetRequestHandler(EditCreateRowRequest.Type, HandleCreateRowRequest, true);
serviceHost.SetRequestHandler(EditDeleteRowRequest.Type, HandleDeleteRowRequest); serviceHost.SetRequestHandler(EditDeleteRowRequest.Type, HandleDeleteRowRequest, true);
serviceHost.SetRequestHandler(EditDisposeRequest.Type, HandleDisposeRequest); serviceHost.SetRequestHandler(EditDisposeRequest.Type, HandleDisposeRequest, true);
serviceHost.SetRequestHandler(EditInitializeRequest.Type, HandleInitializeRequest); serviceHost.SetRequestHandler(EditInitializeRequest.Type, HandleInitializeRequest, true);
serviceHost.SetRequestHandler(EditRevertCellRequest.Type, HandleRevertCellRequest); serviceHost.SetRequestHandler(EditRevertCellRequest.Type, HandleRevertCellRequest, true);
serviceHost.SetRequestHandler(EditRevertRowRequest.Type, HandleRevertRowRequest); serviceHost.SetRequestHandler(EditRevertRowRequest.Type, HandleRevertRowRequest, true);
serviceHost.SetRequestHandler(EditSubsetRequest.Type, HandleSubsetRequest); serviceHost.SetRequestHandler(EditSubsetRequest.Type, HandleSubsetRequest, true);
serviceHost.SetRequestHandler(EditUpdateCellRequest.Type, HandleUpdateCellRequest); serviceHost.SetRequestHandler(EditUpdateCellRequest.Type, HandleUpdateCellRequest, true);
serviceHost.SetRequestHandler(EditCommitRequest.Type, HandleCommitRequest); serviceHost.SetRequestHandler(EditCommitRequest.Type, HandleCommitRequest, true);
} }
#region Request Handlers #region Request Handlers

View File

@@ -49,8 +49,8 @@ namespace Microsoft.SqlTools.ServiceLayer.ExecutionPlan
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
ServiceHost = serviceHost; ServiceHost = serviceHost;
ServiceHost.SetRequestHandler(GetExecutionPlanRequest.Type, HandleGetExecutionPlan); ServiceHost.SetRequestHandler(GetExecutionPlanRequest.Type, HandleGetExecutionPlan, true);
ServiceHost.SetRequestHandler(ExecutionPlanComparisonRequest.Type, HandleExecutionPlanComparisonRequest); ServiceHost.SetRequestHandler(ExecutionPlanComparisonRequest.Type, HandleExecutionPlanComparisonRequest, true);
} }
private async Task HandleGetExecutionPlan(GetExecutionPlanParams requestParams, RequestContext<GetExecutionPlanResult> requestContext) private async Task HandleGetExecutionPlan(GetExecutionPlanParams requestParams, RequestContext<GetExecutionPlanResult> requestContext)

View File

@@ -73,16 +73,16 @@ namespace Microsoft.SqlTools.ServiceLayer.FileBrowser
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
// Open a file browser // Open a file browser
serviceHost.SetRequestHandler(FileBrowserOpenRequest.Type, HandleFileBrowserOpenRequest); serviceHost.SetRequestHandler(FileBrowserOpenRequest.Type, HandleFileBrowserOpenRequest, true);
// Expand a folder node // Expand a folder node
serviceHost.SetRequestHandler(FileBrowserExpandRequest.Type, HandleFileBrowserExpandRequest); serviceHost.SetRequestHandler(FileBrowserExpandRequest.Type, HandleFileBrowserExpandRequest, true);
// Validate the selected files // Validate the selected files
serviceHost.SetRequestHandler(FileBrowserValidateRequest.Type, HandleFileBrowserValidateRequest); serviceHost.SetRequestHandler(FileBrowserValidateRequest.Type, HandleFileBrowserValidateRequest, true);
// Close the file browser // Close the file browser
serviceHost.SetRequestHandler(FileBrowserCloseRequest.Type, HandleFileBrowserCloseRequest); serviceHost.SetRequestHandler(FileBrowserCloseRequest.Type, HandleFileBrowserCloseRequest, true);
} }
#region request handlers #region request handlers

View File

@@ -42,8 +42,8 @@ namespace Microsoft.SqlTools.ServiceLayer.Formatter
public override void InitializeService(IProtocolEndpoint serviceHost) public override void InitializeService(IProtocolEndpoint serviceHost)
{ {
Logger.Write(TraceEventType.Verbose, "TSqlFormatter initialized"); Logger.Write(TraceEventType.Verbose, "TSqlFormatter initialized");
serviceHost.SetRequestHandler(DocumentFormattingRequest.Type, HandleDocFormatRequest); serviceHost.SetRequestHandler(DocumentFormattingRequest.Type, HandleDocFormatRequest, true);
serviceHost.SetRequestHandler(DocumentRangeFormattingRequest.Type, HandleDocRangeFormatRequest); serviceHost.SetRequestHandler(DocumentRangeFormattingRequest.Type, HandleDocRangeFormatRequest, true);
WorkspaceService?.RegisterConfigChangeCallback(HandleDidChangeConfigurationNotification); WorkspaceService?.RegisterConfigChangeCallback(HandleDidChangeConfigurationNotification);
} }

View File

@@ -60,10 +60,10 @@ namespace Microsoft.SqlTools.ServiceLayer.LanguageExtensibility
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(ExternalLanguageStatusRequest.Type, this.HandleExternalLanguageStatusRequest); serviceHost.SetRequestHandler(ExternalLanguageStatusRequest.Type, this.HandleExternalLanguageStatusRequest, true);
serviceHost.SetRequestHandler(ExternalLanguageListRequest.Type, this.HandleExternalLanguageListRequest); serviceHost.SetRequestHandler(ExternalLanguageListRequest.Type, this.HandleExternalLanguageListRequest, true);
serviceHost.SetRequestHandler(ExternalLanguageDeleteRequest.Type, this.HandleExternalLanguageDeleteRequest); serviceHost.SetRequestHandler(ExternalLanguageDeleteRequest.Type, this.HandleExternalLanguageDeleteRequest, true);
serviceHost.SetRequestHandler(ExternalLanguageUpdateRequest.Type, this.HandleExternalLanguageUpdateRequest); serviceHost.SetRequestHandler(ExternalLanguageUpdateRequest.Type, this.HandleExternalLanguageUpdateRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -252,6 +252,7 @@ namespace Microsoft.SqlTools.ServiceLayer.LanguageServices
// serviceHost.SetRequestHandler(ReferencesRequest.Type, HandleReferencesRequest); // serviceHost.SetRequestHandler(ReferencesRequest.Type, HandleReferencesRequest);
// serviceHost.SetRequestHandler(DocumentHighlightRequest.Type, HandleDocumentHighlightRequest); // serviceHost.SetRequestHandler(DocumentHighlightRequest.Type, HandleDocumentHighlightRequest);
// Not enabling parallel processing for LanguageService as message order might matter.
serviceHost.SetRequestHandler(SignatureHelpRequest.Type, HandleSignatureHelpRequest); serviceHost.SetRequestHandler(SignatureHelpRequest.Type, HandleSignatureHelpRequest);
serviceHost.SetRequestHandler(CompletionResolveRequest.Type, HandleCompletionResolveRequest); serviceHost.SetRequestHandler(CompletionResolveRequest.Type, HandleCompletionResolveRequest);
serviceHost.SetRequestHandler(HoverRequest.Type, HandleHoverRequest); serviceHost.SetRequestHandler(HoverRequest.Type, HandleHoverRequest);

View File

@@ -50,9 +50,9 @@ namespace Microsoft.SqlTools.ServiceLayer.Metadata
/// <param name="context"></param> /// <param name="context"></param>
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(MetadataListRequest.Type, HandleMetadataListRequest); serviceHost.SetRequestHandler(MetadataListRequest.Type, HandleMetadataListRequest, true);
serviceHost.SetRequestHandler(TableMetadataRequest.Type, HandleGetTableRequest); serviceHost.SetRequestHandler(TableMetadataRequest.Type, HandleGetTableRequest, true);
serviceHost.SetRequestHandler(ViewMetadataRequest.Type, HandleGetViewRequest); serviceHost.SetRequestHandler(ViewMetadataRequest.Type, HandleGetViewRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -121,16 +121,16 @@ namespace Microsoft.SqlTools.ServiceLayer.Migration
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
this.ServiceHost = serviceHost; this.ServiceHost = serviceHost;
this.ServiceHost.SetRequestHandler(MigrationAssessmentsRequest.Type, HandleMigrationAssessmentsRequest); this.ServiceHost.SetRequestHandler(MigrationAssessmentsRequest.Type, HandleMigrationAssessmentsRequest, true);
this.ServiceHost.SetRequestHandler(StartPerfDataCollectionRequest.Type, HandleStartPerfDataCollectionRequest); this.ServiceHost.SetRequestHandler(StartPerfDataCollectionRequest.Type, HandleStartPerfDataCollectionRequest, true);
this.ServiceHost.SetRequestHandler(StopPerfDataCollectionRequest.Type, HandleStopPerfDataCollectionRequest); this.ServiceHost.SetRequestHandler(StopPerfDataCollectionRequest.Type, HandleStopPerfDataCollectionRequest, true);
this.ServiceHost.SetRequestHandler(RefreshPerfDataCollectionRequest.Type, HandleRefreshPerfDataCollectionRequest); this.ServiceHost.SetRequestHandler(RefreshPerfDataCollectionRequest.Type, HandleRefreshPerfDataCollectionRequest, true);
this.ServiceHost.SetRequestHandler(GetSkuRecommendationsRequest.Type, HandleGetSkuRecommendationsRequest); this.ServiceHost.SetRequestHandler(GetSkuRecommendationsRequest.Type, HandleGetSkuRecommendationsRequest, true);
this.ServiceHost.SetRequestHandler(StartLoginMigrationRequest.Type, HandleStartLoginMigration); this.ServiceHost.SetRequestHandler(StartLoginMigrationRequest.Type, HandleStartLoginMigration, true);
this.ServiceHost.SetRequestHandler(ValidateLoginMigrationRequest.Type, HandleValidateLoginMigration); this.ServiceHost.SetRequestHandler(ValidateLoginMigrationRequest.Type, HandleValidateLoginMigration, true);
this.ServiceHost.SetRequestHandler(MigrateLoginsRequest.Type, HandleMigrateLogins); this.ServiceHost.SetRequestHandler(MigrateLoginsRequest.Type, HandleMigrateLogins, true);
this.ServiceHost.SetRequestHandler(EstablishUserMappingRequest.Type, HandleEstablishUserMapping); this.ServiceHost.SetRequestHandler(EstablishUserMappingRequest.Type, HandleEstablishUserMapping, true);
this.ServiceHost.SetRequestHandler(MigrateServerRolesAndSetPermissionsRequest.Type, HandleMigrateServerRolesAndSetPermissions); this.ServiceHost.SetRequestHandler(MigrateServerRolesAndSetPermissionsRequest.Type, HandleMigrateServerRolesAndSetPermissions, true);
} }
/// <summary> /// <summary>

View File

@@ -62,13 +62,13 @@ namespace Microsoft.SqlTools.ServiceLayer.ModelManagement
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(ImportModelRequest.Type, this.HandleModelImportRequest); serviceHost.SetRequestHandler(ImportModelRequest.Type, this.HandleModelImportRequest, true);
serviceHost.SetRequestHandler(ConfigureModelTableRequest.Type, this.HandleConfigureModelTableRequest); serviceHost.SetRequestHandler(ConfigureModelTableRequest.Type, this.HandleConfigureModelTableRequest, true);
serviceHost.SetRequestHandler(DeleteModelRequest.Type, this.HandleDeleteModelRequest); serviceHost.SetRequestHandler(DeleteModelRequest.Type, this.HandleDeleteModelRequest, true);
serviceHost.SetRequestHandler(DownloadModelRequest.Type, this.HandleDownloadModelRequest); serviceHost.SetRequestHandler(DownloadModelRequest.Type, this.HandleDownloadModelRequest, true);
serviceHost.SetRequestHandler(GetModelsRequest.Type, this.HandleGetModelsRequest); serviceHost.SetRequestHandler(GetModelsRequest.Type, this.HandleGetModelsRequest, true);
serviceHost.SetRequestHandler(UpdateModelRequest.Type, this.HandleUpdateModelRequest); serviceHost.SetRequestHandler(UpdateModelRequest.Type, this.HandleUpdateModelRequest, true);
serviceHost.SetRequestHandler(VerifyModelTableRequest.Type, this.HandleVerifyModelTableRequest); serviceHost.SetRequestHandler(VerifyModelTableRequest.Type, this.HandleVerifyModelTableRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -66,8 +66,8 @@ namespace Microsoft.SqlTools.ServiceLayer.NotebookConvert
{ {
this.ServiceHost = serviceHost; this.ServiceHost = serviceHost;
this.ServiceHost.SetRequestHandler(ConvertNotebookToSqlRequest.Type, HandleConvertNotebookToSqlRequest); this.ServiceHost.SetRequestHandler(ConvertNotebookToSqlRequest.Type, HandleConvertNotebookToSqlRequest, true);
this.ServiceHost.SetRequestHandler(ConvertSqlToNotebookRequest.Type, HandleConvertSqlToNotebookRequest); this.ServiceHost.SetRequestHandler(ConvertSqlToNotebookRequest.Type, HandleConvertSqlToNotebookRequest, true);
} }

View File

@@ -128,6 +128,7 @@ namespace Microsoft.SqlTools.ServiceLayer.ObjectExplorer
this.ConnectedBindingQueue.OnUnhandledException += OnUnhandledException; this.ConnectedBindingQueue.OnUnhandledException += OnUnhandledException;
// Not enabling parallel processing for OEService as it might cause OE to hang.
// Register handlers for requests // Register handlers for requests
serviceHost.SetRequestHandler(CreateSessionRequest.Type, HandleCreateSessionRequest); serviceHost.SetRequestHandler(CreateSessionRequest.Type, HandleCreateSessionRequest);
serviceHost.SetRequestHandler(ExpandRequest.Type, HandleExpandRequest); serviceHost.SetRequestHandler(ExpandRequest.Type, HandleExpandRequest);

View File

@@ -46,7 +46,7 @@ namespace Microsoft.SqlTools.ServiceLayer.ObjectManagement
public void InitializeService(IProtocolEndpoint serviceHost) public void InitializeService(IProtocolEndpoint serviceHost)
{ {
this.serviceHost = serviceHost; this.serviceHost = serviceHost;
this.serviceHost.SetRequestHandler(RenameRequest.Type, HandleRenameRequest); this.serviceHost.SetRequestHandler(RenameRequest.Type, HandleRenameRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -97,12 +97,12 @@ namespace Microsoft.SqlTools.ServiceLayer.Profiler
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
this.ServiceHost = serviceHost; this.ServiceHost = serviceHost;
this.ServiceHost.SetRequestHandler(CreateXEventSessionRequest.Type, HandleCreateXEventSessionRequest); this.ServiceHost.SetRequestHandler(CreateXEventSessionRequest.Type, HandleCreateXEventSessionRequest, true);
this.ServiceHost.SetRequestHandler(StartProfilingRequest.Type, HandleStartProfilingRequest); this.ServiceHost.SetRequestHandler(StartProfilingRequest.Type, HandleStartProfilingRequest, true);
this.ServiceHost.SetRequestHandler(StopProfilingRequest.Type, HandleStopProfilingRequest); this.ServiceHost.SetRequestHandler(StopProfilingRequest.Type, HandleStopProfilingRequest, true);
this.ServiceHost.SetRequestHandler(PauseProfilingRequest.Type, HandlePauseProfilingRequest); this.ServiceHost.SetRequestHandler(PauseProfilingRequest.Type, HandlePauseProfilingRequest, true);
this.ServiceHost.SetRequestHandler(GetXEventSessionsRequest.Type, HandleGetXEventSessionsRequest); this.ServiceHost.SetRequestHandler(GetXEventSessionsRequest.Type, HandleGetXEventSessionsRequest, true);
this.ServiceHost.SetRequestHandler(DisconnectSessionRequest.Type, HandleDisconnectSessionRequest); this.ServiceHost.SetRequestHandler(DisconnectSessionRequest.Type, HandleDisconnectSessionRequest, true);
this.SessionMonitor.AddSessionListener(this); this.SessionMonitor.AddSessionListener(this);
} }

View File

@@ -170,21 +170,21 @@ namespace Microsoft.SqlTools.ServiceLayer.QueryExecution
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
// Register handlers for requests // Register handlers for requests
serviceHost.SetRequestHandler(ExecuteDocumentSelectionRequest.Type, HandleExecuteRequest); serviceHost.SetRequestHandler(ExecuteDocumentSelectionRequest.Type, HandleExecuteRequest, true);
serviceHost.SetRequestHandler(ExecuteDocumentStatementRequest.Type, HandleExecuteRequest); serviceHost.SetRequestHandler(ExecuteDocumentStatementRequest.Type, HandleExecuteRequest, true);
serviceHost.SetRequestHandler(ExecuteStringRequest.Type, HandleExecuteRequest); serviceHost.SetRequestHandler(ExecuteStringRequest.Type, HandleExecuteRequest, true);
serviceHost.SetRequestHandler(SubsetRequest.Type, HandleResultSubsetRequest); serviceHost.SetRequestHandler(SubsetRequest.Type, HandleResultSubsetRequest, true);
serviceHost.SetRequestHandler(QueryDisposeRequest.Type, HandleDisposeRequest); serviceHost.SetRequestHandler(QueryDisposeRequest.Type, HandleDisposeRequest, true);
serviceHost.SetRequestHandler(QueryCancelRequest.Type, HandleCancelRequest); serviceHost.SetRequestHandler(QueryCancelRequest.Type, HandleCancelRequest, true);
serviceHost.SetEventHandler(ConnectionUriChangedNotification.Type, HandleConnectionUriChangedNotification); serviceHost.SetEventHandler(ConnectionUriChangedNotification.Type, HandleConnectionUriChangedNotification);
serviceHost.SetRequestHandler(SaveResultsAsCsvRequest.Type, HandleSaveResultsAsCsvRequest); serviceHost.SetRequestHandler(SaveResultsAsCsvRequest.Type, HandleSaveResultsAsCsvRequest, true);
serviceHost.SetRequestHandler(SaveResultsAsExcelRequest.Type, HandleSaveResultsAsExcelRequest); serviceHost.SetRequestHandler(SaveResultsAsExcelRequest.Type, HandleSaveResultsAsExcelRequest, true);
serviceHost.SetRequestHandler(SaveResultsAsJsonRequest.Type, HandleSaveResultsAsJsonRequest); serviceHost.SetRequestHandler(SaveResultsAsJsonRequest.Type, HandleSaveResultsAsJsonRequest, true);
serviceHost.SetRequestHandler(SaveResultsAsMarkdownRequest.Type, this.HandleSaveResultsAsMarkdownRequest); serviceHost.SetRequestHandler(SaveResultsAsMarkdownRequest.Type, this.HandleSaveResultsAsMarkdownRequest, true);
serviceHost.SetRequestHandler(SaveResultsAsXmlRequest.Type, HandleSaveResultsAsXmlRequest); serviceHost.SetRequestHandler(SaveResultsAsXmlRequest.Type, HandleSaveResultsAsXmlRequest, true);
serviceHost.SetRequestHandler(QueryExecutionPlanRequest.Type, HandleExecutionPlanRequest); serviceHost.SetRequestHandler(QueryExecutionPlanRequest.Type, HandleExecutionPlanRequest, true);
serviceHost.SetRequestHandler(SimpleExecuteRequest.Type, HandleSimpleExecuteRequest); serviceHost.SetRequestHandler(SimpleExecuteRequest.Type, HandleSimpleExecuteRequest, true);
serviceHost.SetRequestHandler(QueryExecutionOptionsRequest.Type, HandleQueryExecutionOptionsRequest); serviceHost.SetRequestHandler(QueryExecutionOptionsRequest.Type, HandleQueryExecutionOptionsRequest, true);
// Register the file open update handler // Register the file open update handler
WorkspaceService<SqlToolsSettings>.Instance.RegisterTextDocCloseCallback(HandleDidCloseTextDocumentNotification); WorkspaceService<SqlToolsSettings>.Instance.RegisterTextDocCloseCallback(HandleDidCloseTextDocumentNotification);

View File

@@ -34,8 +34,8 @@ namespace Microsoft.SqlTools.ServiceLayer.QueryExecution
public override void InitializeService(IProtocolEndpoint serviceHost) public override void InitializeService(IProtocolEndpoint serviceHost)
{ {
Logger.Write(TraceEventType.Verbose, "SerializationService initialized"); Logger.Write(TraceEventType.Verbose, "SerializationService initialized");
serviceHost.SetRequestHandler(SerializeStartRequest.Type, HandleSerializeStartRequest); serviceHost.SetRequestHandler(SerializeStartRequest.Type, HandleSerializeStartRequest, true);
serviceHost.SetRequestHandler(SerializeContinueRequest.Type, HandleSerializeContinueRequest); serviceHost.SetRequestHandler(SerializeContinueRequest.Type, HandleSerializeContinueRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -48,15 +48,15 @@ namespace Microsoft.SqlTools.ServiceLayer.SchemaCompare
/// <param name="serviceHost"></param> /// <param name="serviceHost"></param>
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(SchemaCompareRequest.Type, this.HandleSchemaCompareRequest); serviceHost.SetRequestHandler(SchemaCompareRequest.Type, this.HandleSchemaCompareRequest, true);
serviceHost.SetRequestHandler(SchemaCompareCancellationRequest.Type, this.HandleSchemaCompareCancelRequest); serviceHost.SetRequestHandler(SchemaCompareCancellationRequest.Type, this.HandleSchemaCompareCancelRequest, true);
serviceHost.SetRequestHandler(SchemaCompareGenerateScriptRequest.Type, this.HandleSchemaCompareGenerateScriptRequest); serviceHost.SetRequestHandler(SchemaCompareGenerateScriptRequest.Type, this.HandleSchemaCompareGenerateScriptRequest, true);
serviceHost.SetRequestHandler(SchemaComparePublishDatabaseChangesRequest.Type, this.HandleSchemaComparePublishDatabaseChangesRequest); serviceHost.SetRequestHandler(SchemaComparePublishDatabaseChangesRequest.Type, this.HandleSchemaComparePublishDatabaseChangesRequest, true);
serviceHost.SetRequestHandler(SchemaComparePublishProjectChangesRequest.Type, this.HandleSchemaComparePublishProjectChangesRequest); serviceHost.SetRequestHandler(SchemaComparePublishProjectChangesRequest.Type, this.HandleSchemaComparePublishProjectChangesRequest, true);
serviceHost.SetRequestHandler(SchemaCompareIncludeExcludeNodeRequest.Type, this.HandleSchemaCompareIncludeExcludeNodeRequest); serviceHost.SetRequestHandler(SchemaCompareIncludeExcludeNodeRequest.Type, this.HandleSchemaCompareIncludeExcludeNodeRequest, true);
serviceHost.SetRequestHandler(SchemaCompareGetDefaultOptionsRequest.Type, this.HandleSchemaCompareGetDefaultOptionsRequest); serviceHost.SetRequestHandler(SchemaCompareGetDefaultOptionsRequest.Type, this.HandleSchemaCompareGetDefaultOptionsRequest, true);
serviceHost.SetRequestHandler(SchemaCompareOpenScmpRequest.Type, this.HandleSchemaCompareOpenScmpRequest); serviceHost.SetRequestHandler(SchemaCompareOpenScmpRequest.Type, this.HandleSchemaCompareOpenScmpRequest, true);
serviceHost.SetRequestHandler(SchemaCompareSaveScmpRequest.Type, this.HandleSchemaCompareSaveScmpRequest); serviceHost.SetRequestHandler(SchemaCompareSaveScmpRequest.Type, this.HandleSchemaCompareSaveScmpRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -65,9 +65,9 @@ namespace Microsoft.SqlTools.ServiceLayer.Scripting
/// <param name="context"></param> /// <param name="context"></param>
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(ScriptingRequest.Type, this.HandleScriptExecuteRequest); serviceHost.SetRequestHandler(ScriptingRequest.Type, this.HandleScriptExecuteRequest, true);
serviceHost.SetRequestHandler(ScriptingCancelRequest.Type, this.HandleScriptCancelRequest); serviceHost.SetRequestHandler(ScriptingCancelRequest.Type, this.HandleScriptCancelRequest, true);
serviceHost.SetRequestHandler(ScriptingListObjectsRequest.Type, this.HandleListObjectsRequest); serviceHost.SetRequestHandler(ScriptingListObjectsRequest.Type, this.HandleListObjectsRequest, true);
// Register handler for shutdown event // Register handler for shutdown event
serviceHost.RegisterShutdownTask((shutdownParams, requestContext) => serviceHost.RegisterShutdownTask((shutdownParams, requestContext) =>

View File

@@ -75,10 +75,10 @@ namespace Microsoft.SqlTools.ServiceLayer.Security
this.ServiceHost = serviceHost; this.ServiceHost = serviceHost;
// Credential request handlers // Credential request handlers
this.ServiceHost.SetRequestHandler(CreateCredentialRequest.Type, HandleCreateCredentialRequest); this.ServiceHost.SetRequestHandler(CreateCredentialRequest.Type, HandleCreateCredentialRequest, true);
this.ServiceHost.SetRequestHandler(UpdateCredentialRequest.Type, HandleUpdateCredentialRequest); this.ServiceHost.SetRequestHandler(UpdateCredentialRequest.Type, HandleUpdateCredentialRequest, true);
this.ServiceHost.SetRequestHandler(DeleteCredentialRequest.Type, HandleDeleteCredentialRequest); this.ServiceHost.SetRequestHandler(DeleteCredentialRequest.Type, HandleDeleteCredentialRequest, true);
this.ServiceHost.SetRequestHandler(GetCredentialsRequest.Type, HandleGetCredentialsRequest); this.ServiceHost.SetRequestHandler(GetCredentialsRequest.Type, HandleGetCredentialsRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -49,9 +49,9 @@ namespace Microsoft.SqlTools.ServiceLayer.ServerConfigurations
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
serviceHost.SetRequestHandler(ServerConfigViewRequest.Type, this.HandleServerConfigViewRequest); serviceHost.SetRequestHandler(ServerConfigViewRequest.Type, this.HandleServerConfigViewRequest, true);
serviceHost.SetRequestHandler(ServerConfigUpdateRequest.Type, this.HandleServerConfigUpdateRequest); serviceHost.SetRequestHandler(ServerConfigUpdateRequest.Type, this.HandleServerConfigUpdateRequest, true);
serviceHost.SetRequestHandler(ServerConfigListRequest.Type, this.HandleServerConfigListRequest); serviceHost.SetRequestHandler(ServerConfigListRequest.Type, this.HandleServerConfigListRequest, true);
} }
/// <summary> /// <summary>

View File

@@ -102,9 +102,9 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlAssessment
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
// Register handlers for requests // Register handlers for requests
serviceHost.SetRequestHandler(InvokeRequest.Type, HandleInvokeRequest); serviceHost.SetRequestHandler(InvokeRequest.Type, HandleInvokeRequest, true);
serviceHost.SetRequestHandler(GetAssessmentItemsRequest.Type, HandleGetAssessmentItemsRequest); serviceHost.SetRequestHandler(GetAssessmentItemsRequest.Type, HandleGetAssessmentItemsRequest, true);
serviceHost.SetRequestHandler(GenerateScriptRequest.Type, HandleGenerateScriptRequest); serviceHost.SetRequestHandler(GenerateScriptRequest.Type, HandleGenerateScriptRequest, true);
// Register handler for shutdown event // Register handler for shutdown event
serviceHost.RegisterShutdownTask((shutdownParams, requestContext) => serviceHost.RegisterShutdownTask((shutdownParams, requestContext) =>

View File

@@ -58,12 +58,12 @@ namespace Microsoft.SqlTools.ServiceLayer.TableDesigner
public void InitializeService(ServiceHost serviceHost) public void InitializeService(ServiceHost serviceHost)
{ {
this.ServiceHost = serviceHost; this.ServiceHost = serviceHost;
this.ServiceHost.SetRequestHandler(InitializeTableDesignerRequest.Type, HandleInitializeTableDesignerRequest); this.ServiceHost.SetRequestHandler(InitializeTableDesignerRequest.Type, HandleInitializeTableDesignerRequest, true);
this.ServiceHost.SetRequestHandler(ProcessTableDesignerEditRequest.Type, HandleProcessTableDesignerEditRequest); this.ServiceHost.SetRequestHandler(ProcessTableDesignerEditRequest.Type, HandleProcessTableDesignerEditRequest, true);
this.ServiceHost.SetRequestHandler(PublishTableChangesRequest.Type, HandlePublishTableChangesRequest); this.ServiceHost.SetRequestHandler(PublishTableChangesRequest.Type, HandlePublishTableChangesRequest, true);
this.ServiceHost.SetRequestHandler(GenerateScriptRequest.Type, HandleGenerateScriptRequest); this.ServiceHost.SetRequestHandler(GenerateScriptRequest.Type, HandleGenerateScriptRequest, true);
this.ServiceHost.SetRequestHandler(GeneratePreviewReportRequest.Type, HandleGeneratePreviewReportRequest); this.ServiceHost.SetRequestHandler(GeneratePreviewReportRequest.Type, HandleGeneratePreviewReportRequest, true);
this.ServiceHost.SetRequestHandler(DisposeTableDesignerRequest.Type, HandleDisposeTableDesignerRequest); this.ServiceHost.SetRequestHandler(DisposeTableDesignerRequest.Type, HandleDisposeTableDesignerRequest, true);
Workspace.WorkspaceService<SqlToolsSettings>.Instance.RegisterConfigChangeCallback(UpdateSettings); Workspace.WorkspaceService<SqlToolsSettings>.Instance.RegisterConfigChangeCallback(UpdateSettings);
} }

View File

@@ -52,8 +52,8 @@ namespace Microsoft.SqlTools.ServiceLayer.TaskServices
{ {
this.serviceHost = serviceHost; this.serviceHost = serviceHost;
Logger.Write(TraceEventType.Verbose, "TaskService initialized"); Logger.Write(TraceEventType.Verbose, "TaskService initialized");
serviceHost.SetRequestHandler(ListTasksRequest.Type, HandleListTasksRequest); serviceHost.SetRequestHandler(ListTasksRequest.Type, HandleListTasksRequest, true);
serviceHost.SetRequestHandler(CancelTaskRequest.Type, HandleCancelTaskRequest); serviceHost.SetRequestHandler(CancelTaskRequest.Type, HandleCancelTaskRequest, true);
TaskManager.TaskAdded += OnTaskAdded; TaskManager.TaskAdded += OnTaskAdded;
} }

View File

@@ -127,6 +127,7 @@ namespace Microsoft.SqlTools.ServiceLayer.Workspace
// Create a workspace that will handle state for the session // Create a workspace that will handle state for the session
Workspace = new Workspace(); Workspace = new Workspace();
// Not enabling parallel processing for WorkspaceService as it might cause doc out of sync.
// Register the handlers for when changes to the workspae occur // Register the handlers for when changes to the workspae occur
serviceHost.SetEventHandler(DidChangeTextDocumentNotification.Type, HandleDidChangeTextDocumentNotification); serviceHost.SetEventHandler(DidChangeTextDocumentNotification.Type, HandleDidChangeTextDocumentNotification);
serviceHost.SetEventHandler(DidOpenTextDocumentNotification.Type, HandleDidOpenTextDocumentNotification); serviceHost.SetEventHandler(DidOpenTextDocumentNotification.Type, HandleDidOpenTextDocumentNotification);

View File

@@ -4,6 +4,8 @@
// //
using System; using System;
using System.Diagnostics;
using System.Threading;
using System.Threading.Tasks; using System.Threading.Tasks;
using Microsoft.SqlTools.Hosting.Protocol; using Microsoft.SqlTools.Hosting.Protocol;
using Microsoft.SqlTools.Hosting.Protocol.Channel; using Microsoft.SqlTools.Hosting.Protocol.Channel;
@@ -84,5 +86,70 @@ namespace Microsoft.SqlTools.ServiceLayer.UnitTests.Messaging
Assert.True(handlerCalled); Assert.True(handlerCalled);
} }
} }
[Test]
public void ParallelMessageProcessingTest()
{
int numOfRequests = 10;
int msForEachRequest = 1000;
// Without parallel processing, this should take around numOfRequests * msForEachRequest ms to finish.
// With parallel process, this should take around 1 * msForEachRequest ms to finish.
// The diff should be around (numOfRequests - 1) * msForEachRequest ms.
// In order to make this test stable, we loose the assertion by checking the diff against
// (numOfRequests / 2) * msForEachRequest ms, which should for sure pass.
Assert.IsTrue(GetTimeToHandleRequests(false, numOfRequests, msForEachRequest) - GetTimeToHandleRequests(true, numOfRequests, msForEachRequest) > msForEachRequest * (numOfRequests / 2));
}
/// <summary>
/// Gets the time to handle certain amount of requests in ms
/// </summary>
/// <param name="parallelMessageProcessing">Wheater to enable parallel processing</param>
/// <param name="numOfRequests">num of requests to handle</param>
/// <param name="msForEachRequest">rough time taken to finish each reqeust in ms</param>
/// <returns></returns>
private long GetTimeToHandleRequests(bool parallelMessageProcessing, int numOfRequests, int msForEachRequest)
{
RequestType<int, int> requestType = RequestType<int, int>.Create("test/requestType");
var mockChannel = new Mock<ChannelBase>();
SemaphoreSlim unfinishedRequestCount = new SemaphoreSlim(numOfRequests);
bool okayToEnd = false;
mockChannel.Setup(c => c.MessageReader.ReadMessage())
.Returns(Task.FromResult(Message.Request("1", "test/requestType", null)));
var dispatcher = new MessageDispatcher(mockChannel.Object);
dispatcher.ParallelMessageProcessing = parallelMessageProcessing;
Stopwatch stopwatch = Stopwatch.StartNew();
var handler = async (int _, RequestContext<int> _) =>
{
// simulate a slow sync call
Thread.Sleep(msForEachRequest / 2);
// simulate a delay async call
await Task.Delay(msForEachRequest / 2);
await unfinishedRequestCount.WaitAsync();
if (unfinishedRequestCount.CurrentCount == 0)
{
// cut off when we reach numOfRequests
stopwatch.Stop();
okayToEnd = true;
}
await Task.CompletedTask;
};
dispatcher.SetRequestHandler(requestType, handler, false, true);
dispatcher.Start();
while (true)
{
if (okayToEnd)
{
// wait until we finish handling the required amount of requests
break;
}
Thread.Sleep(1000);
}
dispatcher.Stop();
return stopwatch.ElapsedMilliseconds;
}
} }
} }