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

Improper CSS LINKS !! #5787

Closed
1 task
louiss0 opened this issue Jan 7, 2023 · 22 comments
Closed
1 task

Improper CSS LINKS !! #5787

louiss0 opened this issue Jan 7, 2023 · 22 comments

Comments

@louiss0
Copy link
Contributor

louiss0 commented Jan 7, 2023

What version of astro are you using?

1.9.0

Are you using an SSR adapter? If so, which one?

None

What package manager are you using?

pnpm

What operating system are you using?

Windows

Describe the Bug

CSS Files aren't linked in properly. I saw this in my dist folder under index.html when I was looking at the build for my site. Luckily it only cost me a few light house points.
linked-css-files

All I did for my app was import the stylesheet that was here.
base-file

Then I imported the layout from that file into here.

hmf-file

I imported the base into the 404.html file and thought that the stylesheet had something to do with the bundling problem but that does not seem to be the case. Why is the stylesheet for the 404.html loaded into the index.html page that makes no sense.
The pages have nothing to do with each other and it's costing me performance problems.

Link to Minimal Reproducible Example

https://stackblitz.com/edit/withastro-astro-9gn3do

Participation

  • I am willing to submit a pull request for this issue.
@Princesseuh
Copy link
Member

Hello!

What behavior are you expecting? Also it seems like the reproduction link doesn't work.

@louiss0
Copy link
Contributor Author

louiss0 commented Jan 7, 2023

Hello!

What behavior are you expecting? Also it seems like the reproduction link doesn't work.

I sent a new link it should work now [https://stackblitz.com/edit](https://stackblitz.com/edit/withastro-astro-9gn3do good luckj

@delucis
Copy link
Member

delucis commented Jan 7, 2023

Copying over the extra comment from the reproduction for context:

Look inside of the /dist/index.html file you will see links to files that should not be there. It will be familiar to the one from my portfolio site. I hope that be enough run pnpm build then look at the dist folder.

I notice that no matter what two files are linked. But at the same time is there supposed to be only one per page?

(For the future, it's helpful to include all this information in the issue @louiss0 so someone can get a grasp of things even before opening the Stackblitz.)

@louiss0 Is the main issue you are reporting that there is more than one CSS link per page?

@louiss0
Copy link
Contributor Author

louiss0 commented Jan 7, 2023

Copying over the extra comment from the reproduction for context:

Look inside of the /dist/index.html file you will see links to files that should not be there. It will be familiar to the one from my portfolio site. I hope that be enough run pnpm build then look at the dist folder.
I notice that no matter what two files are linked. But at the same time is there supposed to be only one per page?

(For the future, it's helpful to include all this information in the issue @louiss0 so someone can get a grasp of things even before opening the Stackblitz.)

@louiss0 Is the main issue you are reporting that there is more than one CSS link per page?

The problem is that the links that are being created are not supposed to be there. A link is supposed to only be created if I import a style.css file. Am I missing something. A link is supposed to per CSS import. In the example you should see only one style.css file.

@delucis
Copy link
Member

delucis commented Jan 7, 2023

Gotcha. So here’s what I see in dist/index.html after running the build:

<link rel="stylesheet" href="/assets/about.9e97b164.css" />
<link rel="stylesheet" href="/assets/about.635685ef.css" />
<link rel="stylesheet" href="/assets/index.d62cedb6.css" />

It’s not super obvious, but this is expected behaviour. Here’s why:

  1. You have the Tailwind integration installed in astro.config.mjs which will generate a CSS file injected into all pages. This is about.9e97b164.css in this case and contains styles generated by Tailwind.

  2. Next, we have about.635685ef.css. Looking at its contents I can see these are common page styles, like from the <Header> and <HeaderLink> components.

  3. By looking at the contents of index.d62cedb6.css I can see it mostly seems to be the styles from the <Base> layout.

A couple of questions you may have:

  1. Why are those first two CSS filenames start with about?

    Instead of choosing a completely random name for assets like CSS, we try to set a name associated with the route an asset is used on, e.g. “about” for the /about/ route. When an asset is used on multiple routes, the alphabetically first route is used for the filename. This can lead to slightly confusing naming because you might think about.css is just for the /about/ route, but in fact it’s just the first of several routes that use some shared styles. (In many sites this is 404.css which is alphabetically first, but can also cause confusion.)

  2. Why doesn’t Astro bundle these three files together?

    The dependency graph Astro creates during bundling, means we can detect what makes sense to combine, and what makes sense to split. For example <Header> and <HeaderLink> styles were always used together and got combined into a single file. However, some pages use the <Base> layout and others the <BlogPost> layout so those don’t get bundled together to avoid loading unnecessary CSS.

Hopefully that helps explain what’s going on! I’ll close this for now as I don’t think this is a bug, but let me know if I’ve misunderstood the problem.

@delucis delucis closed this as completed Jan 7, 2023
@louiss0
Copy link
Contributor Author

louiss0 commented Jan 7, 2023

Gotcha. So here’s what I see in dist/index.html after running the build:

<link rel="stylesheet" href="/assets/about.9e97b164.css" />
<link rel="stylesheet" href="/assets/about.635685ef.css" />
<link rel="stylesheet" href="/assets/index.d62cedb6.css" />

It’s not super obvious, but this is expected behaviour. Here’s why:

  1. You have the Tailwind integration installed in astro.config.mjs which will generate a CSS file injected into all pages. This is about.9e97b164.css in this case and contains styles generated by Tailwind.
  2. Next, we have about.635685ef.css. Looking at its contents I can see these are common page styles, like from the <Header> and <HeaderLink> components.
  3. By looking at the contents of index.d62cedb6.css I can see it mostly seems to be the styles from the <Base> layout.

A couple of questions you may have:

  1. Why are those first two CSS filenames start with about?
    Instead of choosing a completely random name for assets like CSS, we try to set a name associated with the route an asset is used on, e.g. “about” for the /about/ route. When an asset is used on multiple routes, the alphabetically first route is used for the filename. This can lead to slightly confusing naming because you might think about.css is just for the /about/ route, but in fact it’s just the first of several routes that use some shared styles. (In many sites this is 404.css which is alphabetically first, but can also cause confusion.)
  2. Why doesn’t Astro bundle these three files together?
    The dependency graph Astro creates during bundling, means we can detect what makes sense to combine, and what makes sense to split. For example <Header> and <HeaderLink> styles were always used together and got combined into a single file. However, some pages use the <Base> layout and others the <BlogPost> layout so those don’t get bundled together to avoid loading unnecessary CSS.

Hopefully that helps explain what’s going on! I’ll close this for now as I don’t think this is a bug, but let me know if I’ve misunderstood the problem.

This is not a good idea if you do a light house score on this page and you will see that it will complain about render blocking resources https://www.sheltonportfolio.com. The style sheet that it is complaining about is this. https://www.sheltonportfolio.com/assets/404.2f759cc7.css. This is the on that is for my 404 page not for the index page. The problem is that astro is adding stylesheets to pages that have noting to do with each other.

@delucis
Copy link
Member

delucis commented Jan 7, 2023

I guess I wasn’t clear. https://www.sheltonportfolio.com/assets/404.2f759cc7.css is not the CSS for your 404 page. It is CSS shared across all your pages (Tailwind styles by the looks of the contents). The name “404” is just because Astro looks at the list of your pages — just / and /404/ in your case, I think — and uses the name of one of these for the CSS file. But those styles are being used on your homepage.

Lighthouse will inform you about render-blocking CSS almost always but that’s not actually usually an issue unless you have huge quantities of CSS you aren’t using (not your case). Instead, check for metrics flagged for improvement. On your site all metrics are green except for Cumulative Layout Shift:

image

You can then filter down audits to only show those relevant to that metric:

image

This will show that CSS is not the key performance issue. Instead the custom font loading and an image without width and height attributes causes layout shift. You can read more about addressing these issues here: https://web.dev/optimize-cls/

@louiss0
Copy link
Contributor Author

louiss0 commented Jan 7, 2023

It suddenly changed to a 97 I guess the only thing I'd recommend now is that Astro finds a way to indicate to the developer which stylesheet is the main stylesheet. Good luck getting to 2.0

@louiss0
Copy link
Contributor Author

louiss0 commented Jan 7, 2023

I guess I wasn’t clear. https://www.sheltonportfolio.com/assets/404.2f759cc7.css is not the CSS for your 404 page. It is CSS shared across all your pages (Tailwind styles by the looks of the contents). The name “404” is just because Astro looks at the list of your pages — just / and /404/ in your case, I think — and uses the name of one of these for the CSS file. But those styles are being used on your homepage.

Lighthouse will inform you about render-blocking CSS almost always but that’s not actually usually an issue unless you have huge quantities of CSS you aren’t using (not your case). Instead, check for metrics flagged for improvement. On your site all metrics are green except for Cumulative Layout Shift:

image

You can then filter down audits to only show those relevant to that metric:

image

This will show that CSS is not the key performance issue. Instead the custom font loading and an image without width and height attributes causes layout shift. You can read more about addressing these issues here: https://web.dev/optimize-cls/

It suddenly changed to a 97 I guess the only thing I'd recommend now is that Astro finds a way to indicate to the developer which stylesheet is the main stylesheet. Good luck getting to 2.0

@kevinzunigacuellar
Copy link
Member

@louiss0 about CSS as a render-blocking asset. CSS will always be a render-blocking resource because most pages are not usable without CSS. For this reason, the browser tries to load the HTML and the CSS together so the user is able to see the intended content. You can read more on web.dev

@louiss0
Copy link
Contributor Author

louiss0 commented Jan 7, 2023

@louiss0 about CSS as a render-blocking asset. CSS will always be a render-blocking resource because most pages are not usable without CSS. For this reason, the browser tries to load the HTML and the CSS together so the user is able to see the intended content. You can read more on web.dev

I understand I have figured out what was causing most of the layout shift. There are some issues that I could not solve regarding layout shift. But I'm fine. I now wish for a way for Astro to indicate to the developer which CSS file is the main CSS file. Part of the confusion that came from this issue was me not knowing which CSS file was the main one. I hope that could get fixed maybe. Other than that I'm done with this problem I hope I Can now soon use markdoc.

@matthewp
Copy link
Contributor

matthewp commented Jan 9, 2023

There isn't really a main CSS file. There are CSS files that are shared throughout the site. Those will create bundles for those shared CSS files. There isn't necessarily 1 of them. They are created to prevent duplication.

The alternative is 1 CSS file per page, but that would be duplicating large CSS files like the Tailwind one for each page. Which is also not desirable. There isn't a 1 size fits all approach to CSS bundling that I'm aware of.

I'd love to improve how we bundle CSS but I'm not sure what the better way is at the moment.

@stormitornado
Copy link

Sorry for I'm using closed thread, but I've faced related problem.
I use Astro to generate static files for backend integration, so they need stable names like common.css on every page and some additional css files for exact page. For this I import common.scss in layout.astro file.
But Astro generates name for common css file from first page-file in alphabet order, and if I'll add another page - naming will change, which is not desirable.
Is there any method exists to define names for output css files, at least for common or critical css ?

@maxchang3
Copy link

maxchang3 commented Mar 21, 2023

Sorry for I'm using closed thread, but I've faced related problem. I use Astro to generate static files for backend integration, so they need stable names like common.css on every page and some additional css files for exact page. For this I import common.scss in layout.astro file. But Astro generates name for common css file from first page-file in alphabet order, and if I'll add another page - naming will change, which is not desirable. Is there any method exists to define names for output css files, at least for common or critical css ?

this might be helpful:

https://docs.astro.build/en/guides/configuring-astro/#customising-output-filenames

import { defineConfig } from 'astro/config'

export default defineConfig({
  vite: {
    build: {
      rollupOptions: {
        output: {
          entryFileNames: 'entry.[hash].js',
          chunkFileNames: 'chunks/chunk.[hash].js',
          assetFileNames: 'assets/asset.[hash][extname]',
        },
      },
    },
  },
})

@stormitornado
Copy link

finally I had to write a magic comment, like /* rollupAssetname: common; */
and parse it in assetFileNames function in config

@habibi9325
Copy link

habibi9325 commented Sep 5, 2023

Hi, I've had this issue and I solved it.

So - astro will create separate css files on build which will show up as a chained requests when loading a website that has links to that other website.

In my case, the separate css files were due to two different layouts being used on the two pages.
I had:
1: INDEX - using BaseLayout.astro component, and
2: THANK-YOU - using AlternateLayout.astro component.

Both layout components were loading component and had for content, the only difference was that BaseLayout component had and

components, whereas had nothing except

I solved it like this:

I created an EmptyLayout.astro file which had only and basic html stuff inside:

---
import BaseHead from "src/components/base-head.astro";
---

 <html
  lang="en"
  class="scroll-smooth selection:bg-accent-500 selection:text-white">
  <head> <BaseHead /></head>
  <body class="bg-white">
    <slot />
  </body>
</html>

and I used that file for my thank-you page.

I then created another component BaseLayout.astro which had navigation and footer inside and used that in my other pages, BUT, I referenced the already-made EmptyLayout.astro like this:

---
import EmptyLayout from "./empty-layout.astro";
import Navigation from "src/components/global/navigation.astro";
import Footer from "src/components/global/footer.astro";
---

<EmptyLayout>
    <Navigation />
    <slot />
    <Footer />
</EmptyLayout>

This way, when loading my homepage, tailwind bundled only ONE css file since those two layouts are not considered as two separate pages.

@Michael0520
Copy link

finally I had to write a magic comment, like /* rollupAssetname: common; */ and parse it in assetFileNames function in config

@stormitornado Could you please provide me with the program code for reference? I also encountered the same problem

@stormitornado
Copy link

finally I had to write a magic comment, like /* rollupAssetname: common; */ and parse it in assetFileNames function in config

@stormitornado Could you please provide me with the program code for reference? I also encountered the same problem

Hi, @Michael0520
As I mentioned before, I was needed to give stable names just for some css files, so I wrote some kind of "magic comment" to the start of scss file (common.scss in my case)

/*! rollupAssetname: common; */

@import 'common';
@import 'bs-icons';
@import 'bs-overrides';
@import 'swiper-overrides';
.... 

and parsed this string in assetFileNames function in astro.config.mjs

vite: {
    build: {
      rollupOptions: {
        output: {
          ....
          assetFileNames: assetInfo => {
            let ext = assetInfo.name.slice(assetInfo.name.lastIndexOf('.') + 1);

            if (ext == 'css') {
              var firstline = assetInfo.source.slice(0, assetInfo.source.indexOf('*\/'));

              if (firstline.includes('rollupAssetname')) {
                var hardcoded_name = assetInfo.source.match(/rollupAssetname\: (\w+);/);

                if (hardcoded_name) {
                  return `assets/css/${hardcoded_name[1]}.css`;
                }
              }
              else {
                return 'assets/css/[name].css';
              }
            }
            else if (ext == 'js') {
              return 'assets/js/[name].js';
            }
            else if (ext.match(/eot|ttf|woff|woff2/) || assetInfo.name.match('solid|regular|light|duotone|brands')) {
              return 'assets/fonts/[name][extname]';
            }
            else if (ext.match(/png|jpg|jpeg|gif|avif|webp|svg/)) {
              return 'assets/img/[name][extname]';
            }
            return 'assets/[name][extname]';
          }
        }
      }
    }
  }
}

But I'm confused, is Astro still have this problem? (I've only used it once)

@Michael0520
Copy link

Michael0520 commented Dec 16, 2023

@stormitornado
Thanks for your reply, but the problem still exists

I have several global styles in assets/styles, such as base & main, etc. In other pages, I use tailwindCSS to write styles.

In the built html file, it is found that the naming of the imported css file is judged according to the order of route name A-Z under the project.

For example I have two pages about.astro & demo.astro
In the final build result, the names of the css of about & demo import are all about.css, which is very strange, and when there is too much content, about-1.css & about.css will appear.

screenshot

CleanShot 2023-12-17 at 04 31 06

@stormitornado
Copy link

@stormitornado

Thanks for your reply, but the problem still exists
I have several global styles in assets/styles, such as base & main, etc. In other pages, I use tailwindCSS to write styles.

It will only work, if you manually create css (or scss) file with necessary imports, and add it name in comments.
I don´t know how tailwind works, but suppose that it injects or imports its styles on the page, where Astro devide them to different files with alphabet naming. And this part we cannot control. So, ask the creators about this problem...

@Michael0520
Copy link

Michael0520 commented Dec 17, 2023

I want to fix the style or the name of other resources,
I've seen the same problem in other close PRs, but it doesn't seem to have been fixed yet.
I'm still looking for other solutions

#7469

@mschoeffmann
Copy link

mschoeffmann commented Aug 3, 2024

I just created an integration for this: https://www.npmjs.com/package/astro-generic-build-filenames

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

10 participants