Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
30 changes: 17 additions & 13 deletions src/components/AppVersion.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ const AppVersion = () => {
return (
<>
<div
className="flex items-center gap-1 mr-3 cursor-pointer hover:text-secondary-content"
className="flex items-center gap-1 mr-3 cursor-pointer hover:text-neutral-content"
onClick={handleClick}
>
<IoGitBranch size={18} />
Expand All @@ -40,18 +40,22 @@ const AppVersion = () => {
</span>
</div>
<dialog id="my_modal_2" className="modal backdrop-blur-sm" ref={modalRef}>
<div className="modal-box text-start h-1/2 max-w-2xl">
{changelog.map((data: Record<string, string>) => (
<MarkdownRenderedComponent
content={data.body}
key={data.tag_name}
/>
))}
<form method="dialog">
<button className=" btn-sm btn-circle absolute right-2 top-2 hover:text-secondary-content">
<IoCloseSharp />
</button>
</form>
<div className="modal-box flex flex-col gap-4 text-start h-1/2 max-w-2xl">
<div className="text-end">
<form method="dialog">
<button className="hover:text-secondary-content">
<IoCloseSharp />
</button>
</form>
</div>
<div className="h-full overflow-y-scroll">
{changelog.map((data: Record<string, string>) => (
<MarkdownRenderedComponent
content={data.body}
key={data.tag_name}
/>
))}
</div>
</div>
<form method="dialog" className="modal-backdrop">
<button>close</button>
Expand Down
5 changes: 3 additions & 2 deletions src/components/Footer.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import { Shortcut } from '../enums/shortcut.enum';
import AppVersion from './AppVersion';
import ShortKeys from './ShortKeys';
import ThemeController from './ThemeController';
Expand All @@ -6,8 +7,8 @@ import { FaGithub } from 'react-icons/fa';
const Footer = () => {
return (
<div className="mt-10">
<ShortKeys />
<div className="flex items-center text-sm justify-around text-secondary">
<ShortKeys keys={Object.values(Shortcut)} />
<div className="flex items-center text-sm justify-around text-base-content">
<p>© 2024 Nikola Nenovski. All right reserved.</p>
<div className="flex items-center gap-2 cursor-default">
<AppVersion />
Expand Down
25 changes: 22 additions & 3 deletions src/components/HistoryModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,12 @@ import { useEffect, useMemo, useRef, useState } from 'react';
import { useHistoryModal } from '../providers/HistoryProvider';
import { HistoryObject } from '../interfaces/HistoryObject';
import { useNavigate, useSearchParams } from 'react-router-dom';
import ShortKeys from './ShortKeys';
import { Shortcut } from '../enums/shortcut.enum';
import { FaTrash } from 'react-icons/fa';

const HistoryModal = () => {
const { setIsModalOpen, isModalOpen, history, historyPush } =
const { setIsModalOpen, isModalOpen, history, historyPush, clearHistory } =
useHistoryModal();
const historyInputRef = useRef<HTMLInputElement | null>(null);
const [searchQuery, setSearchQuery] = useState<string>('');
Expand Down Expand Up @@ -56,9 +59,9 @@ const HistoryModal = () => {

return (
<dialog id="history_modal" className="modal backdrop-blur-sm">
<div className="modal-box">
<div className="modal-box flex flex-col gap-4">
<label
className="flex items-center input input-sm input-bordered w-full mb-4"
className="flex items-center input input-sm input-bordered w-full"
style={{ outline: 'none', boxShadow: 'none' }}
>
<input
Expand All @@ -71,6 +74,7 @@ const HistoryModal = () => {
/>
<kbd className="kbd kbd-sm text-xs py-0.5 px-1">t</kbd>
</label>
<ShortKeys keys={[Shortcut.T, Shortcut.ESCAPE]} />
<div className="h-72 overflow-y-scroll">
<table className="table table-xs table-pin-rows">
<thead className="cursor-default">
Expand Down Expand Up @@ -115,7 +119,22 @@ const HistoryModal = () => {
</tbody>
</table>
</div>
<div className="text-start">
<button
className="btn btn-outline btn-error btn-sm"
onClick={() => {
localStorage.removeItem('history');
clearHistory();
}}
>
<FaTrash />
history
</button>
</div>
</div>
<form method="dialog" className="modal-backdrop">
<button onClick={() => setIsModalOpen(false)}>close</button>
</form>
</dialog>
);
};
Expand Down
189 changes: 142 additions & 47 deletions src/components/Markers.tsx
Original file line number Diff line number Diff line change
@@ -1,13 +1,23 @@
import { FaCheck } from 'react-icons/fa';
import { IoClose } from 'react-icons/io5';
import { DnsRecordAnswer } from '../types/DnsRecordAnswer';
import { useMemo } from 'react';
import NotAvailableMarker from './NotAvailableMarker';
import VerticalSeparator from './VerticalSeparator';

interface MarkersPropsType {
AAAA: DnsRecordAnswer[] | string | undefined;
hasWp: boolean;
hasWwwRecord: boolean;
dnssec: string | undefined;
wwwSsl: boolean;
cdnInfo: string[];
domainStatusCodes: string[] | string;
isWhoisLoading: boolean;
isDnsLoading: boolean;
isSslLoading: boolean;
isCdnCheckLoading: boolean;
isWpCheckLoading: boolean;
}

const Markers: React.FC<MarkersPropsType> = ({
Expand All @@ -16,45 +26,80 @@ const Markers: React.FC<MarkersPropsType> = ({
hasWwwRecord,
dnssec,
wwwSsl,
cdnInfo,
domainStatusCodes,
isWhoisLoading,
isDnsLoading,
isSslLoading,
isCdnCheckLoading,
isWpCheckLoading,
}) => {
const transferCheck = useMemo(() => {
if (!domainStatusCodes) return;

if (domainStatusCodes.includes('ok')) return 'active';
else if (domainStatusCodes.includes('pendingTransfer'))
return 'pending transfer';
else return 'locked';
}, [domainStatusCodes]);

const domainStatus = useMemo(() => {
if (!domainStatusCodes) return;

const statuses: string[] | string = Array.isArray(domainStatusCodes)
? domainStatusCodes.map((status: string) =>
status.substring(0, status.indexOf(' '))
)
: domainStatusCodes.substring(0, domainStatusCodes.indexOf(' '));

if (statuses.includes('clientHold')) return 'hold';
else if (statuses.includes('pendingDelete')) return 'pending delete';
else if (statuses.includes('redemptionPeriod')) return 'redemption';
else if (statuses.includes('inactive')) return 'inactive';
else if (statuses.includes('pendingUpdate')) return 'pending update';
else return 'active';
}, [domainStatusCodes]);

return (
<div className="mb-5 bg-base-200 py-2 px-4 rounded-lg text-secondary cursor-default">
<div className="mb-5 bg-base-200 py-2 px-4 rounded-lg text-neutral-content cursor-default">
<ul className="flex gap-6 text-xs items-center">
<li className="flex items-center gap-2">
<h3 className="font-semibold">NO AAAA</h3>
{Array.isArray(AAAA) ? (
<div className="bg-error text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center">
<IoClose size={12} />
</div>
) : typeof AAAA === 'string' ? (
<div className="bg-success text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center">
<FaCheck size={8} />
</div>
{!AAAA ? (
<NotAvailableMarker loading={isDnsLoading} />
) : (
<span className="bg-secondary text-neutral font-semibold text-xs px-1 rounded">
N/A
<span
className={`${
Array.isArray(AAAA) ? 'bg-error' : 'bg-success'
} text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center`}
>
{Array.isArray(AAAA) ? (
<IoClose size={12} />
) : (
<FaCheck size={8} />
)}
</span>
)}
</li>
<li className="flex items-center gap-2">
<h3 className="font-semibold">WWW DNS</h3>
{hasWwwRecord ? (
<div className="bg-success text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center">
<FaCheck size={8} />
</div>
{!hasWwwRecord ? (
<NotAvailableMarker loading={isDnsLoading} />
) : (
<div className="bg-error text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center">
<IoClose size={12} />
</div>
<span
className={`${
hasWwwRecord ? 'bg-success' : 'bg-error'
} text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center`}
>
{hasWwwRecord ? <FaCheck size={8} /> : <IoClose size={12} />}
</span>
)}
</li>
<div className="bg-secondary w-0.5 h-3 rounded-full"></div>
<VerticalSeparator />
<li className="flex items-center gap-2">
<h3 className="font-semibold">DNSSEC</h3>
{!dnssec ? (
<span className="bg-secondary text-neutral font-semibold text-xs px-1 rounded">
N/A
</span>
<NotAvailableMarker loading={isWhoisLoading} />
) : dnssec === 'unsigned' ? (
<span className="bg-success text-neutral font-semibold text-xs px-1 rounded">
unsigned
Expand All @@ -67,45 +112,95 @@ const Markers: React.FC<MarkersPropsType> = ({
</li>
<li className="flex gap-2">
<h3 className="font-semibold">STATUS</h3>
<span className="bg-success text-neutral font-semibold text-xs px-1 rounded">
active
</span>
<div className="dropdown dropdown-hover">
{!domainStatus ? (
<NotAvailableMarker loading={isWhoisLoading} />
) : (
<span
tabIndex={0}
role="button"
className={`${
domainStatus === 'active' ? 'bg-success' : 'bg-error'
} text-neutral font-semibold text-xs px-1 rounded`}
>
{domainStatus}
</span>
)}
<a
tabIndex={0}
className="dropdown-content menu bg-base-100 link font-semibold link-primary rounded-box z-[1] w-44 p-2 shadow"
href="https://www.icann.org/resources/pages/epp-status-codes-2014-06-16-en"
target="_blank"
>
EPP Status Codes
</a>
</div>
</li>
<li className="flex gap-2">
<h3 className="font-semibold">TRANSFER</h3>
<span className="bg-error text-neutral font-semibold text-xs px-1 rounded">
locked
</span>
{!domainStatus ? (
<NotAvailableMarker loading={isWhoisLoading} />
) : (
<span
className={`${
transferCheck === 'active'
? 'bg-success'
: transferCheck === 'pending transfer'
? 'bg-warning'
: 'bg-error'
} text-neutral font-semibold text-xs px-1 rounded`}
>
{transferCheck}
</span>
)}
</li>
<div className="bg-secondary w-0.5 h-3 rounded-full"></div>
<VerticalSeparator />
<li className="flex gap-2">
<h3 className="font-semibold">HAS CDN</h3>
<div className="bg-success text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center">
<FaCheck size={8} />
</div>
<h3 className="font-semibold">CDN</h3>
{cdnInfo.length === 0 ? (
<NotAvailableMarker loading={isCdnCheckLoading} />
) : (
<div
className={`${
cdnInfo.length === 1 ? 'bg-success' : 'bg-warning'
} text-neutral font-semibold text-xs px-1 rounded`}
>
{cdnInfo.length === 1 ? (
<span>{cdnInfo[0].toLowerCase()}</span>
) : (
<span className="tooltip" data-tip={cdnInfo.join(', ')}>
multiple
</span>
)}
</div>
)}
</li>
<li className="flex gap-2">
<h3 className="font-semibold">WWW SSL</h3>
{wwwSsl ? (
<div className="bg-success text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center">
<FaCheck size={8} />
</div>
{!wwwSsl ? (
<NotAvailableMarker loading={isSslLoading} />
) : (
<div className="bg-error text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center">
<IoClose size={12} />
</div>
<span
className={`${
wwwSsl ? 'bg-success' : 'bg-error'
} text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center`}
>
{wwwSsl ? <FaCheck size={8} /> : <IoClose size={12} />}
</span>
)}
</li>
<li className="flex gap-2">
<h3 className="font-semibold">HAS WP</h3>
{hasWp ? (
<div className="bg-success text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center">
<FaCheck size={8} />
</div>
{isWpCheckLoading ? (
<NotAvailableMarker loading={isWpCheckLoading} />
) : (
<div className="bg-error text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center">
<IoClose size={12} />
</div>
<span
className={`${
hasWp ? 'bg-success' : 'bg-error'
} text-neutral w-4 h-4 rounded-full font-semibold flex justify-center items-center`}
>
{hasWp ? <FaCheck size={8} /> : <IoClose size={12} />}
</span>
)}
</li>
</ul>
Expand Down
25 changes: 25 additions & 0 deletions src/components/NotAvailableMarker.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import { cn } from '../helpers/cn.helper';

const NotAvailableMarker: React.FC<{
className?: string;
loading?: boolean;
}> = ({ className, loading }) => {
return (
<div
className={cn(
`${
loading ? 'bg-none' : 'bg-secondary'
} text-neutral font-semibold text-xs px-1 rounded flex items-center`,
className
)}
>
{loading ? (
<span className="loading loading-spinner loading-xs text-primary"></span>
) : (
<span>N/A</span>
)}
</div>
);
};

export default NotAvailableMarker;
Loading
Loading