Browse Source

Работа над opds

Book Pauk 2 năm trước cách đây
mục cha
commit
6a3b919f5f

+ 30 - 18
server/core/opds/AuthorPage.js

@@ -68,10 +68,12 @@ class AuthorPage extends BasePage {
         const query = {
             author: req.query.author || '',
             series: req.query.series || '',
+            genre: req.query.genre || '',
+            del: 0,
+            limit: 100,
+            
             all: req.query.all || '',
             depth: 0,
-            del: 0,
-            limit: 100
         };
         query.depth = query.author.length + 1;
 
@@ -91,6 +93,18 @@ class AuthorPage extends BasePage {
                 const filtered = (query.all ? books : this.filterBooks(books, query));
                 const sorted = this.sortSeriesBooks(filtered);
 
+                if (books.length > filtered.length) {
+                    entry.push(
+                        this.makeEntry({
+                            id: 'all_series_books',
+                            title: '[Все книги серии]',
+                            link: this.navLink({
+                                href: `/${this.id}?author=${encodeURIComponent(query.author)}` +
+                                    `&series=${encodeURIComponent(query.series)}&all=1`}),
+                        })
+                    );
+                }
+
                 for (const book of sorted) {
                     let title = `${book.serno ? `${book.serno}. `: ''}${book.title || 'Без названия'}`;
                     if (query.all) {
@@ -106,18 +120,6 @@ class AuthorPage extends BasePage {
                         })
                     );
                 }
-
-                if (books.length > filtered.length) {
-                    entry.push(
-                        this.makeEntry({
-                            id: 'all_series_books',
-                            title: 'Все книги серии',
-                            link: this.navLink({
-                                href: `/${this.id}?author=${encodeURIComponent(query.author)}` +
-                                    `&series=${encodeURIComponent(query.series)}&all=1`}),
-                        })
-                    );
-                }
             }
         } else if (query.author && query.author[0] == '=') {
             //книги по автору
@@ -135,7 +137,7 @@ class AuthorPage extends BasePage {
                                 title: `Серия: ${b.book.series}`,
                                 link: this.navLink({
                                     href: `/${this.id}?author=${encodeURIComponent(query.author)}` +
-                                        `&series=${encodeURIComponent(b.book.series)}`}),
+                                        `&series=${encodeURIComponent(b.book.series)}&genre=${encodeURIComponent(query.genre)}`}),
                             })
                         );
                     } else {
@@ -151,15 +153,25 @@ class AuthorPage extends BasePage {
                 }
             }
         } else {
-            //поиск по каталогу
-            const queryRes = await this.opdsQuery('author', query, 'Остальные авторы');
+            if (query.depth == 1 && !query.genre && !query.others) {
+                entry.push(
+                    this.makeEntry({
+                        id: 'select_genre',
+                        title: '[Выбрать жанр]',
+                        link: this.navLink({href: `/genre?from=${this.id}`}),
+                    })
+                );
+            }
+
+            //навигация по каталогу
+            const queryRes = await this.opdsQuery('author', query, '[Остальные авторы]');
 
             for (const rec of queryRes) {                
                 entry.push(
                     this.makeEntry({
                         id: rec.id,
                         title: this.bookAuthor(rec.title),//${(query.depth > 1 && rec.count ? ` (${rec.count})` : '')}
-                        link: this.navLink({href: `/${this.id}?author=${rec.q}`}),
+                        link: this.navLink({href: `/${this.id}?author=${rec.q}&genre=${encodeURIComponent(query.genre)}`}),
                     })
                 );
             }

+ 4 - 1
server/core/opds/BasePage.js

@@ -138,7 +138,7 @@ class BasePage {
         return result;
     }
 
-    async opdsQuery(from, query, otherTitle = 'Другие') {
+    async opdsQuery(from, query, otherTitle = '[Другие]') {
         const queryRes = await this.webWorker.opdsQuery(from, query);
         let count = 0;
         for (const row of queryRes.found)
@@ -302,9 +302,12 @@ class BasePage {
             result = {
                 genreTree: res.genreTree,
                 genreMap: new Map(),
+                genreSection: new Map(),
             };
 
             for (const section of result.genreTree) {
+                result.genreSection.set(section.name, section.value);
+
                 for (const g of section.value)
                     result.genreMap.set(g.value, g.name);
             }

+ 72 - 0
server/core/opds/GenrePage.js

@@ -0,0 +1,72 @@
+const BasePage = require('./BasePage');
+
+class GenrePage extends BasePage {
+    constructor(config) {
+        super(config);
+
+        this.id = 'genre';
+        this.title = 'Жанры';
+
+    }
+
+    async body(req) {
+        const result = {};
+
+        const query = {
+            from: req.query.from || '',
+            section: req.query.section || '',
+        };
+
+        const entry = [];
+        if (query.from) {
+
+            if (query.section) {
+                //выбираем подразделы
+                const {genreSection} = await this.getGenres();
+                const section = genreSection.get(query.section);
+
+                if (section) {
+                    let id = 0;
+                    const all = [];
+                    for (const g of section) {
+                        all.push(g.value);
+                        entry.push(
+                            this.makeEntry({
+                                id: ++id,
+                                title: g.name,
+                                link: this.navLink({href: `/${encodeURIComponent(query.from)}?genre=${encodeURIComponent(g.value)}`}),
+                            })
+                        );
+                    }
+
+                    entry.unshift(
+                        this.makeEntry({
+                            id: 'whole_section',
+                            title: '[Весь раздел]',
+                            link: this.navLink({href: `/${encodeURIComponent(query.from)}?genre=${encodeURIComponent(all.join(','))}`}),
+                        })
+                    );
+                }
+            } else {
+                //выбираем разделы
+                const {genreTree} = await this.getGenres();
+                let id = 0;
+                for (const section of genreTree) {
+                    entry.push(
+                        this.makeEntry({
+                            id: ++id,
+                            title: section.name,
+                            link: this.navLink({href: `/genre?from=${encodeURIComponent(query.from)}&section=${encodeURIComponent(section.name)}`}),
+                        })
+                    );
+                }
+            }
+        }
+
+        result.entry = entry;
+
+        return this.makeBody(result, req);
+    }
+}
+
+module.exports = GenrePage;

+ 3 - 0
server/core/opds/index.js

@@ -1,5 +1,6 @@
 const RootPage = require('./RootPage');
 const AuthorPage = require('./AuthorPage');
+const GenrePage = require('./GenrePage');
 const BookPage = require('./BookPage');
 
 module.exports = function(app, config) {
@@ -8,12 +9,14 @@ module.exports = function(app, config) {
 
     const root = new RootPage(config);
     const author = new AuthorPage(config);
+    const genre = new GenrePage(config);
     const book = new BookPage(config);
 
     const routes = [
         ['', root],
         ['/root', root],
         ['/author', author],
+        ['/genre', genre],
         ['/book', book],
     ];