I need to work with georaphic distances.
I got
public class Clinic
{
...
public double Latitude
public double Longitud
...
}
This clinics are on a SQL Server DB. I need to return them ordered by distance to a certain point. For what I read, Entity Framework Core has no support for DbGeography or something of that sort as to represent the SQL Server type:
geography
I added to the database a column with the calculated geography point of each clinic
UPDATE Clinics SET Geo = geography::Point(Clinics.Latitude, Clinics.Longitud,4326)
OK, know i need to return them ordered. SQL supports this by querying
DECLARE @p geography;
SET @p = geography::Point(41,2,4326);
SELECT * FROM Clinics c ORDER BY @p.STDistance(c.Geo);
and Entity Framework Core supports querying with a raw SQL.
context.Clinics.FromSql("..query..")
Thing is, as the documentation of the FromSql says, if the data you are returning doesn't exactly match the model it crashes. As in C# I cant have a DbGeography that represents Geo I can't figure out how to resolve this.
EDIT 1:
Got it to partially work with the following:
string rawSQL = @"
DECLARE @p geography;
SET @p = geography::Point(41,2,4326);
SELECT c.Id, c.Name, c.Price, c.Quote, c.QuoteAuthor, c.QuoteSource, c.Description, c.Image, c.Latitude, c.Longitude, c.Category, c.CenterDistance, c.NumReviews, c.Stars
FROM Clinics c
ORDER BY @p.STDistance(c.Geo); ";
query = query.FromSql(rawSQL);
So now I get all the attributes of Clinics and it works! Thing is, clinics has a related class Amenities
public class Clinic
{
...
public double Latitude
public double Longitud
public Amenity amenity
...
}
So when I run a query I need to include the amenities by linq
query = query.Include(c => c.ClinicAmenities).ThenInclude(ca => ca.Amenity);
Dies because Orderby from the raw sql comes before the include I believe
SQL Server supports two spatial data types: the geometry data type and the geography data type. The geometry type represents data in a Euclidean (flat) coordinate system. The geography type represents data in a round-earth coordinate system.
Entity Framework Core is a modern object-database mapper for . NET. It supports LINQ queries, change tracking, updates, and schema migrations. EF Core works with many databases, including SQL Database (on-premises and Azure), SQLite, MySQL, PostgreSQL, and Azure Cosmos DB.
NetTopologySuite (NTS) is a spatial library for . NET. EF Core enables mapping to spatial data types in the database by using NTS types in your model.
The connecting edge between two vertices in a geometry type is a straight line. However, the connecting edge between two vertices in a geography type is a short great elliptic arc between the two vertices.
You didn't specify what error you get.
It seems to me you get error "The Include operation is not supported when calling a stored procedure."
What you could do is execute two queries.
Something like this
dbContext.Amenities.Load();
string rawSQL = @"
DECLARE @p geography;
SET @p = geography::Point(41,2,4326);
SELECT c.Id, c.Name, c.Price, c.Quote, c.QuoteAuthor
FROM Clinics c
ORDER BY @p.STDistance(c.Geo)";
// EF will automatically wire up the references between entities
// that have been queried for
var clinicsWithAmenities = dbContext.Clinics.FromSql(rawSQL).ToList();
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With