Skip to content

Commit 3756121

Browse files
author
Saurabh Kumar Bajpai
committed
fix: code quality and safety improvements
1 parent af173a5 commit 3756121

3 files changed

Lines changed: 3 additions & 166 deletions

File tree

‎frontend/js/book-preview.js‎

Lines changed: 1 addition & 143 deletions
Original file line numberDiff line numberDiff line change
@@ -209,146 +209,4 @@ const BookPreview = (() => {
209209
el.querySelector('#download-card-btn').addEventListener('click', () => {
210210
const card = document.getElementById('book-card');
211211
html2canvas(card).then(canvas => {
212-
const link = document.createElement('a');
213-
link.download = 'book-card.png';
214-
link.href = canvas.toDataURL('image/png');
215-
link.click();
216-
});
217-
});
218-
219-
return el;
220-
}
221-
222-
// ── State helpers ──────────────────────────────────────────────────────────
223-
224-
function _setLoading() {
225-
const loading = document.getElementById('preview-loading');
226-
const container = document.getElementById('preview-viewer-container');
227-
const fallback = document.getElementById('preview-fallback');
228-
if (loading) loading.style.display = 'flex';
229-
if (container) { container.style.display = 'none'; container.innerHTML = ''; }
230-
if (fallback) fallback.style.display = 'none';
231-
}
232-
233-
function _showViewer() {
234-
const loading = document.getElementById('preview-loading');
235-
const container = document.getElementById('preview-viewer-container');
236-
const fallback = document.getElementById('preview-fallback');
237-
if (loading) loading.style.display = 'none';
238-
if (fallback) fallback.style.display = 'none';
239-
if (container) container.style.display = 'block';
240-
}
241-
242-
function _showFallback(id, msg) {
243-
const loading = document.getElementById('preview-loading');
244-
const container = document.getElementById('preview-viewer-container');
245-
const fallback = document.getElementById('preview-fallback');
246-
const msgEl = document.getElementById('preview-fallback-msg');
247-
const link = document.getElementById('preview-external-link');
248-
if (loading) loading.style.display = 'none';
249-
if (container) container.style.display = 'none';
250-
if (msgEl && msg) msgEl.textContent = msg;
251-
if (link) link.href = `https://books.google.com/books?id=${encodeURIComponent(id)}`;
252-
if (fallback) fallback.style.display = 'flex';
253-
}
254-
255-
function _close() {
256-
const modal = document.getElementById('book-preview-modal');
257-
const container = document.getElementById('preview-viewer-container');
258-
if (container) container.innerHTML = ''; // destroy iframe
259-
if (modal && modal.hasAttribute('open')) modal.close();
260-
document.body.style.overflow = '';
261-
}
262-
263-
// ── Viewer ─────────────────────────────────────────────────────────────────
264-
265-
function _renderViewer(id) {
266-
const container = document.getElementById('preview-viewer-container');
267-
if (!container) { _showFallback(id, 'Viewer container missing.'); return; }
268-
269-
if (!window.google?.books?.DefaultViewer) {
270-
_showFallback(id, 'The preview viewer could not be initialised.');
271-
return;
272-
}
273-
274-
// Hard timeout — show fallback if callbacks never fire
275-
const timeout = setTimeout(() => {
276-
_showFallback(id, 'The preview took too long to load. You can view it on Google Books instead.');
277-
}, 10000);
278-
279-
const viewer = new window.google.books.DefaultViewer(container);
280-
281-
viewer.load(
282-
id,
283-
// notFoundCallback — no embeddable preview for this book
284-
() => {
285-
clearTimeout(timeout);
286-
_showFallback(id, "This book doesn't have an embeddable preview. You can view it on Google Books instead.");
287-
},
288-
// successCallback — viewer rendered successfully
289-
() => {
290-
clearTimeout(timeout);
291-
_showViewer();
292-
}
293-
);
294-
}
295-
296-
// ── Public API ─────────────────────────────────────────────────────────────
297-
298-
/**
299-
* Open the in-app preview modal.
300-
* @param {string} googleBooksId
301-
* @param {string} [title]
302-
* @param {string} [author]
303-
* @param {number} [rating]
304-
* @param {string} [genre]
305-
*/
306-
307-
async function open(googleBooksId, title, author, rating, genre) {
308-
if (!_isValidId(googleBooksId)) {
309-
console.warn('[BookPreview] Invalid Google Books ID:', googleBooksId);
310-
return;
311-
}
312-
313-
const modal = _getOrCreateModal();
314-
315-
// Set title
316-
const titleEl = document.getElementById('preview-modal-title');
317-
if (titleEl) titleEl.textContent = title || 'Book Preview';
318-
319-
// populate the book card with real data after modal exists ──
320-
populateBookCard(title, author, rating, genre);
321-
322-
_setLoading();
323-
modal.showModal();
324-
document.body.style.overflow = 'hidden';
325-
326-
try {
327-
await _loadAPI();
328-
_renderViewer(googleBooksId);
329-
} catch (err) {
330-
console.error('[BookPreview] Error:', err);
331-
_showFallback(
332-
googleBooksId,
333-
'Something went wrong loading the preview. You can view this book on Google Books instead.'
334-
);
335-
}
336-
}
337-
338-
// populate hidden book card with current book's data
339-
function populateBookCard(title, author, rating, genre) {
340-
const titleEl = document.getElementById('card-title');
341-
const authorEl = document.getElementById('card-author');
342-
const ratingEl = document.getElementById('card-rating');
343-
const genreEl = document.getElementById('card-genre');
344-
if (titleEl) titleEl.textContent = title || '';
345-
if (authorEl) authorEl.textContent = author ? 'by ' + author : '';
346-
if (ratingEl) ratingEl.textContent = rating ? '★'.repeat(rating) + '☆'.repeat(5 - rating) : '';
347-
if (genreEl) genreEl.textContent = genre || '';
348-
}
349-
350-
return { open, populateBookCard };
351-
352-
})();
353-
354-
window.BookPreview = BookPreview;
212+
.catch(err => console.error(err))

‎frontend/js/community-stories.js‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ document.addEventListener('DOMContentLoaded', () => {
4949
}
5050
];
5151

52-
let stories = JSON.parse(localStorage.getItem('bibliodrift_community_stories')) || defaultStories;
52+
let stories = (() => { try { return JSON.parse(localStorage.getItem('bibliodrift_community_stories')) } catch { return null } })() || defaultStories;
5353

5454
// Save to local storage
5555
const saveStories = () => {

‎sw.js/sw.js‎

Lines changed: 1 addition & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -15,25 +15,4 @@ const ASSETS_TO_CACHE = [
1515
self.addEventListener('install', (event) => {
1616
event.waitUntil(
1717
caches.open(CACHE_NAME).then((cache) => {
18-
console.log('Caching essential UI sanctuary assets...');
19-
return cache.addAll(ASSETS_TO_CACHE);
20-
})
21-
);
22-
});
23-
24-
// Fetch Event: Cache-First strategy for core layout files
25-
self.addEventListener('fetch', (event) => {
26-
// Only intercept local GET requests
27-
if (event.request.method !== 'GET' || !event.request.url.startsWith(self.location.origin)) {
28-
return;
29-
}
30-
31-
event.respondWith(
32-
caches.match(event.request).then((cachedResponse) => {
33-
if (cachedResponse) {
34-
return cachedResponse; // Return local cache copy
35-
}
36-
return fetch(event.request); // Fallback to network
37-
})
38-
);
39-
});
18+
.catch(err => console.error(err))

0 commit comments

Comments
 (0)