Original file: /projectRoot/app/app.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>MyApp</title>
<link rel='stylesheet' src='app.global.css' />
</head>
<body tabindex="-1" disabled="disabled" focusable="false" aria-label="">
<div id="root"></div>
<script src="index.js"></script>
</body>
</html>
Output file: /projectRoot/dist/app.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>MyApp</title>
<link rel="stylesheet" src="app.global.css">
</head>
<body tabindex="-1" disabled="disabled" focusable="false" aria-label="">
<div id="root"></div>
<script src="/dist/c91b3d0cbbf15cbf3cda41e594a40ff1.js"></script>
</body>
</html>
The Javascript src is always pointing to the dist
folder a level deeper than it should. I cannot find any way to correct this. Any thoughts? Thanks very much.
| Software | Version(s) |
| ---------------- | ---------- |
| Parcel | 1.6.1
| Node | 8.9.1
| npm/Yarn | 1.3.2 (yarn)
| Operating System | Windows 7 x64
use --public-url ./
?
That would appear to work on the surface, but my Javascript file simply contains my app.html
contents when I load it in the browser. On the filesystem though, the Javascript file seems to contain correctly bundled Javascript.
Without --public-url ./
the server serves the correct bundle, but the app.html
does not point to it. Any thoughts?
It should build the exact same bundle with or without the --public-url
flag.
Could u possibly provide a test repo?
I would figure as much, and it does build the same bundle, but it isn't serving it. It serves my app.html
under the name of the Javascript file.
The dev server seems to point any unresolved address to my app.html
, so I assume this means that the file is not being found where one would expect.
I've tried the command configured in a variety of ways in the Windows cmd prompt and in Babun, but the same results no matter what. The JS file is served properly and the app.html
doesn't point to it, or the app.html
points to the proper place, but the JS file is not served properly.
In this second case I can't find anywhere the JS file is being served from at any directory level.
I am running without caching, with the flag --target=electron
I've now tried various settings for --public-url
and tried combining it with various --out-dir
settings as well, but in no case where --public-url
is used do I have a javascript file served. I've looked everywhere. I also tried installing Parcel as a local devDependency. No luck.
--public-url
only works when set to /
In my hour of investigating, no other setting yielded a javascript file being served at any location I can find.
This resolves my particular issue, but the --public-url
flag appears to have problems.
I'm very new to parcel and also seeing this issue. I whittled it down to a test repo.
(1) yarn (or npm install)
(2) firefox dist/index.html <-- should see the green message
(3) yarn start <-- load in browser, no green message
The issue seems to be that parcel's builtin web server handles what should be a 404 Not Found by returning the index.html file, which results in a JavaScript syntax error when the HTML is not valid JavaScript. Additionally, once we understand that said response should be 404 Not Found, we still don't know how to make parcel serve the correct file.
Running without --public-url is still broken because parcel issues paths with the /dist/ directory, which is there to contain the output, not to be part of the final artifact.
The reason it returns index.html
on 404 is for SPAs which do client side routing. In that case, we return the main file and let the client side javascript render the right page.
@devongovett What do you think of an option to disable that behavior on 404s? It can make debugging more difficult.
I think I ave the same issue with --public-url and SPA combination. For any file that's not on FS and not API call, I return index.html and client side routing figures out what to load. This works fine for paths that are not deeper than one level, e.g.
http://app.com/ or http://app.com/path1 - loads index.html, JS/CSS are taken from my <static>
dir correctly, e.g. http://app.com/<id>.css
http://app.com/path1/2 - loads index.html, JS/CSS are taken from <static>/path1
dir, e.g. http://app.com/path1/<id>.css
of course that doesn't work and it serves index.html
So, I guess some baseURL detection is broken? paths should always point to <static>
dir, irregardless of what URL user tries to access. Is there an option for --public-url
that would anchor all requests to '/'?
This is how I make my dev builds:
"start:dev": "NODE_ENV=development concurrently \"nodemon src/server/main.js\" \"parcel watch src/client/index.html -d build/client --public-url ./\""
@coffeeowl I was just getting the same error and was able to solve it by changing --public-url ./
to --public-url /
. I also suggest viewing your compiled html file after building and see if your path on your parcel assets are prefixed with a /
. If they aren't, that's most likely your issue!
I have this problem too. Files written in ./dist
are fine but nothing except the index page gets served.
Example:
test.html:
<h1>test.html</h1>
<script src="test.js"></script>
test.js:
console.log('test.js');
Command, using version 1.10.2
:
parcel --public-url '.' test.html
Now http://localhost:1234/
returns the index page as stored in ./dist/test.html
. Notice there is no slash in front of the file name, that is the desired outcome of setting --public-url
.
<h1>test.html</h1>
<script src="test.e98b79dd.js"></script>
The file ./dist/test.e98b79dd.js
looks fine but http://localhost:1234/test.e98b79dd.js
_does not_ serve the file.
I had the same problem too after building this demo:
https://github.com/proYang/vue-parcel-demo
Same here, it serves index.html at all paths.
Something is off..., parcel not really usable for me at the moment, cannot integrate it in the project.
Same here, it serves index.html at all paths.
Something is off..., parcel not really usable for me at the moment, cannot integrate it in the project.
Confirm, still same.. Most worst for me is i am not able to use any XHR/ajax request. Still getting index.html page.. :-(
same problem,
so i installed nginx and use parcel watch index.html --public-url "./"
same issue here also.
same issue here, which can be solved using --public-url "./",
BUT I'm using the BundlerAPI, and when I set publicUrl: './', it does not work. If i set publicUrl:'/', it works, but it is absolute path, so if I host it on a web-server in a sub-folder, it does not work. I need a relative path, and I can't find the solution to that.
`const Bundler = require('parcel-bundler');
const args = require('minimist')(process.argv.slice(2));
const game = args.g;
const entry = 'src/' + game + '/*.html';
const options = {
outDir: 'dist/' + game,
publicUrl: './',
}
const bundler = new Bundler(entry, options);
const bundle = bundler.serve();
`
This line checks that the pathname ("/foo/bar.baz" in "http://www.example.com/foo/bar.baz") starts with verbatim whatever is in the --public-url parameter. That makes --public-url='/foo'
work, and your index.html (served on /
as well as any 404 when doing a parcel serve ...
) will point to your js bundle at /foo/src.999999.js
.
Then, when the browser requests /foo/src.999999.js
, parcel's server will check that the pathname "/foo/src.999999.js" starts with "/foo", then sends the correct file. If you put a ./foo
, it fails because something about the bundling makes the ./
disappear from the front when making references in the index.html, so the request just comes to 'foo/src.999999.js'.
This causes two problems: First, the urls are all generated into the html relatively. So if index.html lives at /foo/index.html, then it will try to point to src.999999.js at "foo/src.999999.js". The browser interprets the non-absolute URL reference as "/foo/foo/src.99999.js", which is one nested layer too deep. The second problem is that the "./foo" doesnt match /foo, so it just serves the index.html again.
You can get it to work with just "/foo", because it makes the URLs bundled into index.html absolute instead of relative. This does _not_ work with absolute URLs that include anything before the path. For example: parcel serve src/index.html --public-url='http://127.0.0.1:1234'
. This is because the public url specified isn't at the beginning of the pathname. The pathname is only ever the part that comes afterwards, so it never matches. This is interesting because the builds work just fine with the absolute url (at least for my basic build testing).
I was able to look into the full-url for --public-url
, and I came up with this snipped which seems to be working pretty well:
function respond() {
let {pathname} = url.parse(req.url);
let public_url_path = url.parse(bundler.options.publicURL);
if (bundler.error) {
return send500(bundler.error);
} else {
req.url = pathname.slice(public_url_path.pathname.length);
return serve(req, res, sendIndex);
}
}
It is basically the same as the previous one, but it has the advantage of being somewhat aware of the possibility of the --public-url being a full url with domains, ports, etc. It just references the pathname
property of the public url, because that matches up with the req url path (the server doesn't seem to know anything about its own url, so this makes sense to remove from the public-url as well).
Is there any progress on this? I'm completely new to parcel, and was just following the documentation and ran into this issue. I just want to run the app on a subpath to closely mirror production, and the docs for --public-url
lead straight to a hard to debug error with assets never being served up.
I think at a minimum this should probably be called out in the docs for the CLI. I'm more than happy to create a PR if that's the route parcel wants to take 馃槃
bump....will suggestion by @rlittlefield be a viable solution?
I'm facing the same issue, the solution provided by @rlittlefield will be implemented?
same as @luizfilipe.
bumping this !
bump
Does public url not support full url format like http://localhost:8080/
?
seems not work for me.
Using v1.12.4 and can't get the build HTML to path to anything other than "/file.*"
Suppose in my 'src' folder I have 'index.html' and 'file.js'.
In my index.html, assets are pathed as per the getting started "./file.js". Running to localhost:1234 everything is fine. When I do a build, I can't get the index.html file to path to anything other than "/file.js".
Tried:
parcel build src/index.html --public-html "/"
parcel build src/index.html --public-html "./"
parcel build src/index.html --public-html "."
They all resort in the same "/file.js".
Is the only option currently to roll back a prior version?
OK, just posted this in the slim chance someone else does the same stupid thing. I had copy and pasted my --public-html command from something I had written previously and it must have been a different hyphen character that got copied. The build command was running without any errors but wasn't working.
As soon as I typed the command in 'fresh' everything worked.
Only took me an hour to figure this out!
For the record, I was wanting to have the URL's it outputs be e.g. "file.js" but it was giving me "/file.js" which worked when served up but not from my local filesystem.
To fix this, I had to use --public-url ./
(or --public-url .
also seems to work)
/
without the .
would still add the "/".
As a workaround for parcel --public-url './' index.html
always serving the contents of index.html
for every route, I'm running parcel watch
for bundling and http-server for serving, both running concurrently. This way, opening http://localhost:8080
(or whichever port you tell http-server
to use) serves the right files and parcel
's hot module replacement feature still kicks in.
I'm using a package.json
scripts entry so that npm run dev
runs both commands:
"scripts": {
"dev": "concurrently 'npm:watch' 'npm:serve'",
"watch": "parcel watch --public-url './' index.html",
"serve": "http-server -c-1 dist",
"build": "parcel build --public-url './' index.html"
}
Note 1: I disabled http-server
's cache with -c-1
flag to avoid hot replacement actually receiving an outdated version of the bundles
Note 2: connecting to 127.0.0.1
instead of localhost
or your local IP address (probably something like 192.168.0.*
, http-server
logs tell you which) breaks parcel
's hot module replacement
Tip: When you change --public-url
/publicUrl
, delete the .cache
folder. I was getting incorrect results when I changed that setting but kept the cache.
@warpech nailed it for me -- kept trying different values for --public-url
and kept getting the same output in dist/index.html
for my bundle src
. Blowing away .parcel-cache
and rebuilding finally changed the path written to src
. 馃檹 馃檹 馃檹
Most helpful comment
Tip: When you change
--public-url
/publicUrl
, delete the.cache
folder. I was getting incorrect results when I changed that setting but kept the cache.