대용량 데이터 집합에 대해 매우 자주 쿼리를 실행해야하는 페이지가 있습니다. 데이터베이스 부담을 덜기 위해 5 분마다 캐시를 새로 고침했습니다. 논리는 다음과 같습니다. 호출이 이루어지면 캐시에 데이터가 있는지 확인하십시오. 캐시에있는 데이터가 있으면 캐시에서 queryu를 실행하십시오. 그렇지 않은 경우 저장소에서 쿼리를 실행하는 동안 데이터베이스의 모든 행에서 페치 (fetching) 작업을 시작하여 해당 호출에 필요한 데이터 만 가져옵니다. 모든 행을 가져 오면 다음 호출시 액세스 할 수 있도록 캐시에 넣습니다. 문제는 내가 때때로 얻을 수 있다는 것입니다. "Message ="이 명령과 관련된 열려있는 DataReader가 먼저 닫혀 있어야합니다. "이것은 동일한 저장소에 두 개의 쿼리를 동시에 실행하기 때문에 발생하는 것입니다. 모든 행과 쿼리에 대한 하나). 나는캐시에서 데이터를 가져올 수있는 경우 가져 오기
public IQueryable<TrackDto> TrackDtos([FromUri] int[] Ids)
{
if (HttpContext.Current.Cache["Tracks"] != null && ((IQueryable<TrackDto>)HttpContext.Current.Cache["Tracks"]).Any())
{
var trackDtos = Ids.Length > 0
? ((IQueryable<TrackDto>)HttpContext.Current.Cache["Tracks"]).Where(trackDto => Ids.Contains(trackDto.Id).AsQueryable()
: ((IQueryable<TrackDto>)HttpContext.Current.Cache["Tracks"]).AsQueryable();
return trackDtos;
}
else
{
UpdateTrackDtoCache(DateTime.Today);
var trackDtos = Ids.Length > 0
? WebRepository.TrackDtos.Where(trackDto => trackDto.Date == DateTime.Today && Ids.Contains(trackDto.Id)).AsQueryable()
: WebRepository.TrackDtos.Where(trackDto => trackDto.Date == DateTime.Today).AsQueryable().AsQueryable();
return trackDtos;
}
}
private IQueryable<TrackDto> MapTrackDtosFromDb(DateTime date)
{
return WebRepository.TrackDtos.Where(tdto => tdto.Date == date.Date);
}
private void UpdateTrackDtoCache(DateTime date)
{
if (CacheIsUpdating)
return;
CacheIsUpdating = true;
var task = Task.Factory.StartNew(
state =>
{
var context = (HttpContext)state;
context.Cache.Insert("Tracks", MapTrackDtosFromDb(date), null, Cache.NoAbsoluteExpiration,
new TimeSpan(0, 5, 0));
CacheIsUpdating = false;
},
HttpContext.Current);
}