Fix postgres enum mapping

This commit is contained in:
Zoe Roux 2024-03-26 00:27:17 +01:00
parent db6670f699
commit 39ce601344
No known key found for this signature in database
2 changed files with 50 additions and 56 deletions

View File

@ -24,6 +24,12 @@ using Microsoft.AspNetCore.Http;
using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Query.SqlExpressions; using Microsoft.EntityFrameworkCore.Query.SqlExpressions;
using Npgsql; using Npgsql;
using System.Collections.Generic;
using System.Text.RegularExpressions;
using Dapper;
using InterpolatedSql.SqlBuilders;
using Kyoo.Postgresql.Utils;
using Kyoo.Utils;
namespace Kyoo.Postgresql; namespace Kyoo.Postgresql;
@ -42,15 +48,6 @@ public class PostgresContext : DatabaseContext
/// </summary> /// </summary>
private readonly bool _skipConfigure; private readonly bool _skipConfigure;
// TODO: This needs ot be updated but ef-core still does not offer a way to use this.
[Obsolete]
static PostgresContext()
{
NpgsqlConnection.GlobalTypeMapper.MapEnum<Status>();
NpgsqlConnection.GlobalTypeMapper.MapEnum<Genre>();
NpgsqlConnection.GlobalTypeMapper.MapEnum<WatchStatus>();
}
/// <summary> /// <summary>
/// Design time constructor (dotnet ef migrations add). Do not use /// Design time constructor (dotnet ef migrations add). Do not use
/// </summary> /// </summary>
@ -102,11 +99,46 @@ public class PostgresContext : DatabaseContext
"md5", "md5",
args, args,
nullable: true, nullable: true,
argumentsPropagateNullability: new[] { false }, argumentsPropagateNullability: [false],
type: args[0].Type, type: args[0].Type,
typeMapping: args[0].TypeMapping typeMapping: args[0].TypeMapping
)); ));
SqlMapper.TypeMapProvider = (type) =>
{
return new CustomPropertyTypeMap(
type,
(type, name) =>
{
string newName = Regex.Replace(
name,
"(^|_)([a-z])",
(match) => match.Groups[2].Value.ToUpperInvariant()
);
// TODO: Add images handling here (name: poster_source, newName: PosterSource) should set Poster.Source
return type.GetProperty(newName)!;
}
);
};
SqlMapper.AddTypeHandler(
typeof(Dictionary<string, MetadataId>),
new JsonTypeHandler<Dictionary<string, MetadataId>>()
);
SqlMapper.AddTypeHandler(
typeof(Dictionary<string, string>),
new JsonTypeHandler<Dictionary<string, string>>()
);
SqlMapper.AddTypeHandler(
typeof(Dictionary<string, ExternalToken>),
new JsonTypeHandler<Dictionary<string, ExternalToken>>()
);
SqlMapper.AddTypeHandler(typeof(List<string>), new ListTypeHandler<string>());
SqlMapper.AddTypeHandler(typeof(List<Genre>), new ListTypeHandler<Genre>());
SqlMapper.AddTypeHandler(typeof(Wrapper), new Wrapper.Handler());
InterpolatedSqlBuilderOptions.DefaultOptions.ReuseIdenticalParameters = true;
InterpolatedSqlBuilderOptions.DefaultOptions.AutoFixSingleQuotes = false;
base.OnModelCreating(modelBuilder); base.OnModelCreating(modelBuilder);
} }

View File

@ -16,16 +16,9 @@
// You should have received a copy of the GNU General Public License // You should have received a copy of the GNU General Public License
// along with Kyoo. If not, see <https://www.gnu.org/licenses/>. // along with Kyoo. If not, see <https://www.gnu.org/licenses/>.
using System;
using System.Collections.Generic;
using System.Data.Common; using System.Data.Common;
using System.Text.RegularExpressions;
using Dapper;
using InterpolatedSql.SqlBuilders;
using Kyoo.Abstractions.Controllers;
using Kyoo.Abstractions.Models; using Kyoo.Abstractions.Models;
using Kyoo.Postgresql.Utils; using Kyoo.Abstractions.Controllers;
using Kyoo.Utils;
using Microsoft.AspNetCore.Hosting; using Microsoft.AspNetCore.Hosting;
using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Configuration; using Microsoft.Extensions.Configuration;
@ -43,43 +36,6 @@ public class PostgresModule(IConfiguration configuration, IWebHostEnvironment en
/// <inheritdoc /> /// <inheritdoc />
public string Name => "Postgresql"; public string Name => "Postgresql";
static PostgresModule()
{
SqlMapper.TypeMapProvider = (type) =>
{
return new CustomPropertyTypeMap(
type,
(type, name) =>
{
string newName = Regex.Replace(
name,
"(^|_)([a-z])",
(match) => match.Groups[2].Value.ToUpperInvariant()
);
// TODO: Add images handling here (name: poster_source, newName: PosterSource) should set Poster.Source
return type.GetProperty(newName)!;
}
);
};
SqlMapper.AddTypeHandler(
typeof(Dictionary<string, MetadataId>),
new JsonTypeHandler<Dictionary<string, MetadataId>>()
);
SqlMapper.AddTypeHandler(
typeof(Dictionary<string, string>),
new JsonTypeHandler<Dictionary<string, string>>()
);
SqlMapper.AddTypeHandler(
typeof(Dictionary<string, ExternalToken>),
new JsonTypeHandler<Dictionary<string, ExternalToken>>()
);
SqlMapper.AddTypeHandler(typeof(List<string>), new ListTypeHandler<string>());
SqlMapper.AddTypeHandler(typeof(List<Genre>), new ListTypeHandler<Genre>());
SqlMapper.AddTypeHandler(typeof(Wrapper), new Wrapper.Handler());
InterpolatedSqlBuilderOptions.DefaultOptions.ReuseIdenticalParameters = true;
InterpolatedSqlBuilderOptions.DefaultOptions.AutoFixSingleQuotes = false;
}
/// <inheritdoc /> /// <inheritdoc />
public void Configure(IServiceCollection services) public void Configure(IServiceCollection services)
{ {
@ -96,10 +52,16 @@ public class PostgresModule(IConfiguration configuration, IWebHostEnvironment en
["TIMEOUT"] = "30" ["TIMEOUT"] = "30"
}; };
NpgsqlDataSourceBuilder dsBuilder = new(builder.ConnectionString);
dsBuilder.MapEnum<Status>();
dsBuilder.MapEnum<Genre>();
dsBuilder.MapEnum<WatchStatus>();
var dataSource = dsBuilder.Build();
services.AddDbContext<DatabaseContext, PostgresContext>( services.AddDbContext<DatabaseContext, PostgresContext>(
x => x =>
{ {
x.UseNpgsql(builder.ConnectionString).UseProjectables(); x.UseNpgsql(dataSource).UseProjectables();
if (environment.IsDevelopment()) if (environment.IsDevelopment())
x.EnableDetailedErrors().EnableSensitiveDataLogging(); x.EnableDetailedErrors().EnableSensitiveDataLogging();
}, },