diff --git a/.gitignore b/.gitignore
index b82599c845..147cee218a 100644
--- a/.gitignore
+++ b/.gitignore
@@ -128,6 +128,7 @@ collectors/python.d.plugin/python.d.plugin
 collectors/fping.plugin/fping.plugin
 collectors/ioping.plugin/ioping.plugin
 collectors/go.d.plugin
+web/netdata-switch-dashboard.sh
 
 # installer generated files
 /netdata-uninstaller.sh
diff --git a/Makefile.am b/Makefile.am
index 76b6a9348e..9f1e7868ed 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -60,6 +60,8 @@ dist_noinst_DATA = \
     package.json \
     docs \
     packaging/version \
+    packaging/dashboard.version \
+    packaging/dashboard.checksums \
     packaging/go.d.version \
     packaging/go.d.checksums \
     packaging/libwebsockets.version \
diff --git a/build/subst.inc b/build/subst.inc
index db891f24c1..c705fcbad3 100644
--- a/build/subst.inc
+++ b/build/subst.inc
@@ -8,6 +8,7 @@
 		-e 's#[@]cachedir_POST@#$(cachedir)#g' \
 		-e 's#[@]registrydir_POST@#$(registrydir)#g' \
 		-e 's#[@]varlibdir_POST@#$(varlibdir)#g' \
+		-e 's#[@]webdir_POST@#$(webdir)#g' \
 		$< > $@.tmp; then \
 		mv "$@.tmp" "$@"; \
 	else \
diff --git a/netdata-installer.sh b/netdata-installer.sh
index 8374169745..3676cb7d76 100755
--- a/netdata-installer.sh
+++ b/netdata-installer.sh
@@ -571,6 +571,13 @@ bundle_libwebsockets() {
 
 bundle_libwebsockets
 
+# -----------------------------------------------------------------------------
+# If we have the dashboard switching logic, make sure we're on the classic
+# dashboard during the install (updates don't work correctly otherwise).
+if [ -x "${NETDATA_PREFIX}/usr/libexec/netdata-switch-dashboard.sh" ] ; then
+  "${NETDATA_PREFIX}/usr/libexec/netdata-switch-dashboard.sh" classic
+fi
+
 # -----------------------------------------------------------------------------
 echo >&2
 progress "Run autotools to configure the build environment"
@@ -964,6 +971,57 @@ fi
 
 # -----------------------------------------------------------------------------
 
+copy_react_dashboard() {
+  run rm -rf "${NETDATA_WEB_DIR}-react"
+  run rm -rf "${NETDATA_WEB_DIR}-classic"
+  run cp -a "${1}/" "${NETDATA_WEB_DIR}-react"
+  run cp -a "${NETDATA_WEB_DIR}/dashboard_info.js" "${NETDATA_WEB_DIR}-react"
+  run cp -a "${NETDATA_WEB_DIR}/dashboard.slate.css" "${NETDATA_WEB_DIR}-react"
+  run cp -a "${NETDATA_WEB_DIR}/dashboard.css" "${NETDATA_WEB_DIR}-react"
+  run cp -a "${NETDATA_WEB_DIR}/main.css" "${NETDATA_WEB_DIR}-react"
+  run echo "$(cd ${NETDATA_WEB_DIR}-react && find . -type f | sed -e 's/\.\///')" > "${NETDATA_WEB_DIR}-react/.files"
+  run cp -a "${NETDATA_WEB_DIR}" "${NETDATA_WEB_DIR}-classic"
+  run echo "$(find web/gui -type f | sed -e "s/web\/gui\///")" > "${NETDATA_WEB_DIR}-classic/.files"
+  run chown -R "${NETDATA_WEB_USER}:${NETDATA_WEB_GROUP}" "${NETDATA_WEB_DIR}-react"
+}
+
+install_react_dashboard() {
+  progress "Fetching and installing dashboard"
+
+  DASHBOARD_PACKAGE_VERSION="$(cat packaging/dashboard.version)"
+
+  tmp="$(mktemp -d -t netdata-dashboard-XXXXXX)"
+  DASHBOARD_PACKAGE_BASENAME="dashboard.tar.gz"
+
+  if fetch_and_verify "dashboard" \
+                      "https://github.com/netdata/dashboard/releases/download/${DASHBOARD_PACKAGE_VERSION}/${DASHBOARD_PACKAGE_BASENAME}" \
+                      "${DASHBOARD_PACKAGE_BASENAME}" \
+                      "${tmp}" \
+                      "${NETDATA_LOCAL_TARBALL_OVERRIDE_DASHBOARD}"
+  then
+    if run tar -xf "${tmp}/${DASHBOARD_PACKAGE_BASENAME}" -C "${tmp}" && \
+       copy_react_dashboard "${tmp}/build" && \
+       rm -rf "${tmp}"
+    then
+      if run "${NETDATA_PREFIX}/usr/libexec/netdata/netdata-switch-dashboard.sh" "${NETDATA_SELECTED_DASHBOARD:-react}" ; then
+        run_ok "React dashboard installed."
+      else
+        run_failed "Failed to switch to React dashboard."
+        run rm -rf "${NETDATA_WEB_DIR}"
+        run cp -a "${NETDATA_WEB_DIR}-classic" "${NETDATA_WEB_DIR}"
+      fi
+    else
+      run_failed "Failed to install React dashboard. The install process will continue, but you will not be able to use the new dashboard."
+    fi
+  else
+    run_failed "Unable to fetch React dashboard. The install process will continue, but you will not be able to use the new dashboard."
+  fi
+}
+
+install_react_dashboard
+
+# -----------------------------------------------------------------------------
+
 # govercomp compares go.d.plugin versions. Exit codes:
 # 0 - version1 == version2
 # 1 - version1 > version2
@@ -1512,6 +1570,7 @@ REINSTALL_OPTIONS="${REINSTALL_OPTIONS}"
 RELEASE_CHANNEL="${RELEASE_CHANNEL}"
 IS_NETDATA_STATIC_BINARY="${IS_NETDATA_STATIC_BINARY}"
 NETDATA_LIB_DIR="${NETDATA_LIB_DIR}"
+NETDATA_SELECTED_DASHBOARD="${NETDATA_SELECTED_DASHBOARD:-react}"
 EOF
 run chmod 0644 "${NETDATA_USER_CONFIG_DIR}/.environment"
 
diff --git a/packaging/dashboard.checksums b/packaging/dashboard.checksums
new file mode 100644
index 0000000000..4193691d94
--- /dev/null
+++ b/packaging/dashboard.checksums
@@ -0,0 +1 @@
+42e43aa7caf411f01799c2858621f9cd23061bf55e3ceef3f1bb9b2327ff3172  dashboard.tar.gz
diff --git a/packaging/dashboard.version b/packaging/dashboard.version
new file mode 100644
index 0000000000..4ea4ea46e0
--- /dev/null
+++ b/packaging/dashboard.version
@@ -0,0 +1 @@
+v0.4.9
diff --git a/packaging/installer/netdata-updater.sh b/packaging/installer/netdata-updater.sh
index 57c521b925..781575c711 100755
--- a/packaging/installer/netdata-updater.sh
+++ b/packaging/installer/netdata-updater.sh
@@ -185,8 +185,12 @@ update() {
       do_not_start="--dont-start-it"
     fi
 
+    if [ -n "${NETDATA_SELECTED_DASHBOARD}" ] ; then
+        env="NETDATA_SELECTED_DASHBOARD=${NETDATA_SELECTED_DASHBOARD}"
+    fi
+
     info "Re-installing netdata..."
-    eval "./netdata-installer.sh ${REINSTALL_OPTIONS} --dont-wait ${do_not_start}" >&3 2>&3 || fatal "FAILED TO COMPILE/INSTALL NETDATA"
+    eval "${env} ./netdata-installer.sh ${REINSTALL_OPTIONS} --dont-wait ${do_not_start}" >&3 2>&3 || fatal "FAILED TO COMPILE/INSTALL NETDATA"
 
     # We no longer store checksum info here. but leave this so that we clean up all environment files upon next update.
     sed -i '/NETDATA_TARBALL/d' "${ENVIRONMENT_FILE}"
diff --git a/web/Makefile.am b/web/Makefile.am
index ccaccd764c..0c8b0332c3 100644
--- a/web/Makefile.am
+++ b/web/Makefile.am
@@ -9,8 +9,20 @@ SUBDIRS = \
     server \
     $(NULL)
 
+CLEANFILES = \
+    netdata-switch-dashboard.sh \
+    $(NULL)
+
 usersslconfigdir=$(configdir)/ssl
 
+include $(top_srcdir)/build/subst.inc
+SUFFIXES = .in
+
+scriptsdir=${prefix}/libexec/netdata
+scripts_SCRIPTS = \
+    netdata-switch-dashboard.sh \
+    $(NULL)
+
 # Explicitly install directories to avoid permission issues due to umask
 install-exec-local:
 	$(INSTALL) -d $(DESTDIR)$(usersslconfigdir)
@@ -19,4 +31,5 @@ dist_noinst_DATA = \
     README.md \
     gui/confluence/README.md \
     gui/custom/README.md \
+    netdata-switch-dashboard.sh.in \
     $(NULL)
diff --git a/web/netdata-switch-dashboard.sh.in b/web/netdata-switch-dashboard.sh.in
new file mode 100644
index 0000000000..c09ff6b936
--- /dev/null
+++ b/web/netdata-switch-dashboard.sh.in
@@ -0,0 +1,60 @@
+#!/bin/sh
+# SPDX-License-Identifier: GPL-3.0-or-later
+# (c) 2020 Netdata Incorporated
+
+set -e
+
+webdir="@webdir_POST@"
+configdir="@configdir_POST@"
+
+usage() {
+    cat << EOF
+USAGE: switch-netdata-dashboard.sh <dashboard-name>
+
+<dashboard-name> is required, it specifies which dashboard to use. Valid
+arguments are 'react' to use the new React dashboard, and 'classic'
+to use the old dashboard.
+
+Once run, you can use the new dashboard by performing a valdiating reload
+in your browser (Ctrl-Shift-R in most browsers).
+EOF
+exit 1
+}
+
+switch_dashboard() {
+    new="${1}"
+    path="${webdir}-${new}"
+
+    echo "Switching to ${new} dashboard..."
+
+    for dashboard in classic react ; do
+        # shellcheck disable=SC2013
+        for item in $(cat ${webdir}-${dashboard}/.files) ; do
+            rm -f "${webdir}/${item}"
+        done
+    done
+
+    cp -a "${path}/." "${webdir}"
+
+    if [ -e "${configdir}/.environment" ] ; then
+        if grep -q NETDATA_SELECTED_DASHBOARD "${configdir}/.environment" ; then
+            sed -E "s/^NETDATA_SELECTED_DASHBOARD=\".*\"$/NETDATA_SELECTED_DASHBOARD=\"${new}\"/" "${configdir}/.environment"
+        else
+            echo "NETDATA_SELECTED_DASHBOARD=\"${new}\"" >> "${configdir}/.environment"
+        fi
+    fi
+
+    exit 0
+}
+
+case "${1}" in
+    react)
+        switch_dashboard react
+        ;;
+    classic)
+        switch_dashboard classic
+        ;;
+    *)
+        usage
+        ;;
+esac