Add Greatest of All Time manga dashboard
This commit is contained in:
1 parent
c8dd46d0fb
commit
5df94db9a3
16 files changed
+2717
-1
No files matched your search
@@ -14,6 +14,8 @@
|
||||
const http = require('http'), fs = require('fs'), path = require('path'), crypto = require('crypto');
|
||||
const { scanLibrary, scanChangedLibrary, libraryStamps, snapshotIndex, restoreIndex } = require('./library');
|
||||
const { Catalog, CatalogError, collectionViews, TYPES, ROLES } = require('./catalog');
|
||||
const { RATINGS: GREATEST_RATINGS, loadCatalog: loadGreatestCatalog, findOwned: findGreatestOwned,
|
||||
countsFor: greatestCounts, scoreFor: greatestScore } = require('./greatest');
|
||||
const { secret } = require('./runtime/config');
|
||||
const {
|
||||
applyPulse, applyVisit, chapterInsight, eligiblePages, emptyRecord, libraryInsight, mangaInsight, publicSummary,
|
||||
@@ -40,8 +42,10 @@ const MIME = {
|
||||
// ---------- storage: one JSON file, written atomically ----------
|
||||
fs.mkdirSync(DATA, { recursive: true });
|
||||
const catalog = new Catalog(DATA);
|
||||
const greatestCatalog = loadGreatestCatalog();
|
||||
const greatestById = new Map(greatestCatalog.entries.map(entry => [entry.id, entry]));
|
||||
const DB_FILE = path.join(DATA, 'db.json'), CACHE_FILE = path.join(DATA, 'scan-cache.json'), INDEX_FILE = path.join(DATA, 'library-index.json');
|
||||
const db = { users: {}, sessions: {}, progress: {}, reading: {}, follows: {}, notes: {}, votes: {}, known: {} };
|
||||
const db = { users: {}, sessions: {}, progress: {}, reading: {}, follows: {}, notes: {}, votes: {}, greatestRatings: {}, known: {} };
|
||||
// A corrupt db.json stops the server instead of silently starting empty and overwriting it.
|
||||
if (fs.existsSync(DB_FILE)) Object.assign(db, JSON.parse(fs.readFileSync(DB_FILE, 'utf8')));
|
||||
function writeAtomic(file, text) { fs.writeFileSync(file + '.tmp', text); fs.renameSync(file + '.tmp', file); }
|
||||
@@ -364,6 +368,36 @@ const routes = {
|
||||
};
|
||||
},
|
||||
|
||||
'GET /api/greatest': ({ u }) => ({
|
||||
title: greatestCatalog.title, updatedAt: greatestCatalog.updatedAt, periods: greatestCatalog.periods,
|
||||
ratings: GREATEST_RATINGS,
|
||||
entries: greatestCatalog.entries.map(entry => {
|
||||
const owned = findGreatestOwned(entry, lib.mangas);
|
||||
const counts = greatestCounts(entry.id, db.greatestRatings || {}, db.users);
|
||||
return {
|
||||
...entry,
|
||||
cover: owned?.cover ? url(owned.cover) : entry.cover,
|
||||
chapters: owned ? owned.chapters.length : entry.chapters,
|
||||
status: owned?.meta?.status || entry.status,
|
||||
library: owned ? { id: owned.id, chapters: owned.chapters.length } : null,
|
||||
myRating: db.greatestRatings?.[u.name]?.[entry.id] || null,
|
||||
votes: counts, score: greatestScore(counts),
|
||||
};
|
||||
}),
|
||||
}),
|
||||
'POST /api/greatest/rating': ({ u, b }) => {
|
||||
const id = String(b.id || '');
|
||||
if (!greatestById.has(id)) bad(404, 'Catalog entry not found');
|
||||
const rating = b.rating === null || b.rating === '' ? null : String(b.rating || '');
|
||||
if (rating !== null && !GREATEST_RATINGS.includes(rating)) bad(400, 'Unknown rating');
|
||||
const all = (db.greatestRatings = db.greatestRatings || {});
|
||||
const mine = (all[u.name] = all[u.name] || {});
|
||||
if (rating === null) delete mine[id]; else mine[id] = rating;
|
||||
save();
|
||||
const votes = greatestCounts(id, all, db.users);
|
||||
return { id, myRating: rating, votes, score: greatestScore(votes) };
|
||||
},
|
||||
|
||||
'GET /api/manga': ({ u, q }) => {
|
||||
const m = mangaOf(q.get('m')), prog = progressOf(u, m), showStory = settingsOf(u).readingStory;
|
||||
const records = mangaReadingOf(u, m);
|
||||
@@ -545,6 +579,7 @@ const routes = {
|
||||
const name = String(b.name || '');
|
||||
if (name === u.name) bad(400, "You can't delete your own account.");
|
||||
delete db.users[name]; delete db.progress[name]; delete db.reading[name]; delete db.follows[name]; delete db.notes[name];
|
||||
if (db.greatestRatings) delete db.greatestRatings[name];
|
||||
for (const [k, s] of Object.entries(db.sessions)) if (s.u === name) delete db.sessions[k];
|
||||
save();
|
||||
return { ok: true };
|
||||
|
||||
Reference in new issue
Block a user