mirror of
https://github.com/zoriya/Kyoo.git
synced 2025-05-24 02:02:36 -04:00
Updating the search api
This commit is contained in:
parent
6a0fb2dd38
commit
2df3562045
@ -292,6 +292,26 @@ namespace Kyoo.Controllers
|
||||
Expression<Func<Library, object>> sort,
|
||||
Pagination limit = default
|
||||
) => GetLibrariesFromCollection(slug, where, new Sort<Library>(sort), limit);
|
||||
|
||||
Task<ICollection<ShowRole>> GetRolesFromPeople(int showID,
|
||||
Expression<Func<ShowRole, bool>> where = null,
|
||||
Sort<ShowRole> sort = default,
|
||||
Pagination limit = default);
|
||||
Task<ICollection<ShowRole>> GetRolesFromPeople(int showID,
|
||||
[Optional] Expression<Func<ShowRole, bool>> where,
|
||||
Expression<Func<ShowRole, object>> sort,
|
||||
Pagination limit = default
|
||||
) => GetRolesFromPeople(showID, where, new Sort<ShowRole>(sort), limit);
|
||||
|
||||
Task<ICollection<ShowRole>> GetRolesFromPeople(string showSlug,
|
||||
Expression<Func<ShowRole, bool>> where = null,
|
||||
Sort<ShowRole> sort = default,
|
||||
Pagination limit = default);
|
||||
Task<ICollection<ShowRole>> GetRolesFromPeople(string showSlug,
|
||||
[Optional] Expression<Func<ShowRole, bool>> where,
|
||||
Expression<Func<ShowRole, object>> sort,
|
||||
Pagination limit = default
|
||||
) => GetRolesFromPeople(showSlug, where, new Sort<ShowRole>(sort), limit);
|
||||
|
||||
|
||||
// Helpers
|
||||
|
@ -395,6 +395,26 @@ namespace Kyoo.Controllers
|
||||
Expression<Func<PeopleLink, object>> sort,
|
||||
Pagination limit = default
|
||||
) => GetFromShow(showSlug, where, new Sort<PeopleLink>(sort), limit);
|
||||
|
||||
Task<ICollection<ShowRole>> GetFromPeople(int showID,
|
||||
Expression<Func<ShowRole, bool>> where = null,
|
||||
Sort<ShowRole> sort = default,
|
||||
Pagination limit = default);
|
||||
Task<ICollection<ShowRole>> GetFromPeople(int showID,
|
||||
[Optional] Expression<Func<ShowRole, bool>> where,
|
||||
Expression<Func<ShowRole, object>> sort,
|
||||
Pagination limit = default
|
||||
) => GetFromPeople(showID, where, new Sort<ShowRole>(sort), limit);
|
||||
|
||||
Task<ICollection<ShowRole>> GetFromPeople(string showSlug,
|
||||
Expression<Func<ShowRole, bool>> where = null,
|
||||
Sort<ShowRole> sort = default,
|
||||
Pagination limit = default);
|
||||
Task<ICollection<ShowRole>> GetFromPeople(string showSlug,
|
||||
[Optional] Expression<Func<ShowRole, bool>> where,
|
||||
Expression<Func<ShowRole, object>> sort,
|
||||
Pagination limit = default
|
||||
) => GetFromPeople(showSlug, where, new Sort<ShowRole>(sort), limit);
|
||||
}
|
||||
public interface IProviderRepository : IRepository<ProviderID> {}
|
||||
}
|
@ -411,6 +411,22 @@ namespace Kyoo.Controllers
|
||||
{
|
||||
return LibraryRepository.GetFromCollection(slug, where, sort, limit);
|
||||
}
|
||||
|
||||
public Task<ICollection<ShowRole>> GetRolesFromPeople(int id,
|
||||
Expression<Func<ShowRole, bool>> where = null,
|
||||
Sort<ShowRole> sort = default,
|
||||
Pagination limit = default)
|
||||
{
|
||||
return PeopleRepository.GetFromPeople(id, where, sort, limit);
|
||||
}
|
||||
|
||||
public Task<ICollection<ShowRole>> GetRolesFromPeople(string slug,
|
||||
Expression<Func<ShowRole, bool>> where = null,
|
||||
Sort<ShowRole> sort = default,
|
||||
Pagination limit = default)
|
||||
{
|
||||
return PeopleRepository.GetFromPeople(slug, where, sort, limit);
|
||||
}
|
||||
|
||||
public Task AddShowLink(int showID, int? libraryID, int? collectionID)
|
||||
{
|
||||
|
@ -1,4 +1,6 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq.Expressions;
|
||||
using Newtonsoft.Json;
|
||||
|
||||
namespace Kyoo.Models
|
||||
@ -21,6 +23,12 @@ namespace Kyoo.Models
|
||||
set => People.Name = value;
|
||||
}
|
||||
|
||||
public string Poster
|
||||
{
|
||||
get => People.Poster;
|
||||
set => People.Poster = value;
|
||||
}
|
||||
|
||||
public IEnumerable<MetadataID> ExternalIDs
|
||||
{
|
||||
get => People.ExternalIDs;
|
||||
@ -42,11 +50,79 @@ namespace Kyoo.Models
|
||||
Type = type;
|
||||
}
|
||||
|
||||
public PeopleLink(string slug, string name, string role, string type, string imgPrimary, IEnumerable<MetadataID> externalIDs)
|
||||
public PeopleLink(string slug,
|
||||
string name,
|
||||
string role,
|
||||
string type,
|
||||
string poster,
|
||||
IEnumerable<MetadataID> externalIDs)
|
||||
{
|
||||
People = new People(slug, name, imgPrimary, externalIDs);
|
||||
People = new People(slug, name, poster, externalIDs);
|
||||
Role = role;
|
||||
Type = type;
|
||||
}
|
||||
}
|
||||
|
||||
public class ShowRole : IResource
|
||||
{
|
||||
public int ID { get; set; }
|
||||
public string Role { get; set; }
|
||||
public string Type { get; set; }
|
||||
|
||||
public string Slug { get; set; }
|
||||
public string Title { get; set; }
|
||||
public IEnumerable<string> Aliases { get; set; }
|
||||
[JsonIgnore] public string Path { get; set; }
|
||||
public string Overview { get; set; }
|
||||
public Status? Status { get; set; }
|
||||
public string TrailerUrl { get; set; }
|
||||
public int? StartYear { get; set; }
|
||||
public int? EndYear { get; set; }
|
||||
public string Poster { get; set; }
|
||||
public string Logo { get; set; }
|
||||
public string Backdrop { get; set; }
|
||||
public bool IsMovie { get; set; }
|
||||
|
||||
public ShowRole() {}
|
||||
|
||||
public ShowRole(PeopleLink x)
|
||||
{
|
||||
ID = x.ID;
|
||||
Role = x.Role;
|
||||
Type = x.Type;
|
||||
Slug = x.Show.Slug;
|
||||
Title = x.Show.Title;
|
||||
Aliases = x.Show.Aliases;
|
||||
Path = x.Show.Path;
|
||||
Overview = x.Show.Overview;
|
||||
Status = x.Show.Status;
|
||||
TrailerUrl = x.Show.TrailerUrl;
|
||||
StartYear = x.Show.StartYear;
|
||||
EndYear = x.Show.EndYear;
|
||||
Poster = x.Show.Poster;
|
||||
Logo = x.Show.Logo;
|
||||
Backdrop = x.Show.Backdrop;
|
||||
IsMovie = x.Show.IsMovie;
|
||||
}
|
||||
|
||||
public static Expression<Func<PeopleLink, ShowRole>> FromPeopleRole => x => new ShowRole
|
||||
{
|
||||
ID = x.ID,
|
||||
Role = x.Role,
|
||||
Type = x.Type,
|
||||
Slug = x.Show.Slug,
|
||||
Title = x.Show.Title,
|
||||
Aliases = x.Show.Aliases,
|
||||
Path = x.Show.Path,
|
||||
Overview = x.Show.Overview,
|
||||
Status = x.Show.Status,
|
||||
TrailerUrl = x.Show.TrailerUrl,
|
||||
StartYear = x.Show.StartYear,
|
||||
EndYear = x.Show.EndYear,
|
||||
Poster = x.Show.Poster,
|
||||
Logo = x.Show.Logo,
|
||||
Backdrop = x.Show.Backdrop,
|
||||
IsMovie = x.Show.IsMovie
|
||||
};
|
||||
}
|
||||
}
|
@ -13,7 +13,7 @@ namespace Kyoo.Models
|
||||
public string Poster { get; set; }
|
||||
public string Overview { get; set; }
|
||||
[NotMergable] [JsonIgnore] public virtual IEnumerable<CollectionLink> Links { get; set; }
|
||||
public virtual IEnumerable<Show> Shows
|
||||
[JsonIgnore] public virtual IEnumerable<Show> Shows
|
||||
{
|
||||
get => Links.Select(x => x.Show);
|
||||
set => Links = value.Select(x => new CollectionLink(this, x));
|
||||
|
@ -9,18 +9,18 @@ namespace Kyoo.Models
|
||||
public int ID { get; set; }
|
||||
public string Slug { get; set; }
|
||||
public string Name { get; set; }
|
||||
[JsonIgnore] public string ImgPrimary { get; set; }
|
||||
public string Poster { get; set; }
|
||||
public virtual IEnumerable<MetadataID> ExternalIDs { get; set; }
|
||||
|
||||
[JsonIgnore] public virtual IEnumerable<PeopleLink> Roles { get; set; }
|
||||
|
||||
public People() {}
|
||||
|
||||
public People(string slug, string name, string imgPrimary, IEnumerable<MetadataID> externalIDs)
|
||||
public People(string slug, string name, string poster, IEnumerable<MetadataID> externalIDs)
|
||||
{
|
||||
Slug = slug;
|
||||
Name = name;
|
||||
ImgPrimary = imgPrimary;
|
||||
Poster = poster;
|
||||
ExternalIDs = externalIDs;
|
||||
}
|
||||
}
|
||||
|
@ -77,8 +77,9 @@ namespace Kyoo.Controllers
|
||||
{
|
||||
ContractResolver = new JsonPropertySelector(null, new Dictionary<Type, HashSet<string>>()
|
||||
{
|
||||
{typeof(Show), new HashSet<string> {"genres", "studio", "people", "seasons"}},
|
||||
{typeof(Episode), new HashSet<string> {"tracks"}}
|
||||
{typeof(Show), new HashSet<string> {"genres", "studio"}},
|
||||
{typeof(Episode), new HashSet<string> {"tracks"}},
|
||||
{typeof(PeopleLink), new HashSet<string> {"show"}}
|
||||
})
|
||||
},
|
||||
context.HttpContext.RequestServices.GetRequiredService<ArrayPool<char>>(),
|
||||
|
@ -102,8 +102,8 @@ namespace Kyoo.Controllers
|
||||
};
|
||||
}
|
||||
|
||||
ICollection<PeopleLink> people = await ApplyFilters(_database.PeopleLinks.Where(x => x.ShowID == showID),
|
||||
id => _database.PeopleLinks.FirstOrDefaultAsync(x => x.ID == id),
|
||||
ICollection<PeopleLink> people = await ApplyFilters(_database.PeopleRoles.Where(x => x.ShowID == showID),
|
||||
id => _database.PeopleRoles.FirstOrDefaultAsync(x => x.ID == id),
|
||||
x => x.People.Name,
|
||||
where,
|
||||
sort,
|
||||
@ -128,8 +128,8 @@ namespace Kyoo.Controllers
|
||||
};
|
||||
}
|
||||
|
||||
ICollection<PeopleLink> people = await ApplyFilters(_database.PeopleLinks.Where(x => x.Show.Slug == showSlug),
|
||||
id => _database.PeopleLinks.FirstOrDefaultAsync(x => x.ID == id),
|
||||
ICollection<PeopleLink> people = await ApplyFilters(_database.PeopleRoles.Where(x => x.Show.Slug == showSlug),
|
||||
id => _database.PeopleRoles.FirstOrDefaultAsync(x => x.ID == id),
|
||||
x => x.People.Name,
|
||||
where,
|
||||
sort,
|
||||
@ -138,5 +138,39 @@ namespace Kyoo.Controllers
|
||||
throw new ItemNotFound();
|
||||
return people;
|
||||
}
|
||||
|
||||
public async Task<ICollection<ShowRole>> GetFromPeople(int peopleID,
|
||||
Expression<Func<ShowRole, bool>> where = null,
|
||||
Sort<ShowRole> sort = default,
|
||||
Pagination limit = default)
|
||||
{
|
||||
ICollection<ShowRole> roles = await ApplyFilters(_database.PeopleRoles.Where(x => x.PeopleID == peopleID)
|
||||
.Select(ShowRole.FromPeopleRole),
|
||||
async id => new ShowRole(await _database.PeopleRoles.FirstOrDefaultAsync(x => x.ID == id)),
|
||||
x => x.Title,
|
||||
where,
|
||||
sort,
|
||||
limit);
|
||||
if (!roles.Any() && await Get(peopleID) == null)
|
||||
throw new ItemNotFound();
|
||||
return roles;
|
||||
}
|
||||
|
||||
public async Task<ICollection<ShowRole>> GetFromPeople(string slug,
|
||||
Expression<Func<ShowRole, bool>> where = null,
|
||||
Sort<ShowRole> sort = default,
|
||||
Pagination limit = default)
|
||||
{
|
||||
ICollection<ShowRole> roles = await ApplyFilters(_database.PeopleRoles.Where(x => x.People.Slug == slug)
|
||||
.Select(ShowRole.FromPeopleRole),
|
||||
async id => new ShowRole(await _database.PeopleRoles.FirstOrDefaultAsync(x => x.ID == id)),
|
||||
x => x.Title,
|
||||
where,
|
||||
sort,
|
||||
limit);
|
||||
if (!roles.Any() && await Get(slug) == null)
|
||||
throw new ItemNotFound();
|
||||
return roles;
|
||||
}
|
||||
}
|
||||
}
|
@ -78,9 +78,10 @@ namespace Kyoo.Controllers
|
||||
|
||||
public override async Task<ICollection<Show>> Search(string query)
|
||||
{
|
||||
query = $"%{query}%";
|
||||
return await _database.Shows
|
||||
.Where(x => EF.Functions.ILike(x.Title, $"%{query}%")
|
||||
/*|| EF.Functions.ILike(x.Aliases, $"%{query}%")*/)
|
||||
.Where(x => EF.Functions.ILike(x.Title, query)
|
||||
/*|| x.Aliases.Any(y => EF.Functions.ILike(y, query))*/) // NOT TRANSLATABLE.
|
||||
.Take(20)
|
||||
.ToListAsync();
|
||||
}
|
||||
|
@ -68,10 +68,10 @@ namespace Kyoo.Controllers
|
||||
foreach (PeopleLink peop in people)
|
||||
{
|
||||
string localPath = Path.Combine(root, peop.People.Slug + ".jpg");
|
||||
if (peop.People.ImgPrimary == null)
|
||||
if (peop.People.Poster == null)
|
||||
continue;
|
||||
if (alwaysDownload || !File.Exists(localPath))
|
||||
await DownloadImage(peop.People.ImgPrimary, localPath, $"The profile picture of {peop.People.Name}");
|
||||
await DownloadImage(peop.People.Poster, localPath, $"The profile picture of {peop.People.Name}");
|
||||
}
|
||||
|
||||
return people;
|
||||
|
@ -9,6 +9,7 @@ using IdentityServer4.EntityFramework.Interfaces;
|
||||
using IdentityServer4.EntityFramework.Options;
|
||||
using Kyoo.Models;
|
||||
using Kyoo.Models.Exceptions;
|
||||
using Kyoo.Models.Watch;
|
||||
using Microsoft.AspNetCore.Identity;
|
||||
using Microsoft.AspNetCore.Identity.EntityFrameworkCore;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
@ -68,37 +69,46 @@ namespace Kyoo
|
||||
public DbSet<ProviderID> Providers { get; set; }
|
||||
public DbSet<MetadataID> MetadataIds { get; set; }
|
||||
|
||||
public DbSet<LibraryLink> LibraryLinks { get; set; }
|
||||
public DbSet<CollectionLink> CollectionLinks { get; set; }
|
||||
public DbSet<PeopleLink> PeopleLinks { get; set; }
|
||||
public DbSet<PeopleLink> PeopleRoles { get; set; }
|
||||
|
||||
|
||||
// This is used because EF doesn't support Many-To-Many relationships so for now we need to override the getter/setters to store this.
|
||||
public DbSet<LibraryLink> LibraryLinks { get; set; }
|
||||
public DbSet<CollectionLink> CollectionLinks { get; set; }
|
||||
public DbSet<GenreLink> GenreLinks { get; set; }
|
||||
public DbSet<ProviderLink> ProviderLinks { get; set; }
|
||||
|
||||
|
||||
private readonly ValueConverter<IEnumerable<string>, string> _stringArrayConverter =
|
||||
new ValueConverter<IEnumerable<string>, string>(
|
||||
arr => string.Join("|", arr),
|
||||
str => str.Split("|", StringSplitOptions.None));
|
||||
|
||||
public DatabaseContext()
|
||||
{
|
||||
NpgsqlConnection.GlobalTypeMapper.MapEnum<Status>();
|
||||
NpgsqlConnection.GlobalTypeMapper.MapEnum<ItemType>();
|
||||
NpgsqlConnection.GlobalTypeMapper.MapEnum<StreamType>();
|
||||
}
|
||||
|
||||
private readonly ValueComparer<IEnumerable<string>> _stringArrayComparer =
|
||||
new ValueComparer<IEnumerable<string>>(
|
||||
(l1, l2) => l1.SequenceEqual(l2),
|
||||
arr => arr.Aggregate(0, (i, s) => s.GetHashCode()));
|
||||
|
||||
(l1, l2) => l1.SequenceEqual(l2),
|
||||
arr => arr.Aggregate(0, (i, s) => s.GetHashCode()));
|
||||
|
||||
protected override void OnModelCreating(ModelBuilder modelBuilder)
|
||||
{
|
||||
base.OnModelCreating(modelBuilder);
|
||||
|
||||
modelBuilder.Entity<Library>().Property(e => e.Paths)
|
||||
.HasConversion(_stringArrayConverter).Metadata
|
||||
.SetValueComparer(_stringArrayComparer);
|
||||
modelBuilder.Entity<Show>().Property(e => e.Aliases)
|
||||
.HasConversion(_stringArrayConverter).Metadata
|
||||
.SetValueComparer(_stringArrayComparer);
|
||||
modelBuilder.HasPostgresEnum<Status>();
|
||||
modelBuilder.HasPostgresEnum<ItemType>();
|
||||
modelBuilder.HasPostgresEnum<StreamType>();
|
||||
|
||||
modelBuilder.Entity<Library>()
|
||||
.Property(x => x.Paths)
|
||||
.HasColumnType("text[]")
|
||||
.Metadata.SetValueComparer(_stringArrayComparer);
|
||||
|
||||
modelBuilder.Entity<Show>()
|
||||
.Property(x => x.Aliases)
|
||||
.HasColumnType("text[]")
|
||||
.Metadata.SetValueComparer(_stringArrayComparer);
|
||||
|
||||
|
||||
modelBuilder.Entity<Track>()
|
||||
.Property(t => t.IsDefault)
|
||||
.ValueGeneratedNever();
|
||||
@ -127,6 +137,7 @@ namespace Kyoo
|
||||
modelBuilder.Entity<PeopleLink>()
|
||||
.Ignore(x => x.Slug)
|
||||
.Ignore(x => x.Name)
|
||||
.Ignore(x => x.Poster)
|
||||
.Ignore(x => x.ExternalIDs);
|
||||
|
||||
modelBuilder.Entity<Genre>()
|
||||
|
@ -1,5 +1,6 @@
|
||||
// <auto-generated />
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Kyoo;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using Microsoft.EntityFrameworkCore.Infrastructure;
|
||||
@ -10,13 +11,16 @@ using Npgsql.EntityFrameworkCore.PostgreSQL.Metadata;
|
||||
namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
{
|
||||
[DbContext(typeof(DatabaseContext))]
|
||||
[Migration("20200803040029_Initial")]
|
||||
[Migration("20200804172021_Initial")]
|
||||
partial class Initial
|
||||
{
|
||||
protected override void BuildTargetModel(ModelBuilder modelBuilder)
|
||||
{
|
||||
#pragma warning disable 612, 618
|
||||
modelBuilder
|
||||
.HasAnnotation("Npgsql:Enum:item_type", "show,movie,collection")
|
||||
.HasAnnotation("Npgsql:Enum:status", "finished,airing,planned,unknown")
|
||||
.HasAnnotation("Npgsql:Enum:stream_type", "unknow,video,audio,subtitle")
|
||||
.HasAnnotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn)
|
||||
.HasAnnotation("ProductVersion", "3.1.3")
|
||||
.HasAnnotation("Relational:MaxIdentifierLength", 63);
|
||||
@ -167,8 +171,8 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
b.Property<string>("Name")
|
||||
.HasColumnType("text");
|
||||
|
||||
b.Property<string>("Paths")
|
||||
.HasColumnType("text");
|
||||
b.Property<IEnumerable<string>>("Paths")
|
||||
.HasColumnType("text[]");
|
||||
|
||||
b.Property<string>("Slug")
|
||||
.HasColumnType("text");
|
||||
@ -262,10 +266,10 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
.HasColumnType("integer")
|
||||
.HasAnnotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn);
|
||||
|
||||
b.Property<string>("ImgPrimary")
|
||||
b.Property<string>("Name")
|
||||
.HasColumnType("text");
|
||||
|
||||
b.Property<string>("Name")
|
||||
b.Property<string>("Poster")
|
||||
.HasColumnType("text");
|
||||
|
||||
b.Property<string>("Slug")
|
||||
@ -304,7 +308,7 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
|
||||
b.HasIndex("ShowID");
|
||||
|
||||
b.ToTable("PeopleLinks");
|
||||
b.ToTable("PeopleRoles");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Kyoo.Models.ProviderID", b =>
|
||||
@ -393,8 +397,8 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
.HasColumnType("integer")
|
||||
.HasAnnotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn);
|
||||
|
||||
b.Property<string>("Aliases")
|
||||
.HasColumnType("text");
|
||||
b.Property<IEnumerable<string>>("Aliases")
|
||||
.HasColumnType("text[]");
|
||||
|
||||
b.Property<string>("Backdrop")
|
||||
.HasColumnType("text");
|
@ -8,6 +8,11 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
{
|
||||
protected override void Up(MigrationBuilder migrationBuilder)
|
||||
{
|
||||
migrationBuilder.AlterDatabase()
|
||||
.Annotation("Npgsql:Enum:item_type", "show,movie,collection")
|
||||
.Annotation("Npgsql:Enum:status", "finished,airing,planned,unknown")
|
||||
.Annotation("Npgsql:Enum:stream_type", "unknow,video,audio,subtitle");
|
||||
|
||||
migrationBuilder.CreateTable(
|
||||
name: "Collections",
|
||||
columns: table => new
|
||||
@ -46,7 +51,7 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
.Annotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn),
|
||||
Slug = table.Column<string>(nullable: true),
|
||||
Name = table.Column<string>(nullable: true),
|
||||
Paths = table.Column<string>(nullable: true)
|
||||
Paths = table.Column<string[]>(type: "text[]", nullable: true)
|
||||
},
|
||||
constraints: table =>
|
||||
{
|
||||
@ -61,7 +66,7 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
.Annotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn),
|
||||
Slug = table.Column<string>(nullable: true),
|
||||
Name = table.Column<string>(nullable: true),
|
||||
ImgPrimary = table.Column<string>(nullable: true)
|
||||
Poster = table.Column<string>(nullable: true)
|
||||
},
|
||||
constraints: table =>
|
||||
{
|
||||
@ -131,7 +136,7 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
.Annotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn),
|
||||
Slug = table.Column<string>(nullable: true),
|
||||
Title = table.Column<string>(nullable: true),
|
||||
Aliases = table.Column<string>(nullable: true),
|
||||
Aliases = table.Column<string[]>(type: "text[]", nullable: true),
|
||||
Path = table.Column<string>(nullable: true),
|
||||
Overview = table.Column<string>(nullable: true),
|
||||
Status = table.Column<int>(nullable: true),
|
||||
@ -239,7 +244,7 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
});
|
||||
|
||||
migrationBuilder.CreateTable(
|
||||
name: "PeopleLinks",
|
||||
name: "PeopleRoles",
|
||||
columns: table => new
|
||||
{
|
||||
ID = table.Column<int>(nullable: false)
|
||||
@ -251,15 +256,15 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
},
|
||||
constraints: table =>
|
||||
{
|
||||
table.PrimaryKey("PK_PeopleLinks", x => x.ID);
|
||||
table.PrimaryKey("PK_PeopleRoles", x => x.ID);
|
||||
table.ForeignKey(
|
||||
name: "FK_PeopleLinks_People_PeopleID",
|
||||
name: "FK_PeopleRoles_People_PeopleID",
|
||||
column: x => x.PeopleID,
|
||||
principalTable: "People",
|
||||
principalColumn: "ID",
|
||||
onDelete: ReferentialAction.Cascade);
|
||||
table.ForeignKey(
|
||||
name: "FK_PeopleLinks_Shows_ShowID",
|
||||
name: "FK_PeopleRoles_Shows_ShowID",
|
||||
column: x => x.ShowID,
|
||||
principalTable: "Shows",
|
||||
principalColumn: "ID",
|
||||
@ -500,13 +505,13 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
unique: true);
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
name: "IX_PeopleLinks_PeopleID",
|
||||
table: "PeopleLinks",
|
||||
name: "IX_PeopleRoles_PeopleID",
|
||||
table: "PeopleRoles",
|
||||
column: "PeopleID");
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
name: "IX_PeopleLinks_ShowID",
|
||||
table: "PeopleLinks",
|
||||
name: "IX_PeopleRoles_ShowID",
|
||||
table: "PeopleRoles",
|
||||
column: "ShowID");
|
||||
|
||||
migrationBuilder.CreateIndex(
|
||||
@ -569,7 +574,7 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
name: "MetadataIds");
|
||||
|
||||
migrationBuilder.DropTable(
|
||||
name: "PeopleLinks");
|
||||
name: "PeopleRoles");
|
||||
|
||||
migrationBuilder.DropTable(
|
||||
name: "ProviderLinks");
|
@ -1,5 +1,6 @@
|
||||
// <auto-generated />
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Kyoo;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using Microsoft.EntityFrameworkCore.Infrastructure;
|
||||
@ -15,6 +16,9 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
{
|
||||
#pragma warning disable 612, 618
|
||||
modelBuilder
|
||||
.HasAnnotation("Npgsql:Enum:item_type", "show,movie,collection")
|
||||
.HasAnnotation("Npgsql:Enum:status", "finished,airing,planned,unknown")
|
||||
.HasAnnotation("Npgsql:Enum:stream_type", "unknow,video,audio,subtitle")
|
||||
.HasAnnotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn)
|
||||
.HasAnnotation("ProductVersion", "3.1.3")
|
||||
.HasAnnotation("Relational:MaxIdentifierLength", 63);
|
||||
@ -165,8 +169,8 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
b.Property<string>("Name")
|
||||
.HasColumnType("text");
|
||||
|
||||
b.Property<string>("Paths")
|
||||
.HasColumnType("text");
|
||||
b.Property<IEnumerable<string>>("Paths")
|
||||
.HasColumnType("text[]");
|
||||
|
||||
b.Property<string>("Slug")
|
||||
.HasColumnType("text");
|
||||
@ -260,10 +264,10 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
.HasColumnType("integer")
|
||||
.HasAnnotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn);
|
||||
|
||||
b.Property<string>("ImgPrimary")
|
||||
b.Property<string>("Name")
|
||||
.HasColumnType("text");
|
||||
|
||||
b.Property<string>("Name")
|
||||
b.Property<string>("Poster")
|
||||
.HasColumnType("text");
|
||||
|
||||
b.Property<string>("Slug")
|
||||
@ -302,7 +306,7 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
|
||||
b.HasIndex("ShowID");
|
||||
|
||||
b.ToTable("PeopleLinks");
|
||||
b.ToTable("PeopleRoles");
|
||||
});
|
||||
|
||||
modelBuilder.Entity("Kyoo.Models.ProviderID", b =>
|
||||
@ -391,8 +395,8 @@ namespace Kyoo.Models.DatabaseMigrations.Internal
|
||||
.HasColumnType("integer")
|
||||
.HasAnnotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn);
|
||||
|
||||
b.Property<string>("Aliases")
|
||||
.HasColumnType("text");
|
||||
b.Property<IEnumerable<string>>("Aliases")
|
||||
.HasColumnType("text[]");
|
||||
|
||||
b.Property<string>("Backdrop")
|
||||
.HasColumnType("text");
|
||||
|
@ -1,36 +0,0 @@
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Kyoo.Controllers;
|
||||
using Kyoo.Models;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
|
||||
namespace Kyoo.Api
|
||||
{
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
public class PeopleController : ControllerBase
|
||||
{
|
||||
private readonly ILibraryManager _libraryManager;
|
||||
|
||||
public PeopleController(ILibraryManager libraryManager)
|
||||
{
|
||||
_libraryManager = libraryManager;
|
||||
}
|
||||
|
||||
[HttpGet("{peopleSlug}")]
|
||||
[Authorize(Policy="Read")]
|
||||
public async Task<ActionResult<Collection>> GetPeople(string peopleSlug)
|
||||
{
|
||||
People people = await _libraryManager.GetPeople(peopleSlug);
|
||||
|
||||
if (people == null)
|
||||
return NotFound();
|
||||
return new Collection(people.Slug, people.Name, null, null)
|
||||
{
|
||||
Shows = people.Roles.Select(x => x.Show),
|
||||
Poster = "peopleimg/" + people.Slug
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
93
Kyoo/Views/API/PeopleApi.cs
Normal file
93
Kyoo/Views/API/PeopleApi.cs
Normal file
@ -0,0 +1,93 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Kyoo.CommonApi;
|
||||
using Kyoo.Controllers;
|
||||
using Kyoo.Models;
|
||||
using Kyoo.Models.Exceptions;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
|
||||
namespace Kyoo.Api
|
||||
{
|
||||
[Route("api/people")]
|
||||
[ApiController]
|
||||
public class PeopleApi : CrudApi<People>
|
||||
{
|
||||
private readonly ILibraryManager _libraryManager;
|
||||
|
||||
public PeopleApi(ILibraryManager libraryManager, IConfiguration configuration)
|
||||
: base(libraryManager.PeopleRepository, configuration)
|
||||
{
|
||||
_libraryManager = libraryManager;
|
||||
}
|
||||
|
||||
[HttpGet("{id:int}/role")]
|
||||
[HttpGet("{id:int}/roles")]
|
||||
[Authorize(Policy = "Read")]
|
||||
[JsonDetailed]
|
||||
public async Task<ActionResult<Page<ShowRole>>> GetRoles(int id,
|
||||
[FromQuery] string sortBy,
|
||||
[FromQuery] int afterID,
|
||||
[FromQuery] Dictionary<string, string> where,
|
||||
[FromQuery] int limit = 20)
|
||||
{
|
||||
where.Remove("sortBy");
|
||||
where.Remove("limit");
|
||||
where.Remove("afterID");
|
||||
|
||||
try
|
||||
{
|
||||
ICollection<ShowRole> resources = await _libraryManager.GetRolesFromPeople(id,
|
||||
ApiHelper.ParseWhere<ShowRole>(where),
|
||||
new Sort<ShowRole>(sortBy),
|
||||
new Pagination(limit, afterID));
|
||||
|
||||
return Page(resources, limit);
|
||||
}
|
||||
catch (ItemNotFound)
|
||||
{
|
||||
return NotFound();
|
||||
}
|
||||
catch (ArgumentException ex)
|
||||
{
|
||||
return BadRequest(new {Error = ex.Message});
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet("{slug}/role")]
|
||||
[HttpGet("{slug}/roles")]
|
||||
[Authorize(Policy = "Read")]
|
||||
[JsonDetailed]
|
||||
public async Task<ActionResult<Page<ShowRole>>> GetRoles(string slug,
|
||||
[FromQuery] string sortBy,
|
||||
[FromQuery] int afterID,
|
||||
[FromQuery] Dictionary<string, string> where,
|
||||
[FromQuery] int limit = 20)
|
||||
{
|
||||
where.Remove("sortBy");
|
||||
where.Remove("limit");
|
||||
where.Remove("afterID");
|
||||
|
||||
try
|
||||
{
|
||||
ICollection<ShowRole> ressources = await _libraryManager.GetRolesFromPeople(slug,
|
||||
ApiHelper.ParseWhere<ShowRole>(where),
|
||||
new Sort<ShowRole>(sortBy),
|
||||
new Pagination(limit, afterID));
|
||||
|
||||
return Page(ressources, limit);
|
||||
}
|
||||
catch (ItemNotFound)
|
||||
{
|
||||
return NotFound();
|
||||
}
|
||||
catch (ArgumentException ex)
|
||||
{
|
||||
return BadRequest(new {Error = ex.Message});
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -6,13 +6,13 @@ using Microsoft.AspNetCore.Mvc;
|
||||
|
||||
namespace Kyoo.Api
|
||||
{
|
||||
[Route("api/[controller]")]
|
||||
[Route("api/search")]
|
||||
[ApiController]
|
||||
public class SearchController : ControllerBase
|
||||
public class SearchApi : ControllerBase
|
||||
{
|
||||
private readonly ILibraryManager _libraryManager;
|
||||
|
||||
public SearchController(ILibraryManager libraryManager)
|
||||
public SearchApi(ILibraryManager libraryManager)
|
||||
{
|
||||
_libraryManager = libraryManager;
|
||||
}
|
||||
@ -21,7 +21,7 @@ namespace Kyoo.Api
|
||||
[Authorize(Policy="Read")]
|
||||
public async Task<ActionResult<SearchResult>> Search(string query)
|
||||
{
|
||||
SearchResult result = new SearchResult
|
||||
return new SearchResult
|
||||
{
|
||||
Query = query,
|
||||
Collections = await _libraryManager.SearchCollections(query),
|
||||
@ -31,7 +31,6 @@ namespace Kyoo.Api
|
||||
Genres = await _libraryManager.SearchGenres(query),
|
||||
Studios = await _libraryManager.SearchStudios(query)
|
||||
};
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
@ -1 +1 @@
|
||||
Subproject commit de1b3b069aa4f920bd5248223eda151b1eedf541
|
||||
Subproject commit 3dad4b29d6565d08ef0bce1e450b5de65f6fac16
|
Loading…
x
Reference in New Issue
Block a user