How can I clear the SQL Server query cache? - sql-server

I've got a simple query running against SQL Server 2005
SELECT *
FROM Table
WHERE Col = 'someval'
The first time I execute the query can take > 15 secs. Subsequent executes are back in < 1 sec.
How can I get SQL Server 2005 not to use any cached results? I've tried running
DBCC DROPCLEANBUFFERS
DBCC FREEPROCCACHE
But this seems to have no effect on the query speed (still < 1 sec).

Here is some good explaination. check out it.
http://www.mssqltips.com/tip.asp?tip=1360
CHECKPOINT;
GO
DBCC DROPCLEANBUFFERS;
GO
From the linked article:
If all of the performance testing is conducted in SQL Server the best approach may be to issue a CHECKPOINT and then issue the DBCC DROPCLEANBUFFERS command. Although the CHECKPOINT process is an automatic internal system process in SQL Server and occurs on a regular basis, it is important to issue this command to write all of the dirty pages for the current database to disk and clean the buffers. Then the DBCC DROPCLEANBUFFERS command can be executed to remove all buffers from the buffer pool.

Eight different ways to clear the plan cache
1. Remove all elements from the plan cache for the entire instance
DBCC FREEPROCCACHE;
Use this to clear the plan cache carefully. Freeing the plan cache causes, for example, a stored procedure to be recompiled instead of reused from the cache. This can cause a sudden, temporary decrease in query performance.
2. Flush the plan cache for the entire instance and suppress the regular completion message
"DBCC execution completed. If DBCC printed error messages, contact your system administrator."
DBCC FREEPROCCACHE WITH NO_INFOMSGS;
3. Flush the ad hoc and prepared plan cache for the entire instance
DBCC FREESYSTEMCACHE ('SQL Plans');
4. Flush the ad hoc and prepared plan cache for one resource pool
DBCC FREESYSTEMCACHE ('SQL Plans', 'LimitedIOPool');
5. Flush the entire plan cache for one resource pool
DBCC FREEPROCCACHE ('LimitedIOPool');
6. Remove all elements from the plan cache for one database (does not work in SQL Azure)
-- Get DBID from one database name first
DECLARE #intDBID INT;
SET #intDBID = (SELECT [dbid]
FROM master.dbo.sysdatabases
WHERE name = N'AdventureWorks2014');
DBCC FLUSHPROCINDB (#intDBID);
7. Clear plan cache for the current database
USE AdventureWorks2014;
GO
-- New in SQL Server 2016 and SQL Azure
ALTER DATABASE SCOPED CONFIGURATION CLEAR PROCEDURE_CACHE;
8. Remove one query plan from the cache
USE AdventureWorks2014;
GO
-- Run a stored procedure or query
EXEC dbo.uspGetEmployeeManagers 9;
-- Find the plan handle for that query
-- OPTION (RECOMPILE) keeps this query from going into the plan cache
SELECT cp.plan_handle, cp.objtype, cp.usecounts,
DB_NAME(st.dbid) AS [DatabaseName]
FROM sys.dm_exec_cached_plans AS cp CROSS APPLY sys.dm_exec_sql_text(plan_handle) AS st
WHERE OBJECT_NAME (st.objectid)
LIKE N'%uspGetEmployeeManagers%' OPTION (RECOMPILE);
-- Remove the specific query plan from the cache using the plan handle from the above query
DBCC FREEPROCCACHE (0x050011007A2CC30E204991F30200000001000000000000000000000000000000000000000000000000000000);
Source 1 2 3

Note that neither DBCC DROPCLEANBUFFERS; nor DBCC FREEPROCCACHE; is supported in SQL Azure / SQL Data Warehouse.
However, if you need to reset the plan cache in SQL Azure, you can alter one of the tables in the query (for instance, just add then remove a column), this will have the side-effect of removing the plan from the cache.
I personally do this as a way of testing query performance without having to deal with cached plans.
More details about SQL Azure Procedure Cache here

While the question is just a bit old, this might still help. I'm running into similar issues and using the option below has helped me. Not sure if this is a permanent solution, but it's fixing it for now.
OPTION (OPTIMIZE FOR UNKNOWN)
Then your query will be like this
select * from Table where Col = 'someval' OPTION (OPTIMIZE FOR UNKNOWN)

EXEC sys.sp_configure N'max server memory (MB)', N'2147483646'
GO
RECONFIGURE WITH OVERRIDE
GO
What value you specify for the server memory is not important, as long as it differs from the current one.
Btw, the thing that causes the speedup is not the query cache, but the data cache.

Related

How to clear sqlserver cache to get correct execution plan

I had a query that was running slow (2.5 mins) on sqlserver.
I got actual execution plan, and there was a suggestion for an index. I created the index and now execution time is < 2 seconds.
Then we had to restart sql server.
Query went back to being slow (2.5 mins), again, I looked at execution plan. This time there was a suggestion for a different index!
It would appear that first execution plan index suggestion was taking into account some sort of cached index maybe?
How can I clear cache (if this is the issue) before looking at execution plan?
The symptoms suggest parameter sniffing, where the query plan was generated for the initially supplied parameter values but the plan is suboptimal for subsequent queries with different values. You can invalidate the currently cached plan for specific query by providing the plan handle to DBCC FREEPROCCACHE:
DBCC FREEPROCCACHE(plan_pandle);
There are a number of ways to avoid parameter sniffing. If the query is not executed frequently, a recompile query hint will provide the optimal plan for the parameter values supplied. Otherwise, you could specify an optimize for unknown hint or use the Query Store (depending on your SQL Server version) to force a specific plan or have SQL Server automatically identify plan regression and select a plan.
Dont clear the cache in PRODUCTION environment. It will lead to serious performance issues.
If you want to generate new plan instead of existing plan, you can go for RECOMPILE option as part of stored procedure execution to see whether new index is being considered in the new plan.
EXEC dbo.Procedure WITH RECOMPILE;
or you can regenerate the execution plan for the procedure, by using the below command. Next time, it will be using the newly generated plan.
EXEC sp_recompile `dbo.procedure`
If you want to measure performance improvement repeatedly in a test environment, you can go with below clearing approaches:
DBCC FREEPROCCACHE -- It will clear the plan cache completely
DBCC DROPCLEANBUFFERS -- It will clear the unchanged data brought from disk to memory.
More elegant approach is to write the dirty pages to disk and then issue the cleaning of unchanged data.
CHECKPOINT;
GO
DBCC DROPCLEANBUFFERS;
GO
DBCC FREEPROCCACHE;
GO

Query terrible slow after DBCC DROPCLEANBUFFERS / FREEPROCCACHE

I have a complex query that runs under 2 seconds (which is ok), however if i run
DBCC DROPCLEANBUFFERS
DBCC FREEPROCCACHE
first the query performans goes oder 40 seconds. Should I be worried?
No, Sql server is doing EXACTLY what you just told it to. You asked it to empty out ALL it's hard earned buffers.
It ran first previously because it had stored the information about the tables and the query in the caches and deleted the execution plans. Having purged them it has to rebuild them from scratch.
Don't do that unless you've a good reason to.
Use DBCC FREEPROCCACHE to clear the plan cache carefully. Freeing the plan cache causes, for example, a stored procedure to be recompiled instead of reused from the cache. This can cause a sudden, temporary decrease in query performance. For each cleared cachestore in the plan cache, the SQL Server error log will contain the following informational message: "SQL Server has encountered %d occurrence(s) of cachestore flush for the ‘%s’ cachestore (part of plan cache) due to ‘DBCC FREEPROCCACHE’ or ‘DBCC FREESYSTEMCACHE’ operations." This message is logged every five minutes as long as the cache is flushed within that time interval.
Use DBCC DROPCLEANBUFFERS to test queries with a cold buffer cache without shutting down and restarting the server.
To drop clean buffers from the buffer pool, first use CHECKPOINT to produce a cold buffer cache. This forces all dirty pages for the current database to be written to disk and cleans the buffers. After you do this, you can issue DBCC DROPCLEANBUFFERS command to remove all buffers from the buffer pool.

Clearing the cache (recompile) for a database in sqlserver without restarting it sqlserver

Is there a way to clear all of the cache for a specific database somewhat equivalent to what OPTION(RECOMPILE) does for a stored proc?
I think the closest thing is:
DBCC DROPCLEANBUFFERS
More on: MSDN
Look at remarks section closely:
Use DBCC DROPCLEANBUFFERS to test queries with a cold buffer cache
without shutting down and restarting the server. To drop clean buffers
from the buffer pool, first use CHECKPOINT to produce a cold buffer
cache. This forces all dirty pages for the current database to be
written to disk and cleans the buffers. After you do this, you can
issue DBCC DROPCLEANBUFFERS command to remove all buffers from the
buffer pool.
You will usually use this:
CHECKPOINT;
GO
DBCC DROPCLEANBUFFERS;
GO
What cache are you talking about?
If Procedure Cache you can use DBCC FLUSHPROCINDB(<db_id>);
If all caches, including procedure cache and buffer cache, you can use
ALTER DATABASE YourDB SET OFFLINE --WITH ROLLBACK IMMEDIATE
ALTER DATABASE YourDB SET ONLINE

SQL Server 2008 plan cache is almost always empty

In order to investigate query plan usage I'm trying to understand what kind of query plan is stored in the memory.
Using this query:
SELECT objtype AS 'Cached Object Type',
COUNT(*) AS 'Numberof Plans',
SUM(CAST(size_in_bytes AS BIGINT))/1048576 AS 'Plan Cache SIze (MB)',
AVG(usecounts) AS 'Avg Use Counts'
FROM sys.dm_exec_cached_plans
GROUP BY objtype
ORDER BY objtype
I got almost empty plan cache structure. .
There is 128Gb of RAM on the server and ~20% is free. SQL Server instance is not constrained by memory.
Yes basically I have Adhoc queries (not parameterized, not stored procedures).
But why SQL Server empties the query plan cache so frequent? What kind of issue do I have?
Finally, only instance restart solved my problem. Now plan cache looks more healthy.
If the server isn't under memory pressure then some other possibilities from the plan caching white paper are below.
Are any of these actions scheduled frequently? Do you have auto close enabled?
The following operations flush the entire plan cache, and therefore,
cause fresh compilations of batches that are submitted the first time
afterwards:
Detaching a database
Upgrading a database to SQL Server 2005
Upgrading a database to SQL Server 2008
Restoring a database
DBCC FREEPROCCACHE command
RECONFIGURE command
ALTER DATABASE ,,, MODIFY FILEGROUP command
Modifying a collation using ALTER DATABASE … COLLATE command
The following operations flush the plan cache entries that refer to a
particular database, and cause fresh compilations afterwards.
DBCC FLUSHPROCINDB command
ALTER DATABASE … MODIFY NAME = command
ALTER DATABASE … SET ONLINE command
ALTER DATABASE … SET OFFLINE command
ALTER DATABASE … SET EMERGENCY command
DROP DATABASE command
When a database auto-closes
When a view is created with CHECK OPTION, the plan cache entries of the database in which the view is created are flushed.
When DBCC CHECKDB is run, a replica of the specified database is created. As part of DBCC CHECKDB's execution, some queries against the
replica are executed, and their plans cached. At the end of DBCC
CHECKDB's execution, the replica is deleted and so are the query plans
of the queries posed on the replica.
The following sp_configure/reconfigure operations also clear the procedure cache:
access check cache bucket count
access check cache quota
clr enabled
cost threshold for parallelism
cross db ownership chaining
index create memory
max degree of parallelism
max server memory
max text repl size
max worker threads
min memory per query
min server memory
query governor cost limit
query wait
remote query timeout
user options
I had the same issue just about a week ago and also posted several questions. Even though I have not actually found the answer to the problem I 've got some insight on the process. And silly as it sounds SQL Server service restart helped but raised another problem - the recovery process continued for 4 hours. Seems like a pretty large transaction was in place...
empty-plan-cache-problem
Almost empty plan cache
Almost empty plan cache

DROPCLEANBUFFERS does not work in SQL Server

I have a stored procedure which I am trying to optimize. In order to know how much time is spent for an execution I have added at the beginning of the script:
use MyDatabase
go
CHECKPOINT;
GO
DBCC DROPCLEANBUFFERS;
GO
between two execution I can see the time to run the query decreasing. I thought only cache could fasten the execution of my script, are there other mechanism in SQL Server to do the trick?
thanks,
The first time you run a stored procedure, the query plan is calculated and compiled. This typically takes 20ms, can be a bit more for a long procedure.
If you run the query once, before checkpoint; dbcc dropcleanbuffers;, the plan should be cached.

Resources