diff --git a/Kyoo.Common/Controllers/ILibraryManager.cs b/Kyoo.Common/Controllers/ILibraryManager.cs index d4fff41d..1d23460a 100644 --- a/Kyoo.Common/Controllers/ILibraryManager.cs +++ b/Kyoo.Common/Controllers/ILibraryManager.cs @@ -63,6 +63,7 @@ namespace Kyoo.Controllers long RegisterEpisode(Episode episode); long RegisterTrack(Track track); void RegisterShowLinks(Library library, Collection collection, Show show); + IEnumerable ValidateExternalIDs(IEnumerable ids); void RemoveShow(long showID); void RemoveSeason(long seasonID); diff --git a/Kyoo.Common/Kyoo.Common.csproj b/Kyoo.Common/Kyoo.Common.csproj index 2bf5d69c..5154a72c 100644 --- a/Kyoo.Common/Kyoo.Common.csproj +++ b/Kyoo.Common/Kyoo.Common.csproj @@ -11,7 +11,7 @@ SDG GPL-3.0-or-later true - 1.0.19 + 1.0.20 diff --git a/Kyoo.Common/Models/ImageTypes.cs b/Kyoo.Common/Models/ImageTypes.cs index fc643362..6dea10d4 100644 --- a/Kyoo.Common/Models/ImageTypes.cs +++ b/Kyoo.Common/Models/ImageTypes.cs @@ -1,4 +1,4 @@ namespace Kyoo.Models { - public enum ImageType { Poster, Background, Thumbnail, Logo } + public enum ImageType { Poster, Background, Logo } } \ No newline at end of file diff --git a/Kyoo.Common/Models/ProviderLink.cs b/Kyoo.Common/Models/ProviderLink.cs index 6c14d955..5abfc260 100644 --- a/Kyoo.Common/Models/ProviderLink.cs +++ b/Kyoo.Common/Models/ProviderLink.cs @@ -7,8 +7,6 @@ namespace Kyoo.Models [JsonIgnore] public long ID { get; set; } [JsonIgnore] public long ProviderID { get; set; } [JsonIgnore] public virtual ProviderID Provider { get; set; } - [JsonIgnore] public long? ShowID { get; set; } - [JsonIgnore] public virtual Show Show { get; set; } [JsonIgnore] public long? LibraryID { get; set; } [JsonIgnore] public virtual Library Library { get; set; } diff --git a/Kyoo.Common/Models/Show.cs b/Kyoo.Common/Models/Show.cs index 79e59756..89cc8ae4 100644 --- a/Kyoo.Common/Models/Show.cs +++ b/Kyoo.Common/Models/Show.cs @@ -19,10 +19,9 @@ namespace Kyoo.Models public long? StartYear { get; set; } public long? EndYear { get; set; } - public string ImgPrimary { get; set; } - [JsonIgnore] public string ImgThumb { get; set; } - [JsonIgnore] public string ImgLogo { get; set; } - [JsonIgnore] public string ImgBackdrop { get; set; } + public string Poster { get; set; } + public string Logo { get; set; } + public string Backdrop { get; set; } public virtual IEnumerable ExternalIDs { get; set; } @@ -77,10 +76,9 @@ namespace Kyoo.Models Status? status, long? startYear, long? endYear, - string imgPrimary, - string imgThumb, - string imgLogo, - string imgBackdrop, + string poster, + string logo, + string backdrop, IEnumerable externalIDs) { Slug = slug; @@ -92,10 +90,9 @@ namespace Kyoo.Models Status = status; StartYear = startYear; EndYear = endYear; - ImgPrimary = imgPrimary; - ImgThumb = imgThumb; - ImgLogo = imgLogo; - ImgBackdrop = imgBackdrop; + Poster = poster; + Logo = logo; + Backdrop = backdrop; ExternalIDs = externalIDs; IsCollection = false; } @@ -122,10 +119,9 @@ namespace Kyoo.Models Status ??= other.Status; StartYear ??= other.StartYear; EndYear ??= other.EndYear; - ImgPrimary ??= other.ImgPrimary; - ImgThumb ??= other.ImgThumb; - ImgLogo ??= other.ImgLogo; - ImgBackdrop ??= other.ImgBackdrop; + Poster ??= other.Poster; + Logo ??= other.Logo; + Backdrop ??= other.Backdrop; Studio ??= other.Studio; ExternalIDs = Utility.MergeLists(ExternalIDs, other.ExternalIDs, (x, y) => x.Provider.Name == y.Provider.Name); diff --git a/Kyoo.Common/Utility.cs b/Kyoo.Common/Utility.cs index d2afb8de..bb21aef7 100644 --- a/Kyoo.Common/Utility.cs +++ b/Kyoo.Common/Utility.cs @@ -47,17 +47,16 @@ namespace Kyoo switch(type) { case ImageType.Poster: - show.ImgPrimary = imgUrl; - break; - case ImageType.Thumbnail: - show.ImgThumb = imgUrl; + show.Poster = imgUrl; break; case ImageType.Logo: - show.ImgLogo = imgUrl; + show.Logo = imgUrl; break; case ImageType.Background: - show.ImgBackdrop = imgUrl; + show.Backdrop = imgUrl; break; + default: + throw new ArgumentOutOfRangeException(nameof(type), type, null); } } diff --git a/Kyoo/Controllers/LibraryManager.cs b/Kyoo/Controllers/LibraryManager.cs index af41337d..10457943 100644 --- a/Kyoo/Controllers/LibraryManager.cs +++ b/Kyoo/Controllers/LibraryManager.cs @@ -429,6 +429,16 @@ namespace Kyoo.Controllers return edited.ID; } + public IEnumerable ValidateExternalIDs(IEnumerable ids) + { + return ids.Select(x => + { + x.Provider = _database.Providers.FirstOrDefault(y => y.Name == x.Provider.Name) ?? x.Provider; + x.ProviderID = x.Provider.ID; + return x; + }).ToList(); + } + public long RegisterMovie(Episode movie) { if (movie == null) @@ -453,6 +463,9 @@ namespace Kyoo.Controllers { if (episode == null) return 0; + episode.ExternalIDs = new List(); + episode.Show.ExternalIDs = new List(); + episode.Season.ExternalIDs = new List(); if (_database.Entry(episode).State == EntityState.Detached) _database.Episodes.Add(episode); _database.SaveChanges(); diff --git a/Kyoo/Controllers/ThumbnailsManager.cs b/Kyoo/Controllers/ThumbnailsManager.cs index ec059677..5602fd9b 100644 --- a/Kyoo/Controllers/ThumbnailsManager.cs +++ b/Kyoo/Controllers/ThumbnailsManager.cs @@ -26,12 +26,12 @@ namespace Kyoo.Controllers string localBackdrop = Path.Combine(show.Path, "backdrop.jpg"); - if (show.ImgPrimary != null && !File.Exists(localThumb)) + if (show.Poster != null && !File.Exists(localThumb)) { try { using WebClient client = new WebClient(); - await client.DownloadFileTaskAsync(new Uri(show.ImgPrimary), localThumb); + await client.DownloadFileTaskAsync(new Uri(show.Poster), localThumb); } catch (WebException exception) { @@ -39,12 +39,12 @@ namespace Kyoo.Controllers } } - if (show.ImgLogo != null && !File.Exists(localLogo)) + if (show.Logo != null && !File.Exists(localLogo)) { try { using WebClient client = new WebClient(); - await client.DownloadFileTaskAsync(new Uri(show.ImgLogo), localLogo); + await client.DownloadFileTaskAsync(new Uri(show.Logo), localLogo); } catch (WebException exception) { @@ -52,12 +52,12 @@ namespace Kyoo.Controllers } } - if (show.ImgBackdrop != null && !File.Exists(localBackdrop)) + if (show.Backdrop != null && !File.Exists(localBackdrop)) { try { using WebClient client = new WebClient(); - await client.DownloadFileTaskAsync(new Uri(show.ImgBackdrop), localBackdrop); + await client.DownloadFileTaskAsync(new Uri(show.Backdrop), localBackdrop); } catch (WebException exception) { diff --git a/Kyoo/Models/DatabaseContext.cs b/Kyoo/Models/DatabaseContext.cs index ecd69660..3d4b9b13 100644 --- a/Kyoo/Models/DatabaseContext.cs +++ b/Kyoo/Models/DatabaseContext.cs @@ -76,7 +76,7 @@ namespace Kyoo public DbSet Genres { get; set; } public DbSet Peoples { get; set; } public DbSet Studios { get; set; } - public DbSet ProviderIds { get; set; } + public DbSet Providers { get; set; } public DbSet MetadataIds { get; set; } public DbSet LibraryLinks { get; set; } diff --git a/Kyoo/Models/DatabaseMigrations/Internal/20200423211516_Initial.Designer.cs b/Kyoo/Models/DatabaseMigrations/Internal/20200423211516_Initial.Designer.cs deleted file mode 100644 index 95a37efd..00000000 --- a/Kyoo/Models/DatabaseMigrations/Internal/20200423211516_Initial.Designer.cs +++ /dev/null @@ -1,633 +0,0 @@ -// -using System; -using Kyoo; -using Microsoft.EntityFrameworkCore; -using Microsoft.EntityFrameworkCore.Infrastructure; -using Microsoft.EntityFrameworkCore.Migrations; -using Microsoft.EntityFrameworkCore.Storage.ValueConversion; - -namespace Kyoo.Models.DatabaseMigrations.Internal -{ - [DbContext(typeof(DatabaseContext))] - [Migration("20200423211516_Initial")] - partial class Initial - { - protected override void BuildTargetModel(ModelBuilder modelBuilder) - { -#pragma warning disable 612, 618 - modelBuilder - .HasAnnotation("ProductVersion", "3.1.3"); - - modelBuilder.Entity("Kyoo.Models.Collection", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("ImgPrimary") - .HasColumnType("TEXT"); - - b.Property("Name") - .HasColumnType("TEXT"); - - b.Property("Overview") - .HasColumnType("TEXT"); - - b.Property("Poster") - .HasColumnType("TEXT"); - - b.Property("Slug") - .HasColumnType("TEXT"); - - b.HasKey("ID"); - - b.HasIndex("Slug") - .IsUnique(); - - b.ToTable("Collections"); - }); - - modelBuilder.Entity("Kyoo.Models.CollectionLink", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("CollectionID") - .HasColumnType("INTEGER"); - - b.Property("ShowID") - .HasColumnType("INTEGER"); - - b.HasKey("ID"); - - b.HasIndex("CollectionID"); - - b.HasIndex("ShowID"); - - b.ToTable("CollectionLinks"); - }); - - modelBuilder.Entity("Kyoo.Models.Episode", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("AbsoluteNumber") - .HasColumnType("INTEGER"); - - b.Property("EpisodeNumber") - .HasColumnType("INTEGER"); - - b.Property("ImgPrimary") - .HasColumnType("TEXT"); - - b.Property("Overview") - .HasColumnType("TEXT"); - - b.Property("Path") - .HasColumnType("TEXT"); - - b.Property("ReleaseDate") - .HasColumnType("TEXT"); - - b.Property("Runtime") - .HasColumnType("INTEGER"); - - b.Property("SeasonID") - .HasColumnType("INTEGER"); - - b.Property("SeasonNumber") - .HasColumnType("INTEGER"); - - b.Property("ShowID") - .HasColumnType("INTEGER"); - - b.Property("Title") - .HasColumnType("TEXT"); - - b.HasKey("ID"); - - b.HasIndex("SeasonID"); - - b.HasIndex("ShowID"); - - b.ToTable("Episodes"); - }); - - modelBuilder.Entity("Kyoo.Models.Genre", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("Name") - .HasColumnType("TEXT"); - - b.Property("Slug") - .HasColumnType("TEXT"); - - b.HasKey("ID"); - - b.HasIndex("Slug") - .IsUnique(); - - b.ToTable("Genres"); - }); - - modelBuilder.Entity("Kyoo.Models.GenreLink", b => - { - b.Property("ShowID") - .HasColumnType("INTEGER"); - - b.Property("GenreID") - .HasColumnType("INTEGER"); - - b.HasKey("ShowID", "GenreID"); - - b.HasIndex("GenreID"); - - b.ToTable("GenreLinks"); - }); - - modelBuilder.Entity("Kyoo.Models.Library", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("Name") - .HasColumnType("TEXT"); - - b.Property("Paths") - .HasColumnType("TEXT"); - - b.Property("Slug") - .HasColumnType("TEXT"); - - b.HasKey("ID"); - - b.HasIndex("Slug") - .IsUnique(); - - b.ToTable("Libraries"); - }); - - modelBuilder.Entity("Kyoo.Models.LibraryLink", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("CollectionID") - .HasColumnType("INTEGER"); - - b.Property("LibraryID") - .HasColumnType("INTEGER"); - - b.Property("ShowID") - .HasColumnType("INTEGER"); - - b.HasKey("ID"); - - b.HasIndex("CollectionID"); - - b.HasIndex("LibraryID"); - - b.HasIndex("ShowID"); - - b.ToTable("LibraryLinks"); - }); - - modelBuilder.Entity("Kyoo.Models.MetadataID", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("DataID") - .HasColumnType("TEXT"); - - b.Property("EpisodeID") - .HasColumnType("INTEGER"); - - b.Property("Link") - .HasColumnType("TEXT"); - - b.Property("PeopleID") - .HasColumnType("INTEGER"); - - b.Property("ProviderID") - .HasColumnType("INTEGER"); - - b.Property("SeasonID") - .HasColumnType("INTEGER"); - - b.Property("ShowID") - .HasColumnType("INTEGER"); - - b.HasKey("ID"); - - b.HasIndex("EpisodeID"); - - b.HasIndex("PeopleID"); - - b.HasIndex("ProviderID"); - - b.HasIndex("SeasonID"); - - b.HasIndex("ShowID"); - - b.ToTable("MetadataIds"); - }); - - modelBuilder.Entity("Kyoo.Models.People", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("ImgPrimary") - .HasColumnType("TEXT"); - - b.Property("Name") - .HasColumnType("TEXT"); - - b.Property("Slug") - .HasColumnType("TEXT"); - - b.HasKey("ID"); - - b.HasIndex("Slug") - .IsUnique(); - - b.ToTable("Peoples"); - }); - - modelBuilder.Entity("Kyoo.Models.PeopleLink", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("PeopleID") - .HasColumnType("TEXT"); - - b.Property("PeopleID1") - .HasColumnType("INTEGER"); - - b.Property("Role") - .HasColumnType("TEXT"); - - b.Property("ShowID") - .HasColumnType("INTEGER"); - - b.Property("Type") - .HasColumnType("TEXT"); - - b.HasKey("ID"); - - b.HasIndex("PeopleID1"); - - b.HasIndex("ShowID"); - - b.ToTable("PeopleLinks"); - }); - - modelBuilder.Entity("Kyoo.Models.ProviderID", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("Logo") - .HasColumnType("TEXT"); - - b.Property("Name") - .HasColumnType("TEXT"); - - b.HasKey("ID"); - - b.ToTable("ProviderIds"); - }); - - modelBuilder.Entity("Kyoo.Models.ProviderLink", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("LibraryID") - .HasColumnType("INTEGER"); - - b.Property("ProviderID") - .HasColumnType("INTEGER"); - - b.Property("ShowID") - .HasColumnType("INTEGER"); - - b.HasKey("ID"); - - b.HasIndex("LibraryID"); - - b.HasIndex("ProviderID"); - - b.HasIndex("ShowID"); - - b.ToTable("ProviderLinks"); - }); - - modelBuilder.Entity("Kyoo.Models.Season", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("ImgPrimary") - .HasColumnType("TEXT"); - - b.Property("Overview") - .HasColumnType("TEXT"); - - b.Property("SeasonNumber") - .HasColumnType("INTEGER"); - - b.Property("ShowID") - .HasColumnType("INTEGER"); - - b.Property("Title") - .HasColumnType("TEXT"); - - b.Property("Year") - .HasColumnType("INTEGER"); - - b.HasKey("ID"); - - b.HasIndex("ShowID"); - - b.ToTable("Seasons"); - }); - - modelBuilder.Entity("Kyoo.Models.Show", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("Aliases") - .HasColumnType("TEXT"); - - b.Property("EndYear") - .HasColumnType("INTEGER"); - - b.Property("ImgBackdrop") - .HasColumnType("TEXT"); - - b.Property("ImgLogo") - .HasColumnType("TEXT"); - - b.Property("ImgPrimary") - .HasColumnType("TEXT"); - - b.Property("ImgThumb") - .HasColumnType("TEXT"); - - b.Property("IsMovie") - .HasColumnType("INTEGER"); - - b.Property("Overview") - .HasColumnType("TEXT"); - - b.Property("Path") - .HasColumnType("TEXT"); - - b.Property("Slug") - .HasColumnType("TEXT"); - - b.Property("StartYear") - .HasColumnType("INTEGER"); - - b.Property("Status") - .HasColumnType("INTEGER"); - - b.Property("StudioID") - .HasColumnType("INTEGER"); - - b.Property("Title") - .HasColumnType("TEXT"); - - b.Property("TrailerUrl") - .HasColumnType("TEXT"); - - b.HasKey("ID"); - - b.HasIndex("Slug") - .IsUnique(); - - b.HasIndex("StudioID"); - - b.ToTable("Shows"); - }); - - modelBuilder.Entity("Kyoo.Models.Studio", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("Name") - .HasColumnType("TEXT"); - - b.Property("Slug") - .HasColumnType("TEXT"); - - b.HasKey("ID"); - - b.HasIndex("Slug") - .IsUnique(); - - b.ToTable("Studios"); - }); - - modelBuilder.Entity("Kyoo.Models.Track", b => - { - b.Property("ID") - .ValueGeneratedOnAdd() - .HasColumnType("INTEGER"); - - b.Property("Codec") - .HasColumnType("TEXT"); - - b.Property("EpisodeID") - .HasColumnType("INTEGER"); - - b.Property("IsDefault") - .HasColumnType("INTEGER"); - - b.Property("IsExternal") - .HasColumnType("INTEGER"); - - b.Property("IsForced") - .HasColumnType("INTEGER"); - - b.Property("Language") - .HasColumnType("TEXT"); - - b.Property("Path") - .HasColumnType("TEXT"); - - b.Property("Title") - .HasColumnType("TEXT"); - - b.Property("Type") - .HasColumnType("INTEGER"); - - b.HasKey("ID"); - - b.HasIndex("EpisodeID"); - - b.ToTable("Tracks"); - }); - - modelBuilder.Entity("Kyoo.Models.CollectionLink", b => - { - b.HasOne("Kyoo.Models.Collection", "Collection") - .WithMany() - .HasForeignKey("CollectionID"); - - b.HasOne("Kyoo.Models.Show", "Show") - .WithMany() - .HasForeignKey("ShowID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - }); - - modelBuilder.Entity("Kyoo.Models.Episode", b => - { - b.HasOne("Kyoo.Models.Season", "Season") - .WithMany("Episodes") - .HasForeignKey("SeasonID"); - - b.HasOne("Kyoo.Models.Show", "Show") - .WithMany("Episodes") - .HasForeignKey("ShowID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - }); - - modelBuilder.Entity("Kyoo.Models.GenreLink", b => - { - b.HasOne("Kyoo.Models.Genre", "Genre") - .WithMany() - .HasForeignKey("GenreID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - - b.HasOne("Kyoo.Models.Show", "Show") - .WithMany("GenreLinks") - .HasForeignKey("ShowID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - }); - - modelBuilder.Entity("Kyoo.Models.LibraryLink", b => - { - b.HasOne("Kyoo.Models.Collection", "Collection") - .WithMany() - .HasForeignKey("CollectionID"); - - b.HasOne("Kyoo.Models.Library", "Library") - .WithMany() - .HasForeignKey("LibraryID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - - b.HasOne("Kyoo.Models.Show", "Show") - .WithMany() - .HasForeignKey("ShowID"); - }); - - modelBuilder.Entity("Kyoo.Models.MetadataID", b => - { - b.HasOne("Kyoo.Models.Episode", "Episode") - .WithMany("ExternalIDs") - .HasForeignKey("EpisodeID"); - - b.HasOne("Kyoo.Models.People", "People") - .WithMany("ExternalIDs") - .HasForeignKey("PeopleID"); - - b.HasOne("Kyoo.Models.ProviderID", "Provider") - .WithMany() - .HasForeignKey("ProviderID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - - b.HasOne("Kyoo.Models.Season", "Season") - .WithMany("ExternalIDs") - .HasForeignKey("SeasonID"); - - b.HasOne("Kyoo.Models.Show", "Show") - .WithMany("ExternalIDs") - .HasForeignKey("ShowID"); - }); - - modelBuilder.Entity("Kyoo.Models.PeopleLink", b => - { - b.HasOne("Kyoo.Models.People", "People") - .WithMany("Roles") - .HasForeignKey("PeopleID1"); - - b.HasOne("Kyoo.Models.Show", "Show") - .WithMany("People") - .HasForeignKey("ShowID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - }); - - modelBuilder.Entity("Kyoo.Models.ProviderLink", b => - { - b.HasOne("Kyoo.Models.Library", "Library") - .WithMany("Providers") - .HasForeignKey("LibraryID"); - - b.HasOne("Kyoo.Models.ProviderID", "Provider") - .WithMany() - .HasForeignKey("ProviderID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - - b.HasOne("Kyoo.Models.Show", "Show") - .WithMany() - .HasForeignKey("ShowID"); - }); - - modelBuilder.Entity("Kyoo.Models.Season", b => - { - b.HasOne("Kyoo.Models.Show", "Show") - .WithMany("Seasons") - .HasForeignKey("ShowID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - }); - - modelBuilder.Entity("Kyoo.Models.Show", b => - { - b.HasOne("Kyoo.Models.Studio", "Studio") - .WithMany() - .HasForeignKey("StudioID"); - }); - - modelBuilder.Entity("Kyoo.Models.Track", b => - { - b.HasOne("Kyoo.Models.Episode", "Episode") - .WithMany("Tracks") - .HasForeignKey("EpisodeID") - .OnDelete(DeleteBehavior.Cascade) - .IsRequired(); - }); -#pragma warning restore 612, 618 - } - } -} diff --git a/Kyoo/Models/DatabaseMigrations/Internal/20200423211516_Initial.cs b/Kyoo/Models/DatabaseMigrations/Internal/20200423211516_Initial.cs deleted file mode 100644 index bfdc28e0..00000000 --- a/Kyoo/Models/DatabaseMigrations/Internal/20200423211516_Initial.cs +++ /dev/null @@ -1,605 +0,0 @@ -using System; -using Microsoft.EntityFrameworkCore.Migrations; - -namespace Kyoo.Models.DatabaseMigrations.Internal -{ - public partial class Initial : Migration - { - protected override void Up(MigrationBuilder migrationBuilder) - { - migrationBuilder.CreateTable( - name: "Collections", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - Slug = table.Column(nullable: true), - Name = table.Column(nullable: true), - Poster = table.Column(nullable: true), - Overview = table.Column(nullable: true), - ImgPrimary = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_Collections", x => x.ID); - }); - - migrationBuilder.CreateTable( - name: "Genres", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - Slug = table.Column(nullable: true), - Name = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_Genres", x => x.ID); - }); - - migrationBuilder.CreateTable( - name: "Libraries", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - Slug = table.Column(nullable: true), - Name = table.Column(nullable: true), - Paths = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_Libraries", x => x.ID); - }); - - migrationBuilder.CreateTable( - name: "Peoples", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - Slug = table.Column(nullable: true), - Name = table.Column(nullable: true), - ImgPrimary = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_Peoples", x => x.ID); - }); - - migrationBuilder.CreateTable( - name: "ProviderIds", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - Name = table.Column(nullable: true), - Logo = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_ProviderIds", x => x.ID); - }); - - migrationBuilder.CreateTable( - name: "Studios", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - Slug = table.Column(nullable: true), - Name = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_Studios", x => x.ID); - }); - - migrationBuilder.CreateTable( - name: "Shows", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - Slug = table.Column(nullable: true), - Title = table.Column(nullable: true), - Aliases = table.Column(nullable: true), - Path = table.Column(nullable: true), - Overview = table.Column(nullable: true), - Status = table.Column(nullable: true), - TrailerUrl = table.Column(nullable: true), - StartYear = table.Column(nullable: true), - EndYear = table.Column(nullable: true), - ImgPrimary = table.Column(nullable: true), - ImgThumb = table.Column(nullable: true), - ImgLogo = table.Column(nullable: true), - ImgBackdrop = table.Column(nullable: true), - IsMovie = table.Column(nullable: false), - StudioID = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_Shows", x => x.ID); - table.ForeignKey( - name: "FK_Shows_Studios_StudioID", - column: x => x.StudioID, - principalTable: "Studios", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - }); - - migrationBuilder.CreateTable( - name: "CollectionLinks", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - CollectionID = table.Column(nullable: true), - ShowID = table.Column(nullable: false) - }, - constraints: table => - { - table.PrimaryKey("PK_CollectionLinks", x => x.ID); - table.ForeignKey( - name: "FK_CollectionLinks_Collections_CollectionID", - column: x => x.CollectionID, - principalTable: "Collections", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - table.ForeignKey( - name: "FK_CollectionLinks_Shows_ShowID", - column: x => x.ShowID, - principalTable: "Shows", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - }); - - migrationBuilder.CreateTable( - name: "GenreLinks", - columns: table => new - { - ShowID = table.Column(nullable: false), - GenreID = table.Column(nullable: false) - }, - constraints: table => - { - table.PrimaryKey("PK_GenreLinks", x => new { x.ShowID, x.GenreID }); - table.ForeignKey( - name: "FK_GenreLinks_Genres_GenreID", - column: x => x.GenreID, - principalTable: "Genres", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - table.ForeignKey( - name: "FK_GenreLinks_Shows_ShowID", - column: x => x.ShowID, - principalTable: "Shows", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - }); - - migrationBuilder.CreateTable( - name: "LibraryLinks", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - LibraryID = table.Column(nullable: false), - ShowID = table.Column(nullable: true), - CollectionID = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_LibraryLinks", x => x.ID); - table.ForeignKey( - name: "FK_LibraryLinks_Collections_CollectionID", - column: x => x.CollectionID, - principalTable: "Collections", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - table.ForeignKey( - name: "FK_LibraryLinks_Libraries_LibraryID", - column: x => x.LibraryID, - principalTable: "Libraries", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - table.ForeignKey( - name: "FK_LibraryLinks_Shows_ShowID", - column: x => x.ShowID, - principalTable: "Shows", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - }); - - migrationBuilder.CreateTable( - name: "PeopleLinks", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - PeopleID = table.Column(nullable: true), - PeopleID1 = table.Column(nullable: true), - ShowID = table.Column(nullable: false), - Role = table.Column(nullable: true), - Type = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_PeopleLinks", x => x.ID); - table.ForeignKey( - name: "FK_PeopleLinks_Peoples_PeopleID1", - column: x => x.PeopleID1, - principalTable: "Peoples", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - table.ForeignKey( - name: "FK_PeopleLinks_Shows_ShowID", - column: x => x.ShowID, - principalTable: "Shows", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - }); - - migrationBuilder.CreateTable( - name: "ProviderLinks", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - ProviderID = table.Column(nullable: false), - ShowID = table.Column(nullable: true), - LibraryID = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_ProviderLinks", x => x.ID); - table.ForeignKey( - name: "FK_ProviderLinks_Libraries_LibraryID", - column: x => x.LibraryID, - principalTable: "Libraries", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - table.ForeignKey( - name: "FK_ProviderLinks_ProviderIds_ProviderID", - column: x => x.ProviderID, - principalTable: "ProviderIds", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - table.ForeignKey( - name: "FK_ProviderLinks_Shows_ShowID", - column: x => x.ShowID, - principalTable: "Shows", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - }); - - migrationBuilder.CreateTable( - name: "Seasons", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - ShowID = table.Column(nullable: false), - SeasonNumber = table.Column(nullable: false), - Title = table.Column(nullable: true), - Overview = table.Column(nullable: true), - Year = table.Column(nullable: true), - ImgPrimary = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_Seasons", x => x.ID); - table.ForeignKey( - name: "FK_Seasons_Shows_ShowID", - column: x => x.ShowID, - principalTable: "Shows", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - }); - - migrationBuilder.CreateTable( - name: "Episodes", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - ShowID = table.Column(nullable: false), - SeasonID = table.Column(nullable: true), - SeasonNumber = table.Column(nullable: false), - EpisodeNumber = table.Column(nullable: false), - AbsoluteNumber = table.Column(nullable: false), - Path = table.Column(nullable: true), - Title = table.Column(nullable: true), - Overview = table.Column(nullable: true), - ReleaseDate = table.Column(nullable: true), - Runtime = table.Column(nullable: false), - ImgPrimary = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_Episodes", x => x.ID); - table.ForeignKey( - name: "FK_Episodes_Seasons_SeasonID", - column: x => x.SeasonID, - principalTable: "Seasons", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - table.ForeignKey( - name: "FK_Episodes_Shows_ShowID", - column: x => x.ShowID, - principalTable: "Shows", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - }); - - migrationBuilder.CreateTable( - name: "MetadataIds", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - ProviderID = table.Column(nullable: false), - ShowID = table.Column(nullable: true), - EpisodeID = table.Column(nullable: true), - SeasonID = table.Column(nullable: true), - PeopleID = table.Column(nullable: true), - DataID = table.Column(nullable: true), - Link = table.Column(nullable: true) - }, - constraints: table => - { - table.PrimaryKey("PK_MetadataIds", x => x.ID); - table.ForeignKey( - name: "FK_MetadataIds_Episodes_EpisodeID", - column: x => x.EpisodeID, - principalTable: "Episodes", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - table.ForeignKey( - name: "FK_MetadataIds_Peoples_PeopleID", - column: x => x.PeopleID, - principalTable: "Peoples", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - table.ForeignKey( - name: "FK_MetadataIds_ProviderIds_ProviderID", - column: x => x.ProviderID, - principalTable: "ProviderIds", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - table.ForeignKey( - name: "FK_MetadataIds_Seasons_SeasonID", - column: x => x.SeasonID, - principalTable: "Seasons", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - table.ForeignKey( - name: "FK_MetadataIds_Shows_ShowID", - column: x => x.ShowID, - principalTable: "Shows", - principalColumn: "ID", - onDelete: ReferentialAction.Restrict); - }); - - migrationBuilder.CreateTable( - name: "Tracks", - columns: table => new - { - ID = table.Column(nullable: false) - .Annotation("Sqlite:Autoincrement", true), - Title = table.Column(nullable: true), - Language = table.Column(nullable: true), - Codec = table.Column(nullable: true), - Path = table.Column(nullable: true), - Type = table.Column(nullable: false), - EpisodeID = table.Column(nullable: false), - IsDefault = table.Column(nullable: false), - IsForced = table.Column(nullable: false), - IsExternal = table.Column(nullable: false) - }, - constraints: table => - { - table.PrimaryKey("PK_Tracks", x => x.ID); - table.ForeignKey( - name: "FK_Tracks_Episodes_EpisodeID", - column: x => x.EpisodeID, - principalTable: "Episodes", - principalColumn: "ID", - onDelete: ReferentialAction.Cascade); - }); - - migrationBuilder.CreateIndex( - name: "IX_CollectionLinks_CollectionID", - table: "CollectionLinks", - column: "CollectionID"); - - migrationBuilder.CreateIndex( - name: "IX_CollectionLinks_ShowID", - table: "CollectionLinks", - column: "ShowID"); - - migrationBuilder.CreateIndex( - name: "IX_Collections_Slug", - table: "Collections", - column: "Slug", - unique: true); - - migrationBuilder.CreateIndex( - name: "IX_Episodes_SeasonID", - table: "Episodes", - column: "SeasonID"); - - migrationBuilder.CreateIndex( - name: "IX_Episodes_ShowID", - table: "Episodes", - column: "ShowID"); - - migrationBuilder.CreateIndex( - name: "IX_GenreLinks_GenreID", - table: "GenreLinks", - column: "GenreID"); - - migrationBuilder.CreateIndex( - name: "IX_Genres_Slug", - table: "Genres", - column: "Slug", - unique: true); - - migrationBuilder.CreateIndex( - name: "IX_Libraries_Slug", - table: "Libraries", - column: "Slug", - unique: true); - - migrationBuilder.CreateIndex( - name: "IX_LibraryLinks_CollectionID", - table: "LibraryLinks", - column: "CollectionID"); - - migrationBuilder.CreateIndex( - name: "IX_LibraryLinks_LibraryID", - table: "LibraryLinks", - column: "LibraryID"); - - migrationBuilder.CreateIndex( - name: "IX_LibraryLinks_ShowID", - table: "LibraryLinks", - column: "ShowID"); - - migrationBuilder.CreateIndex( - name: "IX_MetadataIds_EpisodeID", - table: "MetadataIds", - column: "EpisodeID"); - - migrationBuilder.CreateIndex( - name: "IX_MetadataIds_PeopleID", - table: "MetadataIds", - column: "PeopleID"); - - migrationBuilder.CreateIndex( - name: "IX_MetadataIds_ProviderID", - table: "MetadataIds", - column: "ProviderID"); - - migrationBuilder.CreateIndex( - name: "IX_MetadataIds_SeasonID", - table: "MetadataIds", - column: "SeasonID"); - - migrationBuilder.CreateIndex( - name: "IX_MetadataIds_ShowID", - table: "MetadataIds", - column: "ShowID"); - - migrationBuilder.CreateIndex( - name: "IX_PeopleLinks_PeopleID1", - table: "PeopleLinks", - column: "PeopleID1"); - - migrationBuilder.CreateIndex( - name: "IX_PeopleLinks_ShowID", - table: "PeopleLinks", - column: "ShowID"); - - migrationBuilder.CreateIndex( - name: "IX_Peoples_Slug", - table: "Peoples", - column: "Slug", - unique: true); - - migrationBuilder.CreateIndex( - name: "IX_ProviderLinks_LibraryID", - table: "ProviderLinks", - column: "LibraryID"); - - migrationBuilder.CreateIndex( - name: "IX_ProviderLinks_ProviderID", - table: "ProviderLinks", - column: "ProviderID"); - - migrationBuilder.CreateIndex( - name: "IX_ProviderLinks_ShowID", - table: "ProviderLinks", - column: "ShowID"); - - migrationBuilder.CreateIndex( - name: "IX_Seasons_ShowID", - table: "Seasons", - column: "ShowID"); - - migrationBuilder.CreateIndex( - name: "IX_Shows_Slug", - table: "Shows", - column: "Slug", - unique: true); - - migrationBuilder.CreateIndex( - name: "IX_Shows_StudioID", - table: "Shows", - column: "StudioID"); - - migrationBuilder.CreateIndex( - name: "IX_Studios_Slug", - table: "Studios", - column: "Slug", - unique: true); - - migrationBuilder.CreateIndex( - name: "IX_Tracks_EpisodeID", - table: "Tracks", - column: "EpisodeID"); - } - - protected override void Down(MigrationBuilder migrationBuilder) - { - migrationBuilder.DropTable( - name: "CollectionLinks"); - - migrationBuilder.DropTable( - name: "GenreLinks"); - - migrationBuilder.DropTable( - name: "LibraryLinks"); - - migrationBuilder.DropTable( - name: "MetadataIds"); - - migrationBuilder.DropTable( - name: "PeopleLinks"); - - migrationBuilder.DropTable( - name: "ProviderLinks"); - - migrationBuilder.DropTable( - name: "Tracks"); - - migrationBuilder.DropTable( - name: "Genres"); - - migrationBuilder.DropTable( - name: "Collections"); - - migrationBuilder.DropTable( - name: "Peoples"); - - migrationBuilder.DropTable( - name: "Libraries"); - - migrationBuilder.DropTable( - name: "ProviderIds"); - - migrationBuilder.DropTable( - name: "Episodes"); - - migrationBuilder.DropTable( - name: "Seasons"); - - migrationBuilder.DropTable( - name: "Shows"); - - migrationBuilder.DropTable( - name: "Studios"); - } - } -} diff --git a/Kyoo/Models/DatabaseMigrations/Internal/DatabaseContextModelSnapshot.cs b/Kyoo/Models/DatabaseMigrations/Internal/DatabaseContextModelSnapshot.cs index 18da5846..32465a57 100644 --- a/Kyoo/Models/DatabaseMigrations/Internal/DatabaseContextModelSnapshot.cs +++ b/Kyoo/Models/DatabaseMigrations/Internal/DatabaseContextModelSnapshot.cs @@ -307,6 +307,9 @@ namespace Kyoo.Models.DatabaseMigrations.Internal b.HasKey("ID"); + b.HasIndex("Name") + .IsUnique(); + b.ToTable("ProviderIds"); }); @@ -322,17 +325,12 @@ namespace Kyoo.Models.DatabaseMigrations.Internal b.Property("ProviderID") .HasColumnType("INTEGER"); - b.Property("ShowID") - .HasColumnType("INTEGER"); - b.HasKey("ID"); b.HasIndex("LibraryID"); b.HasIndex("ProviderID"); - b.HasIndex("ShowID"); - b.ToTable("ProviderLinks"); }); @@ -376,30 +374,27 @@ namespace Kyoo.Models.DatabaseMigrations.Internal b.Property("Aliases") .HasColumnType("TEXT"); + b.Property("Backdrop") + .HasColumnType("TEXT"); + b.Property("EndYear") .HasColumnType("INTEGER"); - b.Property("ImgBackdrop") - .HasColumnType("TEXT"); - - b.Property("ImgLogo") - .HasColumnType("TEXT"); - - b.Property("ImgPrimary") - .HasColumnType("TEXT"); - - b.Property("ImgThumb") - .HasColumnType("TEXT"); - b.Property("IsMovie") .HasColumnType("INTEGER"); + b.Property("Logo") + .HasColumnType("TEXT"); + b.Property("Overview") .HasColumnType("TEXT"); b.Property("Path") .HasColumnType("TEXT"); + b.Property("Poster") + .HasColumnType("TEXT"); + b.Property("Slug") .HasColumnType("TEXT"); @@ -595,10 +590,6 @@ namespace Kyoo.Models.DatabaseMigrations.Internal .HasForeignKey("ProviderID") .OnDelete(DeleteBehavior.Cascade) .IsRequired(); - - b.HasOne("Kyoo.Models.Show", "Show") - .WithMany() - .HasForeignKey("ShowID"); }); modelBuilder.Entity("Kyoo.Models.Season", b => diff --git a/Kyoo/Tasks/Crawler.cs b/Kyoo/Tasks/Crawler.cs index ac58a2eb..9c400cae 100644 --- a/Kyoo/Tasks/Crawler.cs +++ b/Kyoo/Tasks/Crawler.cs @@ -145,6 +145,7 @@ namespace Kyoo.Controllers Genre existing = _libraryManager.GetGenreBySlug(x.Slug); return existing ?? x; }); + show.ExternalIDs = _libraryManager.ValidateExternalIDs(show.ExternalIDs); await _thumbnailsManager.Validate(show); return show; } @@ -152,12 +153,13 @@ namespace Kyoo.Controllers private async Task GetSeason(Show show, long seasonNumber, Library library) { if (seasonNumber == -1) - return null; + return default; Season season = _libraryManager.GetSeason(show.Slug, seasonNumber); if (season == null) - return await _metadataProvider.GetSeason(show, seasonNumber, library); + season = await _metadataProvider.GetSeason(show, seasonNumber, library); season.Show = show; - return await Task.FromResult(season); + season.ExternalIDs = _libraryManager.ValidateExternalIDs(season.ExternalIDs); + return season; } private async Task GetEpisode(Show show, Season season, long episodeNumber, long absoluteNumber, string episodePath, Library library) @@ -172,6 +174,7 @@ namespace Kyoo.Controllers return null; } + episode.ExternalIDs = _libraryManager.ValidateExternalIDs(episode.ExternalIDs); await _thumbnailsManager.Validate(episode); await GetTracks(episode); return episode; @@ -179,10 +182,7 @@ namespace Kyoo.Controllers private async Task GetMovie(Show show, string episodePath) { - Episode episode = new Episode(); - episode.Title = show.Title; - episode.Path = episodePath; - episode.Show = show; + Episode episode = new Episode {Title = show.Title, Path = episodePath, Show = show}; episode.Tracks = await GetTracks(episode); return episode; } diff --git a/Kyoo/Tasks/MetadataLoader.cs b/Kyoo/Tasks/MetadataLoader.cs index b1efcc04..427eb22e 100644 --- a/Kyoo/Tasks/MetadataLoader.cs +++ b/Kyoo/Tasks/MetadataLoader.cs @@ -23,7 +23,7 @@ namespace Kyoo.Tasks DatabaseContext database = serviceScope.ServiceProvider.GetService(); IPluginManager pluginManager = serviceScope.ServiceProvider.GetService(); foreach (IMetadataProvider provider in pluginManager.GetPlugins()) - database.ProviderIds.AddIfNotExist(provider.Provider, x => x.Name == provider.Provider.Name); + database.Providers.AddIfNotExist(provider.Provider, x => x.Name == provider.Provider.Name); database.SaveChanges(); return Task.CompletedTask; } diff --git a/Kyoo/Views/WebClient b/Kyoo/Views/WebClient index 6748d004..4ec71d48 160000 --- a/Kyoo/Views/WebClient +++ b/Kyoo/Views/WebClient @@ -1 +1 @@ -Subproject commit 6748d004b783a9fb4afdc51fec4787de0ddc1021 +Subproject commit 4ec71d48a9d48a054ea68594d3b8b4e2a09b33de