Skip to content
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

Use Fantomas client instead of direct embedding #836

Merged
merged 17 commits into from
Oct 21, 2021

Conversation

nojaf
Copy link
Contributor

@nojaf nojaf commented Oct 8, 2021

Following up on fsprojects/fantomas#1845, I want to try out the new approach in FSAC/Ionide.
@baronfel I have some specific questions that I will ask in the code, but overall I'd like to hear your thoughts.
Are we on to something here you think?

PS: This worked on my local machine, that alpha-004 is not published yet.

let! fantomasResponse = service.FormatDocumentAsync { SourceCode = currentCode; FilePath = (UMX.untag file); IsLastFile = false; Config = None }
match fantomasResponse with
| { Code = 1; Content = Some code } ->
fantomasLogger.info (Log.setMessage (sprintf "Fantomas daemon was able to format \"%A\"" file))
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Where are those logs written to?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

these logs are written to serilog eventually, which is configured in the Program.fs. the default outputs are to write all logs to stderror, because LSP communication is done over the main stdin/stdout channels.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Any idea how to view these in Rider when attaching to an existing project? Or is it easy to have them written to a rolling file thing?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure, you should be able to add a rolling file appender to the logger configuration here, though you will need to add the Serilog.Sinks.File package in order to do so. It would be excellent if you also hooked the configuration of this file up to a CLI option (perhaps --log-file <filepath>?)

@nojaf
Copy link
Contributor Author

nojaf commented Oct 13, 2021

Alright, this is getting in a workable state I think.
@baronfel how would you want to tackle this in terms of migration?
We could support both versions at the same time, but I don't think that will really provide us much feedback.
It also adds another layer of temporary complexity, we introduce a setting that would only last a short time and all that.
I'm a bit more inclined to switch and see how it plays out.
The toast showing users that Fantomas needs to be installed could link to a good documentation page.
And potentially we could prompt to install it (locally or globally) from Ionide, although I'm not sure how and if that would work.

Let me know what you think.

@nojaf
Copy link
Contributor Author

nojaf commented Oct 13, 2021

Oh and we probably want to have some basic tests for this I imagine.
Any thoughts there? Installed a global tool first before running the tests?

@baronfel
Copy link
Contributor

re: tests I think the current project-based test case model could work here, because you can do local-tool installs to those folders to test specific scenarios. so you'd make a folder representing a project, install fantomas as a local tool, then verify that formatting worked. separately another folder could test the case where we install fantomas for the user, etc, etc.

@nojaf
Copy link
Contributor Author

nojaf commented Oct 13, 2021

re:re:tests ah good to hear, then we can indeed have a real test in place.

@nojaf
Copy link
Contributor Author

nojaf commented Oct 14, 2021

@baronfel again, some good stuff today. Man this is a tricky thing to nail down 😋

@nojaf
Copy link
Contributor Author

nojaf commented Oct 15, 2021

Hey again @baronfel, getting pretty happy where this sits right now.
A lot of stuff has been simplified on this side.
Could you review the latest state and perhaps list some action points or things that still need addressing?
Many thanks

@nojaf nojaf requested a review from baronfel October 15, 2021 07:03
@@ -6,12 +6,13 @@ source https://api.nuget.org/v3/index.json
# this is the FCS nightly feed, re-enable at your own risk!
#source https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json
#source: ./libs
source C:\Users\fverdonck\Projects\fantomas\bin\
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

just making a note, we'd want to remove this before final merge

src/FsAutoComplete/FsAutoComplete.Lsp.fs Outdated Show resolved Hide resolved
src/FsAutoComplete/FsAutoComplete.Lsp.fs Outdated Show resolved Hide resolved
src/FsAutoComplete/FsAutoComplete.Lsp.fs Outdated Show resolved Hide resolved
@@ -176,15 +176,13 @@ type FSharpLspServer(backgroundServiceEnabled: bool, state: State, lspClient: FS
let logger = LogProvider.getLoggerByName "LSP"
let fantomasLogger = LogProvider.getLoggerByName "Fantomas"
let backgroundService: BackgroundServices.BackgroundService = if backgroundServiceEnabled then BackgroundServices.ActualBackgroundService() :> _ else BackgroundServices.MockBackgroundService() :> _
let mutable commands = new Commands(FSharpCompilerServiceChecker(backgroundServiceEnabled, false), state, backgroundService, false)
let mutable rootPath : string option = None
let mutable commands = new Commands(FSharpCompilerServiceChecker(backgroundServiceEnabled, false), state, backgroundService, false, rootPath)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is beginning to smell to me. not your code, but just how large Commands is getting.

@baronfel
Copy link
Contributor

I'm really happy with this overall, and really excited for the UX of this change, as well as how it insulates the core of FSAC from changes in Fantomas while enabling users to manage fantomas versions independently!

let dotConfigContent = File.ReadAllText dotConfig
if dotConfigContent.Contains("fantomas-tool") then
// uninstall a older, non-compatible version of fantomas-tool
Process.Start("dotnet", @"tool uninstall fantomas-tool").WaitForExit(5000) |> ignore
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Any objection to bringing in https://github.com/Tyrrrz/CliWrap?
As Process.Start can now fail silently.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nope, go on ahead!

@nojaf
Copy link
Contributor Author

nojaf commented Oct 21, 2021

@baronfel I think the only thing missing here is some sort of unit/integration test.
Otherwise, I believe we are good to go.

@nojaf nojaf marked this pull request as ready for review October 21, 2021 14:49
@nojaf
Copy link
Contributor Author

nojaf commented Oct 21, 2021

The test passed on Windows as well.

@baronfel baronfel changed the title Prototype usage of Fantomas client. Use Fantomas client instead of direct embedding Oct 21, 2021
@baronfel baronfel merged commit f59662d into ionide:master Oct 21, 2021
@baronfel
Copy link
Contributor

Merged! Thank you for this wonderful contribution, I'm very excited to get it out to our users!

@nojaf
Copy link
Contributor Author

nojaf commented Oct 21, 2021

You and me both buddy! Many thanks for all the mentoring along the way.

@nojaf nojaf deleted the fantomas-daemon branch October 21, 2021 15:19
@Krzysztof-Cieslak
Copy link
Member

🥳 Awesome work @nojaf, thanks a lot!.

| Ok FormatDocumentResponse.UnChanged ->
return LspResult.success None
| Ok FormatDocumentResponse.ToolNotPresent ->
let actions =
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could all this logic be added to Fantomas.Client? Thanks

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is all LSP-specific responses/API usage here, it's not really something that I would expect to drop seamlessly into, say, the VS API. The bit below about prompting especially would be editor-specific, I have zero idea what those interfaces look like.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants