public async Task SubsetServiceOutOfRangeSubsetTest() { // If: // ... I have a query that doesn't have any result sets var workspaceService = Common.GetPrimedWorkspaceService(Constants.StandardQuery); var queryService = Common.GetPrimedExecutionService(null, true, false, workspaceService); var executeParams = new ExecuteDocumentSelectionParams { QuerySelection = null, OwnerUri = Constants.OwnerUri }; var executeRequest = RequestContextMocks.Create <ExecuteRequestResult>(null); await queryService.HandleExecuteRequest(executeParams, executeRequest.Object); await queryService.ActiveQueries[Constants.OwnerUri].ExecutionTask; // ... And I then ask for a set of results from it var subsetParams = new SubsetParams { OwnerUri = Constants.OwnerUri, RowsCount = 1, ResultSetIndex = 0, RowsStartIndex = 0 }; var subsetRequest = new EventFlowValidator <SubsetResult>() .AddStandardErrorValidation() .Complete(); await queryService.HandleResultSubsetRequest(subsetParams, subsetRequest.Object); subsetRequest.Validate(); }
public async Task SubsetServiceValidTest() { // If: // ... I have a query that has results (doesn't matter what) var workspaceService = Common.GetPrimedWorkspaceService(Constants.StandardQuery); var queryService = Common.GetPrimedExecutionService(Common.ExecutionPlanTestDataSet, true, false, workspaceService); var executeParams = new ExecuteDocumentSelectionParams { QuerySelection = null, OwnerUri = Constants.OwnerUri }; var executeRequest = RequestContextMocks.Create <ExecuteRequestResult>(null); await queryService.HandleExecuteRequest(executeParams, executeRequest.Object); await queryService.ActiveQueries[Constants.OwnerUri].ExecutionTask; // ... And I then ask for a valid set of results from it var subsetParams = new SubsetParams { OwnerUri = Constants.OwnerUri, RowsCount = 1, ResultSetIndex = 0, RowsStartIndex = 0 }; var subsetRequest = new EventFlowValidator <SubsetResult>() .AddResultValidation(r => { // Then: Subset should not be null Assert.NotNull(r.ResultSubset); }).Complete(); await queryService.HandleResultSubsetRequest(subsetParams, subsetRequest.Object); subsetRequest.Validate(); }
public async Task SubsetServiceUnexecutedQueryTest() { // If: // ... I have a query that hasn't finished executing (doesn't matter what) var workspaceService = Common.GetPrimedWorkspaceService(Constants.StandardQuery); var queryService = Common.GetPrimedExecutionService(Common.StandardTestDataSet, true, false, workspaceService); var executeParams = new ExecuteDocumentSelectionParams { QuerySelection = null, OwnerUri = Constants.OwnerUri }; var executeRequest = RequestContextMocks.Create <ExecuteRequestResult>(null); await queryService.HandleExecuteRequest(executeParams, executeRequest.Object); await queryService.ActiveQueries[Constants.OwnerUri].ExecutionTask; queryService.ActiveQueries[Constants.OwnerUri].Batches[0].ResultSets[0].hasBeenRead = false; // ... And I then ask for a valid set of results from it var subsetParams = new SubsetParams { OwnerUri = Constants.OwnerUri, RowsCount = 1, ResultSetIndex = 0, RowsStartIndex = 0 }; var subsetRequest = new EventFlowValidator <SubsetResult>() .AddStandardErrorValidation() .Complete(); await queryService.HandleResultSubsetRequest(subsetParams, subsetRequest.Object); subsetRequest.Validate(); }
/// <summary> /// Request a subset of results from a query /// </summary> public async Task <SubsetResult> ExecuteSubset(string ownerUri, int batchIndex, int resultSetIndex, int rowStartIndex, int rowCount) { var subsetParams = new SubsetParams(); subsetParams.OwnerUri = ownerUri; subsetParams.BatchIndex = batchIndex; subsetParams.ResultSetIndex = resultSetIndex; subsetParams.RowsStartIndex = rowStartIndex; subsetParams.RowsCount = rowCount; var result = await Driver.SendRequest(SubsetRequest.Type, subsetParams); return(result); }
/// <summary> /// Handles a request to get a subset of the results of this query /// </summary> internal async Task HandleResultSubsetRequest(SubsetParams subsetParams, RequestContext <SubsetResult> requestContext) { try { // Attempt to load the query Query query; if (!ActiveQueries.TryGetValue(subsetParams.OwnerUri, out query)) { await requestContext.SendResult(new SubsetResult { Message = SR.QueryServiceRequestsNoQuery }); return; } // Retrieve the requested subset and return it var result = new SubsetResult { Message = null, ResultSubset = await query.GetSubset(subsetParams.BatchIndex, subsetParams.ResultSetIndex, subsetParams.RowsStartIndex, subsetParams.RowsCount) }; await requestContext.SendResult(result); } catch (InvalidOperationException ioe) { // Return the error as a result await requestContext.SendResult(new SubsetResult { Message = ioe.Message }); } catch (ArgumentOutOfRangeException aoore) { // Return the error as a result await requestContext.SendResult(new SubsetResult { Message = aoore.Message }); } catch (Exception e) { // This was unexpected, so send back as error await requestContext.SendError(e.Message); } }
/// <summary> /// Retrieves the requested subset of rows from the requested result set. Intended to be /// called by another service. /// </summary> /// <param name="subsetParams">Parameters for the subset to retrieve</param> /// <returns>The requested subset</returns> /// <exception cref="ArgumentOutOfRangeException">The requested query does not exist</exception> public async Task <ResultSetSubset> InterServiceResultSubset(SubsetParams subsetParams) { Validate.IsNotNullOrEmptyString(nameof(subsetParams.OwnerUri), subsetParams.OwnerUri); // Attempt to load the query Query query; if (!ActiveQueries.TryGetValue(subsetParams.OwnerUri, out query)) { throw new ArgumentOutOfRangeException(SR.QueryServiceRequestsNoQuery); } // Retrieve the requested subset and return it return(await query.GetSubset(subsetParams.BatchIndex, subsetParams.ResultSetIndex, subsetParams.RowsStartIndex, subsetParams.RowsCount)); }
public async Task SubsetServiceMissingQueryTest() { // If: // ... I ask for a set of results for a file that hasn't executed a query var workspaceService = Common.GetPrimedWorkspaceService(Constants.StandardQuery); var queryService = Common.GetPrimedExecutionService(null, true, false, workspaceService); var subsetParams = new SubsetParams { OwnerUri = Constants.OwnerUri, RowsCount = 1, ResultSetIndex = 0, RowsStartIndex = 0 }; var subsetRequest = new EventFlowValidator <SubsetResult>() .AddStandardErrorValidation() .Complete(); await queryService.HandleResultSubsetRequest(subsetParams, subsetRequest.Object); subsetRequest.Validate(); }
/// <summary> /// Handles a request to get a subset of the results of this query /// </summary> internal async Task HandleResultSubsetRequest(SubsetParams subsetParams, RequestContext <SubsetResult> requestContext) { try { ResultSetSubset subset = await InterServiceResultSubset(subsetParams); var result = new SubsetResult { ResultSubset = subset }; await requestContext.SendResult(result); } catch (Exception e) { // This was unexpected, so send back as error await requestContext.SendError(e.Message); } }
public async Task SubsetServiceMissingQueryTest() { // If: // ... I ask for a set of results for a file that hasn't executed a query var workspaceService = Common.GetPrimedWorkspaceService(Common.StandardQuery); var queryService = Common.GetPrimedExecutionService(null, true, false, workspaceService); var subsetParams = new SubsetParams { OwnerUri = Common.OwnerUri, RowsCount = 1, ResultSetIndex = 0, RowsStartIndex = 0 }; var subsetRequest = new EventFlowValidator <SubsetResult>() .AddResultValidation(r => { // Then: Messages should not be null and the subset should be null Assert.NotNull(r.Message); Assert.Null(r.ResultSubset); }).Complete(); await queryService.HandleResultSubsetRequest(subsetParams, subsetRequest.Object); subsetRequest.Validate(); }
/// <summary> /// Handles a request to get a subset of the results of this query /// </summary> internal async Task HandleResultSubsetRequest(SubsetParams subsetParams, RequestContext <SubsetResult> requestContext) { try { ResultSetSubset subset = await InterServiceResultSubset(subsetParams); var result = new SubsetResult { ResultSubset = subset }; await requestContext.SendResult(result); Logger.Write(TraceEventType.Stop, $"Done Handler for Subset request with for Query:'{subsetParams.OwnerUri}', Batch:'{subsetParams.BatchIndex}', ResultSetIndex:'{subsetParams.ResultSetIndex}', RowsStartIndex'{subsetParams.RowsStartIndex}', Requested RowsCount:'{subsetParams.RowsCount}'\r\n\t\t with subset response of:[ RowCount:'{subset.RowCount}', Rows array of length:'{subset.Rows.Length}']"); } catch (Exception e) { // This was unexpected, so send back as error await requestContext.SendError(e.Message); } }
/// <summary> /// Handles a request to execute a string and return the result /// </summary> internal async Task HandleSimpleExecuteRequest(SimpleExecuteParams executeParams, RequestContext <SimpleExecuteResult> requestContext) { try { string randomUri = Guid.NewGuid().ToString(); ExecuteStringParams executeStringParams = new ExecuteStringParams { Query = executeParams.QueryString, // generate guid as the owner uri to make sure every query is unique OwnerUri = randomUri }; // get connection ConnectionInfo connInfo; if (!ConnectionService.TryFindConnection(executeParams.OwnerUri, out connInfo)) { await requestContext.SendError(SR.QueryServiceQueryInvalidOwnerUri); return; } ConnectParams connectParams = new ConnectParams { OwnerUri = randomUri, Connection = connInfo.ConnectionDetails, Type = ConnectionType.Default }; Task workTask = Task.Run(async() => { await ConnectionService.Connect(connectParams); ConnectionInfo newConn; ConnectionService.TryFindConnection(randomUri, out newConn); Func <string, Task> queryCreateFailureAction = message => requestContext.SendError(message); ResultOnlyContext <SimpleExecuteResult> newContext = new ResultOnlyContext <SimpleExecuteResult>(requestContext); // handle sending event back when the query completes Query.QueryAsyncEventHandler queryComplete = async query => { try { // check to make sure any results were recieved if (query.Batches.Length == 0 || query.Batches[0].ResultSets.Count == 0) { await requestContext.SendError(SR.QueryServiceResultSetHasNoResults); return; } long rowCount = query.Batches[0].ResultSets[0].RowCount; // check to make sure there is a safe amount of rows to load into memory if (rowCount > Int32.MaxValue) { await requestContext.SendError(SR.QueryServiceResultSetTooLarge); return; } SimpleExecuteResult result = new SimpleExecuteResult { RowCount = rowCount, ColumnInfo = query.Batches[0].ResultSets[0].Columns, Rows = new DbCellValue[0][] }; if (rowCount > 0) { SubsetParams subsetRequestParams = new SubsetParams { OwnerUri = randomUri, BatchIndex = 0, ResultSetIndex = 0, RowsStartIndex = 0, RowsCount = Convert.ToInt32(rowCount) }; // get the data to send back ResultSetSubset subset = await InterServiceResultSubset(subsetRequestParams); result.Rows = subset.Rows; } await requestContext.SendResult(result); } finally { Query removedQuery; Task removedTask; // remove the active query since we are done with it ActiveQueries.TryRemove(randomUri, out removedQuery); ActiveSimpleExecuteRequests.TryRemove(randomUri, out removedTask); ConnectionService.Disconnect(new DisconnectParams() { OwnerUri = randomUri, Type = null }); } }; // handle sending error back when query fails Query.QueryAsyncErrorEventHandler queryFail = async(q, e) => { await requestContext.SendError(e); }; await InterServiceExecuteQuery(executeStringParams, newConn, newContext, null, queryCreateFailureAction, queryComplete, queryFail); }); ActiveSimpleExecuteRequests.TryAdd(randomUri, workTask); } catch (Exception ex) { await requestContext.SendError(ex.ToString()); } }
/// <summary> /// Request the active SQL script is parsed for errors /// </summary> public async Task <SubsetResult> RequestQueryExecuteSubset(SubsetParams subsetParams) { return(await Driver.SendRequest(SubsetRequest.Type, subsetParams)); }
/// <summary> /// Handles a request to execute a string and return the result /// </summary> internal Task HandleSimpleExecuteRequest(SimpleExecuteParams executeParams, RequestContext <SimpleExecuteResult> requestContext) { ExecuteStringParams executeStringParams = new ExecuteStringParams { Query = executeParams.QueryString, // generate guid as the owner uri to make sure every query is unique OwnerUri = Guid.NewGuid().ToString() }; // get connection ConnectionInfo connInfo; if (!ConnectionService.TryFindConnection(executeParams.OwnerUri, out connInfo)) { return(requestContext.SendError(SR.QueryServiceQueryInvalidOwnerUri)); } if (connInfo.ConnectionDetails.MultipleActiveResultSets == null || connInfo.ConnectionDetails.MultipleActiveResultSets == false) { // if multipleActive result sets is not allowed, don't specific a connection and make the ownerURI the true owneruri connInfo = null; executeStringParams.OwnerUri = executeParams.OwnerUri; } Func <string, Task> queryCreateFailureAction = message => requestContext.SendError(message); ResultOnlyContext <SimpleExecuteResult> newContext = new ResultOnlyContext <SimpleExecuteResult>(requestContext); // handle sending event back when the query completes Query.QueryAsyncEventHandler queryComplete = async q => { Query removedQuery; // check to make sure any results were recieved if (q.Batches.Length == 0 || q.Batches[0].ResultSets.Count == 0) { await requestContext.SendError(SR.QueryServiceResultSetHasNoResults); ActiveQueries.TryRemove(executeStringParams.OwnerUri, out removedQuery); return; } var rowCount = q.Batches[0].ResultSets[0].RowCount; // check to make sure there is a safe amount of rows to load into memory if (rowCount > Int32.MaxValue) { await requestContext.SendError(SR.QueryServiceResultSetTooLarge); ActiveQueries.TryRemove(executeStringParams.OwnerUri, out removedQuery); return; } SubsetParams subsetRequestParams = new SubsetParams { OwnerUri = executeStringParams.OwnerUri, BatchIndex = 0, ResultSetIndex = 0, RowsStartIndex = 0, RowsCount = Convert.ToInt32(rowCount) }; // get the data to send back ResultSetSubset subset = await InterServiceResultSubset(subsetRequestParams); SimpleExecuteResult result = new SimpleExecuteResult { RowCount = q.Batches[0].ResultSets[0].RowCount, ColumnInfo = q.Batches[0].ResultSets[0].Columns, Rows = subset.Rows }; await requestContext.SendResult(result); // remove the active query since we are done with it ActiveQueries.TryRemove(executeStringParams.OwnerUri, out removedQuery); }; // handle sending error back when query fails Query.QueryAsyncErrorEventHandler queryFail = async(q, e) => { await requestContext.SendError(e); }; return(InterServiceExecuteQuery(executeStringParams, connInfo, newContext, null, queryCreateFailureAction, queryComplete, queryFail)); }