Express can't find Webpack bundle - node.js

So I've been configuring a MERN app with a main package that runs an Express server, and a client folder which contains the React front end and has its own package. To test the client I've been using webpack-dev-server to run an HTML file within the client/public folder that links a Webpack bundle in a dist folder. The HTML file:
<!DOCTYPE html>
<html>
<head>
<title>React Config</title>
</head>
<body>
<div id="root"></div>
<script src="../dist/bundle.js"></script>
</body>
</html>
The relative path for the bundle is correct, and it works fine using WDS. However, when I try to serve this file via my Express server, I get a 404 error for the bundle file. In my server.js:
app.use(express.static('client'));
const appPage = path.join(__dirname, './client/public/index.html');
app.get('/', function(req, res) {
res.sendFile(appPage);
});
This does serve the HTML file correctly, but when I navigate to the local server it's trying to find bundle.js at http://localhost:3000/dist/bundle.js, instead of http://localhost:3000/client/dist/bundle.js. Furthermore, even when I change the path in the HTML to point to the right location, it 404's anyway.
So 2 questions:
1) How can I configure the paths for the Webpack bundle to be accessible both from WDS run within the client folder and from my Express server in the main package?
2) Why is the bundle not being found by Express even when I alter the path to be correct? I've included the entire client folder as static for the server.

You should not use webpack-dev-server for production, webpack-dev-server not build the index.html file, webpack-dev-server is only for developers.
You can use this command to build it:
webpack --config ./webpack.prod.js --mode production

Related

What is the difference between nodemon and live-server?

Can someone help me understand the difference between npm packages nodemon and live-server as they both reload the server and listen for changes?
They serve two different purposes.
Nodemon will restart a Node application when file changes in a directory are detected.
Live-server on the other hand, will refresh your browser when changes are detected to any supported file types (e.g. HTML, JS, CSS). It also enables Ajax requests when you are working locally — these don't normally work with the file:// protocol.
Nodemon
To see this in action, let's create a simple Node server.
First, create a my-app directory, change into it, create a package.json file and a file named server.js. On a 'nix system, like so:
mkdir my-app
cd my-app
npm init -y
touch server.js
Then in server.js add:
const http = require('http');
const server = http.createServer(function (request, response) {
response.writeHead(200, {"Content-Type": "text/plain"});
response.end("Hello, World!\n");
});
server.listen(8000);
console.log("Server running at http://127.0.0.1:8000/");
Now, if you run node server.js, and visit http://127.0.0.1:8000/ in your browser, you will see a "Hello, World!" message.
If you edit server.js, for example to change the message to "Goodbye, World!", then refresh your browser, you will still see the ooriginal "Hello, World!" message.
To see the changes, you have to stop the application (with Ctrl + C), then restart it (with node server.js), then refresh your browser.
What nodemon does, is to wrap your Node application to automate this step of manually stopping and restarting the application.
Install it as a dev dependency:
npm i -D nodemon
And start your application like so:
./node_modules/.bin/nodemon server.js
Now when you make changes to server.js, nodemon will detect this automatically, meaning that all you need to is refresh your browser to see them — you avoid the stop/starting of the application.
Live-server
What live-server does on the other hand is quite different. You should install it globally:
npm install -g live-server
then when you start it in a directory, it will attempt to serve up an index.html file if one exists (otherwise it will display the directory's contents).
Staying in the my-app directory, create an index.html file:
touch index.html
Then add the following content:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Test</title>
<style></style>
</head>
<body>
<p>Hello, World!</p>
<script></script>
</body>
</html>
Start live-server, by entering live-server in a terminal window and http://127.0.0.1:8080 should open in your browser.
Now try changing the message in the HTML file, or adding some styles or some JavaScript. When you make any of these changes and save, the browser will refresh and you will see these changes in your page.
This in itself is very practical, but nothing you couldn't do by refreshing the browser manually. Where a package like this becomes indispensable is when you make an Ajax request, include a file without using a protocol, or do anything else that would be blocked by the browser's security policy if you were to open an HTML file directly.

jhipster index.html not allowing changes

I created a jhipster ui only angular 6 app.
I now want to add a script to index.html:
<head>
...
<script src='widgets/widgets.js'></script>
</head>
When I run the index.html is copied to the build/www directory fine, but in the app my script tag or any other changes are not there.
Seems that webpack does not use my new version.
How do I get webpack to use the changed template?
You have to use webpack in order to achieve the script tag injection.
Add your script to the entry points of webpack in the entry property located in webpack.dev.js (or prod) file, then add the related key inside the chunks array of the HtmlWebpackPlugin (it is located in webpack.common file).
This should inject the script tag inside your index.html

Can i use node as webserver for html app?

I'm sorry to ask such a simple question. I've been sent files by someone, an index.html file which pulls in a js file within script tags. I have to start a webserver to get through authentication and view the files (am in dev).
In my CLI i have navigated to the directory containing index.html. I have checked with node -v that I have it installed globally (yes, v 8.6). I've run the simple command node and checked my browser at http://localhost:3000 and a few other ports but get no joy. I've also tried node index.html but CLI throws an error.
How do i start the webserver? All the examples online tell me to build a .js file, but this is not an option.
Steps to set up a node web server
Create the route folder from your local machine.
Go to the command prompt from the project root path.
Install express using the command npm install express
Create server.js file
create the folder wwww and create the Index.html inside it.
server.js
var express = require('express');
var app = express();
app.use(express.static(__dirname + '/www'));
app.listen('3000');
console.log('working on 3000');
Index.html
<!doctype html
<html>
<head>
<title> my local server </title>
</head>
<body>
<h1> server working </h1>
<p> just put your html,css, js files here and it work on your own local nodejs server </p>
</body>
</html>
Go to the project root path and take the command prompt, then start the server by running the command node server.js
Then go to the browser and run the url localhost:3000.
Now you can see the html page will render on your browser.
Since you don't want to build a backend but just an http server.
I would propose to use an npm package that do just what you need:
Open a console
npm install http-server -g
Go to your "index.html" folder (in the console) then type:
http-server
Then reach your content in your browser at this address:
http://localhost:8080
Documentation here:
https://www.npmjs.com/package/http-server
Yes, this is possible.
A very simple example of how to do this would be to create file, let's call it app.js and put this in it:
const http = require('http'), // to listen to http requests
fs = require('fs'); // to read from the filesystem
const app = http.createServer((req,res) => {
// status should be 'ok'
res.writeHead(200);
// read index.html from the filesystem,
// and return in the body of the response
res.end(fs.readFileSync("index.html"));
});
app.listen(3000); // listen on 3000
Now, run node app.js
Browse to http://localhost:3000
There's loads of other npm packages that will help you out do this, but this is the simplest 'pure node' example to literally read index.html and serve it back as the response.
Its very easy to start a server using node js
Create a server.js file,
const http = require('http')
const fs = require('fs');
http.createServer(function (req, res) {
fs.readFile('index.html', function(err, data) {
res.writeHead(200, {'Content-Type': 'text/html'});
res.write(data);
res.end();
});
}).listen(3000);
Run node server.js
Here is a reference
This will even solve your backslash issue by this

How to make <script src="some_path/bootstrap.js"> work on webpack server?

I just want to test if bootstrap work good with my react app. (I am using a boilerplate which already contain webpack)
I could use bootstrap by import the files at webpack entry which learned from how-to-use-webpack-with-react-and-bootstrap:
install some node packages to cope files with different type
edit webpack.config.js to let it use above installed packages
But, I just want to have a try, and I think it make build slow if bundle other js lib into bundle.js (I need hot load, so not expect webpack bundle all).
Now, I write code like:
<!doctype html>
<html>
<head>
<title>test</title>
<script type="text/javascript" src="res/bootstrap/js/bootstrap.min.js"></script>
<link rel="stylesheet" href="res/bootstrap/css/bootstrap.min.css">
</head>
<body>
<div id="root"></div>
<script src="/static/bundle.js"></script>
</body>
</html>
The content of bootstrap.min.js and bootstrap.min.css is empty.
I have tried to change the path from "res/bootstrap/js/bootstrap.min.js" to "src/res/bootstrap/js/bootstrap.min.js", but not work.
Also try to set resolve in webpack config by Resolving require paths with webpack, it result to another error like Cannot resolve module 'react'
I know I may mistake root path or miss some config, but can't figure it out,
what should I do?
OK, a little late to post answer,
the problem is by express.The project I forked is use express to start webpack project, it does contain webpack.dev.config.js which make me think it is using a webpack devserver.
I understand the problem as soon as see this :
app.get('*', (req, res) => {
res.sendFile(path.join(__dirname, 'index.html'));
});
I didn't care how the base project started before. It used express, not webpack devserver, just a simple route problem.
change to below work,
app.get('/', (req, res) => {
res.sendFile(path.join(__dirname, 'index.html'));
});
One complain: does nodejs devs like to set * router ?

js file not found on Heroku

My socket.js file can not be found when my Node.js server runs on Heroku, however when it runs on localhost, it is found. In addition, although the app.js file is in the same directory with socket.js file, it can not be found. I've seen some posts suggesting to use
app.use('/', express.static(__dirname));
but i guess it is not the case here.
my index.html file :
<script src="/angular-socket-io/socket.js"></script>
<script src="/socket.js"></script>
<script src="/socket.io/socket.io.js"></script>
Amongst them, the only one couldnt be found is the second directory(/socket.js) which contains the 'socket factory'inside.
My folder tree is as follows;
-app
--assets
---app.js
---socket.js
Any help please?
Just add app.use(express.static(path.join(__dirname, 'app/assets'))); to your main code and after that you can use <script src="/socket.js"></script>
My JavaScript file didn't initialize because of how I imported the JQuery script inside of my index.html.
If your JavaScript file that contains JQuery is not initialized. Make sure to import it with HTTPS not HTTP.
WRONG :
<script src="http://code.jquery.com/jquery-3.5.1.js"></script>
CORRECT :
<script src="https://code.jquery.com/jquery-3.5.1.js"></script>
This solved my problem of missing the JavaScript file on Heroku.

Resources