Entity Framework CoreでネイティブSQLクエリを実行する
Entity Framework CoreはDbSet.FromSql()メソッドを提供して、基になるデータベースで生のSQLクエリを実行し、結果をエンティティオブジェクトとして取得します。
次の例は、MS SQL Serverデータベースに対して生のSQLクエリを実行する方法を示しています。
var context = new SchoolContext();
var students = context.Students
.FromSql("Select * from Students where Name = 'Bill'")
.ToList();
上記の例では、Fromエンティティセット(DbSet <Student>)の後にFromSql()メソッドが使用されているため、指定されたSQLクエリは、Studentエンティティで変換されるStudentテーブルからレコードを返す必要があります。Entity Framework Coreは、指定されたクエリをデータベースで実行します。つまり、上記の例では、* from Student with * Name = 'Bill'を選択します。
パラメータ化クエリ
FromSqlメソッドでは、以下に示すように、C#の文字列補間構文を使用してパラメーター化されたクエリを実行できます。
string name = "Bill";
var context = new SchoolContext();
var students = context.Students
.FromSql($"Select * from Students where Name = '{name}'")
.ToList();
The following is also valid.
string name = "Bill";
var context = new SchoolContext();
var students = context.Students
.FromSql("Select * from Students where Name = '{0}'", name)
.ToList();
上記の例では、SQL Serverデータベースで次のSQLクエリを実行します。
exec sp_executesql N'Select * from Students where Name = ''@p0''
',N'@p0 nvarchar(4000)',@p0=N'Bill'
go
LINQオペレーター
FromSqlメソッドを使用して、元のクエリの後にLINQ演算子を使用することもできます。
string name = "Bill";
var context = new SchoolContext();
var students = context.Students
.FromSql("Select * from Students where Name = '{0}'", name)
.OrderBy(s => s.StudentId)
.ToList();
上記の例では、EF CoreはFromSqlメソッドとOrderBy演算子を組み合わせて次のクエリを実行します。
exec sp_executesql N'SELECT [s].[StudentId], [s].[Name]
FROM (
Select * from Students where Name = ''@p0''
) AS [s]
ORDER BY [s].[StudentId]',N'@p0 nvarchar(4000)',@p0=N'Bill'
go
FromSqlの制限
SQLクエリは、DbSet <T>と同じタイプのエンティティを返す必要があります。たとえば、学生の後にFromSqlを使用する場合、指定されたクエリはコースエンティティを返すことができません。FromSql()メソッドから返される一時的な型は、to-doリストにあります。
SQLクエリは、テーブルのすべての列を返す必要があります。たとえば、context.Students.FromSql( "Select StudentId、LastName from student")です。ToList()は例外をスローします
。SQLクエリにJOINクエリを含めて関連データを取得することはできません。FromSql()メソッドの後で、Includeメソッドを使用して関連エンティティをロードします。