{"id":991,"date":"2011-02-20T10:02:22","date_gmt":"2011-02-20T04:02:22","guid":{"rendered":"http:\/\/techsatwork.com\/blog\/?p=991"},"modified":"2016-01-07T11:31:07","modified_gmt":"2016-01-07T05:31:07","slug":"optimization-profiles-in-db2-udb","status":"publish","type":"post","link":"https:\/\/techsatwork.com\/?p=991","title":{"rendered":"Optimization profiles in DB2 UDB"},"content":{"rendered":"<p>How many times have we spend hours trying to figure why DB2 is not choosing a particular index and access path ? Probably many ! \u00c2\u00a0 \u00c2\u00a0DB2 is one of the best cost based optimizer out there , but yet it some rare cases DB2 refuses to choose the optimal path. As a DBA we go through utilities like db2expln, runstats and \u00c2\u00a0db2advis to tune SQLs and find the best access path, but if none of them work you can resort to optimization profiles to force DB2 to use a particular index.\u00c2\u00a0Optimization profiles are similar to the &#8220;hints&#8221; in other RDBMS engines like Oracle and SQL Server.<\/p>\n<p>Optimization profiles in DB2 UDB is an XML document and is then imported into the SYSTOOLS.OPT_PROFILE table. You activate a profile by executing\u00c2\u00a0<span style=\"color: #99cc00;\">SET CURRENT OPTIMIZATION PROFIL<\/span><span style=\"color: #99cc00;\">E<\/span> command \u00c2\u00a0when binding a package or executing a SQL.<\/p>\n<p>SYSTOOLS.OPT_PROFILE \u00c2\u00a0can be created either \u00c2\u00a0by running the sysinstallobjects procedure (recommended) or by creating the table directly :<\/p>\n<p><span style=\"color: #99cc00;\">db2 &#8220;call sysinstallobjects(&#8216;opt_profiles&#8217;, &#8216;c&#8217;, &#8216;toolstbsp&#8217;, &#8221;)&#8221;<br \/>\nor<br \/>\ncreate table systools.opt_profile (<br \/>\nschema\u00c2\u00a0 varchar(128) not null,<br \/>\nname\u00c2\u00a0 \u00c2\u00a0 varchar(128) not null,<br \/>\nprofile blob (2m)\u00c2\u00a0 \u00c2\u00a0 not null,<br \/>\nprimary key (schema, name)<br \/>\n) in toolstbsp;<\/span><\/p>\n<p>Lets take a simple example where DB2 chose a particular access path, but you as a DBA know that a different access path is better , how can you force DB2 optimizer to chose a particular index :<\/p>\n<p><span style=\"line-height: 19px;\"><span style=\"font-size: medium;\">First ensure you have the SYSTOOLS.OPT_PROFILE table created, if not create the table using the method I wrote above. \u00c2\u00a0Lets explain the following sql that can be run against the SAMPLE database:<\/span><\/span><\/p>\n<p><span style=\"color: #99cc00;\">SELECT FIRSTNME, LASTNAME, JOB, WORKDEPT, SALARY<br \/>\nFROM EMPLOYEE\u00c2\u00a0WHERE JOB IN (&#8216;CLERK&#8217;, &#8216;SALESREP&#8217;) AND\u00c2\u00a0WORKDEPT=&#8217;A00&#8217;\u00c2\u00a0ORDER BY JOB, SALARY;<\/span><\/p>\n<p>Below is the explain :<br \/>\n<a rel=\"attachment wp-att-1000\" href=\"https:\/\/techsatwork.com\/blog\/?attachment_id=1000\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-1000\" title=\"before_explain\" src=\"https:\/\/techsatwork.com\/blog\/wp-content\/uploads\/2011\/02\/before_explain.png\" alt=\"\" width=\"272\" height=\"880\" \/><\/a><\/p>\n<p>For instance, if you want to force optimizer to choose another index &#8211; XEMP2, \u00c2\u00a0to do so create the following optimization profile in a file , lets say profile1.xml :<\/p>\n<p><span style=\"color: #99cc00;\"><span style=\"color: #99cc00;\"><span style=\"font-size: medium;\"><span style=\"color: #99cc00;\">?xml version=&#8221;1.0&#8243; encoding=&#8221;UTF-8&#8243;?&gt;<\/span><\/span><\/span><\/span><\/p>\n<p><span style=\"color: #99cc00;\"><span style=\"color: #99cc00;\"><span style=\"font-size: medium;\"><span style=\"color: #99cc00;\">&lt;OPTPROFILE VERSION=&#8221;9.5.1&#8243;&gt;<br \/>\n&lt;STMTPROFILE ID=&#8221;Example 1&#8243;&gt;<\/span><\/span><\/span><\/span><\/p>\n<p><span style=\"color: #99cc00;\"><span style=\"color: #99cc00;\"><span style=\"font-size: medium;\"><span style=\"color: #99cc00;\">&lt;STMTKEY&gt;<br \/>\n&lt;![CDATA[SELECT FIRSTNME, LASTNAME, JOB, WORKDEPT, SALARY<br \/>\nFROM EMPLOYEE<br \/>\nWHERE JOB IN (&#8216;CLERK&#8217;, &#8216;SALESREP&#8217;) AND\u00c2\u00a0WORKDEPT=&#8217;A00&#8242;<br \/>\nORDER BY JOB, SALARY]]&gt;<br \/>\n&lt;\/STMTKEY&gt;<\/span><\/span><\/span><\/span><\/p>\n<p><span style=\"color: #99cc00;\"><span style=\"color: #99cc00;\"><span style=\"font-size: medium;\"><span style=\"color: #99cc00;\">&lt;OPTGUIDELINES&gt;<br \/>\n&lt;INLIST2JOIN OPTION=&#8221;DISABLE&#8221; TABLE=&#8221;EMPLOYEE&#8221; COLUMN=&#8221;JOB&#8221;\/&gt;<br \/>\n&lt;IXOR TABLE=&#8221;EMPLOYEE&#8221; INDEX=&#8221;XEMP2&#8243;\/&gt;<br \/>\n&lt;\/OPTGUIDELINES&gt;<\/span><\/span><\/span><\/span><\/p>\n<p><span style=\"color: #99cc00;\"><span style=\"color: #99cc00;\"><span style=\"font-size: medium;\"><span style=\"color: #99cc00;\">&lt;\/STMTPROFILE&gt;<br \/>\n&lt;\/OPTPROFILE&gt;<\/span><\/span><\/span><\/span><\/p>\n<p><span style=\"color: #99cc00;\"><span><span style=\"font-size: medium;\">No<\/span><\/span><\/span><span style=\"font-size: medium;\">w<\/span> create a file called profile1.del with the following lines :<br \/>\n<span style=\"color: #99cc00;\"> &#8220;DB2INST2&#8243;,&#8221;PROF1&#8243;,&#8221;profile1.xml&#8221;<\/span><\/p>\n<p>Now IMPORT the profile1.del file to systools.opt_profile table:<\/p>\n<p><span style=\"color: #99cc00;\">IMPORT FROM profile1.del OF DEL\u00c2\u00a0\u00c2\u00a0\u00c2\u00a0 MODIFIED BY LOBSINFILE\u00c2\u00a0\u00c2\u00a0\u00c2\u00a0 INSERT INTO SYSTOOLS.OPT_PROFILE<\/span><\/p>\n<p>Its time to see how the optimizer reacts to the profile . Execute the following sqls :<\/p>\n<p><span style=\"color: #99cc00;\">SET CURRENT OPTIMIZATION PROFILE=&#8221;PROF1&#8243;<br \/>\nSET CURRENT EXPLAIN MODE EXPLAIN<br \/>\nSELECT FIRSTNME, LASTNAME, JOB, WORKDEPT, SALARYFROM EMPLOYEEWHERE JOB IN (&#8216;CLERK&#8217;, &#8216;SALESREP&#8217;) ANDWORKDEPT=&#8217;A00&#8217;ORDER BY JOB, SALARY<br \/>\nSET CURRENT EXPLAIN MODE NO<br \/>\ndb2exfmt -d SAMPLE -1 -g -o exfmt_query1.out<\/span><\/p>\n<p>The file exfmt_query1.out should contain a query access plan similar to the following :\u00c2\u00a0<span style=\"font-size: small; line-height: 19px;\"><a rel=\"attachment wp-att-1009\" href=\"https:\/\/techsatwork.com\/blog\/?attachment_id=1009\"><img loading=\"lazy\" decoding=\"async\" class=\"alignnone size-full wp-image-1009\" title=\"after_explain\" src=\"https:\/\/techsatwork.com\/blog\/wp-content\/uploads\/2011\/02\/after_explain.png\" alt=\"\" width=\"201\" height=\"700\" srcset=\"https:\/\/techsatwork.com\/wp-content\/uploads\/2011\/02\/after_explain.png 201w, https:\/\/techsatwork.com\/wp-content\/uploads\/2011\/02\/after_explain-86x300.png 86w\" sizes=\"auto, (max-width: 201px) 100vw, 201px\" \/><\/a><\/span><\/p>\n<p><span style=\"line-height: 19px; font-size: x-small;\"><span style=\"font-size: medium;\">Note the index that the optimizer chose is XEMP2. \u00c2\u00a0You can add other profiles to the opt_profile table for different set of workload or add more STMTKEY to the same xml document. \u00c2\u00a0 You can find more about optimization profile <\/span><a href=\"http:\/\/publib.boulder.ibm.com\/infocenter\/db2luw\/v9\/topic\/com.ibm.db2.udb.admin.doc\/doc\/t0024532.htm\" target=\"_blank\"><span style=\"font-size: medium;\">here<\/span><\/a><span style=\"font-size: medium;\"> . <\/span><\/span>Using optimization profile should be your last resort, like I said earlier db2 optimizer is extremely wise and usually choose the optimal access path.<\/p>\n<p><span style=\"line-height: 19px; font-size: x-small;\"><span style=\"font-size: medium;\">Try out the optimization profile and let me know what your experience.<\/span><\/span><\/p>\n","protected":false},"excerpt":{"rendered":"<p>How many times have we spend hours trying to figure why DB2 is not choosing a particular index and access path ? Probably many ! \u00c2\u00a0 \u00c2\u00a0DB2 is one of the best cost based optimizer out there , but yet it some rare cases DB2 refuses to choose the optimal path. As a DBA we [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"site-container-style":"default","site-container-layout":"default","site-sidebar-layout":"default","site-transparent-header":"default","disable-article-header":"default","disable-site-header":"default","disable-site-footer":"default","disable-content-area-spacing":"default","footnotes":""},"categories":[303,3,358],"tags":[572,559,557,571,553,220,570,76,573,561,560,556,562,563,554,564,555,75,565,558,29],"class_list":["post-991","post","type-post","status-publish","format-standard","hentry","category-database","category-db2","category-how-to","tag-access-path","tag-current-optimization-profile","tag-db2-hints","tag-db2-index-usage","tag-db2-optimizer","tag-db2-performance","tag-db2-tuning","tag-explain","tag-explain-plan","tag-force-access-path","tag-force-index-usage","tag-hints","tag-opt-hint","tag-optguidelines","tag-optimization-profile","tag-optprofile","tag-opt_profile","tag-performance","tag-stmtprofile","tag-sysinstallobjects","tag-tuning"],"_links":{"self":[{"href":"https:\/\/techsatwork.com\/index.php?rest_route=\/wp\/v2\/posts\/991","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/techsatwork.com\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/techsatwork.com\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/techsatwork.com\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/techsatwork.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=991"}],"version-history":[{"count":24,"href":"https:\/\/techsatwork.com\/index.php?rest_route=\/wp\/v2\/posts\/991\/revisions"}],"predecessor-version":[{"id":1022,"href":"https:\/\/techsatwork.com\/index.php?rest_route=\/wp\/v2\/posts\/991\/revisions\/1022"}],"wp:attachment":[{"href":"https:\/\/techsatwork.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=991"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/techsatwork.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=991"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/techsatwork.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=991"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}