diff --git a/locust/webui/index.html b/locust/webui/index.html index c6fa08d331..2c2ae373d7 100644 --- a/locust/webui/index.html +++ b/locust/webui/index.html @@ -2,7 +2,7 @@ - + diff --git a/locust/webui/public/assets/favicon.ico b/locust/webui/public/assets/favicon.ico deleted file mode 100644 index b2d458d9f7..0000000000 Binary files a/locust/webui/public/assets/favicon.ico and /dev/null differ diff --git a/locust/webui/public/assets/favicon.png b/locust/webui/public/assets/favicon.png new file mode 100644 index 0000000000..7acdbc4049 Binary files /dev/null and b/locust/webui/public/assets/favicon.png differ diff --git a/locust/webui/src/assets/Logo.tsx b/locust/webui/src/assets/Logo.tsx new file mode 100644 index 0000000000..cda5efb899 --- /dev/null +++ b/locust/webui/src/assets/Logo.tsx @@ -0,0 +1,49 @@ +export default function Logo({ + isDarkMode, + lightModeBackgroundColor = '#15803d', +}: { + isDarkMode: boolean; + lightModeBackgroundColor?: string; +}) { + return ( + + + + + + + + + ); +} diff --git a/locust/webui/src/assets/logo.png b/locust/webui/src/assets/logo.png deleted file mode 100644 index 9f4651b5b1..0000000000 Binary files a/locust/webui/src/assets/logo.png and /dev/null differ diff --git a/locust/webui/src/components/Layout/Footer/About.tsx b/locust/webui/src/components/Layout/Footer/About.tsx index 951c6f146c..2abdd2126b 100644 --- a/locust/webui/src/components/Layout/Footer/About.tsx +++ b/locust/webui/src/components/Layout/Footer/About.tsx @@ -22,23 +22,29 @@ export default function About() { Locust is free and open source software released under the{' '} - MIT License + MIT License It was originally developed by Carl Byström and{' '} - Jonatan Heyman. Since 2019, it - is primarily maintained by Lars Holmberg - . + Jonatan Heyman. Since 2019, it is + primarily maintained by Lars Holmberg. Many thanks to all our wonderful{' '} - - contributors - - ! + contributors! +
+ + Need help getting started? + + Locust Cloud gives you access to hosted, easily + scalable, and distributed load generation, as well as advanced reporting — all while + preserving the flexible “it’s just Python” approach to load test scripting that Locust + provides +
+
Version @@ -54,7 +60,10 @@ export default function About() { GitHub - Documentation + Documentation + + + Blog
diff --git a/locust/webui/src/components/Layout/Navbar/Navbar.tsx b/locust/webui/src/components/Layout/Navbar/Navbar.tsx index 205f7f9e14..8ac75100d8 100644 --- a/locust/webui/src/components/Layout/Navbar/Navbar.tsx +++ b/locust/webui/src/components/Layout/Navbar/Navbar.tsx @@ -1,34 +1,25 @@ -import { AppBar, Box, Container, Link, Toolbar, Typography } from '@mui/material'; +import { AppBar, Box, Container, Link, Toolbar } from '@mui/material'; -import Logo from 'assets/logo.png'; +import Logo from 'assets/Logo'; import DarkLightToggle from 'components/Layout/Navbar/DarkLightToggle'; import SwarmMonitor from 'components/Layout/Navbar/SwarmMonitor'; import StateButtons from 'components/StateButtons/StateButtons'; +import { useSelector } from 'redux/hooks'; export default function Navbar() { + const isDarkMode = useSelector(({ theme }) => theme.isDarkMode); + return ( - + - - - Locust - + diff --git a/locust/webui/src/components/Layout/Navbar/SwarmMonitor.tsx b/locust/webui/src/components/Layout/Navbar/SwarmMonitor.tsx index c86d5bb13c..4038e50026 100644 --- a/locust/webui/src/components/Layout/Navbar/SwarmMonitor.tsx +++ b/locust/webui/src/components/Layout/Navbar/SwarmMonitor.tsx @@ -1,4 +1,4 @@ -import { Box, Divider, Typography } from '@mui/material'; +import { Box, Divider, Tooltip, Typography } from '@mui/material'; import { connect } from 'react-redux'; import { SWARM_STATE } from 'constants/swarm'; @@ -23,7 +23,18 @@ function SwarmMonitor({ Host - {host} + + + {host} + + @@ -35,7 +46,9 @@ function SwarmMonitor({ Users - {userCount} + + {userCount} + )} @@ -44,19 +57,23 @@ function SwarmMonitor({ Workers - {workerCount} + + {workerCount} + )} RPS - {totalRps} + + {totalRps} + Failures - {`${failRatio}%`} + {`${failRatio}%`} ); diff --git a/locust/webui/src/components/StateButtons/StateButtons.tsx b/locust/webui/src/components/StateButtons/StateButtons.tsx index 6a2312659c..5bc20b934a 100644 --- a/locust/webui/src/components/StateButtons/StateButtons.tsx +++ b/locust/webui/src/components/StateButtons/StateButtons.tsx @@ -15,7 +15,7 @@ export default function StateButtons() { } return ( - + {swarmState === SWARM_STATE.STOPPED ? ( ) : ( diff --git a/locust/webui/src/components/SwarmForm/SwarmEditForm.tsx b/locust/webui/src/components/SwarmForm/SwarmEditForm.tsx index e9843255d6..dfc3283995 100644 --- a/locust/webui/src/components/SwarmForm/SwarmEditForm.tsx +++ b/locust/webui/src/components/SwarmForm/SwarmEditForm.tsx @@ -3,21 +3,23 @@ import { connect } from 'react-redux'; import Form from 'components/Form/Form'; import { useStartSwarmMutation } from 'redux/api/swarm'; -import { ISwarmState } from 'redux/slice/swarm.slice'; +import { ISwarmState, swarmActions } from 'redux/slice/swarm.slice'; import { IRootState } from 'redux/store'; -type ISwarmFormInput = Pick; +type ISwarmFormInput = Pick; interface ISwarmForm extends ISwarmFormInput { onSubmit: () => void; + setSwarm: (swarmPayload: Partial) => void; } -function SwarmEditForm({ onSubmit, numUsers, spawnRate }: ISwarmForm) { +function SwarmEditForm({ onSubmit, userCount, spawnRate, setSwarm }: ISwarmForm) { const [startSwarm] = useStartSwarmMutation(); const onEditSwarm = (inputData: ISwarmFormInput) => { onSubmit(); startSwarm(inputData); + setSwarm(inputData); }; return ( @@ -28,7 +30,7 @@ function SwarmEditForm({ onSubmit, numUsers, spawnRate }: ISwarmForm) { onSubmit={onEditSwarm}> @@ -48,9 +50,13 @@ function SwarmEditForm({ onSubmit, numUsers, spawnRate }: ISwarmForm) { ); } -const storeConnector = ({ swarm: { spawnRate, numUsers } }: IRootState) => ({ +const storeConnector = ({ swarm: { spawnRate, userCount } }: IRootState) => ({ spawnRate, - numUsers, + userCount, }); -export default connect(storeConnector)(SwarmEditForm); +const actionCreator = { + setSwarm: swarmActions.setSwarm, +}; + +export default connect(storeConnector, actionCreator)(SwarmEditForm); diff --git a/locust/webui/src/hooks/useTheme.ts b/locust/webui/src/hooks/useTheme.ts index 707e3698cf..bd20fcd47b 100644 --- a/locust/webui/src/hooks/useTheme.ts +++ b/locust/webui/src/hooks/useTheme.ts @@ -12,5 +12,5 @@ export default function useTheme() { [isDarkMode], ); - return theme; + return { theme, isDarkMode }; } diff --git a/locust/webui/src/images.d.ts b/locust/webui/src/images.d.ts index e2937d470e..e238d01ca3 100644 --- a/locust/webui/src/images.d.ts +++ b/locust/webui/src/images.d.ts @@ -1 +1,2 @@ declare module '*.png'; +declare module '*.svg'; diff --git a/locust/webui/src/pages/Auth.tsx b/locust/webui/src/pages/Auth.tsx index 4808e25bf1..0e021109cd 100644 --- a/locust/webui/src/pages/Auth.tsx +++ b/locust/webui/src/pages/Auth.tsx @@ -2,13 +2,13 @@ import { Alert, Box, Button, IconButton, TextField, Typography } from '@mui/mate import CssBaseline from '@mui/material/CssBaseline'; import { ThemeProvider } from '@mui/material/styles'; -import Logo from 'assets/logo.png'; +import Logo from 'assets/Logo'; import DarkLightToggle from 'components/Layout/Navbar/DarkLightToggle'; import useTheme from 'hooks/useTheme'; import { IAuthArgs } from 'types/auth.types'; export default function Auth({ authProviders, error, usernamePasswordCallback }: IAuthArgs) { - const theme = useTheme(); + const { theme, isDarkMode } = useTheme(); return ( @@ -34,19 +34,7 @@ export default function Auth({ authProviders, error, usernamePasswordCallback }: }} > - - - Locust - + {usernamePasswordCallback && (
diff --git a/locust/webui/src/pages/Dashboard.tsx b/locust/webui/src/pages/Dashboard.tsx index d57a3bded5..537015e094 100644 --- a/locust/webui/src/pages/Dashboard.tsx +++ b/locust/webui/src/pages/Dashboard.tsx @@ -24,7 +24,7 @@ function Dashboard({ swarmState, tabs, extendedTabs }: IDashboard) { useSwarmUi(); useLogViewer(); - const theme = useTheme(); + const { theme } = useTheme(); return ( diff --git a/locust/webui/src/pages/tests/Dashboard.test.tsx b/locust/webui/src/pages/tests/Dashboard.test.tsx index 01d2ff3aef..2daf70e263 100644 --- a/locust/webui/src/pages/tests/Dashboard.test.tsx +++ b/locust/webui/src/pages/tests/Dashboard.test.tsx @@ -9,13 +9,12 @@ describe('Dashboard', () => { test('renders the layout', () => { const { getByRole } = renderWithProvider(); - const logo = getByRole('img'); + const logo = getByRole('img', { name: 'Locust' }); const heading = getByRole('link', { name: 'Locust' }); expect(heading).toBeTruthy(); expect(heading.getAttribute('href')).toEqual('/'); expect(logo).toBeTruthy(); - expect(logo.getAttribute('src')).toEqual('/src/assets/logo.png'); }); test('renders the swarm form by default', () => {