diff --git a/client/src/components/AccountSettings/LinkedDevices.tsx b/client/src/components/AccountSettings/LinkedDevices.tsx
index 92b9c733208fa2912ea981e923966f39ac120456..8fc86f2a551de294a1aebf7de7b1289580dade87 100644
--- a/client/src/components/AccountSettings/LinkedDevices.tsx
+++ b/client/src/components/AccountSettings/LinkedDevices.tsx
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2022-2025 Savoir-faire Linux Inc.
+ * Copyright (C) 2025 Savoir-faire Linux Inc.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU Affero General Public License as
@@ -15,121 +15,405 @@
  * License along with this program.  If not, see
  * <https://www.gnu.org/licenses/>.
  */
-
+import DeleteIcon from '@mui/icons-material/Delete'
 import DevicesIcon from '@mui/icons-material/Devices'
-import { Box } from '@mui/material'
-import Card from '@mui/material/Card'
-import CardContent from '@mui/material/CardContent'
-import Grid from '@mui/material/Grid'
-import ListItem from '@mui/material/ListItem'
-import ListItemText from '@mui/material/ListItemText'
+import { useMediaQuery } from '@mui/material'
+import Box from '@mui/material/Box'
+import Checkbox from '@mui/material/Checkbox'
+import IconButton from '@mui/material/IconButton'
+import Paper from '@mui/material/Paper'
+import { alpha, useTheme } from '@mui/material/styles'
+import Table from '@mui/material/Table'
+import TableBody from '@mui/material/TableBody'
+import TableCell from '@mui/material/TableCell'
+import TableContainer from '@mui/material/TableContainer'
+import TableHead from '@mui/material/TableHead'
+import TablePagination from '@mui/material/TablePagination'
+import TableRow from '@mui/material/TableRow'
+import TableSortLabel from '@mui/material/TableSortLabel'
+import Toolbar from '@mui/material/Toolbar'
+import Tooltip from '@mui/material/Tooltip'
 import Typography from '@mui/material/Typography'
-import { useMemo, useState } from 'react'
+import { visuallyHidden } from '@mui/utils'
+import { ChangeEvent, MouseEvent, useMemo, useState } from 'react'
 import { useTranslation } from 'react-i18next'
 
 import { useAuthContext } from '../../contexts/AuthProvider'
 import { useRemoveLinkedDevice } from '../../services/accountQueries'
 import EllipsisMiddle from '../EllipsisMiddle'
-import { TrashBinIcon } from '../SvgIcon'
 import PasswordRequiredModal from './PasswordRequiredModal'
 
-function LinkedDevices() {
+interface DeviceRow {
+  deviceId: string
+  deviceName: string
+}
+
+const rowsPerPageOptions = [10, 25, 50, 100]
+const paddingValue = '20px'
+
+function descendingComparator<T>(a: T, b: T, orderBy: keyof T) {
+  if (b[orderBy] < a[orderBy]) {
+    return -1
+  }
+  if (b[orderBy] > a[orderBy]) {
+    return 1
+  }
+  return 0
+}
+
+type Order = 'asc' | 'desc'
+
+function getComparator<Key extends keyof any>(
+  order: Order,
+  orderBy: Key,
+): (a: { [key in Key]: string }, b: { [key in Key]: string }) => number {
+  return order === 'desc'
+    ? (a, b) => descendingComparator(a, b, orderBy)
+    : (a, b) => -descendingComparator(a, b, orderBy)
+}
+
+interface HeadCell {
+  disablePadding: boolean
+  id: keyof DeviceRow | 'removeDevice'
+  label: string
+  numeric: boolean
+}
+
+const headCells: readonly HeadCell[] = [
+  {
+    id: 'deviceName',
+    numeric: false,
+    disablePadding: true,
+    label: 'Device Name',
+  },
+  {
+    id: 'deviceId',
+    numeric: false,
+    disablePadding: false,
+    label: 'Device ID',
+  },
+]
+
+interface EnhancedTableProps {
+  numSelected: number
+  onRequestSort: (event: MouseEvent<unknown>, property: keyof DeviceRow) => void
+  onSelectAllClick: (event: ChangeEvent<HTMLInputElement>) => void
+  order: Order
+  orderBy: string
+  rowCount: number
+}
+
+function EnhancedTableHead(props: EnhancedTableProps) {
+  const { onSelectAllClick, order, orderBy, numSelected, rowCount, onRequestSort } = props
+
+  const createSortHandler = (property: keyof DeviceRow) => (event: MouseEvent<unknown>) => {
+    onRequestSort(event, property)
+  }
+
+  return (
+    <TableHead>
+      <TableRow>
+        {headCells.map((headCell) => {
+          const isSortable = headCell.id !== 'removeDevice'
+          return (
+            <TableCell
+              key={headCell.id}
+              sx={{ paddingLeft: paddingValue }}
+              align={headCell.numeric ? 'right' : 'left'}
+              padding={headCell.disablePadding ? 'none' : 'normal'}
+              sortDirection={orderBy === headCell.id ? order : false}
+            >
+              {isSortable ? (
+                <TableSortLabel
+                  active={orderBy === headCell.id}
+                  direction={orderBy === headCell.id ? order : 'asc'}
+                  onClick={createSortHandler(headCell.id as keyof DeviceRow)}
+                >
+                  {headCell.label}
+                  {orderBy === headCell.id ? (
+                    <Box component="span" sx={visuallyHidden}>
+                      {order === 'desc' ? 'sorted descending' : 'sorted ascending'}
+                    </Box>
+                  ) : null}
+                </TableSortLabel>
+              ) : (
+                headCell.label
+              )}
+            </TableCell>
+          )
+        })}
+        <TableCell padding="checkbox">
+          <Checkbox
+            color="primary"
+            indeterminate={numSelected > 0 && numSelected < rowCount}
+            checked={rowCount > 0 && numSelected === rowCount}
+            onChange={onSelectAllClick}
+            inputProps={{
+              'aria-label': 'select all devices',
+            }}
+          />
+        </TableCell>
+      </TableRow>
+    </TableHead>
+  )
+}
+
+interface EnhancedTableToolbarProps {
+  numSelected: number
+  devicesNumber: number
+  onDelete: () => void
+}
+
+function EnhancedTableToolbar(props: EnhancedTableToolbarProps) {
+  const { numSelected, devicesNumber, onDelete } = props
+  const { t } = useTranslation()
   const { account } = useAuthContext()
+  const theme = useTheme()
+  const isMobile = useMediaQuery(theme.breakpoints.down('sm'))
+
+  return (
+    <>
+      <Toolbar
+        sx={[
+          {
+            pl: { sm: 2 },
+            pr: { xs: 1, sm: 1 },
+          },
+          numSelected > 0 && {
+            bgcolor: (theme) => alpha(theme.palette.primary.main, theme.palette.action.activatedOpacity),
+          },
+        ]}
+      >
+        {numSelected > 0 ? (
+          <Typography sx={{ flex: '1 1 100%' }} color="inherit" variant="subtitle1" component="div">
+            {numSelected} selected
+          </Typography>
+        ) : (
+          <Typography variant="h6" id="tableTitle" component="div">
+            {t('settings_devices_linked', { count: devicesNumber })}
+          </Typography>
+        )}
+        {numSelected > 0 && (
+          <Tooltip title="Delete">
+            <IconButton onClick={onDelete}>
+              <DeleteIcon />
+            </IconButton>
+          </Tooltip>
+        )}
+      </Toolbar>
+      <Box
+        sx={{
+          paddingLeft: paddingValue,
+          display: 'flex',
+          flexDirection: 'column',
+          gap: '10px',
+        }}
+      >
+        <Box
+          sx={{ display: 'flex', justifyContent: 'start', alignItems: 'center', alignContent: 'center', gap: '5px' }}
+        >
+          {t('Current device:')}
+        </Box>
+        <Box sx={{ display: 'flex', flexDirection: 'row', gap: '5px', alignItems: 'center', alignContent: 'center' }}>
+          <Box
+            sx={{ fontSize: '14px', display: 'flex', justifyContent: 'center', alignContent: 'center', gap: '10px' }}
+          >
+            {' '}
+            <DevicesIcon sx={{ height: '20px', width: '20px', marginTop: '1px' }} />{' '}
+            <Box sx={{ textWrap: 'nowrap' }}>{account.details['Account.deviceName']}</Box>
+          </Box>{' '}
+          <Box
+            sx={{ fontFamily: 'monospace', fontSize: '12px', marginTop: '2px', maxWidth: isMobile ? '150px' : 'unset' }}
+          >
+            <EllipsisMiddle text={account.volatileDetails['Account.deviceID']} />
+          </Box>
+        </Box>
+      </Box>
+    </>
+  )
+}
+
+export default function LinkedDevices() {
+  const [order, setOrder] = useState<Order>('asc')
+  const [orderBy, setOrderBy] = useState<keyof DeviceRow>('deviceName')
+  const [selected, setSelected] = useState<readonly string[]>([])
+  const [page, setPage] = useState(0)
+  const [rowsPerPage, setRowsPerPage] = useState(rowsPerPageOptions[0])
+  const [open, setOpen] = useState(false)
   const { t } = useTranslation()
   const removeLinkedDeviceMutation = useRemoveLinkedDevice()
-  const [selectedDeviceId, setSelectedDeviceId] = useState<string | null>(null)
+  const { account } = useAuthContext()
 
-  const devices = useMemo(() => {
-    const deviceList: string[][] = []
-    const accountDevices = account.devices
+  const rows = useMemo<DeviceRow[]>(() => {
+    const accountDevices = account.devices || {}
+    const deviceList: DeviceRow[] = []
 
-    for (const deviceId in accountDevices) {
-      if (deviceId === account.volatileDetails['Account.deviceID']) continue
-      deviceList.push([deviceId, accountDevices[deviceId]])
+    for (const uri in accountDevices) {
+      if (uri === account.volatileDetails['Account.deviceID']) continue
+      deviceList.push({
+        deviceId: uri,
+        deviceName: accountDevices[uri],
+      })
     }
-
     return deviceList
   }, [account.devices, account.volatileDetails])
 
-  function selectDevice(deviceId: string) {
-    setSelectedDeviceId(deviceId)
+  const handleRequestSort = (event: MouseEvent<unknown>, property: keyof DeviceRow) => {
+    const isAsc = orderBy === property && order === 'asc'
+    setOrder(isAsc ? 'desc' : 'asc')
+    setOrderBy(property)
+  }
+
+  const handleSelectAllClick = (event: ChangeEvent<HTMLInputElement>) => {
+    if (event.target.checked) {
+      const newSelected = rows.map((r) => r.deviceId)
+      setSelected(newSelected)
+      return
+    }
+    setSelected([])
+  }
+
+  const handleClick = (event: MouseEvent<unknown>, deviceId: string) => {
+    const selectedIndex = selected.indexOf(deviceId)
+    let newSelected: readonly string[] = []
+
+    if (selectedIndex === -1) {
+      newSelected = newSelected.concat(selected, deviceId)
+    } else if (selectedIndex === 0) {
+      newSelected = newSelected.concat(selected.slice(1))
+    } else if (selectedIndex === selected.length - 1) {
+      newSelected = newSelected.concat(selected.slice(0, -1))
+    } else if (selectedIndex > 0) {
+      newSelected = newSelected.concat(selected.slice(0, selectedIndex), selected.slice(selectedIndex + 1))
+    }
+    setSelected(newSelected)
+  }
+
+  const handleChangePage = (event: unknown, newPage: number) => {
+    setPage(newPage)
+  }
+
+  const handleChangeRowsPerPage = (event: ChangeEvent<HTMLInputElement>) => {
+    setRowsPerPage(parseInt(event.target.value, 10))
+    setPage(0)
   }
 
-  function removeDevice(password: string) {
-    if (selectedDeviceId === null) return
-    removeLinkedDeviceMutation.mutate({ deviceId: selectedDeviceId, password })
-    onClose()
+  const handleDeleteSelected = () => {
+    setOpen(true)
   }
 
-  function onClose() {
-    setSelectedDeviceId(null)
+  const handleValidateDeleteSelected = (password: string) => {
+    selected.forEach((deviceId) => {
+      removeLinkedDeviceMutation.mutate({ deviceId: deviceId, password: password })
+    })
+    setSelected([])
+    setOpen(false)
   }
 
+  const visibleRows = useMemo(() => {
+    const sorted = [...rows].sort(getComparator(order, orderBy))
+    return sorted.slice(page * rowsPerPage, page * rowsPerPage + rowsPerPage)
+  }, [rows, order, orderBy, page, rowsPerPage])
+
+  const emptyRows = page > 0 ? Math.max(0, (1 + page) * rowsPerPage - rows.length) : 0
+
   return (
-    <>
-      <Grid item xs={12} sm={12} aria-label="linked-device">
-        <Card>
-          <CardContent sx={{ width: '100%' }}>
-            <Typography sx={{}} color="textSecondary" gutterBottom>
-              {t('settings_linked_devices')}
-            </Typography>
-            <Typography gutterBottom variant="h5" component="h2">
-              <ListItem>
-                <DevicesIcon
-                  sx={{ padding: '4px', margin: '4px', marginRight: '16px', height: '40px', width: '40px' }}
-                />
-                <ListItemText
-                  id="switch-list-label-rendezvous"
-                  primary={
-                    <>
-                      {account.details['Account.deviceName']}
-                      <span style={{ fontSize: 'small', fontWeight: 'bolder', marginLeft: '3%' }}>
-                        {t('current_device')}
-                      </span>
-                    </>
-                  }
-                  secondary={
-                    <Typography noWrap sx={{ textOverflow: 'ellipsis', overflow: 'hidden', maxWidth: '100%' }}>
-                      {account.volatileDetails['Account.deviceID']}
-                    </Typography>
-                  }
-                />
-              </ListItem>
-              {devices.map((device) => (
-                <ListItem key={device[0]}>
-                  <DevicesIcon
-                    sx={{ padding: '4px', margin: '4px', marginRight: '16px', height: '40px', width: '40px' }}
-                  />
-                  <ListItemText
-                    id="switch-list-label-rendezvous"
-                    primary={device[1]}
-                    secondary={
-                      <Box maxWidth={'90%'}>
-                        <EllipsisMiddle text={device[0]} />
-                      </Box>
-                    }
-                  />
-                  <TrashBinIcon sx={{ '&:hover': { cursor: 'pointer' } }} onClick={() => selectDevice(device[0])} />
-                </ListItem>
-              ))}
-              {/* <ListItemTextsion> */}
-            </Typography>
-          </CardContent>
-        </Card>
-      </Grid>
-      <PasswordRequiredModal
-        open={selectedDeviceId !== null}
-        onClose={onClose}
-        title={t('revoke_device')}
-        onValidation={removeDevice}
-        buttonText={t('revoke_device')}
-        info={t('revoke_device_info', {
-          device: selectedDeviceId,
-          deviceName: account.devices[selectedDeviceId || ''],
-        })}
-      />
-    </>
+    <Box sx={{ display: 'flex', width: '100%', justifyContent: 'center' }}>
+      <Box sx={{ width: '85%', marginTop: '5%' }}>
+        <Paper sx={{ width: '100%', mb: 2, borderRadius: '10px', overflow: 'hidden' }}>
+          <EnhancedTableToolbar
+            numSelected={selected.length}
+            devicesNumber={rows.length}
+            onDelete={handleDeleteSelected}
+          />
+          <TableContainer>
+            <Table sx={{ minWidth: 750 }} aria-labelledby="tableTitle" size={'medium'}>
+              <EnhancedTableHead
+                numSelected={selected.length}
+                order={order}
+                orderBy={orderBy}
+                onSelectAllClick={handleSelectAllClick}
+                onRequestSort={handleRequestSort}
+                rowCount={rows.length}
+              />
+              <TableBody>
+                {visibleRows.map((row, index) => {
+                  const isItemSelected = selected.includes(row.deviceId)
+                  const labelId = `enhanced-table-checkbox-${index}`
+
+                  return (
+                    <TableRow
+                      hover
+                      onClick={(event) => handleClick(event, row.deviceId)}
+                      role="checkbox"
+                      aria-checked={isItemSelected}
+                      tabIndex={-1}
+                      key={row.deviceId}
+                      selected={isItemSelected}
+                      sx={{ cursor: 'pointer' }}
+                    >
+                      {/* Device Name */}
+                      <TableCell
+                        component="th"
+                        id={labelId}
+                        scope="row"
+                        padding="none"
+                        sx={{ paddingLeft: paddingValue }}
+                      >
+                        <Box sx={{ display: 'flex', alignItems: 'center', gap: '10px' }}>
+                          <DevicesIcon sx={{ height: '20px', width: '20px' }} />
+                          {row.deviceName}
+                        </Box>
+                      </TableCell>
+
+                      <TableCell sx={{ fontFamily: 'monospace', fontSize: '12px' }} align="left">
+                        {row.deviceId}
+                      </TableCell>
+
+                      <TableCell padding="checkbox">
+                        <Checkbox
+                          color="primary"
+                          checked={isItemSelected}
+                          inputProps={{
+                            'aria-labelledby': labelId,
+                          }}
+                        />
+                      </TableCell>
+                    </TableRow>
+                  )
+                })}
+                {emptyRows > 0 && (
+                  <TableRow style={{ height: 53 * emptyRows }}>
+                    <TableCell colSpan={4} />
+                  </TableRow>
+                )}
+              </TableBody>
+            </Table>
+          </TableContainer>
+
+          <TablePagination
+            rowsPerPageOptions={rowsPerPageOptions}
+            component="div"
+            count={rows.length}
+            rowsPerPage={rowsPerPage}
+            page={page}
+            onPageChange={handleChangePage}
+            onRowsPerPageChange={handleChangeRowsPerPage}
+          />
+        </Paper>
+      </Box>
+      {open && (
+        <PasswordRequiredModal
+          open
+          onClose={() => {
+            setOpen(false)
+          }}
+          onValidation={handleValidateDeleteSelected}
+          title={t('revoke_device')}
+          buttonText={t('revoke_device')}
+          info={t('revoke_device_info')}
+        />
+      )}
+    </Box>
   )
 }
-
-export default LinkedDevices
diff --git a/server/locale/en/translation.json b/server/locale/en/translation.json
index f605ece85a91048e6986ff928b34f79c5fbf3d5d..1d2ea6524e15b476e1ffcc9c7d134ba7bb313eec 100644
--- a/server/locale/en/translation.json
+++ b/server/locale/en/translation.json
@@ -247,7 +247,7 @@
   "reset_nameserver_button": "Reset to default",
   "ressource_not_available": "Resource unavailable",
   "revoke_device": "Revoke device",
-  "revoke_device_info": "You are about to revoke the device {{deviceName}}.\nThis will log out the device and remove it from the linked devices list.",
+  "revoke_device_info": "You are about to revoke devices.\nThis will log out the devices and remove them from the linked devices list.",
   "save_button": "Save",
   "replying_to": "Replying to",
   "replied_to": "Replied to",
@@ -273,6 +273,7 @@
   "settings_appearance": "Appearance",
   "settings_customize_profile": "Customize profile",
   "settings_dark_theme": "Dark theme",
+  "settings_devices_linked": "Devices linked - {{count}}",
   "setting_display_name_success_alert": "Display name updated successfully.",
   "setting_display_name_error_alert": "An error occurred while updating the display name.",
   "settings_language": "User interface language",