尚未偵測到更新。GitHub 發布版本後會顯示在這裡。
個人 GitHub 帳號下公開儲存庫的擁有者可以登入並驗證所有權,自行管理介紹,無需管理員核准。
登入並產生驗證檔案,在 30 分鐘內將其提交至此儲存庫的預設分支。其他分支或分叉儲存庫中的檔案無效。然後在下方檢查檔案,即可無需管理員核准直接管理專案。請保留檔案以維持管理權限。
如需登入,將前往登入頁面。登入後請回到此處,再次點擊所選的驗證按鈕。
在專案資料夾中執行 /nomorevibe verify,即可驗證所有權並自行管理介紹。
一分鐘完成驗證正在載入完整 README。 以下為已儲存的摘錄。
🇪🇸 Español (este documento) · 🇬🇧 English Tu biblioteca personal: lo que has leído, lo que estás leyendo, lo que quieres leer y lo que quieres comprar — con progreso por páginas, tus propias categorías, reseñas, estadísticas y un feed de lo que lee la gente que sigues. 🔗 Probar Shelfy — cuenta de prueba ya cargada con libros, categorías y reseñas: [email protected] / shelfy123 (o regístrate gratis en unos segundos). El backend está en el plan gratuito de Render: si lleva un rato dormido, la primera petición puede tardar hasta un minuto en despertar. Es normal, no un error.檢視完整 README ↗
🇪🇸 Español (este documento) · 🇬🇧 English
Tu biblioteca personal: lo que has leído, lo que estás leyendo, lo que quieres leer y lo que quieres comprar — con progreso por páginas, tus propias categorías, reseñas, estadísticas y un feed de lo que lee la gente que sigues.
🔗 Probar Shelfy — cuenta de prueba ya cargada con libros, categorías y reseñas: [email protected] / shelfy123 (o regístrate gratis en unos segundos).
El backend está en el plan gratuito de Render: si lleva un rato dormido, la primera petición puede tardar hasta un minuto en despertar. Es normal, no un error.
Shelfy es una aplicación fullstack de biblioteca personal: cada usuario gestiona sus propios libros, categorías, reseñas y notas, en su propio idioma y con el tema que prefiera. También tiene una capa social opcional — buscar a otros usuarios por alias, seguirlos para ver su biblioteca y sus reseñas, recibir una notificación cuando alguien te sigue, y un feed con lo último que ha leído o reseñado la gente que sigues —, pensada como un vistazo tipo Goodreads/Leero sin perder el control de quién ve qué: sin seguidor, nada es visible.
Este repositorio es el frontend (Angular). El backend (API REST en Spring Boot) vive en shelfy-backend.
/people./feed): lo último que ha empezado, terminado o reseñado la gente que sigues.| Frontend | Angular 22 · standalone components, sin NgModule · TypeScript estricto · ngx-translate |
| Backend | Spring Boot 3.5 · Java 21 · Spring Data JPA · Spring Security con JWT |
| Base de datos | PostgreSQL (Neon) |
| Despliegue | Vercel (frontend) · Render (backend, Docker) — ambos con Infrastructure as Code (vercel.json, render.yaml) |
Algunas decisiones concretas, por si son de interés:
loadComponent en cada ruta) para no inflar el bundle inicial — ver app.routes.ts.404, no 403, para no filtrar que ese recurso existe.localStorage (antes del primer render) y se sincronizan con la cuenta vía PATCH /api/users/me/preferences si hay sesión iniciada.AuthService, ThemeService, LanguageService...), sin librerías externas de estado.BookLookupService llama a Open Library con fetch directamente (no HttpClient), para no arrastrar el interceptor que añade el JWT de la app a toda petición saliente.Intl.DateTimeFormat directamente con el idioma de LanguageService, en vez de registrar LOCALE_ID/registerLocaleData solo para eso.propio || le sigue) y el frontend simplemente pinta lo que reciba (biblioteca completa o página bloqueada).localStorage: la vista de libros (Tarjetas/Estantería) no se guarda en la cuenta como el tema o el idioma — es una comodidad de "cómo lo veo aquí", no algo que tenga sentido sincronizar entre dispositivos.npm install
npm start
Necesita el backend corriendo en http://localhost:8080 — ver shelfy-backend para levantarlo con datos de ejemplo en un solo comando.
La URL del backend se fija en tiempo de build, no por variable de entorno:
| Fichero | Se usa con | apiUrl |
|---|---|---|
src/environments/environment.ts | npm start | http://localhost:8080/api |
src/environments/environment.prod.ts | npm run build | el backend en Render |
Búsqueda por Google Books (opcional): la pestaña "Google Books (España)" del buscador de libros solo aparece si hay una clave configurada — sin ella, la app funciona igual, solo con Open Library. Para activarla:
https://shelfy-reads.vercel.app/*) — es una clave que viaja al navegador, así que restringirla
evita que otra web la use en tu cuota.GOOGLE_BOOKS_API_KEY con esa
clave (entorno Production) y vuelve a desplegar.npm run build la inyecta en environment.prod.ts en tiempo de compilación
(scripts/set-env.js, vía el hook prebuild de npm) — la clave nunca se guarda en el repo, solo
en la variable de entorno de Vercel. La cuota gratuita de Google (1000 peticiones/día) es de sobra
para uso personal.
en / ca / es, textos en src/assets/i18n/*.json, gestionados con LanguageService.data-theme en <html> desde ThemeService (CSS custom properties en src/styles/_tokens.scss)./settings), la única pantalla donde se puede elegir explícitamente "según el sistema".src/app/
├── core/ servicios, modelos, guards e interceptores HTTP compartidos
├── layout/ cabecera (con notificaciones) y pie de la aplicación
├── shared/ componentes reutilizables (tarjetas, badges, spinner, toasts…)
└── features/
├── auth/ login, registro, verificación de email, recuperar contraseña
├── books/ listado, detalle, formulario, reseñas, notas y recomendaciones
├── categories/ gestión de categorías propias
├── feed/ actividad de la gente que sigues
├── people/ buscar usuarios, perfil público y seguir
├── stats/ estadísticas, calendario, objetivo de lectura y detalle por mes
└── settings/ ajustes de cuenta, tema, idioma e importar/exportar CSV
Vercel (recomendado para el frontend): el repo incluye vercel.json ya
configurado — en el dashboard, Add New → Project → importa este repositorio y despliega, sin
tocar nada más. Solo hay que mantener apiUrl en environment.prod.ts apuntando al backend, y
CORS_ALLOWED_ORIGINS en el backend apuntando a la URL que dé Vercel.
Render (alternativa): el repo también incluye render.yaml para desplegarlo
como Static Site vía Blueprint (New → Blueprint), con el build command y el publish directory
ya rellenos.
Shelfy es una PWA (ngsw-config.json, public/manifest.webmanifest): se puede instalar desde el
navegador tanto en el móvil como en el escritorio, con funcionamiento offline básico. Además, el
mismo frontend se envuelve como app Android nativa vía TWA (Trusted Web Activity, con
Bubblewrap) sin tocar el backend ni el código
Angular — ver shelfy-android.
🇪🇸 Español · 🇬🇧 English (this document)
Your personal library: what you've read, what you're reading, what you want to read and what you want to buy — with page progress, your own categories, reviews, stats and a feed of what the people you follow are reading.
🔗 Try Shelfy — a demo account is already loaded with
books, categories and reviews: [email protected] / shelfy123 (or sign up for free in a few
seconds).
The backend runs on Render's free plan: if it's been asleep for a while, the first request can take up to a minute to wake up. That's expected, not an error.
Shelfy is a fullstack personal-library app: each user manages their own books, categories, reviews and notes, in their own language and with the theme they prefer. It also has an optional social layer — search other users by alias, follow them to see their library and reviews, get a notification when someone follows you, and a feed of what the people you follow have recently read or reviewed —, meant as a Goodreads/Leero-style glance without losing control of who sees what: with no follower, nothing is visible.
This repository is the frontend (Angular). The backend (Spring Boot REST API) lives in shelfy-backend.
/people./feed): the latest books the people you follow have started, finished or reviewed.| Frontend | Angular 22 · standalone components, no NgModule · strict TypeScript · ngx-translate |
| Backend | Spring Boot 3.5 · Java 21 · Spring Data JPA · Spring Security with JWT |
| Database | PostgreSQL (Neon) |
| Deployment | Vercel (frontend) · Render (backend, Docker) — both with Infrastructure as Code (vercel.json, render.yaml) |
Some specific decisions, in case they're of interest:
loadComponent on every route) to keep the initial bundle small — see app.routes.ts.404, not 403, so as not to leak that it exists.localStorage (before the first render) and synced to the account via PATCH /api/users/me/preferences when there's a session.AuthService, ThemeService, LanguageService...), with no external state libraries.BookLookupService calls Open Library directly with fetch (not HttpClient), to avoid dragging in the interceptor that adds the app's JWT to every outgoing request.Intl.DateTimeFormat directly with LanguageService's language, instead of registering LOCALE_ID/registerLocaleData just for that.own || follows them) and the frontend just renders whatever it gets back (full library or a blocked page).localStorage: the book view (Cards/Shelf) isn't saved to the account like the theme or language — it's a "how I see it here" convenience, not something that makes sense to sync across devices.npm install
npm start
Needs the backend running at http://localhost:8080 — see
shelfy-backend to start it with
sample data in a single command.
The backend URL is fixed at build time, not via an environment variable:
| File | Used with | apiUrl |
|---|---|---|
src/environments/environment.ts | npm start | http://localhost:8080/api |
src/environments/environment.prod.ts | npm run build | the backend on Render |
Google Books search (optional): the "Google Books (Spain)" tab in the book search only shows up if a key is configured — without it, the app works the same, just with Open Library only. To enable it:
https://shelfy-reads.vercel.app/*) — it's a key that travels to the browser, so restricting
it keeps others from using it against your quota.GOOGLE_BOOKS_API_KEY with that
key (Production environment) and redeploy.npm run build injects it into environment.prod.ts at build time (scripts/set-env.js, via
npm's prebuild hook) — the key is never stored in the repo, only in Vercel's environment
variable. Google's free quota (1000 requests/day) is plenty for personal use.
en / ca / es, text in src/assets/i18n/*.json, managed by LanguageService.data-theme on <html> from ThemeService (CSS custom properties in src/styles/_tokens.scss)./settings), the only screen where you can explicitly choose "system".src/app/
├── core/ shared services, models, guards and HTTP interceptors
├── layout/ app header (with notifications) and footer
├── shared/ reusable components (cards, badges, spinner, toasts…)
└── features/
├── auth/ login, registration, email verification, password recovery
├── books/ list, detail, form, reviews, notes and recommendations
├── categories/ managing your own categories
├── feed/ activity from the people you follow
├── people/ search users, public profile and following
├── stats/ stats, calendar, reading goal and per-month detail
└── settings/ account settings, theme, language and CSV import/export
Vercel (recommended for the frontend): the repo includes an already-configured
vercel.json — in the dashboard, Add New → Project → import this repository
and deploy, no other changes needed. You just need to keep apiUrl in environment.prod.ts
pointing at the backend, and CORS_ALLOWED_ORIGINS on the backend pointing at whatever URL
Vercel gives you.
Render (alternative): the repo also includes render.yaml to deploy it as a
Static Site via Blueprint (New → Blueprint), with the build command and publish directory
already filled in.
Shelfy is a PWA (ngsw-config.json, public/manifest.webmanifest): it can be installed from the
browser on both mobile and desktop, with basic offline support. On top of that, the same frontend
is wrapped as a native Android app via TWA (Trusted Web Activity, with
Bubblewrap) without touching the backend or the
Angular code — see shelfy-android.