-
Notifications
You must be signed in to change notification settings - Fork 4.8k
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
Project file hygiene #67532
Project file hygiene #67532
Conversation
Tagging subscribers to this area: @dotnet/area-meta Issue DetailsCommit 1 - Infrastructure changes
Commit 2 - Delete dead code that dates back to mono BCL buildCommit 3 - Ref/Src/Gen-Project file hygiene
Commit 4 - React to analyzer warnings/errorsProjects which previously didn't auto-reference System.Memory,
|
Did you confirm that there are zero changes in what code's actually being included? e.g. that the size of the binaries built before and after the changes are identical? |
I did verify that the compile items passed to CSC/VBC are identical before and after but I think it's a good idea to also compare the produced assemblies. Let me do that. |
4ed4ca8
to
834184c
Compare
@@ -84,7 +84,10 @@ | |||
<StrongNameKeyId Condition="$(MSBuildProjectName.StartsWith('Microsoft.Extensions.'))">MicrosoftAspNetCore</StrongNameKeyId> | |||
<!-- We can't generate an apphost without restoring the targeting pack. --> | |||
<UseAppHost>false</UseAppHost> | |||
<EnableDefaultItems>false</EnableDefaultItems> | |||
<!-- TODO: Enable default items in test projects. --> | |||
<EnableDefaultItems Condition="'$(IsTestProject)' == 'true' or |
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.
hmm, I thought we were pretty selective about source inclusions dependent on platforms (say with *.Unix.cs files and all), say with System.Private.Corelib. Are we sure this currently works? Or is there also some massaging in this PR to do that.
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.
The third commit handles updating all projects to work with that setting. Less than 50% of our projects multi-target based on the OS, the majority doesn't. For the projects that don't multi-target based on the OS, this settings work nicely.
For the ones that multi-target based on the OS, this setting still works fine but a bit more work was required to make sure that nothing unexpected is included which previously wasn't. I recommend to look into the third commit yourself as the diff mostly speaks for itself.
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.
FWIW, I really, really, really (insert a string of "really"s until your ears bleed) do not want us to use EnableDefaultItems.
I don't even want the SDK to support it.
It's bad engineering practice that's only good for bootstrapping CS101 students.
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.
I agree with Jeremy (at least on the first part... I think EnableDefaultItems is reasonable for simple, small projects and is an ok default for the SDK to help bootstrap in general). If the overwhelming majority of others disagree, I'll acquiesce, but understanding exactly what's being included and what's not being included is really helpful. And with the variations in our builds and our need to include some files in some configurations and not in others, we're never going to get to a place where everything is just always included, which from my perspective also means the consistent thing is always specifying exactly what should be in every build.
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.
(Also, for fundamental overhauls like this, that impact everyone working on the project, that impact every project, etc., I'd prefer if we have a discussion about the direction rather than an ~500 file diff just appearing. If it was necessary for you to do the work in order to come up with the proposal, then ok, and it being potentially throw-away is just part of the process; but if that could have been achieved just by experimenting with a couple of projects, presumably that would have resulted in less work for everyone?)
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.
Explicit inclusions feels like it supports more predictable engineering at a relatively small cost of adding a line in XML when you create a file. Also, as someone who greps more than using an IDE, it allows me to see exactly what's going on without also look at what file is positioned where on disk.
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.
My thinking is that the lower-level your code is, the more you are writing platform-specific code. And the more platform-specific code you write, the more you need to be explicit about what is and what isn't included in your project. I don't think it has anything to do with size of your project. dotnet/aspnetcore is by no means "small" or CS101, but they use EnableDefaultItems in all their projects.
The same can be said for using #if
s in your code. If you only need them in one or two spots, it is fine. But at the level we need to specialize code in the shared fx, it would be a nightmare.
That's why I think the current situation we have is acceptable. We have code that is both low-level (shared fx) and high-level (Microsoft.Extensions). Using the approach that best fits the project makes sense to me.
/azp run runtime-wasm |
Azure Pipelines successfully started running 1 pipeline(s). |
834184c
to
c3f9616
Compare
@stephentoub (cc @eerhardt) good that you were asking about the diff. I noticed that the Extensions projects which already use the
That fix which is part of the first commit makes the Extensions assemblies now actually smaller :) |
/azp run runtime-wasm |
Azure Pipelines successfully started running 1 pipeline(s). |
Tagging subscribers to this area: @dotnet/area-infrastructure-libraries Issue DetailsCommit 1 - Infrastructure changes
Commit 2 - Delete dead code that dates back to the mono BCL buildCommit 3 - Ref/Src/Gen-Project file hygiene
Commit 4 - React to analyzer warnings/errorsProjects which previously didn't auto-reference System.Memory,
|
c3f9616
to
1c7aa1e
Compare
Resolved merge conflicts. |
1c7aa1e
to
3fe7b7f
Compare
/azp run runtime-wasm |
Azure Pipelines successfully started running 1 pipeline(s). |
1. The generators.targets file had a bug that complained when a project uses the default targeting pack references because the ArrayMarshaller.cs file was not imported. Also cleaning-up the generators.targets file by simplifying conditions. 2. Enable "default items" via the "<EnableDefaultItems />" SDK switch for both ref and source projects. 3. Remove outdated infrastructure that isn't needed anymore based on project file changes.
1. Use the SDK's default items feature so that compile items in the project directory are imported automatically. Disable that feature in few projects which heavily depend on manually including compile items based on the TargetPlatformIdentifier. Changes made mimic the usage in the Microsoft.Extensions.* projects which already used the default items feature. I made sure that the numer of comile items included before the change and after the change is identical. In a follow-up change it would make sense to clean-up all the BCL files to use the same set of suffixes, i.e. - .NETFramework only files: .netframework.cs instead of - .net46.cs - .netfx.cs - .netframework.cs - .net48.cs - etc. That would allow to define central glob exclusion patterns for i.e. .NETFramework builds: - TFI .NETFramework: "*\**.netcoreapp.cs" - TFI .NETCoreApp: "*\**.netframework.cs" - ... 2. Remove the unnecessary declaration of "<Reference />" and "<ProjectReference />" items in out-of-band projects as they already build on top of the shared framework (targeting pack) and make that the default behavior for anything that is out-of-band. 3. Clean-up Reference and ProjectReference items that weren't used by the compiler anymore, i.e. System.Runtime.ComilerServices.Unsafe and System.Runtime.Extensions (as those are now facades). 4. Add empty lines to separate property and item groups from each other so that project files are easier to read and look the same as project files that "dotnet new" produces.
Projects which previously didn't auto-reference System.Memory, do so now (projects which are out-of-band and sit on top of the shared framework). Analyzers which are conditioned on the reference being available now kick in and hence these two files needed to be updated.
3fe7b7f
to
9b8359a
Compare
Resolved merge conflicts. |
/azp run runtime-wasm |
Azure Pipelines successfully started running 1 pipeline(s). |
Spoke with @stephentoub offline and we agreed on that it's easier to review the changes by splitting them into separate logical units. Please hold reviewing this PR. |
Thanks everyone for their comments. Just to clarify, I didn't intend to put up such a big change without an upfront discussion. As noted in #67650 (comment) I unfortunately mis-interpreted a comment when I tested enabling the default items feature on a single library to get feedback from the area owners. I apologize here and now for the way this was perceived by some of you and want to emphasize that this wasn't my intention. On the upside at least trying out the enable default items feature helped me find:
I will make sure that the rest of the changes won't be lost but I will close these PRs to first have another discussion around these other changes to make sure that there isn't another disconnect in communication. |
Thanks, @ViktorHofer. Sorry for any miscommunication on my part. |
Commit 1 - Infrastructure changes
uses the default targeting pack references because the
ArrayMarshaller.cs file was not imported.
I also cleaned the generators.targets file by simplifying
conditions.
<EnableDefaultItems />
SDK switchfor any project except tests (for now).
project file changes.
Commit 2 - Delete dead code
Commit 3 - Ref/Src/Gen-Project file hygiene
Use the SDK's default items feature so that compile items in the
project directory are imported automatically. Disable that feature
in few projects which heavily depend on manually including compile
items based on the TargetPlatformIdentifier.
Changes made mimic the usage in the Microsoft.Extensions.* projects
which already used the default items feature.
I made sure that the numer of comile items included before the change
and after the change is identical.
In a follow-up change it would make sense to clean-up all the
BCL files to use the same set of suffixes, i.e.
That would allow to define central glob
exclusion patterns for i.e. .NETFramework builds:
*\**.netcoreapp.cs
*\**.netframework.cs
Remove the unnecessary declaration of
<Reference />
and<ProjectReference />
items in out-of-band projects as they alreadybuild on top of the shared framework (targeting pack) and make that
the default behavior for anything that is out-of-band.
Clean-up Reference and ProjectReference items that weren't used by
the compiler anymore, i.e. System.Runtime.ComilerServices.Unsafe and
System.Runtime.Extensions (as those are now facades).
Add empty lines to separate property and item groups from each other
so that project files are easier to read and look the same as
project files that "dotnet new" produces.
Commit 4 - React to analyzer warnings/errors
Projects which previously didn't auto-reference System.Memory,
do so now (projects which are out-of-band and sit on top of the
shared framework). Analyzers which are conditioned on the reference
being available now kick in and hence these two files needed to be
updated.