diff --git a/application/src/components/servers/ServerTable.tsx b/application/src/components/servers/ServerTable.tsx
index d906b44..c73172f 100644
--- a/application/src/components/servers/ServerTable.tsx
+++ b/application/src/components/servers/ServerTable.tsx
@@ -47,21 +47,21 @@ export const ServerTable = ({ servers, isLoading, onRefresh }: ServerTableProps)
newSet.delete(serverId);
return newSet;
});
- console.log('Resume server monitoring:', serverId);
+ // console.log('Resume server monitoring:', serverId);
} else {
setPausedServers(prev => new Set(prev).add(serverId));
- console.log('Pause server monitoring:', serverId);
+ // console.log('Pause server monitoring:', serverId);
}
};
const handleEdit = (serverId: string) => {
// TODO: Implement edit functionality
- console.log('Edit server:', serverId);
+ // console.log('Edit server:', serverId);
};
const handleDelete = (serverId: string) => {
// TODO: Implement delete functionality
- console.log('Delete server:', serverId);
+ // console.log('Delete server:', serverId);
};
if (isLoading) {
diff --git a/application/src/components/services/ServicesPagination.tsx b/application/src/components/services/ServicesPagination.tsx
new file mode 100644
index 0000000..a9fab1a
--- /dev/null
+++ b/application/src/components/services/ServicesPagination.tsx
@@ -0,0 +1,131 @@
+
+import {
+ Pagination,
+ PaginationContent,
+ PaginationItem,
+ PaginationLink,
+ PaginationNext,
+ PaginationPrevious
+} from "@/components/ui/pagination";
+import {
+ Select,
+ SelectContent,
+ SelectItem,
+ SelectTrigger,
+ SelectValue
+} from "@/components/ui/select";
+import { PageSize } from "@/hooks/useServicesPagination";
+import { useLanguage } from "@/contexts/LanguageContext";
+
+interface ServicesPaginationProps {
+ currentPage: number;
+ totalPages: number;
+ pageSize: PageSize;
+ totalItems: number;
+ onPageChange: (page: number) => void;
+ onPageSizeChange: (size: PageSize) => void;
+}
+
+export function ServicesPagination({
+ currentPage,
+ totalPages,
+ pageSize,
+ totalItems,
+ onPageChange,
+ onPageSizeChange,
+}: ServicesPaginationProps) {
+ const { t } = useLanguage();
+
+ // Generate page numbers to display
+ const getPageNumbers = () => {
+ const pages = [];
+ const maxVisiblePages = 5;
+ const halfVisible = Math.floor(maxVisiblePages / 2);
+
+ let startPage = Math.max(1, currentPage - halfVisible);
+ let endPage = Math.min(totalPages, startPage + maxVisiblePages - 1);
+
+ // Adjust start page if we don't have enough pages at the end
+ if (endPage - startPage + 1 < maxVisiblePages) {
+ startPage = Math.max(1, endPage - maxVisiblePages + 1);
+ }
+
+ for (let i = startPage; i <= endPage; i++) {
+ pages.push(i);
+ }
+
+ return pages;
+ };
+
+ const startItem = Math.min((currentPage - 1) * pageSize + 1, totalItems);
+ const endItem = Math.min(currentPage * pageSize, totalItems);
+
+ return (
+
+
+
+ {t("rowsPerPage") ?? "Rows per page"}:
+
+
+
+ {totalItems > 0
+ ? `${startItem}-${endItem} of ${totalItems} ${t("services") || "services"}`
+ : `0 ${t("services") || "services"}`
+ }
+
+
+
+ {totalPages > 1 && (
+
+
+
+ onPageChange(Math.max(1, currentPage - 1))}
+ className={
+ currentPage === 1
+ ? "pointer-events-none opacity-50"
+ : "cursor-pointer"
+ }
+ />
+
+
+ {getPageNumbers().map((page) => (
+
+ onPageChange(page)}
+ className="cursor-pointer"
+ >
+ {page}
+
+
+ ))}
+
+
+ onPageChange(Math.min(totalPages, currentPage + 1))}
+ className={
+ currentPage === totalPages
+ ? "pointer-events-none opacity-50"
+ : "cursor-pointer"
+ }
+ />
+
+
+
+ )}
+
+ );
+}
\ No newline at end of file
diff --git a/application/src/components/services/ServicesTableContainer.tsx b/application/src/components/services/ServicesTableContainer.tsx
index d8e65db..589f4ee 100644
--- a/application/src/components/services/ServicesTableContainer.tsx
+++ b/application/src/components/services/ServicesTableContainer.tsx
@@ -2,10 +2,12 @@
import { useEffect } from "react";
import { Service } from "@/types/service.types";
import { ServicesTableView } from "./ServicesTableView";
+import { ServicesPagination } from "./ServicesPagination";
import { ServiceDeleteDialog } from "./ServiceDeleteDialog";
import { ServiceHistoryDialog } from "./ServiceHistoryDialog";
import { ServiceEditDialog } from "./ServiceEditDialog";
import { useServiceActions, useDialogState } from "./hooks";
+import { useServicesPagination } from "@/hooks/useServicesPagination";
interface ServicesTableContainerProps {
services: Service[];
@@ -36,6 +38,16 @@ export const ServicesTableContainer = ({ services }: ServicesTableContainerProps
handleDeleteDialogChange
} = useDialogState();
+ const {
+ paginatedServices,
+ currentPage,
+ totalPages,
+ pageSize,
+ totalItems,
+ handlePageChange,
+ handlePageSizeChange,
+ } = useServicesPagination({ services: localServices });
+
// Update local services state when props change
useEffect(() => {
updateServices(services);
@@ -62,7 +74,7 @@ export const ServicesTableContainer = ({ services }: ServicesTableContainerProps
return (
+
+
);
-}
+}
\ No newline at end of file
diff --git a/application/src/components/services/ServicesTableView.tsx b/application/src/components/services/ServicesTableView.tsx
index 5cdb36c..cc545ca 100644
--- a/application/src/components/services/ServicesTableView.tsx
+++ b/application/src/components/services/ServicesTableView.tsx
@@ -26,8 +26,8 @@ export const ServicesTableView = ({
const { t } = useLanguage();
return (
-
-
+
+
@@ -65,4 +65,4 @@ export const ServicesTableView = ({
);
-};
+};
\ No newline at end of file
diff --git a/application/src/hooks/useServicesPagination.ts b/application/src/hooks/useServicesPagination.ts
new file mode 100644
index 0000000..960aca5
--- /dev/null
+++ b/application/src/hooks/useServicesPagination.ts
@@ -0,0 +1,52 @@
+
+import { useState, useMemo } from 'react';
+import { Service } from '@/types/service.types';
+
+export type PageSize = 10 | 30 | 50;
+
+interface UseServicesPaginationProps {
+ services: Service[];
+ initialPageSize?: PageSize;
+}
+
+export const useServicesPagination = ({
+ services,
+ initialPageSize = 10
+}: UseServicesPaginationProps) => {
+ const [currentPage, setCurrentPage] = useState(1);
+ const [pageSize, setPageSize] = useState(initialPageSize);
+
+ const { paginatedServices, totalPages } = useMemo(() => {
+ const totalItems = services.length;
+ const pages = Math.ceil(totalItems / pageSize);
+ const startIndex = (currentPage - 1) * pageSize;
+ const endIndex = startIndex + pageSize;
+
+ return {
+ paginatedServices: services.slice(startIndex, endIndex),
+ totalPages: Math.max(1, pages)
+ };
+ }, [services, currentPage, pageSize]);
+
+ // Reset to first page when page size changes or services change
+ const handlePageSizeChange = (newPageSize: PageSize) => {
+ setPageSize(newPageSize);
+ setCurrentPage(1);
+ };
+
+ // Reset to first page if current page exceeds total pages
+ const handlePageChange = (page: number) => {
+ const validPage = Math.min(Math.max(1, page), totalPages);
+ setCurrentPage(validPage);
+ };
+
+ return {
+ paginatedServices,
+ currentPage,
+ totalPages,
+ pageSize,
+ totalItems: services.length,
+ handlePageChange,
+ handlePageSizeChange,
+ };
+};
\ No newline at end of file