Использование шаблона UnitOfWork со скомпилированными запросами
Я пытаюсь настроить некоторые скомпилированные запросы в моем проекте, в котором используется шаблон единицы работы. Эти запросы многократно используются во время определенных запросов, и создание скомпилированных запросов очень помогает в ускорении работы приложения. Одна вещь, которую я заметил, это то, что я должен передать текст данных, который я использую, вместо того, чтобы использовать репозитории, которые я настроил в своем классе Unit of Work.
Вот что работает:
private static Func<PivotalDataContext, Binary, Binary, Int32?, IQueryable<Location>> GetLocationFunc
{
get
{
Func<PivotalDataContext, Binary, Binary, Int32?, IQueryable<Location>> func =
CompiledQuery.Compile(
(PivotalDataContext db, Binary destCityId, Binary stateId, Int32? cityNeoId) =>
(
(from cityDest in db.Destination_Cities
where
cityDest.Destination_City_Id == destCityId || cityDest.Neo_Id == cityNeoId
join destCountry in db.Destination_Countries
on cityDest.Destination_Country_Id equals destCountry.Destination_Country_Id into country
from destCountry in country.DefaultIfEmpty()
join destCont in db.Destination_Continents
on destCountry.Destination_Continent_Id equals destCont.Destination_Continent_Id into continent
from destCont in continent.DefaultIfEmpty()
select new Location
{
CityName = destCity.Name,
CountryName = destCountry.Name,
ContinentName = destContinent.Name
})));
return func;
}
}
Вот что я хочу:
Конструктор:
private static IRepository<Destination_Country> _destCountryRepo;
private static IRepository<Destination_Continent> _destContinentRepo;
private static IRepository<Destination_City> _destinationCityRepo;
public LocationService()
{
_destCountryRepo = UnitOfWork.DestCountryRepo;
_destCityRepo = UnitOfWork.DestCityRepo;
_destContinentRepo = UnitOfWork.DestContinentRepo;
_destCountryRepo = UnitOfWork.DestCountryRepo;
}
Вот скомпилированный запрос (я заменил вызовы таблиц из datacontext на таблицы, установленные в конструкторе):
private static Func<PivotalDataContext, Binary, Binary, Int32?, IQueryable<Location>> GetLocationFunc
{
get
{
Func<PivotalDataContext, Binary, Binary, Int32?, IQueryable<Location>> func =
CompiledQuery.Compile(
(PivotalDataContext db, Binary destCityId, Binary stateId, Int32? cityNeoId) =>
(
(from cityDest in _destCityRepo.Table
where
cityDest.Destination_City_Id == _destCityId || cityDest.Neo_Id == cityNeoId
join destCountry in _destCountryRepo.Table
on cityDest.Destination_Country_Id equals destCountry.Destination_Country_Id into country
from destCountry in country.DefaultIfEmpty()
join destCont in _destContinentRepo.Table
on destCountry.Destination_Continent_Id equals destCont.Destination_Continent_Id into continent
from destCont in continent.DefaultIfEmpty()
select new Location
{
CityName = destCity.Name,
CountryName = destCountry.Name,
ContinentName = destContinent.Name
})));
return func;
}
}
Когда я пытаюсь использовать таблицы, настроенные в классе UnitOfWork, и создаю точку останова по скомпилированному запросу, эти таблицы по какой-то причине равны нулю, даже если они устанавливаются при создании класса. Можно ли сделать это? Или скомпилированный запрос всегда должен передавать переданный текст данных?
Заранее спасибо!
1 ответ
Краткий ответ: Да, вы должны передать его.
Ваш код структурирован так, что вы предоставляете DataContext
наряду с другими аргументами для выполнения запроса. Поскольку вы зависаете от статического свойства, вам всегда нужно будет передавать DataContext
потому что это не статично.
Но даже если вы создали запрос в нестатическом контексте, нет подходящего обстоятельства, когда DataContext
будет создан и жить так же долго, как запрос. Вы бы в конечном итоге с долгожителем DataContext
это не то, как он предназначен для использования и создает много проблем.