-
Notifications
You must be signed in to change notification settings - Fork 646
External content packages #247
External content packages #247
Conversation
<ItemGroup Label="Static content supplied by NuGet packages"> | ||
<_BlazorPackageContentOutput Include="@(BlazorPackageContentFile)" Condition="%(SourcePackage) != ''"> | ||
<TargetOutputPath>$(ProjectDir)$(OutputPath)$(BaseBlazorPackageContentOutputPath)%(SourcePackage)\%(RecursiveDir)\%(Filename)%(Extension)</TargetOutputPath> | ||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> |
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'm not sure this does anything on custom items. I think this is a feature of Content. This is good for now, but in the future I think we should move users to use Content for this (as it has all the features). I would need to know more about what we are trying to do here to better judge it, but I'm going to make 2 assumptions.
- Content from 3rd party packages is immutable.
- Just needs to be copied to the output without any prior processing.
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.
BlazorPackageContentFile
items are those specifically nominated by the package for inclusion in the dist
dir.
Content from 3rd party packages is immutable.
Yes
Just needs to be copied to the output without any prior processing.
Pretty much, but:
- We want to output it to
dist
, not just$(OutDir)
(and don't want package authors to hardcode the notion ofdist
in their packages) - We want to strongly guide package authors to give us their
SourcePackage
metadata so that we can drop content intodist/_content/(SourcePackage)/...
to ensure there are no clashes across packages. The implementation here means you have to give a nonemptySourcePackage
otherwise we won't include your item indist
.
</PropertyGroup> | ||
<ItemGroup> | ||
<!-- All files under "content" will be included with the Blazor app build output --> | ||
<BlazorPackageContentFile Include="$(_ContentDir)**" SourcePackage="$(_PackageId)" /> |
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.
For this I would use content and an Additional metadata attribute inside the content. That way you can piggyback on all the features of content.
The only reason I didn't do this for asmjs, wasm and other static content in the blazor core outputs is because it doesn't surface to the user.
That said, this is just a suggestion, you can give content a try or just leave it like this for now.
Another completely different option can be to just define stuff in the package as content and make it go into
(wwwroot|dist)/_blazorcontent/(js|css)/** in the consuming project and have blazor include anything under _blazorcontent/(js|css)/**.* in the index.html
That way as a package author you just have to care about putting stuff in the right folder and everything else happens automatically.
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.
Another completely different option can be to just define stuff in the package as content and make it go into
@javiercn I tried to do this at some length, by putting <PackageCopyToOutput>true</PackageCopyToOutput>
on the <Content>
items in the source package and using PackagePath
to make them land in the correct place in the output directory. It works correctly at build time.
This would a be better way to do it, except for one severe problem, which is that all <Content>
items appear in the consuming project's Solution Explorer tree as files (with little "link" icons). This makes the consuming project look messy, or at least adds totally unfamiliar items to the tree.
If you know of a way of using <Content>
and not having the items show up in the consuming project, please let me know! I'm guessing it's not currently possible due to NuGet/Home#4856 still being unresolved.
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 do believe that you can use the false node in MSBuild to make them not show up in VS https://msdn.microsoft.com/en-us/library/bb629388.aspx
So my idea is that if you put the content on the right folder path then you can have msbuild in our targets that based on the path updates the metadata for the itemgroup. (And this can be just at the top level so it applies globally)
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.
Are you talking about Visible="false"
? I did try that, and although it hid the files, it did not hide the directories. It looked very weird. If you're able to make this work and hide both please let me know!
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.
@SteveSandersonMS Yes. @rynowak This is also what you mentioned to me before, isn't it? To just use Content and use <Visible>false</Visible>
do you know about the folders showing up?
@SteveSandersonMS MSBuild wise looks good. I have a few suggestions that might simplify things, but I'll let you decide what you think its best for now. We can revisit in the future if needed. |
@javiercn I'd like to do this if it's really possible, but I haven't found a way to do so. Can NuGet packages really preserve content file metadata when packed? As far as I can tell, the generated nuspec file doesn't even have a place to store that information. If you think this is possible, could you point me to some example? |
* On build, drop <BlazorPackageContentFiles> items into dist\_content\(PackageName)\ * Add <script> and <link> tags to generated index.html * Add testapp coverage of external content package. Still need to add E2E tests that uses it. * Add missing unit test update * Add example of packaging an entire Blazor component including CSS and images * Add E2E test for component from NuGet package
There is a Problem with this approach: if every package has a props file that includes this: <PropertyGroup>
<!-- Update this to match your package ID exactly -->
<_PackageId>TestContentPackage</_PackageId>
<_ContentDir>$(MSBuildThisFileDirectory)..\content\</_ContentDir>
</PropertyGroup> The Properties Msbuild Output:
This is at least a problem with the A temporary fix for me was to rename these properties. |
Yes, that's exactly it. It's only a problem because of the "reference from source" trick. For people referencing real extension packages, there would be no issue because the build context for the package is independent of the application that references it.
If you want to have a project that references multiple other projects via the "reference from source" trick then yes, you'd need to make all the names different. In other cases you wouldn't have any issue with it. |
@SteveSandersonMS i did some further testing and i don't think this is working. When going the nuget path both build imports are in the same build context. I got this <!DOCTYPE html>
<html>
...
<body>
<app>Loading...</app>
<script src="css/bootstrap/bootstrap-native.min.js"></script>
<script src="_framework/blazor.js" main="WebApplication4.dll" entrypoint="WebApplication4.Program::Main" references="..."></script>
<script src="_content/Microsoft.AspNetCore.Blazor.Browser.Storage/storage.js" defer></script>
<script src="_content/Microsoft.AspNetCore.Blazor.Browser.Storage/storage.js" defer></script></body>
</html> To try this i created a copy of my nupkg with another id. I attached both nupkg. I can't see anything wrong with them. |
@LunicLynx Good point - thanks for this! We probably need to add |
…net#247) * On build, drop <BlazorPackageContentFiles> items into dist\_content\(PackageName)\ * Add <script> and <link> tags to generated index.html * Add testapp coverage of external content package. Still need to add E2E tests that uses it. * Add missing unit test update * Add example of packaging an entire Blazor component including CSS and images * Add E2E test for component from NuGet package
This is so we can have NuGet packages that, when installed, cause you to get extra static content in your
dist
dir, and automatically generate suitable<script>
and<link>
tags referencing any JS/CSS files that the package author nominates.The net result is that people will be able to publish packages that:
Still to be done: E2E test