{"id":1743,"date":"2013-11-07T09:00:00","date_gmt":"2013-11-07T17:00:00","guid":{"rendered":"https:\/\/blogs.technet.microsoft.com\/dataplatforminsider\/2013\/11\/07\/io-resource-governance-in-sql-server-2014\/"},"modified":"2024-01-22T22:49:06","modified_gmt":"2024-01-23T06:49:06","slug":"io-resource-governance-in-sql-server-2014","status":"publish","type":"post","link":"https:\/\/www.microsoft.com\/en-us\/sql-server\/blog\/2013\/11\/07\/io-resource-governance-in-sql-server-2014\/","title":{"rendered":"IO Resource Governance in SQL Server 2014"},"content":{"rendered":"
Resource Governor<\/a> was introduced in SQL Server 2008 to achieve predictable performance in a multi-tenant environment, to support mixed workload patterns,\u00a0to provide mechanisms and tools to deal with runaway queries, and to enforce resource limits for CPU and memory. It enables customers to implement database consolidation or to configure their own database as a service. Since then, we\u2019ve been incrementally enhancing this feature<\/a> in major releases to address the top customer requests in this area. In SQL Server 2014, we are excited to add support for IO resource governance.<\/p>\n What is new?<\/strong><\/p>\n How to use it?<\/strong><\/p>\n Let\u2019s take the following scenario as an example of how IO Resource Governance can be used to control the resource usage in a SQL Server instance:<\/p>\n Let\u2019s suppose we are a Database hoster or running a Private cloud for database consolidation and we need to host multiple databases from different tenants (or customers) within a single SQL Server instance to achieve better density and COGS. If one of the tenants is running a very IO intensive workload, this can saturate the IO subsystem, causing performance problems to concurrent workloads that need to perform IO.<\/p>\n The first step would be to create a Resource Pool for each tenant\/database and a classifier function that will map the sessions from each tenant to the corresponding Resource Pool. For example, sessions for Customer 1 can be mapped to Resource Pool 1 and sessions for Customer 2 to Resource Pool 2.<\/p>\n If you want to use IO Resource Governance, it is important to set the min or max IOPS setting for every Resource Pool so that the IO requests are redirected to the governance subsystem and minimum reservations can be honored. In the example below, we set the MAX_IOPS_PER_VOLUME to the maximum value for every Pool:<\/p>\n Classifying each workload to a different Resource Pool allows us to configure the resource limits we want to provide for each tenant and also monitor the resource usage generated by their workload. The graph below (Performance Monitor) shows that the workload from Customer 1 is issuing too many IO requests causing a performance drop for Customer 2:<\/p>\n \u00a0 In order to protect Customer 2 and guarantee that he gets consistent performance, regardless of the activity from other tenants, we can set the MIN_IOPS_PER_VOLUME setting for the corresponding Resource Pool. From the graph above, it seems that the system can handle around 1300 IOPS, so we decide to reserve 650 IOPS for Customer 2:<\/p>\n With this configuration, SQL Server will try to throttle the workloads that are running in other Resource Pools, in order to satisfy the 650 IOPS reservation for Customer 2. In the graph below, we can see that the IOPS of the system are now fairly distributed among the tenants and that the performance for Customer 2 is back to normal despite its noisy neighbor:<\/p>\n \u00a0 The MIN_IOPS_PER_VOLUME setting will make a reservation for the Resource Pool, but it won\u2019t set any limit for the maximum IOPS it can use. This means that the tenants will still get performance variation depending on how active the rest of the tenants on the instance are. To avoid this problem and guarantee predictable performance, we can set the MAX_IOPS_PER_VOLUME setting for each of the tenants. This will set a hard limit for the maximum IOPS the tenant\u2019s workload can use, guaranteeing predicable performance for the tenant, but also protecting the rest of the tenants on the instance:<\/p>\n By configuring the IO settings on the Resource Pools we can control the resources we want to provide for each tenant. This allows us to guarantee predictable performance regardless of the activity from other tenants or even provide differentiation in SLA for the Database Service based on the amount of the resources customers sign up to reserve.<\/p>\n Another scenario that many of you might find applicable is isolating your OLTP workload from any maintenance operations that need to run in the database. Rebuilding an index, for example, is a common operation that can trigger a large number of IO requests, as it needs to scan the whole index or table. By using IO Resource Governance we can limit the number of IO operations these tasks can perform and guarantee predictable performance for concurrent OLTP workload.<\/p>\n In this case, we need a Resource Pool dedicated for maintenance operations and a classifier function that will map maintenance sessions to the corresponding Resource Pool. Running these operation as a different user might be a good way to distinguish between regular and maintenance sessions. By configuring the MAX_IOPS_PER_VOLUME setting on the \u201cmaintenance\u201d Resource Pool, we can limit the number of IO operations these tasks can perform and protect concurrent OLTP workload from being impacted.<\/p>\n I hope the example scenarios above demonstrate the core value of this feature.<\/p>\n Call to Action<\/strong><\/p>\n Please try this feature right away by downloading the SQL Server 2014 CTP2<\/a>. Even more easily test it in on the SQL Server 2014 CTP2 images that are now available in Windows Azure<\/a>. We look forward to hearing your feedback.<\/p>\n<\/div>\n<\/div>\n","protected":false},"excerpt":{"rendered":" Resource Governor was introduced in SQL Server 2008 to achieve predictable performance in a multi-tenant environment, to support mixed workload patterns,\u00a0to provide mechanisms and tools to deal with runaway queries, and to enforce resource limits for CPU and memory. It enables customers to implement database consolidation or to configure their own database as a service.<\/p>\n","protected":false},"author":1457,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"ep_exclude_from_search":false,"_classifai_error":"","_classifai_text_to_speech_error":"","footnotes":""},"post_tag":[],"product":[],"content-type":[2448],"topic":[],"coauthors":[2487],"class_list":["post-1743","post","type-post","status-publish","format-standard","hentry","content-type-updates"],"yoast_head":"\n\n
-- Create 2 resource pools & 2 workload groups.<\/span>
CREATE RESOURCE POOL<\/span> Customer1Pool;
CREATE RESOURCE POOL<\/span> Customer2Pool;
GO
CREATE WORKLOAD GROUP<\/span> Customer1Group USING<\/span> Customer1Pool;
CREATE WORKLOAD GROUP<\/span> Customer2Group USING<\/span> Customer2Pool;
GO<\/span>
-- Create classifier function<\/span>
CREATE FUNCTION<\/span> fnUserClassifier()
RETURNS SYSNAME<\/span>
WITH SCHEMABINDING<\/span>
AS<\/span>
BEGIN<\/span>
IF<\/span> ORIGINAL_DB_NAME<\/span>() = 'Customer1DB'<\/span>
BEGIN<\/span>
RETURN<\/span> 'Customer1Group'<\/span>
END<\/span>
IF<\/span> ORIGINAL_DB_NAME<\/span>() = 'Customer2DB'<\/span>
BEGIN<\/span>
RETURN<\/span> 'Customer2Group'<\/span>
END<\/span>
RETURN<\/span> 'default'<\/span>
END;<\/span>
GO<\/span>
-- Set the classifier function and enable RG.<\/span>
ALTER RESOURCE GOVERNOR WITH<\/span> (CLASSIFIER_FUNCTION = dbo.fnUserClassifier);
ALTER RESOURCE GOVERNOR RECONFIGURE;<\/span>
GO<\/span>
-- Set default values for the resource pools so that IO RG is enabled.<\/span>
ALTER RESOURCE POOL<\/span> Customer1Pool WITH<\/span> (MIN_IOPS_PER_VOLUME=0, MAX_IOPS_PER_VOLUME=2147483647);
ALTER RESOURCE POOL<\/span> Customer2Pool WITH<\/span> (MIN_IOPS_PER_VOLUME=0, MAX_IOPS_PER_VOLUME=2147483647);
ALTER RESOURCE GOVERNOR RECONFIGURE;<\/span>
GO<\/span>
<\/code><\/pre>\n
<\/a><\/p>\nALTER RESOURCE POOL<\/span> Customer2Pool WITH<\/span> (MIN_IOPS_PER_VOLUME=650);
ALTER RESOURCE GOVERNOR RECONFIGURE;<\/span>
GO<\/span><\/code><\/pre>\n<\/div>\n
<\/a><\/p>\nALTER RESOURCE POOL<\/span> Customer2Pool WITH<\/span> (MAX_IOPS_PER_VOLUME=750)
ALTER RESOURCE GOVERNOR RECONFIGURE<\/span>
GO<\/span><\/code><\/pre>\n