diff --git a/src/assets/img/404/404.svg b/src/assets/img/404/404.svg
new file mode 100644
index 0000000000..aaad7f8396
--- /dev/null
+++ b/src/assets/img/404/404.svg
@@ -0,0 +1,14 @@
+
diff --git a/src/assets/img/globalping/404.svg b/src/assets/img/globalping/404.svg
new file mode 100644
index 0000000000..aaad7f8396
--- /dev/null
+++ b/src/assets/img/globalping/404.svg
@@ -0,0 +1,14 @@
+
diff --git a/src/assets/js/app-globalping.js b/src/assets/js/app-globalping.js
index e425af75e5..b5e03cd362 100644
--- a/src/assets/js/app-globalping.js
+++ b/src/assets/js/app-globalping.js
@@ -11,6 +11,7 @@ const cGlobalpingIntegrations = require('../../views/pages/globalping/integratio
const cGlobalpingAbout = require('../../views/pages/globalping/about-us.html');
const cGlobalpingSponsors = require('../../views/pages/globalping/sponsors.html');
const cGlobalpingCredits = require('../../views/pages/globalping/credits.html');
+const cGlobalpingError = require('../../views/pages/globalping/_404.html');
const { getGlobalpingUser } = require('./utils/http');
Ractive.DEBUG = location.hostname === 'localhost';
@@ -37,6 +38,7 @@ app.router.addRoute('/integrations', cGlobalpingIntegrations);
app.router.addRoute('/about-us', cGlobalpingAbout);
app.router.addRoute('/sponsors', cGlobalpingSponsors);
app.router.addRoute('/credits', cGlobalpingCredits);
+app.router.addRoute('/(.*)', cGlobalpingError);
app.router.replaceQueryParam = function (name, newValue) {
history.replaceState(history.state, null, location.href.replace(new RegExp(`${name}=[^&]+|$`), `${name}=${encodeURIComponent(newValue)}`));
diff --git a/src/assets/js/app.js b/src/assets/js/app.js
index 373c8eb90b..90e3a1230d 100644
--- a/src/assets/js/app.js
+++ b/src/assets/js/app.js
@@ -28,6 +28,7 @@ const cEsmsh = require('../../views/pages/esmsh.html');
const cCustomCdnOss = require('../../views/pages/oss-cdn.html');
const cCustomCdnOssProject = require('../../views/pages/_oss-cdn-project.html');
const cDocumentation = require('../../views/pages/documentation.html');
+const cError = require('../../views/pages/_404.html');
Ractive.DEBUG = location.hostname === 'localhost';
@@ -82,6 +83,7 @@ app.router.addRoute('/esmsh', cEsmsh);
app.router.addRoute('/oss-cdn', cCustomCdnOss);
app.router.addRoute('/oss-cdn/:name', cCustomCdnOssProject);
app.router.addRoute('/documentation', cDocumentation);
+app.router.addRoute('/(.*)', cError);
_.onDocumentReady(() => {
let state = {};
diff --git a/src/assets/less/app-globalping.less b/src/assets/less/app-globalping.less
index 0489a5f0c2..e4bc81eaed 100644
--- a/src/assets/less/app-globalping.less
+++ b/src/assets/less/app-globalping.less
@@ -27,3 +27,4 @@
@import "pages/globalping/about-us.less";
@import "pages/globalping/sponsors.less";
@import "pages/globalping/credits.less";
+@import "pages/globalping/404.less";
diff --git a/src/assets/less/app.less b/src/assets/less/app.less
index 031a5babce..dbb62b5d82 100644
--- a/src/assets/less/app.less
+++ b/src/assets/less/app.less
@@ -64,6 +64,7 @@
@import "pages/gsap.less";
@import "pages/proxy.less";
@import "pages/proxy-project.less";
+@import "pages/404.less";
@import "pages/tools/purge.less";
// This should go after rawgit.
diff --git a/src/assets/less/btn.less b/src/assets/less/btn.less
index 2b593686e2..39601bff7f 100644
--- a/src/assets/less/btn.less
+++ b/src/assets/less/btn.less
@@ -221,3 +221,37 @@
color: #8228f6;
}
}
+
+.btn-404 {
+ display: inline-flex;
+ align-items: center;
+ justify-content: center;
+ font-size: 14px;
+ line-height: 20px;
+ color: #fff;
+ background: #d92a28;
+ border-radius: 6px;
+ padding: 10px 20px;
+ transition: color 200ms, background 200ms;
+ border: none;
+ user-select: none;
+
+ &:hover {
+ background: #e13509;
+ }
+
+ &:active {
+ background: #b02907;
+ }
+
+ &:focus {
+ background: #f65128;
+ box-shadow: 0 0 0 1px #fff, 0 0 0 4px rgba(31, 150, 255, .48);
+ }
+
+ &:active, &:hover, &:focus {
+ color: #fff;
+ outline: none;
+ text-decoration: none;
+ }
+}
diff --git a/src/assets/less/components/header.less b/src/assets/less/components/header.less
index 50b0f5497a..c1ee63f689 100644
--- a/src/assets/less/components/header.less
+++ b/src/assets/less/components/header.less
@@ -21,6 +21,22 @@
}
}
+ &.page-404-header {
+ position: absolute;
+ width: 100%;
+ background: transparent;
+
+ .navbar {
+ background: transparent;
+ border: none;
+ box-shadow: none;
+
+ ul.nav > li > a {
+ color: #fff;
+ }
+ }
+ }
+
&.header-with-globalping-bg, &.header-with-gp-translucent-bg {
--link-highlight-color: @gp-green;
@@ -65,7 +81,7 @@
}
}
- &.gp-about-us-header {
+ &.gp-about-us-header, &.gp-404-header {
position: absolute;
width: 100%;
diff --git a/src/assets/less/pages/404.less b/src/assets/less/pages/404.less
new file mode 100644
index 0000000000..256b214fcc
--- /dev/null
+++ b/src/assets/less/pages/404.less
@@ -0,0 +1,61 @@
+.p-404 {
+ font-family: Lexend, sans-serif;
+ font-style: normal;
+ font-weight: 400;
+ -webkit-font-smoothing: antialiased;
+ width: 100%;
+ height: 1080px;
+ background: linear-gradient(180deg, #e64e3d 7.5%, #fff 100%);
+
+ .page-404 {
+ display: flex;
+ width: 100%;
+ max-width: 1248px;
+ margin: 0 auto;
+ flex-direction: row;
+ align-items: center;
+ padding: 190px 24px 338px;
+
+ &_text-block {
+ display: flex;
+ flex-direction: column;
+ row-gap: 24px;
+ width: 412px;
+ height: 228px;
+
+ &_title {
+ font-size: 32px;
+ font-weight: 600;
+ line-height: 50px;
+ letter-spacing: .2;
+ color: #fff;
+ }
+
+ &_descr {
+ font-size: 16px;
+ font-weight: 400;
+ line-height: 20px;
+ color: #fff;
+ }
+
+ &_btn {
+ font-size: 14px;
+ font-weight: 400;
+ line-height: 20px;
+ width: 172px;
+ padding: 10px 20px;
+ }
+ }
+
+ &_img-block {
+ width: 552px;
+ height: 552px;
+ mix-blend-mode: overlay;/* stylelint-disable */
+ margin-left: auto;
+
+ @media (max-width: @screen-sm-max) {
+ display: none;
+ }
+ }
+ }
+}
diff --git a/src/assets/less/pages/globalping/404.less b/src/assets/less/pages/globalping/404.less
new file mode 100644
index 0000000000..66a0dd7a61
--- /dev/null
+++ b/src/assets/less/pages/globalping/404.less
@@ -0,0 +1,61 @@
+.p-globalping-404 {
+ font-family: Lexend, sans-serif;
+ font-style: normal;
+ font-weight: 400;
+ -webkit-font-smoothing: antialiased;
+ width: 100%;
+ height: 1080px;
+ background: linear-gradient(180deg, #00b88c 8%, #fff 100%);
+
+ .gp-404 {
+ display: flex;
+ width: 100%;
+ max-width: 1248px;
+ margin: 0 auto;
+ flex-direction: row;
+ align-items: center;
+ padding: 190px 24px 338px;
+
+ &_text-block {
+ display: flex;
+ flex-direction: column;
+ row-gap: 24px;
+ width: 412px;
+ height: 228px;
+
+ &_title {
+ font-size: 32px;
+ font-weight: 600;
+ line-height: 50px;
+ letter-spacing: .2;
+ color: #fff;
+ }
+
+ &_descr {
+ font-size: 16px;
+ font-weight: 400;
+ line-height: 20px;
+ color: #fff;
+ }
+
+ &_btn {
+ font-size: 14px;
+ font-weight: 400;
+ line-height: 20px;
+ width: 172px;
+ padding: 10px 20px;
+ }
+ }
+
+ &_img-block {
+ width: 552px;
+ height: 552px;
+ mix-blend-mode: overlay;/* stylelint-disable */
+ margin-left: auto;
+
+ @media (max-width: @screen-sm-max) {
+ display: none;
+ }
+ }
+ }
+}
diff --git a/src/index.js b/src/index.js
index 848f81aca4..b1425c73f8 100644
--- a/src/index.js
+++ b/src/index.js
@@ -252,6 +252,7 @@ if (site === 'globalping') {
koaElasticUtils.addRoutes(router, [
[ '/(.*)', '/(.*)' ],
], async (ctx) => {
+ let path = ctx.path.startsWith('/_') ? '/_404' : ctx.path;
let root = site === 'globalping' ? 'globalping/' : '';
let data = {
..._.pick(ctx.query, [ 'docs', 'limit', 'page', 'query', 'type', 'style', 'measurement' ]),
@@ -259,15 +260,15 @@ koaElasticUtils.addRoutes(router, [
};
try {
- ctx.body = await ctx.render(`pages/${root}` + (ctx.path === '/' ? '_index' : ctx.path) + '.html', data);
+ ctx.body = await ctx.render(`pages/${root}` + (path === '/' ? '_index' : path) + '.html', data);
ctx.maxAge = 5 * 60;
} catch (e) {
if (app.env === 'development') {
console.error(e);
}
- ctx.status = 301;
- return ctx.redirect('/');
+ ctx.status = 404;
+ ctx.body = await ctx.render(`pages/${root}_404.html`, { actualPath: ctx.path });
}
});
diff --git a/src/views/components/header.html b/src/views/components/header.html
index ff3c9c895a..ddca74d955 100644
--- a/src/views/components/header.html
+++ b/src/views/components/header.html
@@ -1,5 +1,5 @@