-
Notifications
You must be signed in to change notification settings - Fork 779
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
Add support for referencing .NET projects in F# interactive #8764
Comments
Considering that projects can be large and take a long time to compile, I would suggest we make this work with the compiled output from the referenced project. That way, it's likely to be much easier to implement (basically, the path should be added to the assembly search paths, and the output exe or dll should be loaded). If the dirty flag is set, perhaps a warning could be given. BTW, I remember there used to be a Powertools VS extension that did something like this, but I think it doesn't exist anymore. |
Right! Last supported Version of Visual Studio was 2015: https://fsprojects.github.io/VisualFSharpPowerTools/generatereferences.html |
I've written an alternative prototype which first restores and compiles the project and references the generated assembly instead of the source files: https://github.com/toburger/DependencyManager.FsProj With this approach I was able to load a more complicated project of mine into F# interactive. |
@toburger nice work! This would be a great thing to add for .NET 5. It could end up getting pretty tricky, though, since we'll want to support more than just F# projects. @KevinRansom @jonsequitur what do you think? |
I think this is great. I'd like to throw out some related ideas and get people's thoughts. Our discussion around
Some of these will require using the interactive dependency manager that @KevinRansom has been building, as it provides more information about packages than you can get from a vanilla build. |
What about |
The only F# project specific API in the prototype is to load the project information (files, references, target path).
For me personally debugging has a very low priority in scripting. 😄
Can you explain more on this? Should we also limit the target projects to SDK-style projects only? |
Interactive debugging in data science scripting is important when project gets complex. |
I would argue that debugging is more important in scenarios where mutation is the dominant paradigm. But given that you are the maintainer of Deedle I take my statement about debugging back. 😉 |
There's some additional considerations here, since the notion of "referencing a project" is very complicated.
|
@cartermp Isn't that distinction part of what MSBuild does so we don't have to do the work ourselves? |
Depends on which MSBuild is involved 🙂 |
There's also more to consider than just MSBuild here. We're still dealing with subtleties around native assemblies and RID-specific configurations with the dependency manager today, for example. |
In my solutions with multiple F# projects, I usually have a Packages.fsx script in the root folder that pretty much duplicates paket.dependencies and references them all either via |
I don't think there is a recommended approach - just a massive gap in tooling support. |
@ntwilson that doesn't sound like a terrible approach, and could probably be automated with a small script that traverses the project file and generates a Project.fsx |
I thought adding a fsx file to generate testdata would be nicer then to write a unit test but just referencing the dll of the main project seems not enough. The Compiler is asking for missing references of types defined in nuget references. |
For everybody who is looking for the references that must be included in a fsx file to call code in a .net project. In VsCode in the "F#: Solution Explorer" of the "Ionide for F#" extension you can right-click on a project and select "Generate references for FSI". Then a referencs.fsx file is generated with many |
A few months ago I used the PoC project form Chris and Ionide.ProjInfo and implemented the functionality. The implementation is here: DependencyManager.FsProj, and in the nuget README is explained how to get it working. It is deployed as a dotnet tool to have all the dependencies in same directory so when registering new dependency manager in fsi everything works. It could also be used as a dotnet tool to generate load script for fsi if the setup is too complicated. I didn't test it extensively but it worked for a few samples I tried. I didn't really used it that much in the end 😅 I am not sure how to move it to fsharp because, I guess, adding Ionide.ProjecInfo as dependency to fsharp is not a good idea. Maybe we could extract the needed functionality? |
@ThisFunctionalTom would you like to update it for net7.0 (currently broken with new fsac and net7.0)? I tried to make this update myself, but the projects are not loaded anymore, logging the loader says it is missing obscure dll with ChangeWaves. The ability to load a project into .fsx is essential for my workflow (experiment interactively with a WIP library and backport experiments in the library) and the current way of doing it (relying in the "generate references for the project" is a little cumbersome and error prone, so doing it at fsac/fsi level is a real boon. (but doesn’t work anymore, as I said, unless I come back to net6.0 and to old ionide versions). |
I am on holidays this week. I hope I can find some time next week to look
into it.
…On Wed, 14 Jun 2023, 19:57 François-David Collin, ***@***.***> wrote:
A few months ago I used the PoC project form Chris and Ionide.ProjInfo and
implemented the functionality. The implementation is here:
DependencyManager.FsProj
<https://github.com/ThisFunctionalTom/DependencyManager.FsProj>, and in
the nuget README
<https://www.nuget.org/packages/DependencyManager.FsProj#readme-body-tab>
is explained how to get it working.
It is deployed as a dotnet tool to have all the dependencies in same
directory so when registering new dependency manager in fsi everything
works.
It could also be used as a dotnet tool to generate load script for fsi if
the setup is too complicated.
I didn't test it extensively but it worked for a few samples I tried. I
didn't really used it that much in the end 😅
I am not sure how to move it to fsharp because, I guess, adding
Ionide.ProjecInfo as dependency to fsharp is not a good idea. Maybe we
could extract the needed functionality?
@ThisFunctionalTom <https://github.com/ThisFunctionalTom> would you
update it for net7.0 (currently broken with new fsac and net7.0. I tried to
make this update myself, but the projects are not loaded anymore, logging
the loader says it is missing obscure dll with ChangeWaves)
The ability to load a project into .fsx is essential for my workflow
(experiment interactively with a WIP library and backport experiments in
the library) and the current way of doing it (relying in the "generate
references for the project" is a little cumbersome and error prone.
—
Reply to this email directly, view it on GitHub
<#8764 (comment)>,
or unsubscribe
<https://github.com/notifications/unsubscribe-auth/AAZJO4TO72TQC45MTNUGEBTXLH3P7ANCNFSM4LQ26BIA>
.
You are receiving this because you were mentioned.Message ID:
***@***.***>
|
So, I had an idea how to remove all the dependencies of the framework version (by using |
Hi Tom, I took a peek at your fork earlier today. And I have some open questions (also for @vzarytovskii):
My main question really boils down to: what would the team accept as PR? |
I would delegate it to @KevinRansom, since he has bigger picture for dependecy manager and interactive in mind. |
I think in context of FSI, it doesn't matter, FSharp.Core is always going to be loaded already, here is a reference that could be useful: there is a hedge case about
If it is going to be "shipping by default" and work for dotnet interactive / polyglot notebooks (for other IL languages that it supports as well: C# & F# for now), I think it is worth to extend the effort, assuming all the plumbing, etc. relies on msbuild, not something that needs to be maintained. I'd suggest I don't think we should turn "proj" into a noun, and given the low character count of invocation versus what it achieves, I don't feel shortenning the extensions is the thing to optimise for.
hoping this is handled through msbuild infrastructure so we don't take responsibility on it in the implementation details managed here. If this introduces a challenge, I'd drop it, people can resort to build the project and load the binaries.
I also could see issues with some projects that require |
@nojaf , #r "nuget: " and #r "paket: " are giant hacks. They are unbelievably useful giant hacks, doing something that is absolutely necessary: I.e. there is no other real way of introducing dependencies to a script that is being typed by the developer in real time, so even with its flaws we continue with it, However, the implementation of shelling out to msbuild executing a restore process and then gathering the dependencies is so lame that the C# team, said ... no way is that ever going anywhere near our beautiful language. Fortunately, in notebooks we were in a position to use the package manager as a library invoked by a pre-processor which enabled dotnet interactive to add the package manager to C# notebooks, although the C# guys always gave me the side eye and muttered about needing to a proper implementation :-). The scripting interface is really ... really limited it is basically: All that command executes the script, and loads assemblies from a list of assemblies and scripts from a list of scripts. Once the package manager has executed the command it will see the string every subsequent invocation. Because of these limitations we still don't have a mechanism for providing credentials for private nuget feeds, a scenario we get asked about a lot ... and tbh absolutely need to support. The difficulties of a packagemanager fall into a bunch of buckets:
If it were up to me, I would design a Third party library for managing dotnet projects from scripts, with an object model for accessing build properties and item collections building individual targets and manipulating projects, almost certainly supporting solutions. If you did that you would less restricted by the FSI integration point and have more freedom to implement the many ... many enhancemets, functionalities you would want to add as soon as you had the basic shape in place. I imagine that Fake has already got some basic dotnet project file support, although it has been close to a decade since I really looked at it. If you still want to go ahead with the #r "projfile: ... " #r "nuget: is extensible, paket exists after all" we should probably do some work to make the nuget global and local tools extension mechanism work, they didn't exist yet when #r "nuget: and #r "paket : were originally created. Indeed we should do something about that anyway to make #r "paket: installation more straightforward. I have been promising that to @cloudRoutine for more years than I am comfortable with. In short:
|
I don't get what the csharp folk think is the usecase for CSI if they're not going to fully complete this loop. It's a half-baked thing today, and if they want to encourage data science / AI / etc to use notebooks, they should also enable project support. Notebooks are toys not tools without being able to load projects and their dependencies. It would be insanely useful to be able to use your project's model & data repository layers to build interactive notebooks to explore your data with your existing code, but loading those is just so tedious now without being able to load projects & their dependencies. Notebooks feel like a giant hack in general right now. |
Reading other comments here I just realized that I underestimated the complexity of this very, very much 😅 . Below I my answers how I thought it could be done, but I am not sure anymore.
All source files and the generated script file with nuget references is then returned from dependency manager. So to actually answer your question, with this solution only fsproj files can actually be referenced because only .fs files can be loaded by the fsi.
|
Hi @KevinRansom, I appreciate your valuable input! Considering the potential impact on user expectations, it wouldn't be fair to overload the team with this task. Even though the original PR can come from the community, the team would be burdened with maintaining it. In the short term, I believe it would be worthwhile to consider a community project as an alternative solution. @ThisFunctionalTom, let's discuss this further next week and evaluate its feasibility. |
this is still amazing if achievable, also and especially for |
@nojaf / @ThisFunctionalTom did anything come of this? We have .NET 8 now and the community supported approach is not working. |
Hi, I will look into it on the weekend. Sorry if it is not maintained faster, but as the solution is not perfect I am not using it myself and so I always forget to update it to the newest .NET SDK. |
Thanks for that. And no apologies needed, as is the nature with community projects, this is all a labor of love done in your free time. I appreciate the great tool you have provided. |
I deployed a new version 0.2.9. I hope this works for you. |
Is your feature request related to a problem? Please describe.
It would be nice to have similar functionality like in other languages, where it is possible to reference a project inside an interactive session.
Languages that support such functionality are for example: Haskell, Elixir, Python, Clojure
Describe the solution you'd like
I would like to start an interactive session and reference the project like I would reference an assembly file today.
An example could be (F# projects only):
or (across languages):
@Krzysztof-Cieslak has already created a prototype where he got working a F# only solution: https://github.com/Krzysztof-Cieslak/DependencyManager.FsProj
So the first question to answer is:
Describe alternatives you've considered
#r: "nuget: Dependency"
for every dependent library and add every source file by handgenerate_load_scripts
) to generate library references in a script file that can be used in your script and then reference every source file by handAdditional context
I've created this issue because there was an ongoing discussion started here: fsharp/fslang-suggestions#542
The text was updated successfully, but these errors were encountered: