Spaces:
Sleeping
Sleeping
Download frontend/src/App.js from vishalharkal/BookMind: direct link, hf CLI and curl.
- Browser
- Download file 3.79 kB
-
https://huggingface.co/spaces/vishalharkal/BookMind/resolve/main/frontend/src/App.js
- Command line
-
hf download hf://spaces/vishalharkal/BookMind/frontend/src/App.js
-
curl -L -o App.js https://huggingface.co/spaces/vishalharkal/BookMind/resolve/main/frontend/src/App.js
3.79 kB
| import React, { useState, useEffect } from 'react'; | |
| import Background from './components/Background'; | |
| import HomeView from './views/HomeView'; | |
| import ResultsView from './views/ResultsView'; | |
| import FavoritesView from './views/FavoritesView'; | |
| import BookDetailsModal from './components/BookDetailsModal'; | |
| import Footer from './components/Footer'; | |
| function App() { | |
| const [popularBooks, setPopularBooks] = useState([]); | |
| const [recommendations, setRecommendations] = useState([]); | |
| const [selectedBook, setSelectedBook] = useState(null); | |
| const [loading, setLoading] = useState(false); | |
| const [view, setView] = useState('home'); // 'home' or 'results' or 'favorites' | |
| const [method, setMethod] = useState('hybrid'); | |
| const [bookTitle, setBookTitle] = useState(''); | |
| const [modalBook, setModalBook] = useState(null); // For book details modal | |
| const [isModalOpen, setIsModalOpen] = useState(false); | |
| useEffect(() => { | |
| fetch('/api/popular') | |
| .then(res => res.json()) | |
| .then(data => setPopularBooks(data)) | |
| .catch(err => console.error(err)); | |
| }, []); | |
| const handleRecommend = async (title, selectedMethod) => { | |
| setLoading(true); | |
| setMethod(selectedMethod); | |
| setBookTitle(title); | |
| try { | |
| const formData = new FormData(); | |
| formData.append('book_title', title); | |
| formData.append('method', selectedMethod); | |
| const resp = await fetch('/api/recommend', { | |
| method: 'POST', | |
| body: formData, | |
| }); | |
| const data = await resp.json(); | |
| setRecommendations(data.recommendations); | |
| setSelectedBook(data.selected_book); | |
| setView('results'); | |
| window.scrollTo({ top: 0, behavior: 'smooth' }); | |
| } catch (err) { | |
| console.error(err); | |
| } finally { | |
| setLoading(false); | |
| } | |
| }; | |
| const handleBack = () => { | |
| setView('home'); | |
| setRecommendations([]); | |
| setSelectedBook(null); | |
| window.scrollTo({ top: 0, behavior: 'smooth' }); | |
| }; | |
| const handleViewDetails = (book) => { | |
| setModalBook(book); | |
| setIsModalOpen(true); | |
| }; | |
| const handleCloseModal = () => { | |
| setIsModalOpen(false); | |
| setModalBook(null); | |
| }; | |
| return ( | |
| <div className="relative min-h-screen text-text-primary bg-bg-body font-inter selection:bg-accent/30"> | |
| <Background /> | |
| {loading && ( | |
| <div className="fixed inset-0 z-[100] bg-white/60 backdrop-blur-sm flex items-center justify-center"> | |
| <div className="flex flex-col items-center gap-4"> | |
| <span className="loading loading-spinner loading-lg text-accent"></span> | |
| <p className="text-accent font-bold animate-pulse uppercase tracking-widest text-xs">Finding matches...</p> | |
| </div> | |
| </div> | |
| )} | |
| <main className="relative z-10"> | |
| {view === 'home' ? ( | |
| <HomeView | |
| popularBooks={popularBooks} | |
| onRecommend={handleRecommend} | |
| onViewDetails={handleViewDetails} | |
| onViewFavorites={() => setView('favorites')} | |
| /> | |
| ) : view === 'favorites' ? ( | |
| <FavoritesView | |
| onRecommend={handleRecommend} | |
| onViewDetails={handleViewDetails} | |
| onBack={() => setView('home')} | |
| /> | |
| ) : ( | |
| <ResultsView | |
| bookTitle={bookTitle} | |
| selectedBook={selectedBook} | |
| recommendations={recommendations} | |
| method={method} | |
| onBack={handleBack} | |
| onRecommend={handleRecommend} | |
| onViewDetails={handleViewDetails} | |
| /> | |
| )} | |
| </main> | |
| {isModalOpen && modalBook && ( | |
| <BookDetailsModal | |
| book={modalBook} | |
| onClose={handleCloseModal} | |
| onRecommend={handleRecommend} | |
| /> | |
| )} | |
| <Footer /> | |
| </div> | |
| ); | |
| } | |
| export default App; | |