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

Clarify direction of COM Interop #55

Closed
JoelLeach opened this issue Oct 11, 2016 · 17 comments
Closed

Clarify direction of COM Interop #55

JoelLeach opened this issue Oct 11, 2016 · 17 comments

Comments

@JoelLeach
Copy link

@JoelLeach JoelLeach commented Oct 11, 2016

What is the current thinking on including full support for COM Interop in .NET Standard and .NET Core? It sounds like you would rather not have Windows-specific things like this in Standard. If I'm reading this correctly, apisof.net (currently down) indicates System.Type.GetTypeFromProgID() will be included in the next release: https://webcache.googleusercontent.com/search?q=cache:tYoULw9HjAcJ:https://apisof.net/catalog/System.Type.GetTypeFromProgID(String,String)+&cd=1&hl=en&ct=clnk&gl=us. Can you clarify, or is this still up in the air?

Personally, I will need to work with other technologies via COM Interop for years to come. I hope that doesn't preclude me from moving to .NET Core one day.

@danmosemsft
Copy link
Member

@danmosemsft danmosemsft commented Oct 11, 2016

.NET Standard is a cross platform standard so we've tried to avoid types that are fundamentally platform specific like COM. COM interop and native interop have been segregated into a possible future extension: https://github.com/dotnet/standard/blob/master/extensions/interop/interop.cs.

@weshaggard there are cases where we've removed something because it's interop even though we could leave it (and have it throw) as it doesn't rely on any other problematic types (example Marshal.CleanupUnusedObjectsInCurrentContext) but in other cases we've left them present and expect them to throw (example: Type.GetTypeFromProgID). Should we remove that also?

Note -- in .NET Core's implementation it will currentlythrow NotImplementedException (https://github.com/dotnet/coreclr/blob/32f0f9721afb584b4a14d69135bea7ddc129f755/src/mscorlib/src/System/RtType.cs#L5333). as opposed to PlatformNotSupportedException. That doesn't seem too big a deal, although we could try to make a pass later.

@JoelLeach
Copy link
Author

@JoelLeach JoelLeach commented Oct 11, 2016

Thanks for the clarification.

@weshaggard
Copy link
Member

@weshaggard weshaggard commented Oct 11, 2016

@jkotas
Copy link
Member

@jkotas jkotas commented Oct 11, 2016

including full support for COM Interop in .NET Standard and .NET Core?

There is often incorrect assumption made that "included in .NET Standard" == "works in .NET Core". There are going to be some APIs that will throw PlaformNotSupportedException on .NET Core, also this set be different between Windows and Unix.

Immo goes into details about this in
https://blogs.msdn.microsoft.com/dotnet/2016/10/11/the-week-in-net-on-net-on-net-standard-2-0-nancy-satellite-reign/

COM interop have been segregated into a possible future extension

The parts of COM interop that were possible to segregate have been segregated. You will find quite a bit of COM interop stuff in netstandard.

other cases we've left them present and expect them to throw (example: Type.GetTypeFromProgID). Should we remove that also?

I do not think Type.GetTypeFromProgID should be removed. I believe it gets used quite a bit in real world code.

@JoelLeach
Copy link
Author

@JoelLeach JoelLeach commented Oct 11, 2016

There is often incorrect assumption made that "included in .NET Standard" == "works in .NET Core". There are going to be some APIs that will throw PlaformNotSupportedException on .NET Core, also this set be different between Windows and Unix.

That's going to take some getting used to. The availability of APIs on unsupported platforms may lead a developer to believe an API is fully functional when it is not. Immo did mention future tooling that would notify the developer up front if an API is not supported on a given platform/runtime. That should solve the issue.

@gulbanana
Copy link

@gulbanana gulbanana commented Oct 15, 2016

it would be great if there was a way to mark netstandard projects as "expected to be used by tfms". so if you e.g. indicated that something would be used by netcoreapp1.1, the IDE could provide notifications when you used APIs unsupported by that platform - perhaps similar to how multi-TFM intellisense works?

@weshaggard
Copy link
Member

@weshaggard weshaggard commented Dec 2, 2016

@gulbanana that is something we are thinking about and would like to try to do as well but it isn't going to be in our up coming releases.

@weshaggard weshaggard closed this Dec 2, 2016
@jnm2
Copy link

@jnm2 jnm2 commented Dec 2, 2016

My fear is that without some type of static type safety in the API preventing you from doing nonportable things without knowing it, this could become a minefield. I know you did this to make it easier to port to, but I can't help feeling it's a compromise that trades off all kinds of reliability.

What would such tooling look like?

@jnm2
Copy link

@jnm2 jnm2 commented Dec 2, 2016

It's possible I've missed the picture, so maybe you can help me understand. What is the .NET Standard, if not a set of APIs to build on which is guaranteed to be implemented in any runtime?

@danmosemsft danmosemsft reopened this Dec 2, 2016
@weshaggard
Copy link
Member

@weshaggard weshaggard commented Dec 2, 2016

@terrajobst do you have a write-up of what our current thoughts are around how to provide some tooling around the APIs not supported on some platforms.

What is the .NET Standard, if not a set of APIs to build on which is guaranteed to be implemented in any runtime?

The goal of .NET Standard is to provide a common set of APIs that you can depend on being present on a platform that supports .NET Standard. We strive to have everything in the standard supported everywhere but it just isn't possible for every API so there will always be some rough edges but those are meant to be the exceptional cases not the norm.

@gulbanana
Copy link

@gulbanana gulbanana commented Dec 4, 2016

I guess the difference between "depend on being present" and "guaranteed to be implemented" is that in the former case your guarantee is that you can compile against this capability and it will be attempted, but not necessarily succeed, at runtime..?

@yizhang82
Copy link

@yizhang82 yizhang82 commented Dec 5, 2016

I guess the difference between "depend on being present" and "guaranteed to be implemented" is that in the former case your guarantee is that you can compile against this capability and it will be attempted, but not necessarily succeed, at runtime..?

@gulbanana Correct. COM interop is actually a good example of this - you'll compile your x-plat app successfully even if you only use COM interop on windows (but the code is there under a if). As long as you correctly detect the current OS and don't use COM interop on non-Windows platform, your app would work in all platforms. If you actually do use it in Linux, for example, your app would blow up.

@jnm2
Copy link

@jnm2 jnm2 commented Dec 5, 2016

I would be much more comfortable with this if there was a warning for code that accesses such APIs if the control flow does not clearly indicate that you know you're on the correct platform.

If I'm, say, a NuGet library author starting out with a new project on netstandard2.0, I may do all my testing on Windows since that's what I have. I may not realize when I've taken a dependency on a Windows-only API. It may even be in an infrequently used codepath. Then when someone runs my library on a Mac or Xbox or Android, with the .NET Standard promise of a unified BCL for every platform, they may not find out about the potential time bomb in the library until it's already in production for a while. From there, they will have to come to me and wait until I have spare time for triage and find the issue in my library and publish a new version, and hope that I've spotted them all and have put the OS check at the correct place.

This is what I've been envisioning ever since I heard about this. It does not appeal to me.

A foolproof analyzer would be a great mitigation.

@JoelLeach
Copy link
Author

@JoelLeach JoelLeach commented Dec 5, 2016

COM interop is actually a good example of this - you'll compile your x-plat app successfully even if you only use COM interop on windows (but the code is there under a if). As long as you correctly detect the current OS and don't use COM interop on non-Windows platform, your app would work in all platforms. If you actually do use it in Linux, for example, your app would blow up.

@yizhang82 That's a good explanation, and I agree with the overall approach. "Guaranteed to be implemented" everywhere only leads back to the Portable Class Libraries approach and an ever-shrinking API set as .NET Core shows up in more places. That said, I do think that many developers will expect .NET Core on Windows to be the "reference implementation" of .NET Standard. It will be confusing to have APIs in the standard that are not functional on the base platform. You have a tough balancing act, to be sure.

In regards to COM interop, I wrote more on the subject here.

I would be much more comfortable with this if there was a warning for code that accesses such APIs if the control flow does not clearly indicate that you know you're on the correct platform.

@jnm2 One of the videos linked above mentions that tooling is coming to help, but I don't know what the timing will be. In practical terms, that should solve the problem without reducing the API surface.

@RickStrahl
Copy link

@RickStrahl RickStrahl commented Dec 21, 2016

It seems to me COM has no place in .NET Standard since it's platform specific technology. It shouldn't be there!

Support for COM should be a framework library that sits on top of standard and hopefully mimics the same interfaces as System.Runtime.Interop provides today. It would just be an OS specific framework assembly.

Anything else would be terribly confusing IMHO.

I realize the main reason this might be included is for compatibility with existing libraries that might expect COM interop features (and there may be quite of that inside of the core of .NET as well as PInvoke), but hopefully this enough of a special case that it can be worked around, especially if the appropriate .NET Core System.Runtime.Interop assemblies match the old signatures.

@terrajobst
Copy link
Member

@terrajobst terrajobst commented Dec 21, 2016

It seems to me COM has no place in .NET Standard since it's platform specific technology. It shouldn't be there!

As Jan said above:

The parts of COM interop that were possible to segregate have been segregated. You will find quite a bit of COM interop stuff in netstandard.

Let me provide a bit more context. Not exposing APIs in .NET Standard is easy -- we could always simply subset the types if necessary. However, we think that's problematic. As I explained in my blog post, our goal is to make it possible to target .NET Standard and install packages that allow you to take dependencies on APIs that don't work everywhere (for example, the registry). This allows being compatible with the past and allowing building libraries that are partially portable.

However, we can't add split types across assemblies and thus packages. In other words, by adding a package reference, you'll never see new APIs on exiting types. Yes, sometimes extension methods would support this, but for one they don't work for all kinds of members and secondly it still doesn't allow for compat shims that allows referencing existing .NET Framework that use those APIs.

Thus, for .NET Standard our goal is to maximize API coverage while avoiding adding platform specific concepts. Unfortunately, not all cases are as clean as the Windows registry and COM is a great example.

We believe it's better to accept that some small number APIs will throw on certain platform than making it impossible to support a source/binary compatible API for the platforms that do support the technologies.

@terrajobst
Copy link
Member

@terrajobst terrajobst commented Dec 21, 2016

@JoelLeach, let me know if you want more clarification but I believe this thread provides a complete answer :-)

@terrajobst terrajobst closed this Dec 21, 2016
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Linked pull requests

Successfully merging a pull request may close this issue.

None yet
9 participants
You can’t perform that action at this time.