Impossible de mapper la colonne SQL Geography à la classe EF DbGeography avec dapper

c# dapper entity-framework sql sqlgeography

Question

J'ai une table avec une colonne de géographie SQL dans ma base de données SQL. J'ai généré des entités pour ma base de données avec EF6. Comme vous le savez, Entitiy Framework génère System.Data.Entity.Spatial.DbGeography pour le type SQL Geography. J'utilise dapper pour exécuter des requêtes et mapper les résultats dans mes entités générées par EF.

Ma classe d'entité

public partial class Fix
{
    public Fix()
    {
        this.FixUsers = new HashSet<FixUser>();
    }

    public long FixID { get; set; }
    public long UserID { get; set; }
    public System.Data.Entity.Spatial.DbGeography Position { get; set; }
    public int Radius { get; set; }
    public System.DateTime CreatedDate { get; set; }

    public virtual MemberProfile MemberProfile { get; set; }
    public virtual ICollection<FixUser> FixUsers { get; set; }
}

Requête SQL qui lance une exception

    var fix = SqlConnection.Query<Fix>(@"SELECT TOP(1) 
                                         f.FixID as FixID, 
                                         f.UserID as UserID, 
                                         f.Radius as Radius, 
                                         f.CreatedDate as CreatedDate, 
                                         f.Position as Position
                                         FROM [Fix] f 
                                         WHERE f.FixID = @fixId", new { fixId }).FirstOrDefault();

Voici l'instantané d'exception

entrer la description de l'image ici

Je pense que dapper essaie par défaut de mapper avec Microsoft.SqlServer.Types.SqlGeography .

Y a-t-il une solution de contournement ici?

ÉDITÉ

Trouvé une solution, créé une classe partielle pour mon entité

public partial class Fix
{
    public string PositionString
    {
        set
        {
            Position = DbGeography.PointFromText(value, 4326);
        }
    }
}

Et changé ma requête

var fix = SqlConnection.Query<Fix>(@"SELECT TOP(1) 
                                     f.FixID as FixID, 
                                     f.UserID as UserID, 
                                     f.Radius as Radius, 
                                     f.CreatedDate as CreatedDate, 
                                     f.Position.ToString() as PositionString
                                     FROM [Fix] f 
                                     WHERE f.FixID = @fixId", new { fixId }).FirstOrDefault();

Réponse d'expert

Dapper prend en charge de nombreux types de données courants, mais pas tous. Vous pouvez envisager d'utiliser un paramètre de requête personnalisé - vous pouvez voir comment cette validation ajoute un support personnalisé pour les paramètres de table en tant que DataTable . Je serais très réticent à ajouter quelque chose qui exige des dépendances supplémentaires, en particulier pour des choses comme EF. Ce qui pourrait être utile à l'avenir, c'est un outil d'enregistrement personnalisable pour les fournisseurs personnalisés (permettant aux données contenues dans les paramètres d'être quelque chose - se déplaçant là où la carte se produit). Cela n'existe pas aujourd'hui cependant.


Réponse populaire

Si vous voulez vraiment utiliser Dapper, vous pouvez convertir SqlGeography en DbGeography:

DbGeography.FromText(sqlGeo.ToString());

Il suffit donc de faire la conversion en mémoire, ou vous pouvez également utiliser SQL avec EF:

dbContext.Fixes.SqlQuery("SELECT TOP(1) 
                                     f.FixID, 
                                     f.UserID, 
                                     f.Radius, 
                                     f.CreatedDate, 
                                     f.Position
                                     FROM [Fix] f 
                                     WHERE f.FixID = @fixId", new SqlParameter("fixId", fixId)).FirstOrDefault();

ou simplement utiliser Entity Framework de la manière habituelle? Puisque ce n'est pas une requête compliquée :)

dbContext.Fixes.Find(fixId);

Je suis toujours curieux de savoir pourquoi vous interrogez avec Dapper pour ensuite le mapper aux entités de EF



Sous licence: CC-BY-SA with attribution
Non affilié à Stack Overflow
Est-ce KB légal? Oui, apprenez pourquoi
Sous licence: CC-BY-SA with attribution
Non affilié à Stack Overflow
Est-ce KB légal? Oui, apprenez pourquoi