Add new personalized home page shelves API endpoint

This commit is contained in:
advplyr 2023-08-02 18:29:28 -05:00
parent 7ec1d8ee5f
commit b9633691f4
5 changed files with 201 additions and 3 deletions

View file

@ -1,3 +1,4 @@
const Database = require('../../Database')
const libraryItemsBookFilters = require('./libraryItemsBookFilters')
const libraryItemsPodcastFilters = require('./libraryItemsPodcastFilters')
@ -30,6 +31,65 @@ module.exports = {
} else {
return libraryItemsPodcastFilters.getFilteredLibraryItems(library.id, userId, filterGroup, filterValue, sortBy, sortDesc, include, limit, offset)
}
},
async getLibraryItemsInProgress(library, userId, include, limit, ebook = false) {
if (library.mediaType === 'book') {
const filterValue = ebook ? 'ebook-in-progress' : 'audio-in-progress'
const { libraryItems, count } = await libraryItemsBookFilters.getFilteredLibraryItems(library.id, userId, 'progress', filterValue, 'progress', true, false, include, limit, 0)
return {
libraryItems: libraryItems.map(li => {
const oldLibraryItem = Database.models.libraryItem.getOldLibraryItem(li).toJSONMinified()
if (li.rssFeed) {
oldLibraryItem.rssFeed = Database.models.feed.getOldFeed(li.rssFeed).toJSONMinified()
}
return oldLibraryItem
}),
count
}
} else {
return {
count: 0,
libraryItems: []
}
}
},
async getLibraryItemsMostRecentlyAdded(library, userId, include, limit) {
if (library.mediaType === 'book') {
const { libraryItems, count } = await libraryItemsBookFilters.getFilteredLibraryItems(library.id, userId, null, null, 'addedAt', true, false, include, limit, 0)
return {
libraryItems: libraryItems.map(li => {
const oldLibraryItem = Database.models.libraryItem.getOldLibraryItem(li).toJSONMinified()
if (li.rssFeed) {
oldLibraryItem.rssFeed = Database.models.feed.getOldFeed(li.rssFeed).toJSONMinified()
}
if (li.size && !oldLibraryItem.media.size) {
oldLibraryItem.media.size = li.size
}
return oldLibraryItem
}),
count
}
} else {
const { libraryItems, count } = await libraryItemsPodcastFilters.getFilteredLibraryItems(library.id, userId, null, null, 'addedAt', true, include, limit, 0)
return {
libraryItems: libraryItems.map(li => {
const oldLibraryItem = Database.models.libraryItem.getOldLibraryItem(li).toJSONMinified()
if (li.rssFeed) {
oldLibraryItem.rssFeed = Database.models.feed.getOldFeed(li.rssFeed).toJSONMinified()
}
if (li.size && !oldLibraryItem.media.size) {
oldLibraryItem.media.size = li.size
}
return oldLibraryItem
}),
count
}
}
},
async getLibraryItemsContinueSeries(library, userId, include, limit) {
await libraryItemsBookFilters.getContinueSeriesLibraryItems(library.id, userId, limit, 0)
}
}

View file

@ -107,6 +107,28 @@ module.exports = {
'$mediaProgresses.isFinished$': false
}
]
} else if (value === 'audio-in-progress') {
mediaWhere[Sequelize.Op.and] = [
{
'$mediaProgresses.currentTime$': {
[Sequelize.Op.gt]: 0
}
},
{
'$mediaProgresses.isFinished$': false
}
]
} else if (value === 'ebook-in-progress') {
mediaWhere[Sequelize.Op.and] = [
{
'$mediaProgresses.ebookProgress$': {
[Sequelize.Op.gt]: 0
}
},
{
'$mediaProgresses.isFinished$': false
}
]
}
} else if (group === 'series' && value === 'no-series') {
mediaWhere['$series.id$'] = null
@ -194,6 +216,8 @@ module.exports = {
} else if (sortBy === 'sequence') {
const nullDir = sortDesc ? 'DESC NULLS FIRST' : 'ASC NULLS LAST'
return [[Sequelize.literal(`\`series.bookSeries.sequence\` COLLATE NOCASE ${nullDir}`)]]
} else if (sortBy === 'progress') {
return [[Sequelize.literal('mediaProgresses.updatedAt'), dir]]
}
return []
},
@ -275,6 +299,9 @@ module.exports = {
if (filterGroup !== 'series' && sortBy === 'sequence') {
sortBy = 'media.metadata.title'
}
if (filterGroup !== 'progress' && sortBy === 'progress') {
sortBy = 'media.metadata.title'
}
const includeRSSFeed = include.includes('rssfeed')
// For sorting by author name an additional attribute must be added
@ -398,7 +425,7 @@ module.exports = {
} else if (filterGroup === 'progress') {
bookIncludes.push({
model: Database.models.mediaProgress,
attributes: ['id', 'isFinished', 'currentTime', 'ebookProgress'],
attributes: ['id', 'isFinished', 'currentTime', 'ebookProgress', 'updatedAt'],
where: {
userId
},
@ -520,5 +547,52 @@ module.exports = {
libraryItems,
count
}
},
async getContinueSeriesLibraryItems(libraryId, userId, limit, offset) {
const { rows: series, count } = await Database.models.series.findAndCountAll({
where: [
Sequelize.where(Sequelize.literal(`(SELECT count(*) FROM books b, bookSeries bs, mediaProgresses mp WHERE mp.mediaItemId = b.id AND mp.userId = :userId AND bs.bookId = b.id AND bs.seriesId = series.id AND mp.isFinished = 1)`), {
[Sequelize.Op.gt]: 0
}),
Sequelize.where(Sequelize.literal(`(SELECT count(*) FROM books b, bookSeries bs, mediaProgresses mp WHERE mp.mediaItemId = b.id AND mp.userId = :userId AND bs.bookId = b.id AND bs.seriesId = series.id AND mp.isFinished = 0 AND mp.currentTime > 0)`), 0),
Sequelize.where(Sequelize.literal(`(SELECT count(*) FROM bookSeries bs LEFT OUTER JOIN mediaProgresses mp ON mp.userId = :userId AND mp.mediaItemId = bs.bookId WHERE bs.seriesId = series.id AND (mp.currentTime = 0 OR mp.currentTime IS NULL) AND (mp.isFinished = 0 OR mp.isFinished IS NULL))`), {
[Sequelize.Op.gt]: 0
})
],
replacements: {
userId
},
distinct: true,
include: [
{
model: Database.models.book,
through: {
attributes: ['sequence']
},
include: [
{
model: Database.models.libraryItem,
where: {
libraryId
}
},
{
model: Database.models.author,
attributes: ['id', 'name'],
through: {
attributes: []
}
}
]
}
],
order: [[Sequelize.literal(`\`books.bookSeries.sequence\` COLLATE NOCASE ASC NULLS LAST`)]],
subQuery: false,
limit,
offset
})
Logger.debug('Found', series.length, 'series to continue', 'total=', count)
}
}