dotnet / aspnetcore

ASP.NET Core is a cross-platform .NET framework for building modern cloud-based web applications on Windows, Mac, or Linux.
https://asp.net
MIT License
35.32k stars 9.97k forks source link

Blazor - CSS Isolation problem - missing scope on selectors #52168

Open jimmygilles opened 10 months ago

jimmygilles commented 10 months ago

Is there an existing issue for this?

Describe the bug

The way Blazor is isolating the selectors seems to be incomplete and is causing conflicts.

When you have a CSS rule with multiple selectors, only the last one is scoped.

For example:

.class1 .class2 {
}

is currently transformed to:

.class1 .class2[random1] {
}

instead of:

.class1[random1] .class2[random1] {
}

This is very problematic because the isolation is not working correctly. I cannot reuse the same class name through different components.

Expected Behavior

All selectors of a component's CSS must be scoped.

.class1[random1] .class2[random1] {
}

Steps To Reproduce

Please take a look at this. The first link is the expected behavior. https://jsfiddle.net/e9kavu5z/7/ When I move my mouse over each "Content", it is correctly highlighted.

This link is the current behavior. https://jsfiddle.net/e9kavu5z/8/ As soon I move my mouse over the main container, all "Content" are highlighted.

Exceptions (if any)

No response

.NET Version

7.0.404

Anything else?

I'm working with VS Code.

dotnet --info:

SDK .NET :
 Version:   7.0.404
 Commit:    22f221a24c

Environnement d'exécution :
 OS Name:     opensuse-tumbleweed
 OS Version:  20231114
 OS Platform: Linux
 RID:         linux-x64
 Base Path:   /usr/share/dotnet/sdk/7.0.404/

Host:
  Version:      7.0.14
  Architecture: x64
  Commit:       808851b07a

.NET SDKs installed:
  7.0.404 [/usr/share/dotnet/sdk]

.NET runtimes installed:
  Microsoft.AspNetCore.App 7.0.14 [/usr/share/dotnet/shared/Microsoft.AspNetCore.App]
  Microsoft.NETCore.App 6.0.25 [/usr/share/dotnet/shared/Microsoft.NETCore.App]
  Microsoft.NETCore.App 7.0.14 [/usr/share/dotnet/shared/Microsoft.NETCore.App]

Other architectures found:
  None

Environment variables:
  Not set

global.json file:
  Not found

Learn more:
  https://aka.ms/dotnet/info

Download .NET:
  https://aka.ms/dotnet/download
Andrzej-W commented 10 months ago

The same problem exists in just released .NET 8.0.0

javiercn commented 10 months ago

@jimmygilles thanks for contacting us.

You can use the ::deep pseudo selector for this.

For example, it should transform

::deep .class1 .class2 {
}

into

[random] .class1 .class2 {
}
ghost commented 10 months ago

Hi @jimmygilles. We have added the "Needs: Author Feedback" label to this issue, which indicates that we have an open question for you before we can take further action. This issue will be closed automatically in 7 days if we do not hear back from you by then - please feel free to re-open it if you come back to this issue after that time.

jimmygilles commented 10 months ago

Hello, Thank you for your comment.

But by using "::deep", you will obviously have other unexpected problems due to the fact that all the descendant components may be impacted by this selector.

Take a look here: https://jsfiddle.net/dofav4y0/ I don't want the component 3 (which is a sub-component of component 2) to be highlighted.

This is the correct behavior: https://jsfiddle.net/dofav4y0/1/

ghost commented 10 months ago

We've moved this issue to the Backlog milestone. This means that it is not going to be worked on for the coming release. We will reassess the backlog following the current release and consider this item at that time. To learn more about our issue management process and to have better expectation regarding different types of issues you can read our Triage Process.

AeonSake commented 8 months ago

This is quite the fundamental issue with CSS isolation as it makes its primary use-case very prone to class pollution from other components. I just encountered this issue in a project and it took me a while to hunt down the reason. I also assumed the top level selector gets the scoped attribute too, which is not the case. Now I need to go through hundreds of components and pages to make sure class selectors are unique enough to not cause scope overlaps. This makes CSS isolation a lot less useful and gives users a false impression of how the CSS style is actually scoped. The docs do mention this behavior but it is easily missed.