mirror of
https://github.com/ckaczor/sqltoolsservice.git
synced 2026-01-18 09:35:38 -05:00
Send Error Object on SendError (#304)
This change ensures that when calling `requestContext.SendError` you are only able to supply parameters that match the language service beta protocol expected Error object. In other words, you have to provide an error message and optionally and error code. # **BREAKING API CHANGES** This will break displaying errors in Microsoft/vscode-mssql. I will be making changes to properly handle the error object shortly. * Adding contract for returning Error objects as per LanguageService "protocol" * Fixes throughout codebase to send only error message in error cases Cleanup of CredentialServiceTest unit test class Adding standard error handling for event flow validator * Adding optional data field as per protocol spec https://github.com/Microsoft/language-server-protocol/blob/master/protocol.md * Adding optional validation for error objects
This commit is contained in:
@@ -14,16 +14,5 @@ namespace Microsoft.SqlTools.ServiceLayer.LanguageServices.Contracts
|
||||
RequestType<TextDocumentPosition, Location[]> Type =
|
||||
RequestType<TextDocumentPosition, Location[]>.Create("textDocument/definition");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Error object for Definition
|
||||
/// </summary>
|
||||
public class DefinitionError
|
||||
{
|
||||
/// <summary>
|
||||
/// Error message
|
||||
/// </summary>
|
||||
public string message { get; set; }
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -319,7 +319,7 @@ namespace Microsoft.SqlTools.ServiceLayer.LanguageServices
|
||||
{
|
||||
if (definitionResult.IsErrorResult)
|
||||
{
|
||||
await requestContext.SendError( new DefinitionError { message = definitionResult.Message });
|
||||
await requestContext.SendError(definitionResult.Message);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -820,52 +820,52 @@ namespace Microsoft.SqlTools.ServiceLayer.LanguageServices
|
||||
return result;
|
||||
}
|
||||
|
||||
private DefinitionResult GetDefinitionFromTokenList(TextDocumentPosition textDocumentPosition, List<Token> tokenList,
|
||||
ScriptParseInfo scriptParseInfo, ScriptFile scriptFile, ConnectionInfo connInfo)
|
||||
{
|
||||
|
||||
DefinitionResult lastResult = null;
|
||||
foreach (var token in tokenList)
|
||||
{
|
||||
|
||||
// Strip "[" and "]"(if present) from the token text to enable matching with the suggestions.
|
||||
// The suggestion title does not contain any sql punctuation
|
||||
string tokenText = TextUtilities.RemoveSquareBracketSyntax(token.Text);
|
||||
textDocumentPosition.Position.Line = token.StartLocation.LineNumber;
|
||||
textDocumentPosition.Position.Character = token.StartLocation.ColumnNumber;
|
||||
if (Monitor.TryEnter(scriptParseInfo.BuildingMetadataLock))
|
||||
{
|
||||
try
|
||||
{
|
||||
var result = QueueTask(textDocumentPosition, scriptParseInfo, connInfo, scriptFile, tokenText);
|
||||
lastResult = result;
|
||||
if (!result.IsErrorResult)
|
||||
{
|
||||
return result;
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
// if any exceptions are raised return error result with message
|
||||
Logger.Write(LogLevel.Error, "Exception in GetDefinition " + ex.ToString());
|
||||
return new DefinitionResult
|
||||
{
|
||||
IsErrorResult = true,
|
||||
Message = SR.PeekDefinitionError(ex.Message),
|
||||
Locations = null
|
||||
};
|
||||
}
|
||||
finally
|
||||
{
|
||||
Monitor.Exit(scriptParseInfo.BuildingMetadataLock);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Logger.Write(LogLevel.Error, "Timeout waiting to query metadata from server");
|
||||
}
|
||||
}
|
||||
return (lastResult != null) ? lastResult : null;
|
||||
private DefinitionResult GetDefinitionFromTokenList(TextDocumentPosition textDocumentPosition, List<Token> tokenList,
|
||||
ScriptParseInfo scriptParseInfo, ScriptFile scriptFile, ConnectionInfo connInfo)
|
||||
{
|
||||
|
||||
DefinitionResult lastResult = null;
|
||||
foreach (var token in tokenList)
|
||||
{
|
||||
|
||||
// Strip "[" and "]"(if present) from the token text to enable matching with the suggestions.
|
||||
// The suggestion title does not contain any sql punctuation
|
||||
string tokenText = TextUtilities.RemoveSquareBracketSyntax(token.Text);
|
||||
textDocumentPosition.Position.Line = token.StartLocation.LineNumber;
|
||||
textDocumentPosition.Position.Character = token.StartLocation.ColumnNumber;
|
||||
if (Monitor.TryEnter(scriptParseInfo.BuildingMetadataLock))
|
||||
{
|
||||
try
|
||||
{
|
||||
var result = QueueTask(textDocumentPosition, scriptParseInfo, connInfo, scriptFile, tokenText);
|
||||
lastResult = result;
|
||||
if (!result.IsErrorResult)
|
||||
{
|
||||
return result;
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
// if any exceptions are raised return error result with message
|
||||
Logger.Write(LogLevel.Error, "Exception in GetDefinition " + ex.ToString());
|
||||
return new DefinitionResult
|
||||
{
|
||||
IsErrorResult = true,
|
||||
Message = SR.PeekDefinitionError(ex.Message),
|
||||
Locations = null
|
||||
};
|
||||
}
|
||||
finally
|
||||
{
|
||||
Monitor.Exit(scriptParseInfo.BuildingMetadataLock);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Logger.Write(LogLevel.Error, "Timeout waiting to query metadata from server");
|
||||
}
|
||||
}
|
||||
return (lastResult != null) ? lastResult : null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -898,36 +898,36 @@ namespace Microsoft.SqlTools.ServiceLayer.LanguageServices
|
||||
return null;
|
||||
}
|
||||
|
||||
if (scriptParseInfo.IsConnected)
|
||||
{
|
||||
//try children tokens first
|
||||
Stack<Token> childrenTokens = selectedToken.Item1;
|
||||
List<Token> tokenList = childrenTokens.ToList();
|
||||
DefinitionResult childrenResult = GetDefinitionFromTokenList(textDocumentPosition, tokenList, scriptParseInfo, scriptFile, connInfo);
|
||||
|
||||
// if the children peak definition returned null then
|
||||
// try the parents
|
||||
if (childrenResult == null || childrenResult.IsErrorResult)
|
||||
{
|
||||
Queue<Token> parentTokens = selectedToken.Item2;
|
||||
tokenList = parentTokens.ToList();
|
||||
DefinitionResult parentResult = GetDefinitionFromTokenList(textDocumentPosition, tokenList, scriptParseInfo, scriptFile, connInfo);
|
||||
return (parentResult == null) ? null : parentResult;
|
||||
}
|
||||
else
|
||||
{
|
||||
return childrenResult;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// User is not connected.
|
||||
return new DefinitionResult
|
||||
{
|
||||
IsErrorResult = true,
|
||||
Message = SR.PeekDefinitionNotConnectedError,
|
||||
Locations = null
|
||||
};
|
||||
if (scriptParseInfo.IsConnected)
|
||||
{
|
||||
//try children tokens first
|
||||
Stack<Token> childrenTokens = selectedToken.Item1;
|
||||
List<Token> tokenList = childrenTokens.ToList();
|
||||
DefinitionResult childrenResult = GetDefinitionFromTokenList(textDocumentPosition, tokenList, scriptParseInfo, scriptFile, connInfo);
|
||||
|
||||
// if the children peak definition returned null then
|
||||
// try the parents
|
||||
if (childrenResult == null || childrenResult.IsErrorResult)
|
||||
{
|
||||
Queue<Token> parentTokens = selectedToken.Item2;
|
||||
tokenList = parentTokens.ToList();
|
||||
DefinitionResult parentResult = GetDefinitionFromTokenList(textDocumentPosition, tokenList, scriptParseInfo, scriptFile, connInfo);
|
||||
return (parentResult == null) ? null : parentResult;
|
||||
}
|
||||
else
|
||||
{
|
||||
return childrenResult;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// User is not connected.
|
||||
return new DefinitionResult
|
||||
{
|
||||
IsErrorResult = true,
|
||||
Message = SR.PeekDefinitionNotConnectedError,
|
||||
Locations = null
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -110,17 +110,6 @@ namespace Microsoft.SqlTools.ServiceLayer.QueryExecution.Contracts
|
||||
public string Messages { get; set; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Error object for save result
|
||||
/// </summary>
|
||||
public class SaveResultRequestError
|
||||
{
|
||||
/// <summary>
|
||||
/// Error message
|
||||
/// </summary>
|
||||
public string message { get; set; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Request type to save results as CSV
|
||||
/// </summary>
|
||||
|
||||
@@ -162,7 +162,7 @@ namespace Microsoft.SqlTools.ServiceLayer.QueryExecution
|
||||
await requestContext.SendResult(new ExecuteRequestResult());
|
||||
return true;
|
||||
};
|
||||
Func<string, Task> queryCreateFailureAction = requestContext.SendError;
|
||||
Func<string, Task> queryCreateFailureAction = message => requestContext.SendError(message);
|
||||
|
||||
// Use the internal handler to launch the query
|
||||
return InterServiceExecuteQuery(executeParams, requestContext, queryCreateSuccessAction, queryCreateFailureAction, null, null);
|
||||
@@ -228,7 +228,7 @@ namespace Microsoft.SqlTools.ServiceLayer.QueryExecution
|
||||
{
|
||||
// Setup action for success and failure
|
||||
Func<Task> successAction = () => requestContext.SendResult(new QueryDisposeResult());
|
||||
Func<string, Task> failureAction = requestContext.SendError;
|
||||
Func<string, Task> failureAction = message => requestContext.SendError(message);
|
||||
|
||||
// Use the inter-service dispose functionality
|
||||
await InterServiceDisposeQuery(disposeParams.OwnerUri, successAction, failureAction);
|
||||
@@ -559,10 +559,7 @@ namespace Microsoft.SqlTools.ServiceLayer.QueryExecution
|
||||
Query query;
|
||||
if (!ActiveQueries.TryGetValue(saveParams.OwnerUri, out query))
|
||||
{
|
||||
await requestContext.SendError(new SaveResultRequestError
|
||||
{
|
||||
message = SR.QueryServiceQueryInvalidOwnerUri
|
||||
});
|
||||
await requestContext.SendError(SR.QueryServiceQueryInvalidOwnerUri);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -574,7 +571,7 @@ namespace Microsoft.SqlTools.ServiceLayer.QueryExecution
|
||||
ResultSet.SaveAsFailureAsyncEventHandler errorHandler = async (parameters, reason) =>
|
||||
{
|
||||
string message = SR.QueryServiceSaveAsFail(Path.GetFileName(parameters.FilePath), reason);
|
||||
await requestContext.SendError(new SaveResultRequestError { message = message });
|
||||
await requestContext.SendError(message);
|
||||
};
|
||||
|
||||
try
|
||||
|
||||
Reference in New Issue
Block a user