浏览代码

Работа над opds

Book Pauk 2 年之前
父节点
当前提交
fd9bc45fb1
共有 5 个文件被更改,包括 130 次插入10 次删除
  1. 1 10
      server/core/opds/AuthorPage.js
  2. 9 0
      server/core/opds/BasePage.js
  3. 3 0
      server/core/opds/RootPage.js
  4. 114 0
      server/core/opds/SeriesPage.js
  5. 3 0
      server/core/opds/index.js

+ 1 - 10
server/core/opds/AuthorPage.js

@@ -8,15 +8,6 @@ class AuthorPage extends BasePage {
         this.title = 'Авторы';
     }
 
-    bookAuthor(author) {
-        if (author) {
-            let a = author.split(',');
-            return a.slice(0, 3).join(', ') + (a.length > 3 ? ' и др.' : '');
-        }
-
-        return '';
-    }
-
     sortBooks(bookList) {
         //схлопывание серий
         const books = [];
@@ -175,7 +166,7 @@ class AuthorPage extends BasePage {
                 entry.push(
                     this.makeEntry({
                         id: rec.id,
-                        title: this.bookAuthor(rec.title),//${(query.depth > 1 && rec.count ? ` (${rec.count})` : '')}
+                        title: this.bookAuthor(rec.title),
                         link: this.navLink({href: `/${this.id}?author=${rec.q}&genre=${encodeURIComponent(query.genre)}`}),
                     })
                 );

+ 9 - 0
server/core/opds/BasePage.js

@@ -298,6 +298,15 @@ class BasePage {
         });
     }
 
+    bookAuthor(author) {
+        if (author) {
+            let a = author.split(',');
+            return a.slice(0, 3).join(', ') + (a.length > 3 ? ' и др.' : '');
+        }
+
+        return '';
+    }
+
     async getGenres() {
         let result;
         if (!this.genres) {

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

@@ -1,5 +1,6 @@
 const BasePage = require('./BasePage');
 const AuthorPage = require('./AuthorPage');
+const SeriesPage = require('./SeriesPage');
 
 class RootPage extends BasePage {
     constructor(config) {
@@ -9,6 +10,7 @@ class RootPage extends BasePage {
         this.title = '';
 
         this.authorPage = new AuthorPage(config);
+        this.seriesPage = new SeriesPage(config);
     }
 
     async body(req) {
@@ -24,6 +26,7 @@ class RootPage extends BasePage {
 
         result.entry = [
             this.authorPage.myEntry(),
+            this.seriesPage.myEntry(),
         ];
 
         return this.makeBody(result, req);

+ 114 - 0
server/core/opds/SeriesPage.js

@@ -0,0 +1,114 @@
+const BasePage = require('./BasePage');
+
+class SeriesPage extends BasePage {
+    constructor(config) {
+        super(config);
+
+        this.id = 'series';
+        this.title = 'Серии';
+    }
+
+    sortSeriesBooks(seriesBooks) {
+        seriesBooks.sort((a, b) => {
+            const dserno = (a.serno || Number.MAX_VALUE) - (b.serno || Number.MAX_VALUE);
+            const dtitle = a.title.localeCompare(b.title);
+            const dext = a.ext.localeCompare(b.ext);
+            return (dserno ? dserno : (dtitle ? dtitle : dext));        
+        });
+
+        return seriesBooks;
+    }
+
+    async body(req) {
+        const result = {};
+
+        const query = {
+            series: req.query.series || '',
+            genre: req.query.genre || '',
+            del: 0,
+            
+            all: req.query.all || '',
+            depth: 0,
+        };
+        query.depth = query.series.length + 1;
+
+        if (query.series == '___others') {
+            query.series = '';
+            query.depth = 1;
+            query.others = true;
+        }
+
+        const entry = [];
+        if (query.series && query.series[0] == '=') {
+            //книги по серии
+            const bookList = await this.webWorker.getSeriesBookList(query.series.substring(1));
+
+            if (bookList.books) {
+                let books = JSON.parse(bookList.books);
+                const booksAll = this.filterBooks(books, {del: 0});
+                const filtered = (query.all ? booksAll : this.filterBooks(books, query));
+                const sorted = this.sortSeriesBooks(filtered);
+
+                if (booksAll.length > filtered.length) {
+                    entry.push(
+                        this.makeEntry({
+                            id: 'all_series_books',
+                            title: '[Все книги серии]',
+                            link: this.navLink({
+                                href: `/${this.id}?series=${encodeURIComponent(query.series)}&all=1`}),
+                        })
+                    );
+                }
+
+                for (const book of sorted) {
+                    const title = `${book.serno ? `${book.serno}. `: ''}${book.title || 'Без названия'} (${book.ext})`;
+
+                    const e = {
+                        id: book._uid,
+                        title,
+                        link: this.acqLink({href: `/book?uid=${encodeURIComponent(book._uid)}`}),
+                    };
+
+                    if (query.all) {
+                        e.content = {
+                            '*ATTRS': {type: 'text'},
+                            '*TEXT': this.bookAuthor(book.author),
+                        }
+                    }
+
+                    entry.push(
+                        this.makeEntry(e)
+                    );
+                }
+            }
+        } else {
+            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('series', query, '[Остальные серии]');
+
+            for (const rec of queryRes) {                
+                entry.push(
+                    this.makeEntry({
+                        id: rec.id,
+                        title: rec.title,
+                        link: this.navLink({href: `/${this.id}?series=${rec.q}&genre=${encodeURIComponent(query.genre)}`}),
+                    })
+                );
+            }
+        }
+
+        result.entry = entry;
+        return this.makeBody(result, req);
+    }
+}
+
+module.exports = SeriesPage;

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

@@ -1,5 +1,6 @@
 const RootPage = require('./RootPage');
 const AuthorPage = require('./AuthorPage');
+const SeriesPage = require('./SeriesPage');
 const GenrePage = require('./GenrePage');
 const BookPage = require('./BookPage');
 
@@ -9,6 +10,7 @@ module.exports = function(app, config) {
 
     const root = new RootPage(config);
     const author = new AuthorPage(config);
+    const series = new SeriesPage(config);
     const genre = new GenrePage(config);
     const book = new BookPage(config);
 
@@ -16,6 +18,7 @@ module.exports = function(app, config) {
         ['', root],
         ['/root', root],
         ['/author', author],
+        ['/series', series],
         ['/genre', genre],
         ['/book', book],
     ];