mirror of
https://github.com/zoriya/Kyoo.git
synced 2025-07-09 03:04:20 -04:00
Creating views for library items
This commit is contained in:
parent
531abee95b
commit
0c537e1cc1
@ -75,6 +75,14 @@ namespace Kyoo
|
||||
/// </summary>
|
||||
public DbSet<WatchedEpisode> WatchedEpisodes { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The list of library items (shows and collections that are part of a library - or the global one)
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// This set is ready only, on most database this will be a view.
|
||||
/// </remarks>
|
||||
public DbSet<LibraryItem> LibraryItems { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Get all metadataIDs (ExternalIDs) of a given resource. See <see cref="MetadataID{T}"/>.
|
||||
/// </summary>
|
||||
@ -322,6 +330,8 @@ namespace Kyoo
|
||||
modelBuilder.Entity<Track>()
|
||||
.Property(x => x.Slug)
|
||||
.ValueGeneratedOnAddOrUpdate();
|
||||
|
||||
// modelBuilder.Ignore<LibraryItem>();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -74,6 +74,25 @@ namespace Kyoo.Postgresql.Migrations
|
||||
migrationBuilder.Sql(@"
|
||||
CREATE TRIGGER show_slug_trigger AFTER UPDATE OF slug ON shows
|
||||
FOR EACH ROW EXECUTE PROCEDURE show_slug_update();");
|
||||
|
||||
|
||||
// language=PostgreSQL
|
||||
migrationBuilder.Sql(@"
|
||||
CREATE VIEW library_items AS
|
||||
SELECT s.id, s.slug, s.title, s.overview, s.status, s.start_air, s.end_air, s.poster, CASE
|
||||
WHEN s.is_movie THEN 'movie'::item_type
|
||||
ELSE 'show'::item_type
|
||||
END AS type
|
||||
FROM shows AS s
|
||||
WHERE NOT (EXISTS (
|
||||
SELECT 1
|
||||
FROM link_collection_show AS l
|
||||
INNER JOIN collections AS c ON l.first_id = c.id
|
||||
WHERE s.id = l.second_id))
|
||||
UNION ALL
|
||||
SELECT -c0.id, c0.slug, c0.name AS title, c0.overview, 'unknown'::status AS status,
|
||||
NULL AS start_air, NULL AS end_air, c0.poster, 'collection'::item_type AS type
|
||||
FROM collections AS c0");
|
||||
}
|
||||
|
||||
protected override void Down(MigrationBuilder migrationBuilder)
|
||||
@ -90,6 +109,8 @@ namespace Kyoo.Postgresql.Migrations
|
||||
migrationBuilder.Sql("DROP TRIGGER episode_slug_trigger ON episodes;");
|
||||
// language=PostgreSQL
|
||||
migrationBuilder.Sql(@"DROP FUNCTION episode_slug_update;");
|
||||
// language=PostgreSQL
|
||||
migrationBuilder.Sql(@"DROP VIEW library_items;");
|
||||
}
|
||||
}
|
||||
}
|
@ -91,6 +91,10 @@ namespace Kyoo.Postgresql
|
||||
modelBuilder.HasPostgresEnum<ItemType>();
|
||||
modelBuilder.HasPostgresEnum<StreamType>();
|
||||
|
||||
modelBuilder.Entity<LibraryItem>()
|
||||
.ToView("library_items")
|
||||
.HasKey(x => x.ID);
|
||||
|
||||
modelBuilder.Entity<User>()
|
||||
.Property(x => x.ExtraData)
|
||||
.HasColumnType("jsonb");
|
||||
|
@ -61,6 +61,25 @@ namespace Kyoo.SqLite.Migrations
|
||||
END
|
||||
WHERE ShowID = new.ID;
|
||||
END;");
|
||||
|
||||
|
||||
// language=SQLite
|
||||
migrationBuilder.Sql(@"
|
||||
CREATE VIEW LibraryItems AS
|
||||
SELECT s.ID, s.Slug, s.Title, s.Overview, s.Status, s.StartAir, s.EndAir, s.Poster, CASE
|
||||
WHEN s.IsMovie THEN 1
|
||||
ELSE 0
|
||||
END AS Type
|
||||
FROM Shows AS s
|
||||
WHERE NOT (EXISTS (
|
||||
SELECT 1
|
||||
FROM 'Link<Collection, Show>' AS l
|
||||
INNER JOIN Collections AS c ON l.FirstID = c.ID
|
||||
WHERE s.ID = l.SecondID))
|
||||
UNION ALL
|
||||
SELECT -c0.ID, c0.Slug, c0.Name AS Title, c0.Overview, 3 AS Status,
|
||||
NULL AS StartAir, NULL AS EndAir, c0.Poster, 2 AS Type
|
||||
FROM collections AS c0");
|
||||
}
|
||||
|
||||
protected override void Down(MigrationBuilder migrationBuilder)
|
||||
|
@ -108,6 +108,10 @@ namespace Kyoo.SqLite
|
||||
modelBuilder.Entity<User>()
|
||||
.Property(x => x.ExtraData)
|
||||
.HasConversion(jsonConvertor);
|
||||
|
||||
modelBuilder.Entity<LibraryItem>()
|
||||
.ToView("LibraryItems")
|
||||
.HasKey(x => x.ID);
|
||||
base.OnModelCreating(modelBuilder);
|
||||
}
|
||||
|
||||
|
@ -30,9 +30,7 @@ namespace Kyoo.Tests
|
||||
ShowRepository show = new(_database, studio, people, genre, provider);
|
||||
SeasonRepository season = new(_database, provider);
|
||||
LibraryItemRepository libraryItem = new(_database,
|
||||
new Lazy<ILibraryRepository>(() => LibraryManager.LibraryRepository),
|
||||
new Lazy<IShowRepository>(() => LibraryManager.ShowRepository),
|
||||
new Lazy<ICollectionRepository>(() => LibraryManager.CollectionRepository));
|
||||
new Lazy<ILibraryRepository>(() => LibraryManager.LibraryRepository));
|
||||
TrackRepository track = new(_database);
|
||||
EpisodeRepository episode = new(_database, provider, track);
|
||||
|
||||
|
@ -22,14 +22,6 @@ namespace Kyoo.Controllers
|
||||
/// A lazy loaded library repository to validate queries (check if a library does exist)
|
||||
/// </summary>
|
||||
private readonly Lazy<ILibraryRepository> _libraries;
|
||||
/// <summary>
|
||||
/// A lazy loaded show repository to get a show from it's id.
|
||||
/// </summary>
|
||||
private readonly Lazy<IShowRepository> _shows;
|
||||
/// <summary>
|
||||
/// A lazy loaded collection repository to get a collection from it's id.
|
||||
/// </summary>
|
||||
private readonly Lazy<ICollectionRepository> _collections;
|
||||
|
||||
/// <inheritdoc />
|
||||
protected override Expression<Func<LibraryItem, object>> DefaultSort => x => x.Title;
|
||||
@ -38,60 +30,41 @@ namespace Kyoo.Controllers
|
||||
/// <summary>
|
||||
/// Create a new <see cref="LibraryItemRepository"/>.
|
||||
/// </summary>
|
||||
/// <param name="database">The databse instance</param>
|
||||
/// <param name="database">The database instance</param>
|
||||
/// <param name="libraries">A lazy loaded library repository</param>
|
||||
/// <param name="shows">A lazy loaded show repository</param>
|
||||
/// <param name="collections">A lazy loaded collection repository</param>
|
||||
public LibraryItemRepository(DatabaseContext database,
|
||||
Lazy<ILibraryRepository> libraries,
|
||||
Lazy<IShowRepository> shows,
|
||||
Lazy<ICollectionRepository> collections)
|
||||
Lazy<ILibraryRepository> libraries)
|
||||
: base(database)
|
||||
{
|
||||
_database = database;
|
||||
_libraries = libraries;
|
||||
_shows = shows;
|
||||
_collections = collections;
|
||||
}
|
||||
|
||||
|
||||
/// <inheritdoc />
|
||||
public override async Task<LibraryItem> GetOrDefault(int id)
|
||||
public override Task<LibraryItem> GetOrDefault(int id)
|
||||
{
|
||||
return id > 0
|
||||
? new LibraryItem(await _shows.Value.GetOrDefault(id))
|
||||
: new LibraryItem(await _collections.Value.GetOrDefault(-id));
|
||||
return _database.LibraryItems.FirstOrDefaultAsync(x => x.ID == id);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override Task<LibraryItem> GetOrDefault(string slug)
|
||||
{
|
||||
throw new InvalidOperationException("You can't get a library item by a slug.");
|
||||
return _database.LibraryItems.SingleOrDefaultAsync(x => x.Slug == slug);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Get a basic queryable with the right mapping from shows & collections.
|
||||
/// Shows contained in a collection are excluded.
|
||||
/// </summary>
|
||||
private IQueryable<LibraryItem> ItemsQuery
|
||||
=> _database.Shows
|
||||
.Where(x => !x.Collections.Any())
|
||||
.Select(LibraryItem.FromShow)
|
||||
.Concat(_database.Collections
|
||||
.Select(LibraryItem.FromCollection));
|
||||
|
||||
/// <inheritdoc />
|
||||
public override Task<ICollection<LibraryItem>> GetAll(Expression<Func<LibraryItem, bool>> where = null,
|
||||
Sort<LibraryItem> sort = default,
|
||||
Pagination limit = default)
|
||||
{
|
||||
return ApplyFilters(ItemsQuery, where, sort, limit);
|
||||
return ApplyFilters(_database.LibraryItems, where, sort, limit);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public override Task<int> GetCount(Expression<Func<LibraryItem, bool>> where = null)
|
||||
{
|
||||
IQueryable<LibraryItem> query = ItemsQuery;
|
||||
IQueryable<LibraryItem> query = _database.LibraryItems;
|
||||
if (where != null)
|
||||
query = query.Where(where);
|
||||
return query.CountAsync();
|
||||
@ -100,7 +73,7 @@ namespace Kyoo.Controllers
|
||||
/// <inheritdoc />
|
||||
public override async Task<ICollection<LibraryItem>> Search(string query)
|
||||
{
|
||||
return await ItemsQuery
|
||||
return await _database.LibraryItems
|
||||
.Where(_database.Like<LibraryItem>(x => x.Title, $"%{query}%"))
|
||||
.OrderBy(DefaultSort)
|
||||
.Take(20)
|
||||
@ -109,7 +82,6 @@ namespace Kyoo.Controllers
|
||||
|
||||
/// <inheritdoc />
|
||||
public override Task<LibraryItem> Create(LibraryItem obj) => throw new InvalidOperationException();
|
||||
|
||||
/// <inheritdoc />
|
||||
public override Task<LibraryItem> CreateIfNotExists(LibraryItem obj) => throw new InvalidOperationException();
|
||||
/// <inheritdoc />
|
||||
|
Loading…
x
Reference in New Issue
Block a user