Skip to content

Make live-reload (HMR) work out-of-the-box by directly exposing ports on the workspace URL #3282

Closed
@jankeromnes

Description

@jankeromnes

Preamble

When you start an HTTP server in a Gitpod workspace, the port can be exposed to the public internet via a HTTPS proxy.

For example, in a workspace called red-fox-abcd, you can:

  • Start some HTTP server on port 3000 (e.g. by running python3 -m http.server 3000)
  • Click on "Open Browser" to open a Preview in a new tab

The Preview tab will have the URL https://3000-red-fox-abcd:443/.

Problems

The web server might expect to run on localhost:3000, but instead it is accessed via a different domain (3000-red-fox-abcd) and a different port (443, the default HTTPS port). But usually, the web server can be configured to accept other domains/ports, and to replace all links in the app with correct URLs, for example by:

  • Setting the host filter to 0.0.0.0 instead of 127.0.0.1
  • Writing a proxy configuration (http://localhost:3000 proxied behind https://3000-red-fox-abcd:443)

However, things get worse when the app wants to run a secondary web server (e.g. backend service, DB, API server, live-reload/HMR) on a different port:

  • Start secondary server on port 3001
  • Suddenly, the web app from port 3000 gets very confused: It tries to access 3000-red-fox-abcd:3001 instead of 3001-red-fox-abcd:443

The fixes there are a bit trickier, or sometimes even impossible. Some workaround we've found to occasionally work are:

  • Configuring the correct domain & port for the secondary server, if possible (and sometimes it's tricky to make the secondary server still run on port 3001 while making the front-end use a port that is not 3001)
  • Some frameworks allow proxying secondary servers via the main server (e.g. Angular) but often "proxying" is not even implemented in development modes (where it's expected you can just use localhost)
  • Implementing support for secondary server proxy configs into the framework and sending a Pull Request(!)
  • As a last resort, "hack" the framework code with sed after installing it in the workspace: https://github.com/sveltejs/svelte/pull/4277/files#diff-370a022e48cb18faf98122794ffc5ce775b2606b09a9d1f80b71333425ec078eR7

Explanation

Probably the core problem here is that Gitpod's proxy behavior is unique and unexpected for most web servers: It encodes the port into the domain, causing a double confusion for web servers (different domain & different port than what's running on localhost, or even on the proxied primary web service).

Solution

We can simplify setups and remove the need for awkward workarounds by making the Gitpod proxy behavior a little more "standard", i.e. by exposing server ports as actual ports and not as domains:

  • 3000-red-fox-abcd:443 --> red-fox-abcd:3000
  • 3001-red-fox-abcd:443 --> red-fox-abcd:3001

This means only the domain needs to be configured/accepted by web servers, and it's the same domain even for secondary servers (so a framework randomly exposing & accessing different ports will most likely just work out-of-the-box without mad configuration wrangling).

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions