Modify requests to targeted URLs manually in Browsersync

In my current setup, I am utilizing BrowserSync in a unique way. I have my web server (Apache in a Docker container) proxied, but I am also serving hot module replacement (HMR) from a Webpack dev server.

In my local development environment, the configuration is as follows:

https://mytestsite.localhost – Apache service in a Docker container

https://localhost:8888 – Webpack Dev server serving HMR

https://localhost:3000 – BrowserSync`

While hard reloads are working perfectly fine, the issue arises with hot reloads. The document served by the BrowserSync proxy should be reading the hotupdate.json served by webpack-dev-server. When a hot update is received, the page attempts to load /hotupdate.json, resulting in a 404 error because the browser is trying to access

https://localhost:3000/hotupdate.json
, whereas the hotupdate.json is actually served by the Webpack server at
https://localhost:8888/hotupdate.json
.

Since I know the absolute URL of this resource, I want to instruct BrowserSync to redirect any requests to /hotupdate.json to

https://localhost:8888/hotupdate.json
. I have attempted to achieve this using middleware, but I seem to be struggling due to a lack of understanding of Express-style middleware.

Although I have tried implementing some middleware, it has not been successful. Here is an example of my attempt:

browserSync({
    proxy: {
        target: `https://${process.env.APP_HOST_PATH}`,
        middleware: [
            dontProxyHotUpdate,
            require('webpack-dev-middleware')(bundler, {
                noInfo: true,
                publicPath: webpackConfig.output.path
            }),
        ]
    },
    files: [
      'app/css/*.css',
      'app/*.html'
    ]
});

function dontProxyHotUpdate (req, res, next){
    if(req.url === '/hotupdate.json'){
        req.url = 'https://127.0.0.1:8888/hotupdate.json';
    }
    next();
}

While the middleware is being loaded (as evident from console.log(req.url)), the request URL is not being rewritten successfully. Possible solutions may involve rewriting the request URL or directly overwriting the response.

It may be questioned why I am not using webpack-dev-server directly, as it already serves HMR effectively. The reason is that it lacks the capability to rewrite anchor elements within a page, such as changing

https://mytestsite.localhost/link
to https://localhost:3000/link. This rewriting is essential for navigating a site during development and ensuring assets, like SVGs, load properly only if the path, host, and port all match.

Answer №1

Finally, I managed to resolve the issue on my own!

I took the initiative to create my own middleware using http-proxy-middleware - just like this.

var proxy = require('http-proxy-middleware');

browserSync({
    proxy: {
        target: `https://${process.env.APP_HOST_PATH}`,
        middleware: [
            dontProxyHotUpdate,
            require('webpack-dev-middleware')(bundler, {
                noInfo: true,
                publicPath: webpackConfig.output.path
            }),
            // require("webpack-hot-middleware")(bundler) // I don't think that we want this here as it can be handled by the webpack dev server
        ],
    },

    // no need to watch '*.js' here, webpack will take care of it for us,
    // including full page reloads if HMR won't work
    files: [
      path.join(source, '**/*.php'),
      path.join(source, 'style.css')
    ]
});

var dontProxyHotUpdate = proxy('/hotupdate*', {
    target: 'https://127.0.0.1:8888/',
    changeOrigin: true, // for vhosted sites, changes host header to match to target's host
    logLevel: 'debug',
    secure: false
});

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Passport and Node.js team up to create powerful user group functionalities

Seeking advice on this topic. I am interested in setting up a page with a login form as the main page. Upon logging in, users would be directed to their personalized dashboard. However, if someone logs in with admin privileges, they should be redirected t ...

What's the best way to keep track of the number of objects I've created

Using this HTML code, I can create member objects. However, I also need to determine the count of these member objects for certain calculations. Additionally, when a member object is deleted, the count of member objects should be reduced accordingly. The ...

Tips for choosing a class with a leading space in the name

Struggling with an issue here. I'm attempting to adjust the CSS of a specific div element that is being created dynamically. The current output looks something like this: <div class=" class-name"></div> It seems there is an extra space b ...

Ways to retrieve the file name from the content-disposition header

I received a file through an AJAX response. I am trying to extract the filename and file type from the content-disposition header in order to display a thumbnail for it. Despite conducting multiple searches, I have been unable to find a solution. $(". ...

Guide on utilizing popup box input to amend CSS (background color)

I'm looking for some guidance on JavaScript and CSS. Is there a way to create a popup box where users can input a color (any main primary color recognized by CSS) and then have the background color of the page change accordingly in an external styles ...

Node.js and Express do not apply the JWT middleware to a specific route

I have been working on implementing JWT authentication exclusion for specific routes. So far, I have been successful in excluding it for some routes but facing challenges with others. Below is the code snippet that I am using. For the route mentioned belo ...

Leverage a collection of paths when performing actions within the app.all() method in Node.js Express

In my express application, I have a list of routes that need specific actions to be performed on them. For example: app.get('/xyz', file.xyz); app.post('/xyz1', file.xyz1); app.post('/xyz2', file.xyz2); app.post('/xy ...

The nodejs express application is experiencing difficulties in serving static files from the public/js directory

Currently, I am working on a nodejs express project. Within the project, there exists a public folder with various subfolders such as js, css, images, and more. Initially, files were being served from these folders using the following code: app.use(expres ...

Extract URL Parameters in Node.js Server

I am facing an issue with passing a parameter (qItems) in XMLHttpRequest.open: index.html (app.listen(8080);) var qItems= 8; var url= 'ItemsList'; var xhr = new XMLHttpRequest(); var tag = document.getElementById("insertHere"); tag.innerHTML = ...

Problem encountered with JavaScript getter on iOS 5

While implementing JavaScript getters in my iPad-optimized website, everything was working perfectly until I updated to iOS 5. Suddenly, the site stopped functioning properly. After thorough investigation, I discovered the root cause of the issue. I have ...

Pressing the enter key within Material UI Autocomplete will allow you to quickly create new

Wouldn't it be great if Autocomplete in material ui could do this: wertarbyte Imagine being able to insert text (string) without the need for a list of elements to select from. This means that the noOptions message shouldn't appear, and instead ...

modify the color of text in a row within a jquery ajax table

Is it possible to change the font color of values in a row based on a condition inside a function? Specifically, if the TotalStudent count exceeds the room capacity, can we add student information to the table with red font color? Below is my attempt using ...

What is the best way to access the current value and name of a textbox in real-time using

How can I retrieve the value of a textbox in JavaScript using onblur and on keyup events, while also performing real-time checking for each individual textbox using "this keyword"? Here is my JSFiddle link. Can you assist me in modifying it? ...

JavaScript validation for radio buttons that are grouped together

Need help with a JavaScript validation issue regarding grouped radio buttons named optionRadios1 to 5. I'm trying to validate them before submitting the form, but my code isn't working as expected and still allows the form submission. Below is t ...

What could be causing me to receive two builds when using Webpack?

I am trying to capture the hash of the build by using a callback function in webpack: const compiler = webpack(webpackConfig, function (err, stats) { debug("Hash", stats.hash) }) However, I am encountering an issue where two builds are generated and on ...

Error: The post method in $setup is not defined in Vue Composition API

Dealing with a frustrating issue in my Vue application. One page is functioning perfectly fine, while the other is causing trouble by displaying this error: The first page loads a collection of wordpress posts (Blog.vue) without any issues, but the second ...

React component that enables radio inputs to repeat upon selection

My current project involves creating a quiz app where users can answer single questions using React on Codepen. I am utilizing an API to fetch a question, along with 3 incorrect answers and 1 correct answer, then storing them in the app's state. Howev ...

Invoke the ng-click function within the ng-change function

Just starting out with angularjs and I have a question. I am currently using single select and I want to retrieve the value selected and based on that value, perform an action. For example, if the value is "DELETE" then I would like to trigger the ng-clic ...

Issue with Material-UI: Unforeseen TypeError arises while toggling between two Drawer elements

Note: I am utilizing material-ui 3.3.0 My goal is to have two <Drawer> components displayed on a page, with one sliding in from the left and the other from the right. In an <AppBar>, there are two <Button> components that toggle the visi ...

Node.js Express is unable to interpret the data of an undefined variable

Utilizing a post request in this scenario app.post('/api/notes', (req, res, next) => { const clientReq = req.body.content; if (!clientReq) { res.status(400).send({ error: `You must provide content`}); } fs.readFile(dataPath, ' ...