dotnet / dotnet/runtime

Unable to reference library made using `Microsoft.NET.Sdk.WebAssembly` SDK.

Open
#132,877 0 comments 0 reactions 0 assignees View on GitHub
area-Build-mono untriaged
Dominant language
C#
Stars
18.3k
Forks
5.6k
PR merge metrics
PR metrics pending

Description

### Description

# `Microsoft.NET.Sdk.WebAssembly` library project causes conflicting static web assets when referenced by another WebAssembly (Library or Executable) project.

## Summary

I am trying to build a browser-based WebAssembly application consisting of two C# projects:

* `App` — executable WebAssembly application
* `Lib` — C# library referenced by `App`

Neither project uses Blazor, Razor, or any ASP.NET framework. The application is a plain .NET WebAssembly application running directly in the browser.

The library also needs to provide JavaScript/TypeScript files. JS files being in wwwroot are served as part of combined static web assets with specified `StaticWebAssetBasePath`. And TypeScript files ready to be consumed by App's TypeScript files.

To make JS assets from the library available to the application, I initially added:

```xml

```

to the library project and it worked.

However, the library's TypeScript files depend on the `dotnet.d.ts` generated/provided by the .NET WebAssembly runtime, so I also need a reliable way for the library to obtain the appropriate `dotnet.d.ts`.

I read up on the topic and found:

1. It's been implemented here (but unavailable in .NET10) https://github.com/dotnet/runtime/pull/120097
2. The workaround here https://github.com/dotnet/runtime/issues/77174

I tried both workaround (below) and attempt to use the flag `WasmEmitTypeScriptDefinitions` with .NET11 RC. Neither worked in Lib project.

```xml


<_DotnetDTsPath Include="%(RuntimePack.PackageDirectory)\runtimes\browser-wasm\native\dotnet.d.ts"
Condition="'%(RuntimePack.Identity)' == 'Microsoft.NETCore.App.Runtime.Mono.browser-wasm'" />

```

Then I changed my Lib project SDK from `` to `` and explicitly specified `Library`

With this setup both the flag and the workaround worked as expected.

However, this introduces a different problem.

When the `Lib` project is referenced by the `App` project, the build fails with an error similar to:

```text
Conflicting assets with the same target path '_framework/Lib#[.{fingerprint}]!.pdb'.

For assets
'Identity: C:\...\Lemon\bin\Lemon.Web\Debug\net10.0-browser\wwwroot\_framework\Lemon.65s2n5qtql.pdb,
SourceType: Project,
SourceId: Lemon,
ContentRoot: C:\...\Lemon\bin\Lemon.Web\Debug\net10.0-browser\wwwroot\,
BasePath: /,
RelativePath: _framework/Lemon#[.{fingerprint}]!.pdb,
AssetKind: Build,
AssetMode: All,
AssetRole: Primary,
RelatedAsset: ,
AssetTraitName: WasmResource,
AssetTraitValue: symbol,
Fingerprint: 65s2n5qtql,
...

and

'Identity: C:\...\Lime\bin\Lime.Web\Debug\net10.0-browser\wwwroot\_framework\Lemon.65s2n5qtql.pdb,
SourceType: Computed,
SourceId: Lime,
ContentRoot: C:\...\Lime\bin\Lime.Web\Debug\net10.0-browser\wwwroot\,
BasePath: /,
RelativePath: _framework/Lemon#[.{fingerprint}]!.pdb,
AssetKind: Build,
AssetMode: All,
AssetRole: Primary,
...
'
from different projects.
```

The `_framework/*` files emitted by the WebAssembly SDK therefore become static web assets of the library. When the library is consumed by another WebAssembly application, those assets overlap with the assets produced by the consuming application.

## Questions

1. Is using `Microsoft.NET.Sdk.WebAssembly` with:

```xml
Library
```

a supported way of creating a reusable WebAssembly library?

2. If so, is it expected that the SDK's generated `_framework/*` output becomes part of the library's Static Web Assets manifest?

3. More generally, what is the intended SDK/project setup for a plain .NET WebAssembly library that:

* does not use Blazor/Razor,
* contains C# code,
* needs to ship JavaScript/TypeScript files through `wwwroot`,
* needs to JSImport/JSExport from/to it's own js.
* and can be referenced by another plain .NET WebAssembly application?

?

### Reproduction Steps

Create projects like this:

App/
App.csproj

Lib/
Lib.csproj

App.csproj:

```xml


net10.0-browser



```

Lib.csproj:

```xml


net10.0-browser
Library
true

```

and try to build the App project.

### Expected behavior

A WebAssembly library should be able to reference another WebAssembly library in the same way as an ordinary .NET library.

To work without the library's generated WebAssembly runtime/application assets being treated as independent static web assets that conflict with the consuming application's own `_framework` assets.

The library needs to be able to provide its own intentional web assets (for example `.js`), while its intermediate/generated WebAssembly files should not cause duplicate static-web-asset entries in the consuming application.

### Actual behavior

Build error.

### Regression?

_No response_

### Known Workarounds

_No response_

### Configuration

_No response_

### Other information

_No response_

Contributor guide

Open the contributing guide

Research direction

Start with the App.csproj and Lib.csproj reproduction and build the App project using Microsoft.NET.Sdk.WebAssembly. Inspect how the library's generated _framework assets enter the Static Web Assets manifest and compare them with the consuming application's assets. Done means a plain WebAssembly library can provide intentional wwwroot assets without duplicate runtime assets causing the build conflict.

Written by the indexing model from the issue text.

Assessment

Tech stack
csharp, javascript, typescript, wasm
Domain
build-system, web-dev
Issue type
Bug
Difficulty
5/5
Estimated time
Over a week
Activity status
Active
Clarity
Mostly clear
Newbie friendliness
35/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.