<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
		>
<channel>
	<title>Comments on: Using &#8220;use index&#8221; With Hibernate/MySQL</title>
	<atom:link href="http://www.znetdevelopment.com/blogs/2009/10/07/using-use-index-with-hibernatemysql/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.znetdevelopment.com/blogs/2009/10/07/using-use-index-with-hibernatemysql/</link>
	<description>Tidbits and blogs from Nicholas Hagen related to software, web design, and usability</description>
	<lastBuildDate>Wed, 01 Feb 2012 14:31:09 +0000</lastBuildDate>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.2.1</generator>
	<item>
		<title>By: Marc</title>
		<link>http://www.znetdevelopment.com/blogs/2009/10/07/using-use-index-with-hibernatemysql/comment-page-1/#comment-146</link>
		<dc:creator>Marc</dc:creator>
		<pubDate>Tue, 04 Jan 2011 01:05:36 +0000</pubDate>
		<guid isPermaLink="false">http://www.znetdevelopment.com/blogs/?p=235#comment-146</guid>
		<description>Right, forget that. This is better. Hibernate does some funny things in some cases, therefore, you have to put quotes around your index name.

&lt;code&gt;
	public String onPrepareStatement(String sql) {
		int loopCount = 0;
		String[] s = sql.split(&quot;\\*/&quot;);
		sql = (s.length &gt; 1)? s[1].trim() : s[0].trim();
		
		while (true) {
			// check if function specified
			int idx = sql.indexOf(&quot;useindex(&quot;);
			if (idx  5) {
				break;
			}

			// find end of function
			int endidx = sql.indexOf(&quot;)=1&quot;, idx);
			if (endidx &lt; idx) {
				throwError(&quot;expected useindex(table, index) is true&quot;);
			}

			// get both parameters
			String[] params = sql.substring(idx + 9, endidx).split(&quot;,&quot;);
			if (params.length != 2) {
				throwError(&quot;expected 2 parameters to useindex(table, index)&quot;);
			}

			// trim parameters and verify
			String tableId = params[0].trim();
			String indexHint = params[1].trim();
			if (tableId.length() == 0 &#124;&#124; indexHint.length() == 0) {
				throwError(&quot;invalid parameters to useindex(table, index)&quot;);
			}

			// find actual table name minus id
			int dotIdx = tableId.indexOf(&#039;.&#039;);
//			if (dotIdx  -1) ? tableId.substring(0,dotIdx) : tableId;
			int tableIdx = sql.indexOf(&quot; &quot; + tableName + &quot; &quot;);
			if (tableIdx &lt; 0) {
				throwError(&quot;unknown table name in useindex(table, index)&quot;);
			}

			Pattern pattern = Pattern.compile(&quot;( [^ ]+ )&quot; + tableName + &quot; &quot;);
			Matcher m = pattern.matcher(sql);
			m.find();
			String entity = m.group(1);
			String[] sqlParts = sql.split(entity);
			
			String newSql = sqlParts[0];
			for (int x = 0; x &lt; sqlParts.length - 1; x++) {
				// Look ahead to the name of the table
				int nxtSpace = sqlParts[x + 1].indexOf(&quot; &quot;);
				String localTable = sqlParts[x + 1].substring(0, nxtSpace);
				newSql += entity + localTable;
				newSql += &quot; use index(&quot; + indexHint.replaceAll(&quot;&#039;&quot;,&quot;&quot;) + &quot;)&quot;;
				for(int a = x + 1;a &lt; sqlParts.length;a++){
					//remove all useindex for this table
					sqlParts[a] = sqlParts[a].replaceAll(&quot;useindex\\(&quot; + localTable + &quot;[^=]+=1 [^ ]+ &quot;, &quot;&quot;);
				}
				newSql += sqlParts[x + 1].substring(nxtSpace);
			}
			sql = newSql;
			if(sql.indexOf(&quot;useindex&quot;) == -1)
				break;
			loopCount++;
		}

		return sql;
	}

	protected void throwError(String message) {
		throw new IllegalStateException(message);
	}
&lt;/code&gt;</description>
		<content:encoded><![CDATA[<p>Right, forget that. This is better. Hibernate does some funny things in some cases, therefore, you have to put quotes around your index name.</p>
<p><code><br />
	public String onPrepareStatement(String sql) {<br />
		int loopCount = 0;<br />
		String[] s = sql.split("\\*/");<br />
		sql = (s.length &gt; 1)? s[1].trim() : s[0].trim();</p>
<p>		while (true) {<br />
			// check if function specified<br />
			int idx = sql.indexOf("useindex(");<br />
			if (idx  5) {<br />
				break;<br />
			}</p>
<p>			// find end of function<br />
			int endidx = sql.indexOf(")=1", idx);<br />
			if (endidx &lt; idx) {<br />
				throwError(&quot;expected useindex(table, index) is true&quot;);<br />
			}</p>
<p>			// get both parameters<br />
			String[] params = sql.substring(idx + 9, endidx).split(&quot;,&quot;);<br />
			if (params.length != 2) {<br />
				throwError(&quot;expected 2 parameters to useindex(table, index)&quot;);<br />
			}</p>
<p>			// trim parameters and verify<br />
			String tableId = params[0].trim();<br />
			String indexHint = params[1].trim();<br />
			if (tableId.length() == 0 || indexHint.length() == 0) {<br />
				throwError(&quot;invalid parameters to useindex(table, index)&quot;);<br />
			}</p>
<p>			// find actual table name minus id<br />
			int dotIdx = tableId.indexOf(&#039;.&#039;);<br />
//			if (dotIdx  -1) ? tableId.substring(0,dotIdx) : tableId;<br />
			int tableIdx = sql.indexOf(" " + tableName + " ");<br />
			if (tableIdx &lt; 0) {<br />
				throwError(&quot;unknown table name in useindex(table, index)&quot;);<br />
			}</p>
<p>			Pattern pattern = Pattern.compile(&quot;( [^ ]+ )&quot; + tableName + &quot; &quot;);<br />
			Matcher m = pattern.matcher(sql);<br />
			m.find();<br />
			String entity = m.group(1);<br />
			String[] sqlParts = sql.split(entity);</p>
<p>			String newSql = sqlParts[0];<br />
			for (int x = 0; x &lt; sqlParts.length - 1; x++) {<br />
				// Look ahead to the name of the table<br />
				int nxtSpace = sqlParts[x + 1].indexOf(&quot; &quot;);<br />
				String localTable = sqlParts[x + 1].substring(0, nxtSpace);<br />
				newSql += entity + localTable;<br />
				newSql += &quot; use index(&quot; + indexHint.replaceAll(&quot;&#039;&quot;,&quot;&quot;) + &quot;)&quot;;<br />
				for(int a = x + 1;a &lt; sqlParts.length;a++){<br />
					//remove all useindex for this table<br />
					sqlParts[a] = sqlParts[a].replaceAll(&quot;useindex\\(&quot; + localTable + &quot;[^=]+=1 [^ ]+ &quot;, &quot;&quot;);<br />
				}<br />
				newSql += sqlParts[x + 1].substring(nxtSpace);<br />
			}<br />
			sql = newSql;<br />
			if(sql.indexOf(&quot;useindex&quot;) == -1)<br />
				break;<br />
			loopCount++;<br />
		}</p>
<p>		return sql;<br />
	}</p>
<p>	protected void throwError(String message) {<br />
		throw new IllegalStateException(message);<br />
	}<br />
</code></p>
]]></content:encoded>
	</item>
	<item>
		<title>By: Marc</title>
		<link>http://www.znetdevelopment.com/blogs/2009/10/07/using-use-index-with-hibernatemysql/comment-page-1/#comment-144</link>
		<dc:creator>Marc</dc:creator>
		<pubDate>Mon, 03 Jan 2011 17:32:09 +0000</pubDate>
		<guid isPermaLink="false">http://www.znetdevelopment.com/blogs/?p=235#comment-144</guid>
		<description>Ok, that basically didn&#039;t work for me. My code generates some cross joins that consequently don&#039;t get parsed. I decided to use a more brute force approach. Because I made this change I was also able to eliminate the cross joins so I ended up not being able to test that but check this out:
[code]
	public String onPrepareStatement(String sql) {
		String newSql = &quot;&quot;;

		// check if function specified
		int idx = sql.indexOf(&quot;useindex(&quot;, 0);
		if (idx &lt; 0) {
			return sql;
		}

		// find end of function
		int endidx = sql.indexOf(&quot;)&quot;, idx);
		if (endidx &lt; idx) {
			throwError(&quot;expected useindex(table, index) is true&quot;);
		}

		// get both parameters
		String[] params = sql.substring(idx + 9, endidx).split(&quot;,&quot;);
		if (params.length != 2) {
			throwError(&quot;expected 2 parameters to useindex(table, index)&quot;);
		}

		// trim parameters and verify
		String tableId = params[0].trim();
		String indexHint = params[1].trim();
		if (tableId.length() == 0 &#124;&#124; indexHint.length() == 0) {
			throwError(&quot;invalid parameters to useindex(table, index)&quot;);
		}

		// find actual table name minus id
		int dotIdx = tableId.indexOf(&#039;.&#039;);
		// if (dotIdx  -1) ? tableId.substring(0,
				dotIdx) : tableId;
		Pattern pattern = Pattern.compile(&quot; &quot; + tableName + &quot; &quot;,
				Pattern.CASE_INSENSITIVE);
		String[] sqlParts = pattern.split(sql);

		newSql += sqlParts[0];
		for (int x = 0; x &lt; sqlParts.length - 1; x++) {
			// Look ahead to the name of the table
			int nxtSpace = sqlParts[x + 1].indexOf(&quot; &quot;);
			String localTable = sqlParts[x + 1].substring(0, nxtSpace);
			newSql += &quot; &quot; + tableName + &quot; &quot; + localTable;
			newSql += &quot; use index(&quot; + indexHint + &quot;)&quot;;
			newSql += sqlParts[x + 1].substring(nxtSpace).replaceAll(
					&quot;useindex[^1]+1 [^ ]+ &quot;, &quot;&quot;);
		}

		return newSql;

	}
[/code]</description>
		<content:encoded><![CDATA[<p>Ok, that basically didn&#8217;t work for me. My code generates some cross joins that consequently don&#8217;t get parsed. I decided to use a more brute force approach. Because I made this change I was also able to eliminate the cross joins so I ended up not being able to test that but check this out:<br />
[code]<br />
	public String onPrepareStatement(String sql) {<br />
		String newSql = "";</p>
<p>		// check if function specified<br />
		int idx = sql.indexOf("useindex(", 0);<br />
		if (idx &lt; 0) {<br />
			return sql;<br />
		}</p>
<p>		// find end of function<br />
		int endidx = sql.indexOf(&quot;)&quot;, idx);<br />
		if (endidx &lt; idx) {<br />
			throwError(&quot;expected useindex(table, index) is true&quot;);<br />
		}</p>
<p>		// get both parameters<br />
		String[] params = sql.substring(idx + 9, endidx).split(&quot;,&quot;);<br />
		if (params.length != 2) {<br />
			throwError(&quot;expected 2 parameters to useindex(table, index)&quot;);<br />
		}</p>
<p>		// trim parameters and verify<br />
		String tableId = params[0].trim();<br />
		String indexHint = params[1].trim();<br />
		if (tableId.length() == 0 || indexHint.length() == 0) {<br />
			throwError(&quot;invalid parameters to useindex(table, index)&quot;);<br />
		}</p>
<p>		// find actual table name minus id<br />
		int dotIdx = tableId.indexOf(&#039;.&#039;);<br />
		// if (dotIdx  -1) ? tableId.substring(0,<br />
				dotIdx) : tableId;<br />
		Pattern pattern = Pattern.compile(" " + tableName + " ",<br />
				Pattern.CASE_INSENSITIVE);<br />
		String[] sqlParts = pattern.split(sql);</p>
<p>		newSql += sqlParts[0];<br />
		for (int x = 0; x &lt; sqlParts.length - 1; x++) {<br />
			// Look ahead to the name of the table<br />
			int nxtSpace = sqlParts[x + 1].indexOf(&quot; &quot;);<br />
			String localTable = sqlParts[x + 1].substring(0, nxtSpace);<br />
			newSql += &quot; &quot; + tableName + &quot; &quot; + localTable;<br />
			newSql += &quot; use index(&quot; + indexHint + &quot;)&quot;;<br />
			newSql += sqlParts[x + 1].substring(nxtSpace).replaceAll(<br />
					&quot;useindex[^1]+1 [^ ]+ &quot;, &quot;&quot;);<br />
		}</p>
<p>		return newSql;</p>
<p>	}<br />
[/code]</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: Flavian</title>
		<link>http://www.znetdevelopment.com/blogs/2009/10/07/using-use-index-with-hibernatemysql/comment-page-1/#comment-101</link>
		<dc:creator>Flavian</dc:creator>
		<pubDate>Wed, 12 May 2010 10:30:43 +0000</pubDate>
		<guid isPermaLink="false">http://www.znetdevelopment.com/blogs/?p=235#comment-101</guid>
		<description>Hi,,

Im using Core Hibernate 3...

I tried using your stuff..


Created package com.citizen.hibernate.dialect
Added Class : MySQL5InnoDBDialect

Created package com.citizen.hibernate.interceptor
Added Class : IndexInterceptor


In my hibernate.cfg i updated the line
from : org.hibernate.dialect.MySQL5InnoDBDialect
To : com.citizen.hibernate.dialect.MySQL5InnoDBDialect


Im stuck in registering IndexInterceptor


How do i do that 


Please help... im in despo need of forcing index...</description>
		<content:encoded><![CDATA[<p>Hi,,</p>
<p>Im using Core Hibernate 3&#8230;</p>
<p>I tried using your stuff..</p>
<p>Created package com.citizen.hibernate.dialect<br />
Added Class : MySQL5InnoDBDialect</p>
<p>Created package com.citizen.hibernate.interceptor<br />
Added Class : IndexInterceptor</p>
<p>In my hibernate.cfg i updated the line<br />
from : org.hibernate.dialect.MySQL5InnoDBDialect<br />
To : com.citizen.hibernate.dialect.MySQL5InnoDBDialect</p>
<p>Im stuck in registering IndexInterceptor</p>
<p>How do i do that </p>
<p>Please help&#8230; im in despo need of forcing index&#8230;</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: nix</title>
		<link>http://www.znetdevelopment.com/blogs/2009/10/07/using-use-index-with-hibernatemysql/comment-page-1/#comment-87</link>
		<dc:creator>nix</dc:creator>
		<pubDate>Wed, 03 Mar 2010 15:35:01 +0000</pubDate>
		<guid isPermaLink="false">http://www.znetdevelopment.com/blogs/?p=235#comment-87</guid>
		<description>the setting for enabling comments in persistence.xml: 

property name=&quot;hibernate.use_sql_comments&quot; value=&quot;true&quot;</description>
		<content:encoded><![CDATA[<p>the setting for enabling comments in persistence.xml: </p>
<p>property name=&#8221;hibernate.use_sql_comments&#8221; value=&#8221;true&#8221;</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: nix</title>
		<link>http://www.znetdevelopment.com/blogs/2009/10/07/using-use-index-with-hibernatemysql/comment-page-1/#comment-86</link>
		<dc:creator>nix</dc:creator>
		<pubDate>Wed, 03 Mar 2010 15:14:40 +0000</pubDate>
		<guid isPermaLink="false">http://www.znetdevelopment.com/blogs/?p=235#comment-86</guid>
		<description>Thanks a lot. Works great!

Instead of creating an own hibernate dialect, you could use the jpa function query.setHint(&quot;org.hibernate.comment&quot;,&quot;xyz&quot;). 
Then you can parse the generated comment (e.g. &quot;/* xyz */ select ... &quot;) in your interceptor class.

Attention: if have to enable the comment-function in persistence.xml (   ).</description>
		<content:encoded><![CDATA[<p>Thanks a lot. Works great!</p>
<p>Instead of creating an own hibernate dialect, you could use the jpa function query.setHint(&#8220;org.hibernate.comment&#8221;,&#8221;xyz&#8221;).<br />
Then you can parse the generated comment (e.g. &#8220;/* xyz */ select &#8230; &#8220;) in your interceptor class.</p>
<p>Attention: if have to enable the comment-function in persistence.xml (   ).</p>
]]></content:encoded>
	</item>
	<item>
		<title>By: bravocharlie</title>
		<link>http://www.znetdevelopment.com/blogs/2009/10/07/using-use-index-with-hibernatemysql/comment-page-1/#comment-80</link>
		<dc:creator>bravocharlie</dc:creator>
		<pubDate>Sat, 02 Jan 2010 10:00:15 +0000</pubDate>
		<guid isPermaLink="false">http://www.znetdevelopment.com/blogs/?p=235#comment-80</guid>
		<description>Nicely done, works like a charm!</description>
		<content:encoded><![CDATA[<p>Nicely done, works like a charm!</p>
]]></content:encoded>
	</item>
</channel>
</rss>

