bookManagement/public/index.html
2025-05-17 16:33:54 -04:00

177 lines
6.7 KiB
HTML

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Ghost Library</title>
<link rel="stylesheet" href="styles.css">
</head>
<body>
<button id="dark-mode-toggle">🌙</button>
<h1>Ghost Library</h1>
<input type="text" id="search-bar" placeholder="Search by title, author, publisher, etc.">
<table id="book-table">
<thead>
<tr>
<th onclick="sortTable(0)">Title</th>
<th onclick="sortTable(1)">Authors</th>
<th onclick="sortTable(2)">Publisher</th>
<th onclick="sortTable(3)">Published Date</th>
<th onclick="sortTable(4)">ISBN</th>
<th onclick="sortTable(5)">Status</th>
<th>Checkout</th>
</tr>
</thead>
<tbody id="book-table-body">
<!-- Book rows will be inserted here -->
</tbody>
</table>
<script>
// Fetch all books when the page loads
window.onload = fetchBooks('');
document.getElementById('search-bar').addEventListener('input', function () {
fetchBooks(this.value);
});
function fetchBooks(query = '') {
let url = '/search-title';
if (query) {
url += `?title=${encodeURIComponent(query)}&internalOnly=true`;
}
fetch(url)
.then(response => response.json())
.then(data => {
if (data.results) {
displayBooks(data.results);
} else {
document.getElementById('book-table-body').innerHTML = '<tr><td colspan="5">No books found</td></tr>';
}
})
.catch(error => console.error('Error fetching books:', error));
}
function displayBooks(books) {
console.debug('Books:', books);
const tbody = document.getElementById('book-table-body');
tbody.innerHTML = '';
books.forEach(book => {
const row = document.createElement('tr');
const isDisabled = book.status === 'Checked Out' ? 'disabled' : '';
row.innerHTML = `
<td><a href="/book/${book.isbn}" target="_blank">${book.title || ''}</a></td>
<td>${book.authors ? book.authors : ''}</td>
<td>${book.publishers || ''}</td>
<td>${book.publishedDate || ''}</td>
<td>${book.isbn || ''}</td>
<td>${book.status || ''}</td>
<td><button id="checkout-btn-${book.isbn}" onclick="requestCheckout('${book.isbn}')" ${isDisabled}>Checkout</button></td>
`;
tbody.appendChild(row);
});
}
// Utility function to get a cookie by name
function getCookie(name) {
const value = `; ${document.cookie}`;
const parts = value.split(`; ${name}=`);
if (parts.length === 2) return parts.pop().split(';').shift();
}
// Utility function to set a cookie
function setCookie(name, value, days) {
const date = new Date();
date.setTime(date.getTime() + (days * 24 * 60 * 60 * 1000));
const expires = `expires=${date.toUTCString()}`;
document.cookie = `${name}=${value}; ${expires}; path=/`;
}
// Client-side function to request checkout
function requestCheckout(isbn) {
let email = getCookie('lastEmail') || '';
let name = getCookie('lastName') || '';
// Prompt the user for email and name, pre-filling with existing values if available
email = prompt('Please enter your email:', email);
name = prompt('Please enter your name:', name);
if (!email || !name) {
alert('Email and name are required to proceed with checkout.');
return;
}
// Store the email and name in cookies for future use
setCookie('lastEmail', email, 7); // Store for 7 days
setCookie('lastName', name, 7); // Store for 7 days
fetch(`/api/checkout/${isbn}`, {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({ email, name })
})
.then(response => response.json())
.then(data => {
if (data.success) {
alert('Checkout request sent successfully.');
} else {
alert(data.error || 'Failed to send checkout request.');
}
})
.catch(error => {
console.error('Error:', error);
alert('An error occurred while sending the checkout request.');
});
}
function sortTable(columnIndex) {
const table = document.getElementById('book-table');
const rows = Array.from(table.rows).slice(1);
const isAscending = table.getAttribute('data-sort-order') === 'asc';
const direction = isAscending ? 1 : -1;
rows.sort((a, b) => {
const aText = a.cells[columnIndex].innerText.toLowerCase();
const bText = b.cells[columnIndex].innerText.toLowerCase();
if (aText < bText) return -1 * direction;
if (aText > bText) return 1 * direction;
return 0;
});
rows.forEach(row => table.tBodies[0].appendChild(row));
table.setAttribute('data-sort-order', isAscending ? 'desc' : 'asc');
}
// Dark mode toggle functionality
const darkModeToggle = document.getElementById('dark-mode-toggle');
const body = document.body;
// Check for saved user preference, if any, on load
if (localStorage.getItem('darkMode') === 'enabled') {
body.classList.add('dark-mode');
darkModeToggle.textContent = '☀️'; // Set to sun icon if dark mode is enabled
}
darkModeToggle.addEventListener('click', () => {
body.classList.toggle('dark-mode');
// Toggle icon
if (body.classList.contains('dark-mode')) {
darkModeToggle.textContent = '☀️'; // Sun icon
localStorage.setItem('darkMode', 'enabled');
} else {
darkModeToggle.textContent = '🌙'; // Moon icon
localStorage.setItem('darkMode', 'disabled');
}
});
</script>
</body>
</html>