systemjs / plugin-css

CSS loader plugin
MIT License
92 stars 60 forks source link

Relative urls are not fixed in bundle #122

Open jgillich opened 7 years ago

jgillich commented 7 years ago

I use font-awesome, which works well in development when no bundle is used. However, with a bundle:

Now, the expected font url is /app/jspm_packages/npm/font-awesome...

But it actually is: jspm_packages/npm/font-awesome..., which resolves to /doc/faq/jspm_packages/.. and therefore fails to load.

jgillich commented 7 years ago

Tried setting rootURL: "/app" as mentioned in #28, now things are getting really weird

src:url('/../home/jgillich/devel/src/github.com/termbox/termbox/app/jspm_packages/npm/font-awesome@4.7.0/fonts/fontawesome-webfont.eot?v=4.7.0');
guybedford commented 7 years ago

rootURL is a file path, not a URL, I know that can seem confusing, but it is a file path reference to the file path that should correspond to the / URL in the browser.

jgillich commented 7 years ago

Ah, so basically when I'm at /foo/bar/ I'd set rootURL to ../../?

But I still wonder why it's not simply using baseURL to rewrite the urls. It works that way in development, so why is it different in the bundle?

guybedford commented 7 years ago

No when your public folder is /Users/.../my_app/www in Node, you would set that as the rootURL (or just my_app/www).

jgillich commented 7 years ago

For some reason the CSS is not injected on my local machine, with the same build steps. :ghost:

But setting rootURL to . works, not sure how much sense that makes. IMO, relative url()'s should just be working out of the box, it's not like they are not well defined, or are they?

staxmanade commented 7 years ago

I've just run into this myself...

I have a nodejs server that practically any url you request returns the root /index.html file - EX: / -> /index.html as well as /my/other/route -> /index.html - this allows deep-linking as well as browser push-state scenarios where people can navigate to another url, copy/paste the url and get back to that page (despite it loading more like a SPA app).

I noticed the following

  1. loading from the root (bundled or not bundled) loads font-awesome
  2. Loading font-awesome from a sub-route ex: /player/some-asset loads fine when UN-bundled
  3. Loading font-awesome from a sub-route ex: /player/some-asset does not load properly.

I'm using import 'font-awesome/css/font-awesome.min.css!'; in a bootstrap.jsx file. When it loads correctly it's loading the following url:

http://localhost/jspm_packages/npm/font-awesome@4.6.3.json

when it fails to load it's using the following path:

http://localhost/player/some-asset/jspm_packages/npm/font-awesome@4.6.3.json

I tried setting rootURL to both . and / - but maybe I'm not setting it right.

Thoughts?

jgillich commented 7 years ago

Did you also set baseUrl: '/', in addition to rootUrl: '.'? That's working for me.

staxmanade commented 7 years ago

@jgillich I already have the baseUrl: '/' and adding the rootUrl: '.' did not seem to do anything for me...

my current work-around is to manually load the font-awesome manually in my html file :(

ZoolWay commented 6 years ago

@guybedford This is a very important statement which should be in the config docs:

rootURL is a file path, not a URL, I know that can seem confusing, but it is a file path reference to the file path that should correspond to the / URL in the browser.

Still I have problems with the rewriting. My document root / wwwroot is d:\a\myapp\wwwroot. That is / for the browser. Inside that I have a folder dev which is my unbundled app. All compiled typescript goes in there and jspm_packages is in dev/jspm_packages as well.

I now create a bundle and put it in wwwroot/bundled(/dist) to check out if my bundle works. When deploying later to production servers, the app should run in a browser root / as well as in any number of subfolders.

Setting rootURL to d:\a\myapp\wwwroot the included font-awesome font URL is rewritten to url('/../../jspm_packages/etc') - As you can see going a folder up (..) from the root of a web url is nonesense so the browser tries to load from /jspm_packages/etc instead of /bundled/jspm_packages/etc or relative to index.html it would be just jspm_packages/etc and relative to the bundle which is place in wwwroot/bundled/dist it would be ../jspm_packages/etc

Recapping my folder structure...

d:\a\myapp
  (this is also the place where I start my npm, jspm and gulp commands)
  package.json
  gulpfile.js
  src/ (typescript source, compiled and put into wwwroot/dev/dist)
  wwwroot/
    dev/
      index.html
      jspm.config.js
      jspm.browser.js
      dist/ (ES6 source files)
      jspm_packages/
      assets/ (other graphics etc)
    bundled/
      index.html (copy of dev)
      jspm.config.js (copy of dev)
      jspm.browser.js (copy of dev)
      jspm.bundled.js (contains SystemJS.config for the bundles, generated from bundle.modules)
      dist/
        app-bundle.js
      jspm_packages/ (copy of dev)

Getting a setup to work where your application is not in the root folder of the webserver seem to be a huge problem.

ffflabs commented 6 years ago

My browser reads all js, css and images from <Project Root>/public

In my config I have

 "baseURL": "public",
 "rootURL":"./public/"

and it works fine for absolute urls (image backgrounds, fonts and imports starting with '/').

If you set an absolute path to rootURL as, for example /, in node this means the very root of your filesystem (in linux). Of course the paths will be rewritten relative to root, which is located at /../home/foo/bar.