mirror of
https://github.com/ajnart/homarr.git
synced 2025-11-10 23:45:48 +01:00
✨Add service ping
This commit is contained in:
64
src/components/Dashboard/Tiles/Service/ServicePing.tsx
Normal file
64
src/components/Dashboard/Tiles/Service/ServicePing.tsx
Normal file
@@ -0,0 +1,64 @@
|
||||
import { Indicator, Tooltip } from '@mantine/core';
|
||||
import { useQuery } from '@tanstack/react-query';
|
||||
import { motion } from 'framer-motion';
|
||||
import { useTranslation } from 'next-i18next';
|
||||
import { useConfigContext } from '../../../../config/provider';
|
||||
import { ServiceType } from '../../../../types/service';
|
||||
|
||||
interface ServicePingProps {
|
||||
service: ServiceType;
|
||||
}
|
||||
|
||||
export const ServicePing = ({ service }: ServicePingProps) => {
|
||||
const { t } = useTranslation('modules/ping');
|
||||
const { config } = useConfigContext();
|
||||
const active =
|
||||
(config?.settings.customization.layout.enabledPing && service.network.enabledStatusChecker) ??
|
||||
false;
|
||||
const { data, isLoading } = useQuery({
|
||||
queryKey: [`ping/${service.id}`],
|
||||
queryFn: async () => {
|
||||
const response = await fetch(`/api/modules/ping?url=${encodeURI(service.url)}`);
|
||||
const isOk = service.network.okStatus.includes(response.status);
|
||||
return {
|
||||
status: response.status,
|
||||
state: isOk ? 'online' : 'down',
|
||||
};
|
||||
},
|
||||
enabled: active,
|
||||
});
|
||||
|
||||
const isOnline = data?.state === 'online';
|
||||
|
||||
if (!active) return null;
|
||||
|
||||
return (
|
||||
<motion.div
|
||||
style={{ position: 'absolute', bottom: 20, right: 20 }}
|
||||
animate={{
|
||||
scale: isOnline ? [1, 0.7, 1] : 1,
|
||||
}}
|
||||
transition={{ repeat: Infinity, duration: 2.5, ease: 'easeInOut' }}
|
||||
>
|
||||
<Tooltip
|
||||
withinPortal
|
||||
radius="lg"
|
||||
label={
|
||||
isLoading
|
||||
? t('states.loading')
|
||||
: isOnline
|
||||
? t('states.online', { response: data.status })
|
||||
: t('states.offline', { response: data?.status })
|
||||
}
|
||||
>
|
||||
<Indicator
|
||||
size={15}
|
||||
color={isLoading ? 'yellow' : isOnline ? 'green' : 'red'}
|
||||
children={null}
|
||||
/>
|
||||
</Tooltip>
|
||||
</motion.div>
|
||||
);
|
||||
};
|
||||
|
||||
type PingState = 'loading' | 'down' | 'online';
|
||||
@@ -6,6 +6,7 @@ import { useCardStyles } from '../../../layout/useCardStyles';
|
||||
import { useEditModeStore } from '../../Views/useEditModeStore';
|
||||
import { BaseTileProps } from '../type';
|
||||
import { ServiceMenu } from './ServiceMenu';
|
||||
import { ServicePing } from './ServicePing';
|
||||
|
||||
interface ServiceTileProps extends BaseTileProps {
|
||||
service: ServiceType;
|
||||
@@ -58,7 +59,7 @@ export const ServiceTile = ({ className, service }: ServiceTileProps) => {
|
||||
{inner}
|
||||
</UnstyledButton>
|
||||
)}
|
||||
{/*<ServicePing service={service} />*/}
|
||||
<ServicePing service={service} />
|
||||
</Card>
|
||||
);
|
||||
};
|
||||
|
||||
@@ -10,6 +10,9 @@ async function Get(req: NextApiRequest, res: NextApiResponse) {
|
||||
const response = await ping.promise.probe(parsedUrl.hostname, {
|
||||
timeout: 1,
|
||||
});
|
||||
|
||||
console.log(response);
|
||||
|
||||
// Return 200 if the alive property is true
|
||||
if (response.alive) {
|
||||
return res.status(200).end();
|
||||
|
||||
Reference in New Issue
Block a user