-
Notifications
You must be signed in to change notification settings - Fork 234
hover support #1010
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
hover support #1010
Changes from all commits
54504e4
b520ac0
0f8572b
8d8feae
24084ab
9da6a48
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,90 @@ | ||
// | ||
// Copyright (c) Microsoft. All rights reserved. | ||
// Licensed under the MIT license. See LICENSE file in the project root for full license information. | ||
// | ||
|
||
using System.Diagnostics; | ||
using System.Management.Automation; | ||
using System.Threading.Tasks; | ||
using Microsoft.PowerShell.EditorServices.Symbols; | ||
|
||
namespace Microsoft.PowerShell.EditorServices | ||
{ | ||
/// <summary> | ||
/// Provides detailed information for a given symbol. | ||
/// </summary> | ||
[DebuggerDisplay("SymbolReference = {SymbolReference.SymbolType}/{SymbolReference.SymbolName}, DisplayString = {DisplayString}")] | ||
public class SymbolDetails | ||
{ | ||
#region Properties | ||
|
||
/// <summary> | ||
/// Gets the original symbol reference which was used to gather details. | ||
/// </summary> | ||
public SymbolReference SymbolReference { get; private set; } | ||
|
||
/// <summary> | ||
/// Gets the display string for this symbol. | ||
/// </summary> | ||
public string DisplayString { get; private set; } | ||
|
||
/// <summary> | ||
/// Gets the documentation string for this symbol. Returns an | ||
/// empty string if the symbol has no documentation. | ||
/// </summary> | ||
public string Documentation { get; private set; } | ||
|
||
#endregion | ||
|
||
#region Constructors | ||
|
||
static internal async Task<SymbolDetails> CreateAsync( | ||
SymbolReference symbolReference, | ||
PowerShellContextService powerShellContext) | ||
{ | ||
SymbolDetails symbolDetails = new SymbolDetails | ||
{ | ||
SymbolReference = symbolReference | ||
}; | ||
|
||
switch (symbolReference.SymbolType) | ||
{ | ||
case SymbolType.Function: | ||
CommandInfo commandInfo = await CommandHelpers.GetCommandInfoAsync( | ||
symbolReference.SymbolName, | ||
powerShellContext); | ||
|
||
if (commandInfo != null) | ||
{ | ||
symbolDetails.Documentation = | ||
await CommandHelpers.GetCommandSynopsisAsync( | ||
commandInfo, | ||
powerShellContext); | ||
|
||
if (commandInfo.CommandType == CommandTypes.Application) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. My preference here would be to There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. refactored |
||
{ | ||
symbolDetails.DisplayString = "(application) " + symbolReference.SymbolName; | ||
return symbolDetails; | ||
} | ||
} | ||
|
||
symbolDetails.DisplayString = "function " + symbolReference.SymbolName; | ||
return symbolDetails; | ||
|
||
case SymbolType.Parameter: | ||
// TODO: Get parameter help | ||
symbolDetails.DisplayString = "(parameter) " + symbolReference.SymbolName; | ||
return symbolDetails; | ||
|
||
case SymbolType.Variable: | ||
symbolDetails.DisplayString = symbolReference.SymbolName; | ||
return symbolDetails; | ||
|
||
default: | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Might be nice to start thinking about adding support for class and enum. Maybe it's as simple as returning a string of There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I like that - lets defer the work to a later PR when everything gets hooked up. |
||
return symbolDetails; | ||
} | ||
} | ||
|
||
#endregion | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,104 @@ | ||
using System.Collections.Generic; | ||
using System.Threading; | ||
using System.Threading.Tasks; | ||
using Microsoft.Extensions.Logging; | ||
using Microsoft.PowerShell.EditorServices; | ||
using OmniSharp.Extensions.LanguageServer.Protocol.Client.Capabilities; | ||
using OmniSharp.Extensions.LanguageServer.Protocol.Models; | ||
using OmniSharp.Extensions.LanguageServer.Protocol.Server; | ||
|
||
namespace PowerShellEditorServices.Engine.Services.Handlers | ||
{ | ||
public class HoverHandler : IHoverHandler | ||
{ | ||
private readonly DocumentSelector _documentSelector = new DocumentSelector( | ||
new DocumentFilter | ||
{ | ||
Language = "powershell" | ||
} | ||
); | ||
|
||
private readonly ILogger _logger; | ||
private readonly SymbolsService _symbolsService; | ||
private readonly WorkspaceService _workspaceService; | ||
private readonly PowerShellContextService _powerShellContextService; | ||
|
||
private HoverCapability _capability; | ||
|
||
public HoverHandler( | ||
ILoggerFactory factory, | ||
SymbolsService symbolsService, | ||
WorkspaceService workspaceService, | ||
PowerShellContextService powerShellContextService) | ||
{ | ||
_logger = factory.CreateLogger<HoverHandler>(); | ||
_symbolsService = symbolsService; | ||
_workspaceService = workspaceService; | ||
_powerShellContextService = powerShellContextService; | ||
} | ||
|
||
public TextDocumentRegistrationOptions GetRegistrationOptions() | ||
{ | ||
return new TextDocumentRegistrationOptions | ||
{ | ||
DocumentSelector = _documentSelector, | ||
}; | ||
} | ||
|
||
public async Task<Hover> Handle(HoverParams request, CancellationToken cancellationToken) | ||
{ | ||
ScriptFile scriptFile = | ||
_workspaceService.GetFile( | ||
request.TextDocument.Uri.ToString()); | ||
|
||
SymbolDetails symbolDetails = | ||
await _symbolsService.FindSymbolDetailsAtLocationAsync( | ||
scriptFile, | ||
(int) request.Position.Line + 1, | ||
(int) request.Position.Character + 1); | ||
|
||
List<MarkedString> symbolInfo = new List<MarkedString>(); | ||
Range symbolRange = null; | ||
|
||
if (symbolDetails != null) | ||
{ | ||
symbolInfo.Add(new MarkedString("PowerShell", symbolDetails.DisplayString)); | ||
|
||
if (!string.IsNullOrEmpty(symbolDetails.Documentation)) | ||
{ | ||
symbolInfo.Add(new MarkedString("markdown", symbolDetails.Documentation)); | ||
} | ||
|
||
symbolRange = GetRangeFromScriptRegion(symbolDetails.SymbolReference.ScriptRegion); | ||
} | ||
|
||
return new Hover | ||
{ | ||
Contents = new MarkedStringsOrMarkupContent(symbolInfo), | ||
Range = symbolRange | ||
}; | ||
} | ||
|
||
public void SetCapability(HoverCapability capability) | ||
{ | ||
_capability = capability; | ||
} | ||
|
||
private static Range GetRangeFromScriptRegion(ScriptRegion scriptRegion) | ||
{ | ||
return new Range | ||
{ | ||
Start = new Position | ||
{ | ||
Line = scriptRegion.StartLineNumber - 1, | ||
Character = scriptRegion.StartColumnNumber - 1 | ||
}, | ||
End = new Position | ||
{ | ||
Line = scriptRegion.EndLineNumber - 1, | ||
Character = scriptRegion.EndColumnNumber - 1 | ||
} | ||
}; | ||
} | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@src/PowerShellEditorServices.Engine/LanguageServer/OmnisharpLanguageServer.cs