Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

🔍 Demo-Modus hinzugefügt #598

Merged
merged 29 commits into from
Mar 10, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
bccf6b0
Added new translations to the en.json
gnmyt Mar 10, 2024
ceddd35
Randomized test values in demo mode
gnmyt Mar 10, 2024
0fe3dec
Updated the server index.js
gnmyt Mar 10, 2024
c1c884a
Protected the config.js routes
gnmyt Mar 10, 2024
83c0942
Protected the integrations.js routes
gnmyt Mar 10, 2024
0fd8732
Protected the nodes.js routes
gnmyt Mar 10, 2024
1499437
Protected the system.js routes
gnmyt Mar 10, 2024
bdc2009
Removed password security during demo mode
gnmyt Mar 10, 2024
84c6487
Updated the config.js controller
gnmyt Mar 10, 2024
7c1c01e
Fixed a bug in the speedtests.js controller
gnmyt Mar 10, 2024
8d25253
Added the WEB_URL to the client index.js
gnmyt Mar 10, 2024
5b23ce8
Removed the healthChecksInfo from the infos.jsx util
gnmyt Mar 10, 2024
64fb533
Updated the DropdownComponent.jsx
gnmyt Mar 10, 2024
5f4ae34
Integrated the demo mode badge into the HeaderComponent.jsx
gnmyt Mar 10, 2024
86d1a54
Integrated the demo mode badge into the HeaderComponent styles.sass
gnmyt Mar 10, 2024
e49b582
Updated the IntegrationItemHeader.jsx
gnmyt Mar 10, 2024
628fd44
Updated the IntegrationDialog.jsx
gnmyt Mar 10, 2024
69c72c4
Updated the IntegrationDialog styles.sass
gnmyt Mar 10, 2024
3493e5f
Updated the nodes.jsx page
gnmyt Mar 10, 2024
be52415
Updated the Nodes styles.sass
gnmyt Mar 10, 2024
c77f035
Fixed a font bug in the Statistics.jsx
gnmyt Mar 10, 2024
45fb1f3
Updated the storage path during preview mode
gnmyt Mar 10, 2024
3e80850
Added new translations to the en.json
gnmyt Mar 10, 2024
db3704b
Added custom provider details in the DropdownComponent.jsx
gnmyt Mar 10, 2024
65b2187
Added a download icon to the HeaderComponent.jsx
gnmyt Mar 10, 2024
0f46fed
Updated the Header styles.sass
gnmyt Mar 10, 2024
66b3ce3
Added the previewMessage value to the config.js route
gnmyt Mar 10, 2024
f55496d
Changed environment variable port to SERVER_PORT
gnmyt Mar 10, 2024
d07a8eb
Fixed the Header styles.sass
gnmyt Mar 10, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions client/public/assets/locales/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@
"language": "Change language",
"view": "Switch view",
"info": "About the project",
"provider": "About the provider",
"integrations": "Integrations"
},
"options": {
Expand Down Expand Up @@ -106,6 +107,7 @@
"running_tooltip": "Speedtest running",
"start_tooltip": "Start speedtest",
"new_update": "Update available",
"download": "Download",
"paused": "Speedtests are currently paused. Please continue them if you want to do one.",
"running": "A speedtest is already running. Please wait a moment.",
"admin_login": "Admin Login",
Expand Down Expand Up @@ -245,6 +247,7 @@
"update_password": "Please update the password of this node",
"password_outdated": "Password outdated",
"password_updated": "The password has been successfully updated",
"preview_active": "Adding and deleting servers is disabled during demo mode.",
"placeholder": {
"name": "MySpeed instance",
"url": "https://your-server.com"
Expand All @@ -265,8 +268,14 @@
"tests_pending": "Test results pending"
}
},
"preview": {
"title": "Demo mode",
"info": "DEMO",
"description": "You are currently in demo mode. Some features are disabled and some settings cannot be changed. If you want to use all features, you can <Link>install MySpeed</Link> on your own server."
},
"integrations": {
"none_active": "This integration is not active. <br/><Bold>Create</Bold>",
"preview_active": "Integrations are disabled during demo mode.",
"display_name": "Integration name",
"create": "Create",
"activity": {
Expand Down
11 changes: 8 additions & 3 deletions client/src/common/components/Dropdown/DropdownComponent.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ import {StatusContext} from "@/common/contexts/Status";
import {InputDialogContext} from "@/common/contexts/InputDialog";
import {SpeedtestContext} from "@/common/contexts/Speedtests";
import {baseRequest, downloadRequest, jsonRequest, patchRequest, postRequest} from "@/common/utils/RequestUtil";
import {creditsInfo, healthChecksInfo, recommendationsInfo} from "@/common/components/Dropdown/utils/infos";
import {creditsInfo, recommendationsInfo} from "@/common/components/Dropdown/utils/infos";
import {
exportOptions, languageOptions, levelOptions,
selectOptions, timeOptions
Expand Down Expand Up @@ -242,14 +242,16 @@ function DropdownComponent() {

const showCredits = () => setDialog({title: "MySpeed", description: creditsInfo(), buttonText: t("dialog.close")});

const showProviderDetails = () => setDialog({title: t("dropdown.provider"), description: config.previewMessage, buttonText: t("dialog.close")});

const options = [
{run: updatePing, icon: faPingPongPaddleBall, text: t("dropdown.ping")},
{run: updateUpload, icon: faArrowUp, text: t("dropdown.upload")},
{run: updateDownload, icon: faArrowDown, text: t("dropdown.download")},
{run: recommendedSettings, icon: faWandMagicSparkles, text: t("dropdown.recommendations")},
{hr: true, key: 1},
{run: updateServer, icon: faServer, text: t("dropdown.server")},
{run: updatePassword, icon: faKey, text: t("dropdown.password")},
{run: updatePassword, icon: faKey, text: t("dropdown.password"), previewHidden: true},
{run: updateCron, icon: faClock, text: t("dropdown.cron")},
{run: updateTime, icon: faCalendarDays, text: t("dropdown.time"), allowView: true},
{run: exportDialog, icon: faFileExport, text: t("dropdown.export")},
Expand All @@ -258,7 +260,8 @@ function DropdownComponent() {
{hr: true, key: 2},
{run: updateLanguage, icon: faGlobeEurope, text: t("dropdown.language"), allowView: true},
{run: () => setShowViewDialog(true), icon: faChartSimple, allowView: true, text: t("dropdown.view")},
{run: showCredits, icon: faInfo, text: t("dropdown.info"), allowView: true}
{run: showCredits, icon: faInfo, text: t("dropdown.info"), allowView: true, previewHidden: true},
{run: showProviderDetails, icon: faInfo, text: t("dropdown.provider"), previewShown: true}
];

return (
Expand All @@ -270,6 +273,8 @@ function DropdownComponent() {
<h2>{t("dropdown.settings")}</h2>
<div className="dropdown-entries">
{options.map(entry => {
if (entry.previewHidden && config.previewMode) return;
if (entry.previewShown && !config.previewMode) return;
if (!config.viewMode || (config.viewMode && entry.allowView)) {
if (!entry.hr) {
return (<div className="dropdown-item" onClick={() => {
Expand Down
8 changes: 2 additions & 6 deletions client/src/common/components/Dropdown/utils/infos.jsx
Original file line number Diff line number Diff line change
@@ -1,12 +1,8 @@
import {PROJECT_URL, PROJECT_WIKI} from "@/index";
import {WEB_URL} from "@/index";
import {Trans} from "react-i18next";
const HEALTHCHECKS_URL = "https://healthchecks.io/";
const CLI_URL = "https://www.speedtest.net/apps/cli";

export const healthChecksInfo = () => <Trans components={{HCLink: <a href={HEALTHCHECKS_URL} target="_blank"/>,
WIKILink: <a href={PROJECT_WIKI + "/instructions/settings"} target="_blank"/>}}>info.healthchecks</Trans>

export const creditsInfo = () => <Trans components={{Link: <a href={PROJECT_URL} target="_blank" />,
export const creditsInfo = () => <Trans components={{Link: <a href={WEB_URL} target="_blank" />,
CLILink: <a href={CLI_URL} target="_blank"/>}}>info.credits</Trans>

export const recommendationsInfo = (ping, down, up) => <Trans components={{Bold: <span className="dialog-value" />}}
Expand Down
25 changes: 23 additions & 2 deletions client/src/common/components/Header/HeaderComponent.jsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import "./styles.sass";
import {FontAwesomeIcon} from "@fortawesome/react-fontawesome";
import {
faCircleArrowUp,
faCircleArrowUp, faDownload,
faGaugeHigh,
faGear,
faLock,
Expand All @@ -18,6 +18,8 @@ import {t} from "i18next";
import {ConfigContext} from "@/common/contexts/Config";
import {LoadingDialog} from "@/common/components/LoadingDialog";
import {NodeContext} from "@/common/contexts/Node";
import {WEB_URL} from "@/index";
import {Trans} from "react-i18next";

function HeaderComponent(props) {
const findNode = useContext(NodeContext)[4];
Expand All @@ -35,6 +37,12 @@ function HeaderComponent(props) {
toggleDropdown(setIcon);
}

const showDemoDialog = () => setDialog({
title: t("preview.title"),
description: <Trans components={{Link: <a href={WEB_URL + "/install"} target="_blank" />}}>preview.description</Trans>,
buttonText: t("dialog.okay")
});

const showPasswordDialog = () => setDialog({
title: t("header.admin_login"),
placeholder: t("dialog.password.placeholder"),
Expand Down Expand Up @@ -70,6 +78,8 @@ function HeaderComponent(props) {
postRequest("/speedtests/run").then(updateTests).then(updateStatus).then(() => setStartedManually(false));
}

const openDownloadPage = () => window.open(WEB_URL + "/install", "_blank");

useEffect(() => {
if (Object.keys(config).length === 0) return;
async function updateVersion() {
Expand All @@ -90,7 +100,13 @@ function HeaderComponent(props) {
<header>
<LoadingDialog isOpen={startedManually}/>
<div className="header-main">
{config.viewMode ? <h2>{t("header.title")}</h2> : <h2 onClick={() => props.showNodePage(true)} className="h2-click"><FontAwesomeIcon icon={faServer} /> {getNodeName()}</h2>}
<div className="header-left">
{config.viewMode && <h2>{t("header.title")}</h2>}
{!config.viewMode && <h2 onClick={() => props.showNodePage(true)} className="h2-click"><FontAwesomeIcon icon={faServer} /> {getNodeName()}</h2>}

{config.previewMode && <h2 className="demo-info" onClick={showDemoDialog}>{t("preview.info")}</h2>}
</div>


<div className="header-right">
{updateAvailable ?
Expand All @@ -113,6 +129,11 @@ function HeaderComponent(props) {
<span className="tooltip">{t("header.admin_login")}</span>
</div> : <></>)}

{(config.previewMode ? <div className="tooltip-element tooltip-bottom">
<FontAwesomeIcon icon={faDownload} className={"header-icon"} onClick={openDownloadPage}/>
<span className="tooltip">{t("header.download")}</span>
</div> : <></>)}

<div className="tooltip-element tooltip-bottom" id="open-header">
<FontAwesomeIcon icon={icon} className="header-icon" onClick={switchDropdown}/>
<span className="tooltip">{t("dropdown.settings")}</span>
Expand Down
62 changes: 50 additions & 12 deletions client/src/common/components/Header/styles.sass
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
@import "@/common/styles/colors"

.header-main
margin-top: 2rem
margin-top: 3rem
display: flex
align-items: center
justify-content: space-between
Expand All @@ -16,18 +16,40 @@
.header-main *
font-size: 24pt

.header-main h2
.header-left
margin-left: 10%
display: flex
gap: 1rem
gap: 0.5rem
align-items: center
justify-content: center
overflow: hidden
text-overflow: ellipsis

.demo-info
display: flex
cursor: pointer
align-items: center
justify-content: center
font-size: 14pt
background-color: $dark-gray
color: $green
margin: 0

.header-main h2
padding: 0.5rem 1rem
border-radius: 1rem
margin: 0

.header-main .h2-click
display: flex
gap: 1rem
align-items: center
cursor: pointer
user-select: none

svg
margin-right: 0.3rem

.header-main .h2-click:hover
color: $green-hover
background-color: $dark-gray
Expand All @@ -37,6 +59,8 @@

.header-icon
cursor: pointer
display: flex

transition: all 50ms ease-in-out
width: 30px
height: 30px
Expand Down Expand Up @@ -68,24 +92,38 @@
100%
box-shadow: 0 0 0 0 #CCA92C00

@media (max-width: 460px)
@media screen and (max-width: 650px)
.header-left
flex-direction: column

@media (max-width: 530px)
.header-main
justify-content: center
.header-main div
.header-left div
margin-right: 0
.header-main h2
.header-left .h2-click
margin-left: 0
font-size: 24pt
font-size: 22pt
.header-icon
width: 25px
height: 25px


@media (max-width: 360px)
.header-main h2
font-size: 16pt
@media (max-width: 480px)
.header-left .h2-click
font-size: 14pt
text-overflow: ellipsis
overflow: hidden
.header-left svg
font-size: 14pt
.header-icon
width: 20px
height: 20px
height: 20px

@media screen and (max-width: 365px)
.header-main .h2-click
gap: 0
.header-left svg
margin-right: 0
.demo-info
font-size: 12pt
padding: 0
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,19 @@ import {DialogContext, DialogProvider} from "@/common/contexts/Dialog";
import "./styles.sass";
import React, {useContext, useEffect, useState} from "react";
import {t} from "i18next";
import {faClose} from "@fortawesome/free-solid-svg-icons";
import {faClose, faExclamationTriangle} from "@fortawesome/free-solid-svg-icons";
import {FontAwesomeIcon} from "@fortawesome/react-fontawesome";
import {jsonRequest} from "@/common/utils/RequestUtil";
import IntegrationItem from "@/common/components/IntegrationDialog/components/IntegrationItem";
import {v4 as uuid} from 'uuid';
import AvailableIntegrations from "./components/AvailableIntegrations";
import IntegrationAddButton from "@/common/components/IntegrationDialog/components/IntegrationAddButton";
import NoIntegrationsTab from "@/common/components/IntegrationDialog/components/NoIntegrationsTab";
import {ConfigContext} from "@/common/contexts/Config";

export const Dialog = ({integrations, active, setActive}) => {
const close = useContext(DialogContext);
const [config] = useContext(ConfigContext);
const [currentTab, setCurrentTab] = useState(integrations[Object.keys(integrations)[0]].name);

const addIntegration = () => setActive([...active, {uuid: uuid(), name: currentTab,
Expand All @@ -31,6 +33,12 @@ export const Dialog = ({integrations, active, setActive}) => {
setCurrentTab={setCurrentTab}/>

<div className="integrations-tab">
{config.previewMode && active.filter(item => item.name === currentTab).length > 0
&& <div className="pr-integration-container">
<FontAwesomeIcon icon={faExclamationTriangle} />
<p>{t("integrations.preview_active")}</p>
</div>}

{active.map((item) => (item.name !== currentTab ? undefined :
<IntegrationItem integration={integrations[currentTab]}
remove={() => deleteIntegration(item.uuid)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,13 @@ import {
faTrashArrowUp
} from "@fortawesome/free-solid-svg-icons";
import "./styles.sass";
import {useEffect, useState} from "react";
import {useContext, useEffect, useState} from "react";
import {ConfigContext} from "@/common/contexts/Config";

export const IntegrationItemHeader = ({integration, displayName, unsavedChanges, changesConfirmed, saveIntegration,
deleteConfirmed, deleteIntegration, open, setOpen, data}) => {
const [lastActivity, setLastActivity] = useState(generateRelativeTime(data.lastActivity));
const [config] = useContext(ConfigContext);

useEffect(() => {
const interval = setInterval(() => {
Expand All @@ -40,11 +42,11 @@ export const IntegrationItemHeader = ({integration, displayName, unsavedChanges,
</div>
</div>
<div className="integration-item-right">
{unsavedChanges && !changesConfirmed && <FontAwesomeIcon icon={faFloppyDisk} onClick={saveIntegration}
{!config.previewMode && unsavedChanges && !changesConfirmed && <FontAwesomeIcon icon={faFloppyDisk} onClick={saveIntegration}
className="integration-green"/>}
{changesConfirmed && <FontAwesomeIcon icon={faCheck} className="icon-green"/>}

{!deleteConfirmed &&
{!config.previewMode && !deleteConfirmed &&
<FontAwesomeIcon icon={faTrash} className="integration-red" onClick={deleteIntegration}/>}
{deleteConfirmed &&
<FontAwesomeIcon icon={faTrashArrowUp} className="integration-red" onClick={deleteIntegration}/>}
Expand Down
15 changes: 15 additions & 0 deletions client/src/common/components/IntegrationDialog/styles.sass
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,21 @@
overflow-x: clip
width: 70%

.pr-integration-container
display: flex
gap: 0.5rem
align-items: center
justify-content: center
padding: 0.5rem
border-radius: 0.5rem
border: 2px solid $red
color: $red
font-size: 1.25rem

p
margin: 0
font-weight: 500

@media (max-width: 781px)
.integration-dialog
width: 90vw
Expand Down
1 change: 1 addition & 0 deletions client/src/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import ReactDOM from "react-dom/client";
import App from './App';

export const PROJECT_URL = "https://github.com/gnmyt/myspeed";
export const WEB_URL = "https://myspeed.dev";
export const PROJECT_WIKI = "https://docs.myspeed.dev";

const root = ReactDOM.createRoot(document.getElementById('root'));
Expand Down
Loading