Merge branch 'check-email' of https://github.com/MuhammadKhalilzadeh/bluewave-uptime into check-email
This commit is contained in:
commit
82323e6260
32 files changed
+1610
-222
No files matched your search
Generated
+230
@@ -13,6 +13,7 @@
|
||||
"@fontsource/roboto": "^5.0.13",
|
||||
"@mui/icons-material": "^5.15.17",
|
||||
"@mui/material": "^5.15.16",
|
||||
"@mui/x-charts": "^7.5.1",
|
||||
"@mui/x-data-grid": "7.3.2",
|
||||
"@mui/x-date-pickers": "7.3.2",
|
||||
"dayjs": "1.11.11",
|
||||
@@ -989,6 +990,44 @@
|
||||
"resolved": "https://registry.npmjs.org/react-is/-/react-is-18.3.1.tgz",
|
||||
"integrity": "sha512-/LLMVyas0ljjAtoYiPqYiL8VWXzUUdThrmU5+n20DZv+a+ClRoevUzw5JxU+Ieh5/c87ytoTBV9G1FiKfNJdmg=="
|
||||
},
|
||||
"node_modules/@mui/x-charts": {
|
||||
"version": "7.5.1",
|
||||
"resolved": "https://registry.npmjs.org/@mui/x-charts/-/x-charts-7.5.1.tgz",
|
||||
"integrity": "sha512-8vMQyJL13cGXMbp+gm2QdABzFuOpP4hxEa/o6nL3ZpVNp7hja6h9F5bc0FNGR8h/eRN+4+swDnrEebnR0w4cbA==",
|
||||
"dependencies": {
|
||||
"@babel/runtime": "^7.24.5",
|
||||
"@mui/base": "^5.0.0-beta.40",
|
||||
"@mui/system": "^5.15.14",
|
||||
"@mui/utils": "^5.15.14",
|
||||
"@react-spring/rafz": "^9.7.3",
|
||||
"@react-spring/web": "^9.7.3",
|
||||
"clsx": "^2.1.1",
|
||||
"d3-color": "^3.1.0",
|
||||
"d3-delaunay": "^6.0.4",
|
||||
"d3-interpolate": "^3.0.1",
|
||||
"d3-scale": "^4.0.2",
|
||||
"d3-shape": "^3.2.0",
|
||||
"prop-types": "^15.8.1"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=14.0.0"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@emotion/react": "^11.9.0",
|
||||
"@emotion/styled": "^11.8.1",
|
||||
"@mui/material": "^5.15.14",
|
||||
"react": "^17.0.0 || ^18.0.0",
|
||||
"react-dom": "^17.0.0 || ^18.0.0"
|
||||
},
|
||||
"peerDependenciesMeta": {
|
||||
"@emotion/react": {
|
||||
"optional": true
|
||||
},
|
||||
"@emotion/styled": {
|
||||
"optional": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"node_modules/@mui/x-data-grid": {
|
||||
"version": "7.3.2",
|
||||
"resolved": "https://registry.npmjs.org/@mui/x-data-grid/-/x-data-grid-7.3.2.tgz",
|
||||
@@ -1123,6 +1162,71 @@
|
||||
"url": "https://opencollective.com/popperjs"
|
||||
}
|
||||
},
|
||||
"node_modules/@react-spring/animated": {
|
||||
"version": "9.7.3",
|
||||
"resolved": "https://registry.npmjs.org/@react-spring/animated/-/animated-9.7.3.tgz",
|
||||
"integrity": "sha512-5CWeNJt9pNgyvuSzQH+uy2pvTg8Y4/OisoscZIR8/ZNLIOI+CatFBhGZpDGTF/OzdNFsAoGk3wiUYTwoJ0YIvw==",
|
||||
"dependencies": {
|
||||
"@react-spring/shared": "~9.7.3",
|
||||
"@react-spring/types": "~9.7.3"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"react": "^16.8.0 || ^17.0.0 || ^18.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@react-spring/core": {
|
||||
"version": "9.7.3",
|
||||
"resolved": "https://registry.npmjs.org/@react-spring/core/-/core-9.7.3.tgz",
|
||||
"integrity": "sha512-IqFdPVf3ZOC1Cx7+M0cXf4odNLxDC+n7IN3MDcVCTIOSBfqEcBebSv+vlY5AhM0zw05PDbjKrNmBpzv/AqpjnQ==",
|
||||
"dependencies": {
|
||||
"@react-spring/animated": "~9.7.3",
|
||||
"@react-spring/shared": "~9.7.3",
|
||||
"@react-spring/types": "~9.7.3"
|
||||
},
|
||||
"funding": {
|
||||
"type": "opencollective",
|
||||
"url": "https://opencollective.com/react-spring/donate"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"react": "^16.8.0 || ^17.0.0 || ^18.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@react-spring/rafz": {
|
||||
"version": "9.7.3",
|
||||
"resolved": "https://registry.npmjs.org/@react-spring/rafz/-/rafz-9.7.3.tgz",
|
||||
"integrity": "sha512-9vzW1zJPcC4nS3aCV+GgcsK/WLaB520Iyvm55ARHfM5AuyBqycjvh1wbmWmgCyJuX4VPoWigzemq1CaaeRSHhQ=="
|
||||
},
|
||||
"node_modules/@react-spring/shared": {
|
||||
"version": "9.7.3",
|
||||
"resolved": "https://registry.npmjs.org/@react-spring/shared/-/shared-9.7.3.tgz",
|
||||
"integrity": "sha512-NEopD+9S5xYyQ0pGtioacLhL2luflh6HACSSDUZOwLHoxA5eku1UPuqcJqjwSD6luKjjLfiLOspxo43FUHKKSA==",
|
||||
"dependencies": {
|
||||
"@react-spring/types": "~9.7.3"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"react": "^16.8.0 || ^17.0.0 || ^18.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@react-spring/types": {
|
||||
"version": "9.7.3",
|
||||
"resolved": "https://registry.npmjs.org/@react-spring/types/-/types-9.7.3.tgz",
|
||||
"integrity": "sha512-Kpx/fQ/ZFX31OtlqVEFfgaD1ACzul4NksrvIgYfIFq9JpDHFwQkMVZ10tbo0FU/grje4rcL4EIrjekl3kYwgWw=="
|
||||
},
|
||||
"node_modules/@react-spring/web": {
|
||||
"version": "9.7.3",
|
||||
"resolved": "https://registry.npmjs.org/@react-spring/web/-/web-9.7.3.tgz",
|
||||
"integrity": "sha512-BXt6BpS9aJL/QdVqEIX9YoUy8CE6TJrU0mNCqSoxdXlIeNcEBWOfIyE6B14ENNsyQKS3wOWkiJfco0tCr/9tUg==",
|
||||
"dependencies": {
|
||||
"@react-spring/animated": "~9.7.3",
|
||||
"@react-spring/core": "~9.7.3",
|
||||
"@react-spring/shared": "~9.7.3",
|
||||
"@react-spring/types": "~9.7.3"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"react": "^16.8.0 || ^17.0.0 || ^18.0.0",
|
||||
"react-dom": "^16.8.0 || ^17.0.0 || ^18.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@remix-run/router": {
|
||||
"version": "1.16.1",
|
||||
"resolved": "https://registry.npmjs.org/@remix-run/router/-/router-1.16.1.tgz",
|
||||
@@ -1674,6 +1778,111 @@
|
||||
"resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz",
|
||||
"integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw=="
|
||||
},
|
||||
"node_modules/d3-array": {
|
||||
"version": "3.2.4",
|
||||
"resolved": "https://registry.npmjs.org/d3-array/-/d3-array-3.2.4.tgz",
|
||||
"integrity": "sha512-tdQAmyA18i4J7wprpYq8ClcxZy3SC31QMeByyCFyRt7BVHdREQZ5lpzoe5mFEYZUWe+oq8HBvk9JjpibyEV4Jg==",
|
||||
"dependencies": {
|
||||
"internmap": "1 - 2"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/d3-color": {
|
||||
"version": "3.1.0",
|
||||
"resolved": "https://registry.npmjs.org/d3-color/-/d3-color-3.1.0.tgz",
|
||||
"integrity": "sha512-zg/chbXyeBtMQ1LbD/WSoW2DpC3I0mpmPdW+ynRTj/x2DAWYrIY7qeZIHidozwV24m4iavr15lNwIwLxRmOxhA==",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/d3-delaunay": {
|
||||
"version": "6.0.4",
|
||||
"resolved": "https://registry.npmjs.org/d3-delaunay/-/d3-delaunay-6.0.4.tgz",
|
||||
"integrity": "sha512-mdjtIZ1XLAM8bm/hx3WwjfHt6Sggek7qH043O8KEjDXN40xi3vx/6pYSVTwLjEgiXQTbvaouWKynLBiUZ6SK6A==",
|
||||
"dependencies": {
|
||||
"delaunator": "5"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/d3-format": {
|
||||
"version": "3.1.0",
|
||||
"resolved": "https://registry.npmjs.org/d3-format/-/d3-format-3.1.0.tgz",
|
||||
"integrity": "sha512-YyUI6AEuY/Wpt8KWLgZHsIU86atmikuoOmCfommt0LYHiQSPjvX2AcFc38PX0CBpr2RCyZhjex+NS/LPOv6YqA==",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/d3-interpolate": {
|
||||
"version": "3.0.1",
|
||||
"resolved": "https://registry.npmjs.org/d3-interpolate/-/d3-interpolate-3.0.1.tgz",
|
||||
"integrity": "sha512-3bYs1rOD33uo8aqJfKP3JWPAibgw8Zm2+L9vBKEHJ2Rg+viTR7o5Mmv5mZcieN+FRYaAOWX5SJATX6k1PWz72g==",
|
||||
"dependencies": {
|
||||
"d3-color": "1 - 3"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/d3-path": {
|
||||
"version": "3.1.0",
|
||||
"resolved": "https://registry.npmjs.org/d3-path/-/d3-path-3.1.0.tgz",
|
||||
"integrity": "sha512-p3KP5HCf/bvjBSSKuXid6Zqijx7wIfNW+J/maPs+iwR35at5JCbLUT0LzF1cnjbCHWhqzQTIN2Jpe8pRebIEFQ==",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/d3-scale": {
|
||||
"version": "4.0.2",
|
||||
"resolved": "https://registry.npmjs.org/d3-scale/-/d3-scale-4.0.2.tgz",
|
||||
"integrity": "sha512-GZW464g1SH7ag3Y7hXjf8RoUuAFIqklOAq3MRl4OaWabTFJY9PN/E1YklhXLh+OQ3fM9yS2nOkCoS+WLZ6kvxQ==",
|
||||
"dependencies": {
|
||||
"d3-array": "2.10.0 - 3",
|
||||
"d3-format": "1 - 3",
|
||||
"d3-interpolate": "1.2.0 - 3",
|
||||
"d3-time": "2.1.1 - 3",
|
||||
"d3-time-format": "2 - 4"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/d3-shape": {
|
||||
"version": "3.2.0",
|
||||
"resolved": "https://registry.npmjs.org/d3-shape/-/d3-shape-3.2.0.tgz",
|
||||
"integrity": "sha512-SaLBuwGm3MOViRq2ABk3eLoxwZELpH6zhl3FbAoJ7Vm1gofKx6El1Ib5z23NUEhF9AsGl7y+dzLe5Cw2AArGTA==",
|
||||
"dependencies": {
|
||||
"d3-path": "^3.1.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/d3-time": {
|
||||
"version": "3.1.0",
|
||||
"resolved": "https://registry.npmjs.org/d3-time/-/d3-time-3.1.0.tgz",
|
||||
"integrity": "sha512-VqKjzBLejbSMT4IgbmVgDjpkYrNWUYJnbCGo874u7MMKIWsILRX+OpX/gTk8MqjpT1A/c6HY2dCA77ZN0lkQ2Q==",
|
||||
"dependencies": {
|
||||
"d3-array": "2 - 3"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/d3-time-format": {
|
||||
"version": "4.1.0",
|
||||
"resolved": "https://registry.npmjs.org/d3-time-format/-/d3-time-format-4.1.0.tgz",
|
||||
"integrity": "sha512-dJxPBlzC7NugB2PDLwo9Q8JiTR3M3e4/XANkreKSUxF8vvXKqm1Yfq4Q5dl8budlunRVlUUaDUgFt7eA8D6NLg==",
|
||||
"dependencies": {
|
||||
"d3-time": "1 - 3"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/data-view-buffer": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/data-view-buffer/-/data-view-buffer-1.0.1.tgz",
|
||||
@@ -1787,6 +1996,14 @@
|
||||
"url": "https://github.com/sponsors/ljharb"
|
||||
}
|
||||
},
|
||||
"node_modules/delaunator": {
|
||||
"version": "5.0.1",
|
||||
"resolved": "https://registry.npmjs.org/delaunator/-/delaunator-5.0.1.tgz",
|
||||
"integrity": "sha512-8nvh+XBe96aCESrGOqMp/84b13H9cdKbG5P2ejQCh4d4sK9RL4371qou9drQjMhvnPmhWl5hnmqbEE0fXr9Xnw==",
|
||||
"dependencies": {
|
||||
"robust-predicates": "^3.0.2"
|
||||
}
|
||||
},
|
||||
"node_modules/doctrine": {
|
||||
"version": "3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz",
|
||||
@@ -2739,6 +2956,14 @@
|
||||
"node": ">= 0.4"
|
||||
}
|
||||
},
|
||||
"node_modules/internmap": {
|
||||
"version": "2.0.3",
|
||||
"resolved": "https://registry.npmjs.org/internmap/-/internmap-2.0.3.tgz",
|
||||
"integrity": "sha512-5Hh7Y1wQbvY5ooGgPbDaL5iYLAPzMTUrjMulskHLH6wnv/A+1q5rgEaiuqEjB+oxGXIVZs1FF+R/KPN3ZSQYYg==",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/is-array-buffer": {
|
||||
"version": "3.0.4",
|
||||
"resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.4.tgz",
|
||||
@@ -3805,6 +4030,11 @@
|
||||
"url": "https://github.com/sponsors/isaacs"
|
||||
}
|
||||
},
|
||||
"node_modules/robust-predicates": {
|
||||
"version": "3.0.2",
|
||||
"resolved": "https://registry.npmjs.org/robust-predicates/-/robust-predicates-3.0.2.tgz",
|
||||
"integrity": "sha512-IXgzBWvWQwE6PrDI05OvmXUIruQTcoMDzRsOd5CDvHCVLcLHMTSYvOK5Cm46kWqlV3yAbuSpBZdJ5oP5OUoStg=="
|
||||
},
|
||||
"node_modules/rollup": {
|
||||
"version": "4.17.2",
|
||||
"resolved": "https://registry.npmjs.org/rollup/-/rollup-4.17.2.tgz",
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
"@fontsource/roboto": "^5.0.13",
|
||||
"@mui/icons-material": "^5.15.17",
|
||||
"@mui/material": "^5.15.16",
|
||||
"@mui/x-charts": "^7.5.1",
|
||||
"@mui/x-data-grid": "7.3.2",
|
||||
"@mui/x-date-pickers": "7.3.2",
|
||||
"dayjs": "1.11.11",
|
||||
|
||||
File renamed without changes.
@@ -0,0 +1,19 @@
|
||||
import { BarChart } from '@mui/x-charts/BarChart';
|
||||
|
||||
const ChartsOverviewDemo = () => {
|
||||
return (
|
||||
<BarChart
|
||||
series={[
|
||||
{ data: [35, 44, 24, 34] },
|
||||
{ data: [51, 6, 49, 30] },
|
||||
{ data: [15, 25, 30, 50] },
|
||||
{ data: [60, 50, 15, 25] },
|
||||
]}
|
||||
height={290}
|
||||
xAxis={[{ data: ['Q1', 'Q2', 'Q3', 'Q4'], scaleType: 'band' }]}
|
||||
margin={{ top: 10, bottom: 30, left: 40, right: 10 }}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
||||
export default ChartsOverviewDemo;
|
||||
File renamed without changes.
@@ -0,0 +1,78 @@
|
||||
import { useState } from 'react';
|
||||
import Box from '@mui/material/Box';
|
||||
import IconButton from '@mui/material/IconButton';
|
||||
import Menu from '@mui/material/Menu';
|
||||
import Tooltip from '@mui/material/Tooltip';
|
||||
import MenuItem from '@mui/material/MenuItem';
|
||||
import Typography from '@mui/material/Typography';
|
||||
import SvgIcon from '@mui/material/SvgIcon';
|
||||
import SettingsIcon from '@mui/icons-material/Settings';
|
||||
import { useTheme } from '@mui/material/styles';
|
||||
|
||||
const settings = ['Open Site', 'Detailed View', 'Incidents', 'Configure', 'Remove'];
|
||||
|
||||
/**
|
||||
* DashboardSettings component
|
||||
*
|
||||
* A component that provides a settings menu accessible from an icon.
|
||||
*
|
||||
* @component
|
||||
* @example
|
||||
* return (
|
||||
* <DashboardSettings />
|
||||
* )
|
||||
*/
|
||||
function DashboardSettings() {
|
||||
const theme = useTheme();
|
||||
const [anchorElUser, setAnchorElUser] = useState(null);
|
||||
|
||||
/**
|
||||
* Handles opening the user menu.
|
||||
*
|
||||
* @param {React.MouseEvent<HTMLElement>} event - The event triggered by clicking the user menu button.
|
||||
*/
|
||||
const handleOpenUserMenu = (event) => {
|
||||
setAnchorElUser(event.currentTarget);
|
||||
};
|
||||
|
||||
/**
|
||||
* Handles closing the user menu.
|
||||
*/
|
||||
const handleCloseUserMenu = () => {
|
||||
setAnchorElUser(null);
|
||||
};
|
||||
|
||||
return (
|
||||
<Box sx={{ flexGrow: 0 }}>
|
||||
<Tooltip title="Open settings">
|
||||
<IconButton onClick={handleOpenUserMenu} sx={{ p: 0 }}>
|
||||
<SvgIcon component={SettingsIcon} />
|
||||
</IconButton>
|
||||
</Tooltip>
|
||||
<Menu
|
||||
sx={{ mt: theme.spacing(5.5) }}
|
||||
id="menu-appbar"
|
||||
anchorEl={anchorElUser}
|
||||
anchorOrigin={{
|
||||
vertical: 'top',
|
||||
horizontal: 'right',
|
||||
}}
|
||||
keepMounted
|
||||
transformOrigin={{
|
||||
vertical: 'top',
|
||||
horizontal: 'right',
|
||||
}}
|
||||
open={Boolean(anchorElUser)}
|
||||
onClose={handleCloseUserMenu}
|
||||
>
|
||||
{settings.map((setting) => (
|
||||
<MenuItem key={setting} onClick={handleCloseUserMenu}>
|
||||
<Typography textAlign="center">{setting}</Typography>
|
||||
</MenuItem>
|
||||
))}
|
||||
</Menu>
|
||||
</Box>
|
||||
);
|
||||
}
|
||||
|
||||
export default DashboardSettings;
|
||||
@@ -1,8 +1,10 @@
|
||||
import React from 'react'
|
||||
import NavBar from '../../Components/NavBar'
|
||||
import { Outlet } from 'react-router'
|
||||
import Home from '../../Pages/Home'
|
||||
import './index.css'
|
||||
import ChartsOverviewDemo from '../../Components/DashboardProgressBars'
|
||||
import DashboardSettings from '../../Components/DashboardSettingsIcon'
|
||||
|
||||
|
||||
const HomeLayout = () => {
|
||||
return (
|
||||
@@ -10,6 +12,8 @@ const HomeLayout = () => {
|
||||
<NavBar />
|
||||
<Home />
|
||||
<Outlet />
|
||||
<ChartsOverviewDemo />
|
||||
<DashboardSettings />
|
||||
</>
|
||||
)
|
||||
}
|
||||
|
||||
@@ -1,10 +0,0 @@
|
||||
// vite.config.js
|
||||
import { defineConfig } from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/vite/dist/node/index.js";
|
||||
import react from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/@vitejs/plugin-react/dist/index.mjs";
|
||||
var vite_config_default = defineConfig({
|
||||
plugins: [react()]
|
||||
});
|
||||
export {
|
||||
vite_config_default as default
|
||||
};
|
||||
//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsidml0ZS5jb25maWcuanMiXSwKICAic291cmNlc0NvbnRlbnQiOiBbImNvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9kaXJuYW1lID0gXCJjOlxcXFxVc2Vyc1xcXFxjb3NtaVxcXFxPbmVEcml2ZVxcXFxEZXNrdG9wXFxcXEJsdWVXYXZlXFxcXFVwdGltZS1Nb25pdG9yXFxcXGJsdWV3YXZlLXVwdGltZVxcXFxDbGllbnRcIjtjb25zdCBfX3ZpdGVfaW5qZWN0ZWRfb3JpZ2luYWxfZmlsZW5hbWUgPSBcImM6XFxcXFVzZXJzXFxcXGNvc21pXFxcXE9uZURyaXZlXFxcXERlc2t0b3BcXFxcQmx1ZVdhdmVcXFxcVXB0aW1lLU1vbml0b3JcXFxcYmx1ZXdhdmUtdXB0aW1lXFxcXENsaWVudFxcXFx2aXRlLmNvbmZpZy5qc1wiO2NvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9pbXBvcnRfbWV0YV91cmwgPSBcImZpbGU6Ly8vYzovVXNlcnMvY29zbWkvT25lRHJpdmUvRGVza3RvcC9CbHVlV2F2ZS9VcHRpbWUtTW9uaXRvci9ibHVld2F2ZS11cHRpbWUvQ2xpZW50L3ZpdGUuY29uZmlnLmpzXCI7aW1wb3J0IHsgZGVmaW5lQ29uZmlnIH0gZnJvbSAndml0ZSdcclxuaW1wb3J0IHJlYWN0IGZyb20gJ0B2aXRlanMvcGx1Z2luLXJlYWN0J1xyXG5cclxuLy8gaHR0cHM6Ly92aXRlanMuZGV2L2NvbmZpZy9cclxuZXhwb3J0IGRlZmF1bHQgZGVmaW5lQ29uZmlnKHtcclxuICBwbHVnaW5zOiBbcmVhY3QoKV0sXHJcbn0pXHJcbiJdLAogICJtYXBwaW5ncyI6ICI7QUFBOGEsU0FBUyxvQkFBb0I7QUFDM2MsT0FBTyxXQUFXO0FBR2xCLElBQU8sc0JBQVEsYUFBYTtBQUFBLEVBQzFCLFNBQVMsQ0FBQyxNQUFNLENBQUM7QUFDbkIsQ0FBQzsiLAogICJuYW1lcyI6IFtdCn0K
|
||||
@@ -1,10 +0,0 @@
|
||||
// vite.config.js
|
||||
import { defineConfig } from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/vite/dist/node/index.js";
|
||||
import react from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/@vitejs/plugin-react/dist/index.mjs";
|
||||
var vite_config_default = defineConfig({
|
||||
plugins: [react()]
|
||||
});
|
||||
export {
|
||||
vite_config_default as default
|
||||
};
|
||||
//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsidml0ZS5jb25maWcuanMiXSwKICAic291cmNlc0NvbnRlbnQiOiBbImNvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9kaXJuYW1lID0gXCJjOlxcXFxVc2Vyc1xcXFxjb3NtaVxcXFxPbmVEcml2ZVxcXFxEZXNrdG9wXFxcXEJsdWVXYXZlXFxcXFVwdGltZS1Nb25pdG9yXFxcXGJsdWV3YXZlLXVwdGltZVxcXFxDbGllbnRcIjtjb25zdCBfX3ZpdGVfaW5qZWN0ZWRfb3JpZ2luYWxfZmlsZW5hbWUgPSBcImM6XFxcXFVzZXJzXFxcXGNvc21pXFxcXE9uZURyaXZlXFxcXERlc2t0b3BcXFxcQmx1ZVdhdmVcXFxcVXB0aW1lLU1vbml0b3JcXFxcYmx1ZXdhdmUtdXB0aW1lXFxcXENsaWVudFxcXFx2aXRlLmNvbmZpZy5qc1wiO2NvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9pbXBvcnRfbWV0YV91cmwgPSBcImZpbGU6Ly8vYzovVXNlcnMvY29zbWkvT25lRHJpdmUvRGVza3RvcC9CbHVlV2F2ZS9VcHRpbWUtTW9uaXRvci9ibHVld2F2ZS11cHRpbWUvQ2xpZW50L3ZpdGUuY29uZmlnLmpzXCI7aW1wb3J0IHsgZGVmaW5lQ29uZmlnIH0gZnJvbSAndml0ZSdcclxuaW1wb3J0IHJlYWN0IGZyb20gJ0B2aXRlanMvcGx1Z2luLXJlYWN0J1xyXG5cclxuLy8gaHR0cHM6Ly92aXRlanMuZGV2L2NvbmZpZy9cclxuZXhwb3J0IGRlZmF1bHQgZGVmaW5lQ29uZmlnKHtcclxuICBwbHVnaW5zOiBbcmVhY3QoKV0sXHJcbn0pXHJcbiJdLAogICJtYXBwaW5ncyI6ICI7QUFBOGEsU0FBUyxvQkFBb0I7QUFDM2MsT0FBTyxXQUFXO0FBR2xCLElBQU8sc0JBQVEsYUFBYTtBQUFBLEVBQzFCLFNBQVMsQ0FBQyxNQUFNLENBQUM7QUFDbkIsQ0FBQzsiLAogICJuYW1lcyI6IFtdCn0K
|
||||
@@ -1,10 +0,0 @@
|
||||
// vite.config.js
|
||||
import { defineConfig } from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/vite/dist/node/index.js";
|
||||
import react from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/@vitejs/plugin-react/dist/index.mjs";
|
||||
var vite_config_default = defineConfig({
|
||||
plugins: [react()]
|
||||
});
|
||||
export {
|
||||
vite_config_default as default
|
||||
};
|
||||
//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsidml0ZS5jb25maWcuanMiXSwKICAic291cmNlc0NvbnRlbnQiOiBbImNvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9kaXJuYW1lID0gXCJjOlxcXFxVc2Vyc1xcXFxjb3NtaVxcXFxPbmVEcml2ZVxcXFxEZXNrdG9wXFxcXEJsdWVXYXZlXFxcXFVwdGltZS1Nb25pdG9yXFxcXGJsdWV3YXZlLXVwdGltZVxcXFxDbGllbnRcIjtjb25zdCBfX3ZpdGVfaW5qZWN0ZWRfb3JpZ2luYWxfZmlsZW5hbWUgPSBcImM6XFxcXFVzZXJzXFxcXGNvc21pXFxcXE9uZURyaXZlXFxcXERlc2t0b3BcXFxcQmx1ZVdhdmVcXFxcVXB0aW1lLU1vbml0b3JcXFxcYmx1ZXdhdmUtdXB0aW1lXFxcXENsaWVudFxcXFx2aXRlLmNvbmZpZy5qc1wiO2NvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9pbXBvcnRfbWV0YV91cmwgPSBcImZpbGU6Ly8vYzovVXNlcnMvY29zbWkvT25lRHJpdmUvRGVza3RvcC9CbHVlV2F2ZS9VcHRpbWUtTW9uaXRvci9ibHVld2F2ZS11cHRpbWUvQ2xpZW50L3ZpdGUuY29uZmlnLmpzXCI7aW1wb3J0IHsgZGVmaW5lQ29uZmlnIH0gZnJvbSAndml0ZSdcclxuaW1wb3J0IHJlYWN0IGZyb20gJ0B2aXRlanMvcGx1Z2luLXJlYWN0J1xyXG5cclxuLy8gaHR0cHM6Ly92aXRlanMuZGV2L2NvbmZpZy9cclxuZXhwb3J0IGRlZmF1bHQgZGVmaW5lQ29uZmlnKHtcclxuICBwbHVnaW5zOiBbcmVhY3QoKV0sXHJcbn0pXHJcbiJdLAogICJtYXBwaW5ncyI6ICI7QUFBOGEsU0FBUyxvQkFBb0I7QUFDM2MsT0FBTyxXQUFXO0FBR2xCLElBQU8sc0JBQVEsYUFBYTtBQUFBLEVBQzFCLFNBQVMsQ0FBQyxNQUFNLENBQUM7QUFDbkIsQ0FBQzsiLAogICJuYW1lcyI6IFtdCn0K
|
||||
@@ -1,10 +0,0 @@
|
||||
// vite.config.js
|
||||
import { defineConfig } from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/vite/dist/node/index.js";
|
||||
import react from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/@vitejs/plugin-react/dist/index.mjs";
|
||||
var vite_config_default = defineConfig({
|
||||
plugins: [react()]
|
||||
});
|
||||
export {
|
||||
vite_config_default as default
|
||||
};
|
||||
//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsidml0ZS5jb25maWcuanMiXSwKICAic291cmNlc0NvbnRlbnQiOiBbImNvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9kaXJuYW1lID0gXCJjOlxcXFxVc2Vyc1xcXFxjb3NtaVxcXFxPbmVEcml2ZVxcXFxEZXNrdG9wXFxcXEJsdWVXYXZlXFxcXFVwdGltZS1Nb25pdG9yXFxcXGJsdWV3YXZlLXVwdGltZVxcXFxDbGllbnRcIjtjb25zdCBfX3ZpdGVfaW5qZWN0ZWRfb3JpZ2luYWxfZmlsZW5hbWUgPSBcImM6XFxcXFVzZXJzXFxcXGNvc21pXFxcXE9uZURyaXZlXFxcXERlc2t0b3BcXFxcQmx1ZVdhdmVcXFxcVXB0aW1lLU1vbml0b3JcXFxcYmx1ZXdhdmUtdXB0aW1lXFxcXENsaWVudFxcXFx2aXRlLmNvbmZpZy5qc1wiO2NvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9pbXBvcnRfbWV0YV91cmwgPSBcImZpbGU6Ly8vYzovVXNlcnMvY29zbWkvT25lRHJpdmUvRGVza3RvcC9CbHVlV2F2ZS9VcHRpbWUtTW9uaXRvci9ibHVld2F2ZS11cHRpbWUvQ2xpZW50L3ZpdGUuY29uZmlnLmpzXCI7aW1wb3J0IHsgZGVmaW5lQ29uZmlnIH0gZnJvbSAndml0ZSdcclxuaW1wb3J0IHJlYWN0IGZyb20gJ0B2aXRlanMvcGx1Z2luLXJlYWN0J1xyXG5cclxuLy8gaHR0cHM6Ly92aXRlanMuZGV2L2NvbmZpZy9cclxuZXhwb3J0IGRlZmF1bHQgZGVmaW5lQ29uZmlnKHtcclxuICBwbHVnaW5zOiBbcmVhY3QoKV0sXHJcbn0pXHJcbiJdLAogICJtYXBwaW5ncyI6ICI7QUFBOGEsU0FBUyxvQkFBb0I7QUFDM2MsT0FBTyxXQUFXO0FBR2xCLElBQU8sc0JBQVEsYUFBYTtBQUFBLEVBQzFCLFNBQVMsQ0FBQyxNQUFNLENBQUM7QUFDbkIsQ0FBQzsiLAogICJuYW1lcyI6IFtdCn0K
|
||||
@@ -1,10 +0,0 @@
|
||||
// vite.config.js
|
||||
import { defineConfig } from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/vite/dist/node/index.js";
|
||||
import react from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/@vitejs/plugin-react/dist/index.mjs";
|
||||
var vite_config_default = defineConfig({
|
||||
plugins: [react()]
|
||||
});
|
||||
export {
|
||||
vite_config_default as default
|
||||
};
|
||||
//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsidml0ZS5jb25maWcuanMiXSwKICAic291cmNlc0NvbnRlbnQiOiBbImNvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9kaXJuYW1lID0gXCJjOlxcXFxVc2Vyc1xcXFxjb3NtaVxcXFxPbmVEcml2ZVxcXFxEZXNrdG9wXFxcXEJsdWVXYXZlXFxcXFVwdGltZS1Nb25pdG9yXFxcXGJsdWV3YXZlLXVwdGltZVxcXFxDbGllbnRcIjtjb25zdCBfX3ZpdGVfaW5qZWN0ZWRfb3JpZ2luYWxfZmlsZW5hbWUgPSBcImM6XFxcXFVzZXJzXFxcXGNvc21pXFxcXE9uZURyaXZlXFxcXERlc2t0b3BcXFxcQmx1ZVdhdmVcXFxcVXB0aW1lLU1vbml0b3JcXFxcYmx1ZXdhdmUtdXB0aW1lXFxcXENsaWVudFxcXFx2aXRlLmNvbmZpZy5qc1wiO2NvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9pbXBvcnRfbWV0YV91cmwgPSBcImZpbGU6Ly8vYzovVXNlcnMvY29zbWkvT25lRHJpdmUvRGVza3RvcC9CbHVlV2F2ZS9VcHRpbWUtTW9uaXRvci9ibHVld2F2ZS11cHRpbWUvQ2xpZW50L3ZpdGUuY29uZmlnLmpzXCI7aW1wb3J0IHsgZGVmaW5lQ29uZmlnIH0gZnJvbSAndml0ZSdcclxuaW1wb3J0IHJlYWN0IGZyb20gJ0B2aXRlanMvcGx1Z2luLXJlYWN0J1xyXG5cclxuLy8gaHR0cHM6Ly92aXRlanMuZGV2L2NvbmZpZy9cclxuZXhwb3J0IGRlZmF1bHQgZGVmaW5lQ29uZmlnKHtcclxuICBwbHVnaW5zOiBbcmVhY3QoKV0sXHJcbn0pXHJcbiJdLAogICJtYXBwaW5ncyI6ICI7QUFBOGEsU0FBUyxvQkFBb0I7QUFDM2MsT0FBTyxXQUFXO0FBR2xCLElBQU8sc0JBQVEsYUFBYTtBQUFBLEVBQzFCLFNBQVMsQ0FBQyxNQUFNLENBQUM7QUFDbkIsQ0FBQzsiLAogICJuYW1lcyI6IFtdCn0K
|
||||
@@ -1,10 +0,0 @@
|
||||
// vite.config.js
|
||||
import { defineConfig } from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/vite/dist/node/index.js";
|
||||
import react from "file:///c:/Users/cosmi/OneDrive/Desktop/BlueWave/Uptime-Monitor/bluewave-uptime/Client/node_modules/@vitejs/plugin-react/dist/index.mjs";
|
||||
var vite_config_default = defineConfig({
|
||||
plugins: [react()]
|
||||
});
|
||||
export {
|
||||
vite_config_default as default
|
||||
};
|
||||
//# sourceMappingURL=data:application/json;base64,ewogICJ2ZXJzaW9uIjogMywKICAic291cmNlcyI6IFsidml0ZS5jb25maWcuanMiXSwKICAic291cmNlc0NvbnRlbnQiOiBbImNvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9kaXJuYW1lID0gXCJjOlxcXFxVc2Vyc1xcXFxjb3NtaVxcXFxPbmVEcml2ZVxcXFxEZXNrdG9wXFxcXEJsdWVXYXZlXFxcXFVwdGltZS1Nb25pdG9yXFxcXGJsdWV3YXZlLXVwdGltZVxcXFxDbGllbnRcIjtjb25zdCBfX3ZpdGVfaW5qZWN0ZWRfb3JpZ2luYWxfZmlsZW5hbWUgPSBcImM6XFxcXFVzZXJzXFxcXGNvc21pXFxcXE9uZURyaXZlXFxcXERlc2t0b3BcXFxcQmx1ZVdhdmVcXFxcVXB0aW1lLU1vbml0b3JcXFxcYmx1ZXdhdmUtdXB0aW1lXFxcXENsaWVudFxcXFx2aXRlLmNvbmZpZy5qc1wiO2NvbnN0IF9fdml0ZV9pbmplY3RlZF9vcmlnaW5hbF9pbXBvcnRfbWV0YV91cmwgPSBcImZpbGU6Ly8vYzovVXNlcnMvY29zbWkvT25lRHJpdmUvRGVza3RvcC9CbHVlV2F2ZS9VcHRpbWUtTW9uaXRvci9ibHVld2F2ZS11cHRpbWUvQ2xpZW50L3ZpdGUuY29uZmlnLmpzXCI7aW1wb3J0IHsgZGVmaW5lQ29uZmlnIH0gZnJvbSAndml0ZSdcclxuaW1wb3J0IHJlYWN0IGZyb20gJ0B2aXRlanMvcGx1Z2luLXJlYWN0J1xyXG5cclxuLy8gaHR0cHM6Ly92aXRlanMuZGV2L2NvbmZpZy9cclxuZXhwb3J0IGRlZmF1bHQgZGVmaW5lQ29uZmlnKHtcclxuICBwbHVnaW5zOiBbcmVhY3QoKV0sXHJcbn0pXHJcbiJdLAogICJtYXBwaW5ncyI6ICI7QUFBOGEsU0FBUyxvQkFBb0I7QUFDM2MsT0FBTyxXQUFXO0FBR2xCLElBQU8sc0JBQVEsYUFBYTtBQUFBLEVBQzFCLFNBQVMsQ0FBQyxNQUFNLENBQUM7QUFDbkIsQ0FBQzsiLAogICJuYW1lcyI6IFtdCn0K
|
||||
@@ -7,9 +7,33 @@ BlueWave uptime monitoring application
|
||||
- Clone this repository to your local machine
|
||||
|
||||
1. [Installation (Client)](#client)
|
||||
1. [Installation (Server)](#server)
|
||||
1. [Configuration(Server)](#config-server)
|
||||
1. [Endpoints](#endpoints)
|
||||
2. [Installation (Server)](#server)
|
||||
3. [Configuration(Server)](#config-server)
|
||||
4. [Endpoints](#endpoints)
|
||||
###### Auth
|
||||
- <code>POST</code> [/api/v1/auth/register](#post-register)
|
||||
- <code>POST</code> [/api/v1/auth/login](#post-login)
|
||||
- <code>POST</code> [/api/v1/auth/user/{userId}](#post-auth-user-edit-id)
|
||||
###### Monitors
|
||||
- <code>GET</code> [/api/v1/monitors](#get-monitors)
|
||||
- <code>GET</code> [/api/v1/monitor/{id}](#get-monitor-id)
|
||||
- <code>GET</code> [/api/v1/monitors/user/{userId}](#get-monitors-user-userid)
|
||||
- <code>POST</code> [/api/v1/monitors](#post-monitors)
|
||||
- <code>POST</code> [/api/v1/monitors/delete/{monitorId}](#post-monitors-del-id)
|
||||
- <code>POST</code> [/api/v1/monitors/edit/{monitorId}](#post-monitors-edit-id)
|
||||
###### Checks
|
||||
- <code>POST</code> [/api/v1/checks/{monitorId}](#post-checks)
|
||||
- <code>GET</code> [/api/v1/checks/{monitorId}](#get-checks)
|
||||
- <code>POST</code> [/api/v1/checks/delete/{monitorId}](#delete-checks)
|
||||
###### Alerts
|
||||
- <code>POST</code> [/api/v1/alerts/{monitorId}](#create-alert)
|
||||
- <code>GET</code> [/api/v1/alerts/user/{userId}](#get-alerts-user-id)
|
||||
- <code>GET</code> [/api/v1/alerts/monitor/{monitorId}](#get-alerts-monitor-id)
|
||||
- <code>GET</code> [/api/v1/alerts/{alertId}](#get-alert-alert-id)
|
||||
- <code>POST</code> [/api/v1/alerts/edit/{alertId}](#edit-alert)
|
||||
- <code>POST</code> [/api/v1/alerts/delete/{alertId}](#delete-alert)
|
||||
5. [Error Handling](#error-handling)
|
||||
6. [Contributors](#contributors)
|
||||
|
||||
---
|
||||
|
||||
@@ -108,10 +132,44 @@ Example:
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
<details>
|
||||
<summary><code>Check</code></summary>
|
||||
|
||||
| Name | Type | Notes |
|
||||
| ------------ | --------- | ----------------------------------------------- |
|
||||
| monitorId | `string` | Unique ID for the monitor |
|
||||
| status | `boolean` | Indicates the service is Up or Down |
|
||||
| responseTime | `integer` | Indicates the response time of the service (ms) |
|
||||
| statusCode | `integer` | Status Code returned from the service |
|
||||
| message | `string` | Message returned from the service |
|
||||
| updatedAt | `Date` | Last time the check was updated |
|
||||
| CreatedAt | `Date` | When the check was created |
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary><code>POST</code> <b>/api/v1/auth/register</b></summary>
|
||||
<summary><code>Alert</code></summary>
|
||||
|
||||
| Name | Type | Notes |
|
||||
| ----------------- | --------- | ------------------------------------------------- |
|
||||
| checkId | `string` | Unique ID for the associated check |
|
||||
| monitorId | `string` | Unique ID for the associated monitor |
|
||||
| userId | `string` | Unique ID for the associated user |
|
||||
| status | `boolean` | Indicates the service is Up or Down |
|
||||
| message | `string` | Message for the user about the down service |
|
||||
| notifiedStatus | `boolean` | Indicates whether the user is notified |
|
||||
| acknowledgeStatus | `boolean` | Indicates whether the user acknowledged the alert |
|
||||
| updatedAt | `Date` | Last time the alert was updated |
|
||||
| CreatedAt | `Date` | When the alert was created |
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
###### Auth
|
||||
|
||||
<details>
|
||||
<summary id='post-register'><code>POST</code> <b>/api/v1/auth/register</b></summary>
|
||||
|
||||
##### Method/Headers
|
||||
|
||||
@@ -161,10 +219,8 @@ curl --request POST \
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
<details>
|
||||
<summary><code>POST</code> <b>/api/v1/auth/login</b></summary>
|
||||
<summary id='post-login'><code>POST</code> <b>/api/v1/auth/login</b></summary>
|
||||
|
||||
##### Method/Headers
|
||||
|
||||
@@ -210,10 +266,71 @@ curl --request POST \
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary id='post-auth-user-edit-id'><code>POST</code><b>/api/v1/auth/user/{userId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | POST |
|
||||
|
||||
##### Body
|
||||
|
||||
> | Name | Type | Notes |
|
||||
> | ------------- | -------- | ----------- |
|
||||
> | firstname | `string` | |
|
||||
> | lastname | `string` | |
|
||||
> | profilePicUrl | `string` | |
|
||||
> | password | `string` | Min 8 chars |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | ------ | ------------------------ |
|
||||
> | `User` | Returns the updated user |
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
curl --request POST \
|
||||
--url http://localhost:5000/api/v1/auth/user/6654d156634754f789e1f10e \
|
||||
--header 'Authorization: <bearer_token>' \
|
||||
--header 'Content-Type: application/json' \
|
||||
--data '{
|
||||
"firstname": "First Name",
|
||||
"lastname: "Last Name"
|
||||
}'
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"msg": "User updated",
|
||||
"data": {
|
||||
"_id": "6654d156634754f789e1f10e",
|
||||
"firstname": "First Name",
|
||||
"lastname": "Last Name",
|
||||
"email": "me@gmail.com",
|
||||
"isActive": true,
|
||||
"isVerified": false,
|
||||
"createdAt": "2024-05-27T18:30:46.358Z",
|
||||
"updatedAt": "2024-05-27T19:21:51.747Z",
|
||||
"__v": 0
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
###### Monitors
|
||||
|
||||
<details>
|
||||
<summary><code>GET</code> <b>/api/v1/monitors</b></summary>
|
||||
<summary id='get-monitors'><code>GET</code> <b>/api/v1/monitors</b></summary>
|
||||
|
||||
##### Method/Headers
|
||||
|
||||
@@ -223,9 +340,9 @@ curl --request POST \
|
||||
|
||||
##### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | ---------------- | ----------------- |
|
||||
> | `Array[Monitor]` | Array of monitors |
|
||||
> | Type | Notes |
|
||||
> | ---------------- | --------------------- |
|
||||
> | `Array<Monitor>` | Array of all monitors |
|
||||
|
||||
###### Sample cURL Request
|
||||
|
||||
@@ -272,10 +389,8 @@ curl --request GET \
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
<details>
|
||||
<summary><code>GET</code> <b>/api/v1/monitor/{id}</b></summary>
|
||||
<summary id='get-monitor-id'><code>GET</code> <b>/api/v1/monitor/{id}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
@@ -320,10 +435,8 @@ curl --request GET \
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
<details>
|
||||
<summary><code>GET</code> <b>/api/v1/monitors/user/{userId}</b></summary>
|
||||
<summary id='get-monitors-user-userid'><code>GET</code> <b>/api/v1/monitors/user/{userId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
@@ -333,9 +446,9 @@ curl --request GET \
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | ---------------- | ------------------------------------------------------------------ |
|
||||
> | `Array[Monitor]` | Array of monitors created by user with userId specified in request |
|
||||
> | Type | Notes |
|
||||
> | ---------------- | ------------------------------------------------------- |
|
||||
> | `Array<Monitor>` | Array of monitors created by user with specified UserID |
|
||||
|
||||
###### Sample cURL Request
|
||||
|
||||
@@ -382,10 +495,8 @@ curl --request GET \
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
<details>
|
||||
<summary><code>POST</code><b>/api/v1/monitors</b></summary>
|
||||
<summary id='post-monitors'><code>POST</code><b>/api/v1/monitors</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
@@ -395,9 +506,9 @@ curl --request GET \
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | --------- | --------------------------------- |
|
||||
> | `Monitor` | Newly created monitor is returned |
|
||||
> | Type | Notes |
|
||||
> | --------- | ------------------------------- |
|
||||
> | `Monitor` | Returns newly created `Monitor` |
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
@@ -437,10 +548,8 @@ curl --request POST \
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
<details>
|
||||
<summary><code>POST</code><b>/api/v1/monitors/delete/{monitorId}</b></summary>
|
||||
<summary id='post-monitors-del-id'><code>POST</code><b>/api/v1/monitors/delete/{monitorId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
@@ -474,10 +583,8 @@ curl --request POST \
|
||||
|
||||
## </details>
|
||||
|
||||
---
|
||||
|
||||
<details>
|
||||
<summary><code>POST</code><b>/api/v1/monitors/edit/{monitorId}</b></summary>
|
||||
<summary id='post-monitors-edit-id'><code>POST</code><b>/api/v1/monitors/edit/{monitorId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
@@ -531,6 +638,321 @@ curl --request POST \
|
||||
}
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
###### Checks
|
||||
|
||||
<details>
|
||||
<summary id='post-checks'><code>POST</code><b>/api/v1/checks/{monitorId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | POST |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | ---- | ------------------- |
|
||||
> | None | No payload returned |
|
||||
|
||||
###### Body
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary id='get-checks'><code>GET</code><b>/api/v1/checks/{monitorId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | POST |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | --------------- | ------------------------ |
|
||||
> | `Array<Checks>` | Array of `Check` objects |
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary id='delete-checks'><code>POST</code><b>/api/v1/checks/delete/{monitorId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | POST |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | ---- | ------------------- |
|
||||
> | None | No payload returned |
|
||||
|
||||
###### Body
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
###### Alerts
|
||||
|
||||
<details>
|
||||
<summary id='create-alert'><code>POST</code><b>/api/v1/alerts/{monitorId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | POST |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | ------- | ----------------------------- |
|
||||
> | `Alert` | Returns newly created `Alert` |
|
||||
|
||||
###### Body
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary id='get-alerts-user-id'><code>GET</code><b>/api/v1/alerts/user/{userId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | GET |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | -------------- | --------------------------------------- |
|
||||
> | `Array<Alert>` | Returns all `Alert` created by a `User` |
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
|
||||
```
|
||||
|
||||
</details>
|
||||
<details>
|
||||
<summary id='get-alerts-monitor-id'><code>GET</code><b>/api/v1/alerts/monitor/{monitorId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | GET |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | -------------- | -------------------------------------------------------------- |
|
||||
> | `Array<Alert>` | Returns an array of `Alert` belonging to a specified `Monitor` |
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary id='get-alert-alert-id'><code>GET</code><b>/api/v1/alerts/{alertId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | GET |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | ------- | ------------------------- |
|
||||
> | `Alert` | Returns specified `Alert` |
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
<details>
|
||||
<summary id='edit-alert'><code>POST</code><b>/api/v1/alerts/edit/{alertId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | POST |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | ------- | -------------------- |
|
||||
> | `Alert` | Returns edited alert |
|
||||
|
||||
###### Body
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
|
||||
```
|
||||
|
||||
</details>
|
||||
<details>
|
||||
<summary id='delete-alert'><code>POST</code><b>/api/v1/alerts/delete/{alertId}</b></summary>
|
||||
|
||||
###### Method/Headers
|
||||
|
||||
> | Method/Headers | Value |
|
||||
> | -------------- | ----- |
|
||||
> | Method | POST |
|
||||
|
||||
###### Response Payload
|
||||
|
||||
> | Type | Notes |
|
||||
> | ---- | ------------------- |
|
||||
> | None | No payload returned |
|
||||
|
||||
###### Body
|
||||
|
||||
##### Sample CURL request
|
||||
|
||||
```
|
||||
|
||||
```
|
||||
|
||||
###### Sample Response
|
||||
|
||||
```json
|
||||
|
||||
```
|
||||
|
||||
</details>
|
||||
|
||||
---
|
||||
|
||||
### Error handling {#error-handling}
|
||||
|
||||
Errors are returned in a standard format:
|
||||
|
||||
`{"success": false, "msg": "No token provided"}`
|
||||
|
||||
Errors are handled by error handling middleware and should be thrown with the following parameters
|
||||
|
||||
| Name | Type | Default | Notes |
|
||||
| ------- | --------- | ---------------------- | ------------------------------------ |
|
||||
| status | `integer` | 500 | Standard HTTP codes |
|
||||
| message | `string` | "Something went wrong" | An error message |
|
||||
| service | `string` | "Unknown Service" | Name of service that threw the error |
|
||||
|
||||
Example:
|
||||
|
||||
```
|
||||
const myRoute = async(req, res, next) => {
|
||||
try{
|
||||
const result = myRiskyOperationHere();
|
||||
}
|
||||
catch(error){
|
||||
error.status = 404
|
||||
error.message = "Resource not found"
|
||||
error.service = service name
|
||||
next(error)
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
```
|
||||
|
||||
Errors should not be handled at the controller level and should be left to the middleware to handle.
|
||||
|
||||
## Contributors
|
||||
|
||||
<a href="https://github.com/bluewave-labs/bluewave-uptime/graphs/contributors">
|
||||
|
||||
@@ -0,0 +1,139 @@
|
||||
const express = require("express");
|
||||
const logger = require("../utils/logger");
|
||||
require("dotenv").config();
|
||||
const {
|
||||
createAlertParamValidation,
|
||||
createAlertBodyValidation,
|
||||
getAlertsByUserIdParamValidation,
|
||||
getAlertsByMonitorIdParamValidation,
|
||||
getAlertByIdParamValidation,
|
||||
editAlertParamValidation,
|
||||
editAlertBodyValidation,
|
||||
deleteAlertParamValidation,
|
||||
} = require("../validation/joi");
|
||||
|
||||
const SERVICE_NAME = "alerts";
|
||||
|
||||
/**
|
||||
* Creates an alert for a monitor
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @returns {Promise<Express.Response>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const createAlert = async (req, res, next) => {
|
||||
try {
|
||||
await createAlertParamValidation.validateAsync(req.params);
|
||||
await createAlertBodyValidation.validateAsync(req.body);
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.message = error.details[0].message;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
req.db.createAlert(req, res);
|
||||
} catch (error) {
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Gets all alerts for a user
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @returns {Promise<Express.Response>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const getAlertsByUserId = async (req, res, next) => {
|
||||
try {
|
||||
await getAlertsByUserIdParamValidation.validateAsync(req.params);
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.message = error.details[0].message;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
req.db.getAlertsByUserId(req, res);
|
||||
} catch (error) {
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
const getAlertsByMonitorId = async (req, res, next) => {
|
||||
try {
|
||||
await getAlertsByMonitorIdParamValidation.validateAsync(req.params);
|
||||
res.status(200).json({
|
||||
success: true,
|
||||
msg: "Get Alerts By MonitorID",
|
||||
data: req.params.monitorId,
|
||||
});
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
res.status(200).json({ success: true, msg: "Edit alert" });
|
||||
|
||||
error.message = error.details[0].message;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
};
|
||||
const getAlertById = async (req, res, next) => {
|
||||
try {
|
||||
await getAlertByIdParamValidation.validateAsync(req.params);
|
||||
res.status(200).json({
|
||||
success: true,
|
||||
msg: "Get Alert By alertID",
|
||||
data: req.params.alertId,
|
||||
});
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.message = error.details[0].message;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
};
|
||||
const editAlert = async (req, res, next) => {
|
||||
try {
|
||||
await editAlertParamValidation(req.params);
|
||||
await editAlertBodyValidation(req.body);
|
||||
res.status(200).json({ success: true, msg: "Edit alert" });
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.message = error.details[0].message;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
};
|
||||
const deleteAlert = async (req, res, next) => {
|
||||
try {
|
||||
await deleteAlertParamValidation(req.params);
|
||||
res.status(200).json({ success: true, msg: "Delete alert" });
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.message = error.details[0].message;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = {
|
||||
createAlert,
|
||||
getAlertsByUserId,
|
||||
getAlertsByMonitorId,
|
||||
getAlertById,
|
||||
editAlert,
|
||||
deleteAlert,
|
||||
};
|
||||
@@ -1,5 +1,10 @@
|
||||
const express = require("express");
|
||||
const { registerValidation, loginValidation } = require("../validation/joi");
|
||||
const {
|
||||
registerValidation,
|
||||
loginValidation,
|
||||
editUserParamValidation,
|
||||
editUserBodyValidation,
|
||||
} = require("../validation/joi");
|
||||
const logger = require("../utils/logger");
|
||||
require("dotenv").config();
|
||||
var jwt = require("jsonwebtoken");
|
||||
@@ -12,7 +17,7 @@ const SERVICE_NAME = "auth";
|
||||
* @returns {String}
|
||||
*/
|
||||
const issueToken = (payload) => {
|
||||
return jwt.sign(payload, process.env.JWT_SECRET, { expiresIn: "1h" });
|
||||
return jwt.sign(payload, process.env.JWT_SECRET, { expiresIn: "99d" });
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -21,35 +26,32 @@ const issueToken = (payload) => {
|
||||
* @param {express.Response} res
|
||||
* @returns {{success: Boolean, msg: String}}
|
||||
*/
|
||||
const registerController = async (req, res) => {
|
||||
const registerController = async (req, res, next) => {
|
||||
// joi validation
|
||||
try {
|
||||
await registerValidation.validateAsync(req.body);
|
||||
} catch (error) {
|
||||
return res
|
||||
.status(400)
|
||||
.json({ success: false, msg: error.details[0].message });
|
||||
error.status = 422;
|
||||
error.service = SERVICE_NAME;
|
||||
error.message = error.details[0].message;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
// Check if the user exists
|
||||
try {
|
||||
const isUser = await req.db.getUserByEmail(req, res);
|
||||
if (isUser) {
|
||||
logger.error("User already exists", {
|
||||
service: SERVICE_NAME,
|
||||
userId: isUser._id,
|
||||
});
|
||||
return res
|
||||
.status(400)
|
||||
.json({ success: false, msg: "User already exists" });
|
||||
throw new Error("User already exists");
|
||||
}
|
||||
} catch (error) {
|
||||
logger.error(error.message, { service: SERVICE_NAME });
|
||||
return res.status(500).json({ success: false, msg: error.message });
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
// Create a new user
|
||||
try {
|
||||
// Create a new user
|
||||
const newUser = await req.db.insertUser(req, res);
|
||||
// TODO: Send an email to user
|
||||
// Will add this later
|
||||
@@ -63,8 +65,8 @@ const registerController = async (req, res) => {
|
||||
.status(200)
|
||||
.json({ success: true, msg: "User created", data: token });
|
||||
} catch (error) {
|
||||
logger.error(error.message, { service: SERVICE_NAME });
|
||||
return res.status(500).json({ success: false, msg: error.message });
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -76,7 +78,7 @@ const registerController = async (req, res) => {
|
||||
* @returns {Promise<Express.Response>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const loginController = async (req, res) => {
|
||||
const loginController = async (req, res, next) => {
|
||||
try {
|
||||
// Validate input
|
||||
await loginValidation.validateAsync(req.body);
|
||||
@@ -104,10 +106,42 @@ const loginController = async (req, res) => {
|
||||
.status(200)
|
||||
.json({ success: true, msg: "Found user", data: token });
|
||||
} catch (error) {
|
||||
error.status = 500;
|
||||
// Anything else should be an error
|
||||
logger.error(error.message, { service: SERVICE_NAME });
|
||||
return res.status(500).json({ success: false, msg: error.message });
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = { registerController, loginController };
|
||||
const userEditController = async (req, res, next) => {
|
||||
try {
|
||||
await editUserParamValidation.validateAsync(req.params);
|
||||
await editUserBodyValidation.validateAsync(req.body);
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.service = SERVICE_NAME;
|
||||
error.message = error.details[0].message;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
if (req.params.userId !== req.user._id.toString()) {
|
||||
const error = new Error("Unauthorized access");
|
||||
error.status = 401;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
const updatedUser = await req.db.updateUser(req, res);
|
||||
res
|
||||
.status(200)
|
||||
.json({ success: true, msg: "User updated", data: updatedUser });
|
||||
} catch (error) {
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = { registerController, loginController, userEditController };
|
||||
@@ -0,0 +1,37 @@
|
||||
var jwt = require("jsonwebtoken");
|
||||
const SERVICE_NAME = "check";
|
||||
|
||||
const createCheck = (req, res, next) => {
|
||||
try {
|
||||
req.db.createCheck(req, res);
|
||||
} catch (error) {
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
const getChecks = (req, res, next) => {
|
||||
try {
|
||||
req.db.getChecks(req, res);
|
||||
// Return all checks for a monitor
|
||||
} catch (error) {
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
const deleteChecks = (req, res, next) => {
|
||||
try {
|
||||
req.db.deleteChecks(req, res);
|
||||
// Delete all checks for a monitor
|
||||
} catch (error) {
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = {
|
||||
createCheck,
|
||||
getChecks,
|
||||
deleteChecks,
|
||||
};
|
||||
@@ -4,7 +4,7 @@ const {
|
||||
monitorValidation,
|
||||
} = require("../validation/joi");
|
||||
|
||||
const logger = require("../utils/logger");
|
||||
const SERVICE_NAME = "monitorController";
|
||||
|
||||
/**
|
||||
* Returns all monitors
|
||||
@@ -14,13 +14,13 @@ const logger = require("../utils/logger");
|
||||
* @returns {Promise<Express.Response>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const getAllMonitors = async (req, res) => {
|
||||
const getAllMonitors = async (req, res, next) => {
|
||||
try {
|
||||
const monitors = await req.db.getAllMonitors();
|
||||
return res.json({ success: true, msg: "Monitors found", data: monitors });
|
||||
} catch (error) {
|
||||
logger.error(error.message, { service: "monitor" });
|
||||
return res.status(500).json({ success: false, msg: error.message });
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -32,20 +32,28 @@ const getAllMonitors = async (req, res) => {
|
||||
* @returns {Promise<Express.Response>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const getMonitorById = async (req, res) => {
|
||||
const { error } = getMonitorByIdValidation.validate(req.params);
|
||||
if (error) {
|
||||
return res
|
||||
.status(422)
|
||||
.json({ success: false, msg: error.details[0].message });
|
||||
const getMonitorById = async (req, res, next) => {
|
||||
try {
|
||||
await getMonitorByIdValidation.validateAsync(req.params);
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.message = error.details[0].message;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
const monitor = await req.db.getMonitorById(req, res);
|
||||
if (!monitor) {
|
||||
const error = new Error("Monitor not found");
|
||||
error.status = 404;
|
||||
throw error;
|
||||
}
|
||||
|
||||
return res.json({ success: true, msg: "Monitor found", data: monitor });
|
||||
} catch (error) {
|
||||
logger.error(error.message, { service: "monitor" });
|
||||
return res.status(500).json({ success: false, msg: error.message });
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -57,7 +65,7 @@ const getMonitorById = async (req, res) => {
|
||||
* @returns {Promise<Express.Response>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const getMonitorsByUserId = async (req, res) => {
|
||||
const getMonitorsByUserId = async (req, res, next) => {
|
||||
const { error } = getMonitorsByUserIdValidation.validate(req.params);
|
||||
if (error) {
|
||||
return res
|
||||
@@ -68,18 +76,21 @@ const getMonitorsByUserId = async (req, res) => {
|
||||
try {
|
||||
const userId = req.params.userId;
|
||||
const monitors = await req.db.getMonitorsByUserId(req, res);
|
||||
logger.info(`Monitors for user ${userId} found`, {
|
||||
service: "monitor",
|
||||
userId: userId,
|
||||
});
|
||||
|
||||
if (monitors && monitors.length === 0) {
|
||||
const err = new Error("No monitors found");
|
||||
err.status = 404;
|
||||
throw err;
|
||||
}
|
||||
|
||||
return res.json({
|
||||
success: true,
|
||||
msg: `Monitors for user ${userId} found`,
|
||||
data: monitors,
|
||||
});
|
||||
} catch (error) {
|
||||
logger.error(error.message, { service: "monitor" });
|
||||
return res.status(500).json({ success: false, msg: error.message });
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -92,12 +103,15 @@ const getMonitorsByUserId = async (req, res) => {
|
||||
* @throws {Error}
|
||||
*/
|
||||
|
||||
const createMonitor = async (req, res) => {
|
||||
const { error } = monitorValidation.validate(req.body);
|
||||
if (error) {
|
||||
return res
|
||||
.status(422)
|
||||
.json({ success: false, msg: error.details[0].message });
|
||||
const createMonitor = async (req, res, next) => {
|
||||
try {
|
||||
await monitorValidation.validateAsync(req.body);
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.service = SERVICE_NAME;
|
||||
error.message = error.details[0].message;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
@@ -106,8 +120,8 @@ const createMonitor = async (req, res) => {
|
||||
.status(201)
|
||||
.json({ success: true, msg: "Monitor created", data: monitor });
|
||||
} catch (error) {
|
||||
logger.error(error.message, { service: "monitor" });
|
||||
return res.status(500).json({ success: false, msg: error.message });
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -120,15 +134,19 @@ const createMonitor = async (req, res) => {
|
||||
* @throws {Error}
|
||||
*/
|
||||
|
||||
const deleteMonitor = async (req, res) => {
|
||||
const { error } = getMonitorByIdValidation.validate(req.params);
|
||||
if (error) {
|
||||
return res
|
||||
.status(422)
|
||||
.json({ success: false, msg: error.details[0].message });
|
||||
}
|
||||
const deleteMonitor = async (req, res, next) => {
|
||||
try {
|
||||
const monitor = await req.db.deleteMonitor(req, res);
|
||||
await getMonitorByIdValidation.validateAsync(req.params);
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.service = SERVICE_NAME;
|
||||
error.message = error.details[0].message;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
const monitor = await req.db.deleteMonitor(req, res, next);
|
||||
/**
|
||||
* TODO
|
||||
* We should remove all checks and alerts associated with this monitor
|
||||
@@ -137,8 +155,8 @@ const deleteMonitor = async (req, res) => {
|
||||
*/
|
||||
return res.status(200).json({ success: true, msg: "Monitor deleted" });
|
||||
} catch (error) {
|
||||
logger.error(error.message, { service: "monitor" });
|
||||
return res.status(500).json({ success: false, msg: error.message });
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -150,19 +168,16 @@ const deleteMonitor = async (req, res) => {
|
||||
* @returns {Promise<Express.Response>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const editMonitor = async (req, res) => {
|
||||
let paramError = getMonitorByIdValidation.validate(req.params);
|
||||
if (paramError.error) {
|
||||
return res
|
||||
.status(422)
|
||||
.json({ success: false, msg: paramError.error.details[0].message });
|
||||
}
|
||||
|
||||
let { error } = monitorValidation.validate(req.body);
|
||||
if (error) {
|
||||
return res
|
||||
.status(422)
|
||||
.json({ success: false, msg: error.details[0].message });
|
||||
const editMonitor = async (req, res, next) => {
|
||||
try {
|
||||
await getMonitorByIdValidation.validateAsync(req.params);
|
||||
await monitorValidation.validateAsync(req.body);
|
||||
} catch (error) {
|
||||
error.status = 422;
|
||||
error.service = SERVICE_NAME;
|
||||
error.message = error.details[0].message;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
@@ -171,8 +186,8 @@ const editMonitor = async (req, res) => {
|
||||
.status(200)
|
||||
.json({ success: true, msg: "Monitor edited", data: editedMonitor });
|
||||
} catch (error) {
|
||||
logger.error(error.message, { service: "monitor" });
|
||||
return res.status(500).json({ success: false, msg: error.message });
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -2,6 +2,10 @@ const Monitor = require("../models/Monitor");
|
||||
const mongoose = require("mongoose");
|
||||
const UserModel = require("../models/user");
|
||||
|
||||
const verifyId = (userId, monitorId) => {
|
||||
return userId.toString() === monitorId.toString();
|
||||
};
|
||||
|
||||
const connect = async () => {
|
||||
try {
|
||||
await mongoose.connect(process.env.DB_CONNECTION_STRING);
|
||||
@@ -12,6 +16,10 @@ const connect = async () => {
|
||||
}
|
||||
};
|
||||
|
||||
//****************************************
|
||||
// Users
|
||||
//****************************************
|
||||
|
||||
/**
|
||||
* Insert a User
|
||||
* @async
|
||||
@@ -51,6 +59,35 @@ const getUserByEmail = async (req, res) => {
|
||||
}
|
||||
};
|
||||
|
||||
//****************************************
|
||||
// Monitors
|
||||
//****************************************
|
||||
|
||||
/**
|
||||
* Update a user by ID
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @returns {Promise<UserModel>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
|
||||
const updateUser = async (req, res) => {
|
||||
const candidateUserId = req.params.userId;
|
||||
const candidateUser = req.body;
|
||||
|
||||
try {
|
||||
const updatedUser = await UserModel.findByIdAndUpdate(
|
||||
candidateUserId,
|
||||
candidateUser,
|
||||
{ new: true } // Returns updated user instead of pre-update user
|
||||
).select("-password");
|
||||
return updatedUser;
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Get all monitors
|
||||
* @async
|
||||
@@ -113,6 +150,7 @@ const getMonitorsByUserId = async (req, res) => {
|
||||
const createMonitor = async (req, res) => {
|
||||
try {
|
||||
const monitor = new Monitor({ ...req.body });
|
||||
monitor.userId = req.user._id;
|
||||
await monitor.save();
|
||||
return monitor;
|
||||
} catch (error) {
|
||||
@@ -164,14 +202,204 @@ const editMonitor = async (req, res) => {
|
||||
}
|
||||
};
|
||||
|
||||
//****************************************
|
||||
// Checks
|
||||
//****************************************
|
||||
|
||||
/**
|
||||
* Create a check for a monitor
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @throws {Error}
|
||||
*/
|
||||
|
||||
const createCheck = async (req, res) => {
|
||||
try {
|
||||
// Create check with monitor id
|
||||
res
|
||||
.status(200)
|
||||
.json({ success: true, msg: "Create check", data: req.params.monitorId });
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Get all checks for a monitor
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @throws {Error}
|
||||
*/
|
||||
|
||||
const getChecks = async (req, res) => {
|
||||
try {
|
||||
// TODO get all checks for a monitor from DB
|
||||
res
|
||||
.status(200)
|
||||
.json({ success: true, msg: "Get checks", data: req.params.monitorId });
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Delete all checks for a monitor
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @throws {Error}
|
||||
*/
|
||||
|
||||
const deleteChecks = async (req, res) => {
|
||||
try {
|
||||
// TODO Delete all checks for a monitor
|
||||
res.status(200).json({
|
||||
success: true,
|
||||
msg: "Deleted checks",
|
||||
data: req.params.monitorId,
|
||||
});
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
//****************************************
|
||||
// Alerts
|
||||
//****************************************
|
||||
|
||||
/**
|
||||
* Creates an Alert associated with a Monitor and User
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @returns {<Promise<Alert>>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const createAlert = async (req, res) => {
|
||||
try {
|
||||
res
|
||||
.status(200)
|
||||
.json({ success: true, msg: "Create Alert", data: req.params.monitorId });
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Gets all alerts a User has set
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @returns {<Promise<Array<Alert>>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const getAlertsByUserId = async (req, res) => {
|
||||
try {
|
||||
res.status(200).json({
|
||||
success: true,
|
||||
msg: "Get Alerts By UserID",
|
||||
data: req.params.userId,
|
||||
});
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Gets all alerts a for an associated Monitor
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @returns {<Promise<Array<Alert>>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const getAlertsByMonitorId = async (req, res) => {
|
||||
try {
|
||||
res.status(200).json({
|
||||
success: true,
|
||||
msg: "Get Alerts By MonitorID",
|
||||
data: req.params.monitorId,
|
||||
});
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Gets an alert with specified ID
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @returns {Promise<Alert>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const getAlertById = async (req, res) => {
|
||||
try {
|
||||
res.status(200).json({
|
||||
success: true,
|
||||
msg: "Get Alert By alertID",
|
||||
data: req.params.alertId,
|
||||
});
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns an edited monitor with the specified ID
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @returns {Promise<Alert>>}
|
||||
* @throws {Error}
|
||||
*/
|
||||
const editAlert = async (req, res) => {
|
||||
try {
|
||||
res
|
||||
.status(200)
|
||||
.json({ success: true, msg: "Edit alert", data: req.params.alertId });
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Deletes a monitor with the specified ID
|
||||
* @async
|
||||
* @param {Express.Request} req
|
||||
* @param {Express.Response} res
|
||||
* @throws {Error}
|
||||
*/
|
||||
const deleteAlert = async (req, res) => {
|
||||
try {
|
||||
res
|
||||
.status(200)
|
||||
.json({ success: true, msg: "Delete alert", data: req.params.alertId });
|
||||
} catch (error) {
|
||||
throw error;
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = {
|
||||
connect,
|
||||
insertUser,
|
||||
getUserByEmail,
|
||||
updateUser,
|
||||
getAllMonitors,
|
||||
getMonitorById,
|
||||
getMonitorsByUserId,
|
||||
createMonitor,
|
||||
deleteMonitor,
|
||||
editMonitor,
|
||||
createCheck,
|
||||
getChecks,
|
||||
deleteChecks,
|
||||
createAlert,
|
||||
getAlertsByUserId,
|
||||
getAlertsByMonitorId,
|
||||
getAlertById,
|
||||
editAlert,
|
||||
deleteAlert,
|
||||
};
|
||||
+12
-1
@@ -3,10 +3,13 @@ const helmet = require("helmet");
|
||||
const cors = require("cors");
|
||||
const authRouter = require("./routes/authRoute");
|
||||
const monitorRouter = require("./routes/monitorRoute");
|
||||
const checkRouter = require("./routes/checkRoute");
|
||||
const alertRouter = require("./routes/alertRoute");
|
||||
const { connectDbAndRunServer } = require("./configs/db");
|
||||
require("dotenv").config();
|
||||
const logger = require("./utils/logger");
|
||||
var { verifyJWT } = require("./middleware/verifyJWT");
|
||||
const { verifyJWT } = require("./middleware/verifyJWT");
|
||||
const { handleErrors } = require("./middleware/handleErrors");
|
||||
|
||||
// const { sendEmail } = require('./utils/sendEmail')
|
||||
|
||||
@@ -61,6 +64,8 @@ app.use((req, res, next) => {
|
||||
//routes
|
||||
app.use("/api/v1/auth", authRouter);
|
||||
app.use("/api/v1/monitors", verifyJWT, monitorRouter);
|
||||
app.use("/api/v1/checks", verifyJWT, checkRouter);
|
||||
app.use("/api/v1/alerts", verifyJWT, alertRouter);
|
||||
|
||||
// Testing email service
|
||||
// app.use('/sendEmail', async (req, res) => {
|
||||
@@ -79,4 +84,10 @@ app.use("/api/v1/healthy", (req, res) => {
|
||||
}
|
||||
});
|
||||
|
||||
/**
|
||||
* Error handler middleware
|
||||
* Should be called last
|
||||
*/
|
||||
app.use(handleErrors);
|
||||
|
||||
connectDbAndRunServer(app, db);
|
||||
@@ -0,0 +1,12 @@
|
||||
const logger = require("../utils/logger");
|
||||
|
||||
const handleErrors = (error, req, res, next) => {
|
||||
const status = error.status || 500;
|
||||
const message = error.message || "Something went wrong";
|
||||
const service = error.service || "Unknown service";
|
||||
|
||||
logger.error(error.message, { service: service });
|
||||
res.status(status).json({ success: false, msg: message });
|
||||
};
|
||||
|
||||
module.exports = { handleErrors };
|
||||
@@ -15,8 +15,11 @@ const verifyJWT = (req, res, next) => {
|
||||
const token = req.headers["authorization"];
|
||||
// Make sure a token is provided
|
||||
if (!token) {
|
||||
logger.error("No token provided", { service: SERVICE_NAME });
|
||||
return res.status(401).json({ success: false, msg: "No token provided" });
|
||||
const error = new Error("No token provided");
|
||||
error.status = 401;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
return;
|
||||
}
|
||||
// Make sure it is properly formatted
|
||||
if (token.startsWith(TOKEN_PREFIX)) {
|
||||
@@ -32,10 +35,9 @@ const verifyJWT = (req, res, next) => {
|
||||
next();
|
||||
});
|
||||
} else {
|
||||
logger.error("Invalid token format", { service: SERVICE_NAME });
|
||||
return res
|
||||
.status(400)
|
||||
.json({ success: false, msg: "Invalid token format" });
|
||||
error.status = 400;
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -0,0 +1,35 @@
|
||||
const logger = require("../utils/logger");
|
||||
const SERVICE_NAME = "verifyOwnership";
|
||||
|
||||
const verifyOwnership = (Model, paramName) => {
|
||||
return async (req, res, next) => {
|
||||
const userId = req.user._id;
|
||||
const documentId = req.params[paramName];
|
||||
try {
|
||||
const doc = await Model.findById(documentId);
|
||||
//If the document is not found, return a 404 error
|
||||
if (!doc) {
|
||||
logger.error("Document not found", {
|
||||
service: SERVICE_NAME,
|
||||
});
|
||||
const error = new Error("Document not found");
|
||||
error.status = 404;
|
||||
throw error;
|
||||
}
|
||||
|
||||
// If the userID does not match the document's userID, return a 403 error
|
||||
if (userId.toString() !== doc.userId.toString()) {
|
||||
console.log("boom");
|
||||
const error = new Error("Unauthorized access");
|
||||
error.status = 403;
|
||||
throw error;
|
||||
}
|
||||
next();
|
||||
} catch (error) {
|
||||
error.service = SERVICE_NAME;
|
||||
next(error);
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
module.exports = { verifyOwnership };
|
||||
@@ -0,0 +1,38 @@
|
||||
const mongoose = require('mongoose')
|
||||
|
||||
const AlertSchema = mongoose.Schema(
|
||||
{
|
||||
checkId: {
|
||||
type: mongoose.Schema.Types.ObjectId,
|
||||
ref: 'Check',
|
||||
immutable: true,
|
||||
},
|
||||
monitorId: {
|
||||
type: mongoose.Schema.Types.ObjectId,
|
||||
ref: 'Monitor',
|
||||
immutable: true,
|
||||
},
|
||||
userId: {
|
||||
type: mongoose.Schema.Types.ObjectId,
|
||||
ref: 'User',
|
||||
immutable: true,
|
||||
},
|
||||
status: {
|
||||
type: Boolean,
|
||||
},
|
||||
message: {
|
||||
type: String,
|
||||
},
|
||||
notifiedStatus: {
|
||||
type: Boolean,
|
||||
},
|
||||
acknowledgeStatus: {
|
||||
type: Boolean,
|
||||
}
|
||||
},
|
||||
{
|
||||
timestamps: true,
|
||||
}
|
||||
);
|
||||
|
||||
module.exports = mongoose.model('Alert', AlertSchema);
|
||||
@@ -0,0 +1,28 @@
|
||||
const mongoose = require('mongoose')
|
||||
|
||||
const CheckSchema = mongoose.Schema(
|
||||
{
|
||||
monitorId: {
|
||||
type: mongoose.Schema.Types.ObjectId,
|
||||
ref: 'Monitor',
|
||||
immutable: true,
|
||||
},
|
||||
status: {
|
||||
type: Boolean,
|
||||
},
|
||||
responseTime: {
|
||||
type: Number, // milliseconds
|
||||
},
|
||||
statusCode: {
|
||||
type: Number, // 200, ... , 500
|
||||
},
|
||||
message: {
|
||||
type: String,
|
||||
}
|
||||
},
|
||||
{
|
||||
timestamps: true,
|
||||
}
|
||||
);
|
||||
|
||||
module.exports = mongoose.model('Check', CheckSchema);
|
||||
+34
-38
@@ -1,44 +1,41 @@
|
||||
const mongoose = require("mongoose");
|
||||
const bcrypt = require("bcrypt");
|
||||
|
||||
const UserSchema = mongoose.Schema({
|
||||
firstname: {
|
||||
type: String,
|
||||
required: true,
|
||||
const UserSchema = mongoose.Schema(
|
||||
{
|
||||
firstname: {
|
||||
type: String,
|
||||
required: true,
|
||||
},
|
||||
lastname: {
|
||||
type: String,
|
||||
required: true,
|
||||
},
|
||||
email: {
|
||||
type: String,
|
||||
required: true,
|
||||
unique: true,
|
||||
},
|
||||
password: {
|
||||
type: String,
|
||||
required: true,
|
||||
},
|
||||
profilePicUrl: {
|
||||
type: String,
|
||||
},
|
||||
isActive: {
|
||||
type: Boolean,
|
||||
default: true,
|
||||
},
|
||||
isVerified: {
|
||||
type: Boolean,
|
||||
default: false,
|
||||
},
|
||||
},
|
||||
lastname: {
|
||||
type: String,
|
||||
required: true,
|
||||
},
|
||||
email: {
|
||||
type: String,
|
||||
required: true,
|
||||
unique: true,
|
||||
},
|
||||
password: {
|
||||
type: String,
|
||||
required: true,
|
||||
},
|
||||
profilePicUrl: {
|
||||
type: String,
|
||||
},
|
||||
isActive: {
|
||||
type: Boolean,
|
||||
default: true,
|
||||
},
|
||||
isVerified: {
|
||||
type: Boolean,
|
||||
default: false,
|
||||
},
|
||||
updated_at: {
|
||||
type: Date,
|
||||
default: Date.now,
|
||||
},
|
||||
created_at: {
|
||||
type: Date,
|
||||
default: Date.now,
|
||||
},
|
||||
});
|
||||
{
|
||||
timestamps: true,
|
||||
}
|
||||
);
|
||||
|
||||
UserSchema.pre("save", async function (next) {
|
||||
if (!this.isModified("password")) {
|
||||
@@ -50,7 +47,6 @@ UserSchema.pre("save", async function (next) {
|
||||
});
|
||||
|
||||
UserSchema.methods.comparePassword = function (submittedPassword) {
|
||||
console.log(submittedPassword, this.password);
|
||||
return bcrypt.compare(submittedPassword, this.password);
|
||||
};
|
||||
|
||||
|
||||
@@ -0,0 +1,27 @@
|
||||
const router = require("express").Router();
|
||||
const alertController = require("../controllers/alertController");
|
||||
const { verifyOwnership } = require("../middleware/verifyOwnership");
|
||||
const Alert = require("../models/Alert");
|
||||
|
||||
// Create alert
|
||||
router.post("/:monitorId", alertController.createAlert);
|
||||
// Get all alerts for a user
|
||||
router.get("/user/:userId", alertController.getAlertsByUserId);
|
||||
// Get all alerts for a monitor
|
||||
router.get("/monitor/:monitorId", alertController.getAlertsByMonitorId);
|
||||
// Get a single alert
|
||||
router.get("/:alertId", alertController.getAlertById);
|
||||
// Edit
|
||||
router.post(
|
||||
"/edit/:alertId",
|
||||
verifyOwnership(Alert, "alertId"),
|
||||
alertController.editAlert
|
||||
);
|
||||
//Delete
|
||||
router.post(
|
||||
"/delete/:alertId",
|
||||
verifyOwnership(Alert, "alertId"),
|
||||
alertController.deleteAlert
|
||||
);
|
||||
|
||||
module.exports = router;
|
||||
@@ -1,10 +1,14 @@
|
||||
const router = require("express").Router();
|
||||
const { verifyJWT } = require("../middleware/verifyJWT");
|
||||
|
||||
const {
|
||||
registerController,
|
||||
loginController,
|
||||
userEditController,
|
||||
} = require("../controllers/authController");
|
||||
|
||||
router.post("/register", registerController);
|
||||
router.post("/login", loginController);
|
||||
router.post("/user/:userId", verifyJWT, userEditController);
|
||||
|
||||
module.exports = router;
|
||||
@@ -0,0 +1,24 @@
|
||||
const router = require("express").Router();
|
||||
const checkController = require("../controllers/checkController");
|
||||
const { verifyOwnership } = require("../middleware/verifyOwnership");
|
||||
const Monitor = require("../models/Monitor");
|
||||
|
||||
router.post(
|
||||
"/:monitorId",
|
||||
verifyOwnership(Monitor, "monitorId"),
|
||||
checkController.createCheck
|
||||
);
|
||||
|
||||
router.get(
|
||||
"/:monitorId",
|
||||
verifyOwnership(Monitor, "monitorId"),
|
||||
checkController.getChecks
|
||||
);
|
||||
|
||||
router.post(
|
||||
"/delete/:monitorId",
|
||||
verifyOwnership(Monitor, "monitorId"),
|
||||
checkController.deleteChecks
|
||||
);
|
||||
|
||||
module.exports = router;
|
||||
@@ -1,11 +1,21 @@
|
||||
const router = require("express").Router();
|
||||
const monitorController = require("../controllers/monitorController");
|
||||
const { verifyOwnership } = require("../middleware/verifyOwnership");
|
||||
const Monitor = require("../models/Monitor");
|
||||
|
||||
router.get("/", monitorController.getAllMonitors);
|
||||
router.get("/:monitorId", monitorController.getMonitorById);
|
||||
router.get("/user/:userId", monitorController.getMonitorsByUserId);
|
||||
|
||||
router.post("/", monitorController.createMonitor);
|
||||
router.post("/delete/:monitorId", monitorController.deleteMonitor);
|
||||
router.post("/edit/:monitorId", monitorController.editMonitor);
|
||||
router.post(
|
||||
"/delete/:monitorId",
|
||||
verifyOwnership(Monitor, "monitorId"),
|
||||
monitorController.deleteMonitor
|
||||
);
|
||||
router.post(
|
||||
"/edit/:monitorId",
|
||||
verifyOwnership(Monitor, "monitorId"),
|
||||
monitorController.editMonitor
|
||||
);
|
||||
module.exports = router;
|
||||
@@ -1,5 +1,4 @@
|
||||
const joi = require("joi");
|
||||
const user = require("../models/user");
|
||||
|
||||
const loginValidation = joi.object({
|
||||
email: joi.string().email().required(),
|
||||
@@ -30,10 +29,71 @@ const monitorValidation = joi.object({
|
||||
interval: joi.number(),
|
||||
});
|
||||
|
||||
const editUserParamValidation = joi.object({
|
||||
userId: joi.string().required(),
|
||||
});
|
||||
|
||||
const editUserBodyValidation = joi.object({
|
||||
firstname: joi.string(),
|
||||
lastname: joi.string(),
|
||||
profilePicUrl: joi.string(),
|
||||
});
|
||||
|
||||
const createAlertParamValidation = joi.object({
|
||||
monitorId: joi.string().required(),
|
||||
});
|
||||
|
||||
const createAlertBodyValidation = joi.object({
|
||||
checkId: joi.string().required(),
|
||||
monitorId: joi.string().required(),
|
||||
userId: joi.string().required(),
|
||||
status: joi.boolean(),
|
||||
message: joi.string(),
|
||||
notifiedStatus: joi.boolean(),
|
||||
acknowledgeStatus: joi.boolean(),
|
||||
});
|
||||
|
||||
const getAlertsByUserIdParamValidation = joi.object({
|
||||
userId: joi.string().required(),
|
||||
});
|
||||
|
||||
const getAlertsByMonitorIdParamValidation = joi.object({
|
||||
monitorId: joi.string().required(),
|
||||
});
|
||||
|
||||
const getAlertByIdParamValidation = joi.object({
|
||||
alertId: joi.string().required(),
|
||||
});
|
||||
|
||||
const editAlertParamValidation = joi.object({
|
||||
alertId: joi.string().required(),
|
||||
});
|
||||
|
||||
const editAlertBodyValidation = joi.object({
|
||||
status: joi.boolean(),
|
||||
message: joi.string(),
|
||||
notifiedStatus: joi.boolean(),
|
||||
acknowledgeStatus: joi.boolean(),
|
||||
});
|
||||
|
||||
const deleteAlertParamValidation = joi.object({
|
||||
alertId: joi.string().required(),
|
||||
});
|
||||
|
||||
module.exports = {
|
||||
loginValidation,
|
||||
registerValidation,
|
||||
getMonitorByIdValidation,
|
||||
getMonitorsByUserIdValidation,
|
||||
monitorValidation,
|
||||
editUserParamValidation,
|
||||
editUserBodyValidation,
|
||||
createAlertParamValidation,
|
||||
createAlertBodyValidation,
|
||||
getAlertsByUserIdParamValidation,
|
||||
getAlertsByMonitorIdParamValidation,
|
||||
getAlertByIdParamValidation,
|
||||
editAlertParamValidation,
|
||||
editAlertBodyValidation,
|
||||
deleteAlertParamValidation,
|
||||
};
|
||||
Generated
-6
@@ -1,6 +0,0 @@
|
||||
{
|
||||
"name": "bluewave-uptime",
|
||||
"lockfileVersion": 3,
|
||||
"requires": true,
|
||||
"packages": {}
|
||||
}
|
||||
Reference in new issue
Block a user