tomcat+jsp(form)+spring+c3p0+jdbc+mysql=焦頭爛額
因為工作上面會用到類似的solution,所以在這陣子花了點時間去學習這樣的組合,學習過程中當然會遇到問題,但大部份都能夠迎刃而解,
為什麼說大部份,因為還是有很稀奇古怪的問題存在,這裡要說的就是tomcat+spring+c3p0+jdbc+mysql這些大雜燴讓我鬧肚子的經驗談。
1.tomcat+spring
這東西還不算太難,搞清楚基本概念,寫到跑的起來就不是什麼難事(困難的是做好設計,要設計的漂亮要花點心思),多花點時間檢查xml是不是有寫錯,網路上的資料很多(地雷也很多,要多求證),這部份很快就解決了。
2.tomcat+jdbc+mysql
簡單的兩樣結束後,就是準備與資料庫大戰,在java裏面當然要用jdbc來解決,為了避免問題同時發生,所以先把spring變因排除,這部份因為之前也寫過很多相關的東西,對mysql來說,處理好UTF-8的問題就算成功80%,測試也很順利就成功了。
3.tomcat+spring+jdbc+mysql
現在把spring加進系統內,利用spring內的JDBCTemplate進行連線與資料處理,發現相當的好用,這個過程中除了xml的設定檔寫錯之外,沒有特別的困難,原來在mysql的UFT-8設定也有起作用,所以也算順利成功了。
4.tomcat+spring+c3p0+jdbc+mysql
一個具有水準的系統,當然要有connection pool啦,預設spring裏面就有附c3p0 (個人無責任亂猜,這個名字應該是從星際大戰裏面來的吧?)這個connection pool,索性就拿來用,這部份在網路上的教學文章也很多,而且大部份都是正確的,實屬難得,xml的設定就不貼在這裡佔文章篇幅,唯一要注意的還是xml檔案不要寫錯….(程式沒寫幾行,但是好多設定檔….)
5.tomcat+jsp(form)+spring+c3p0+jdbc+mysql
一個系統當然要有input與output機制,在tomcat裏面要滿足這些機制當然會用到jsp(html)的form來達成,為什麼要特別說是jsp的form呢?因為不知道從哪一版的tomcat開始,在jsp裏面設定編碼這方法對form的資料傳遞已經起不了作用,有關這部份在網路上的地雷非常多(尤其是簡體的資料,天下文章都亂抄),我花了一個早上的時間才找到問題,原來問題在於tomcat的預設傳遞編碼還是iso-8859-1,導致寫進去mysql的也是亂碼,tomcat的部份除了在servelt接收的時候利用request物件預先進行設定之外(是否有效我也不知道,沒有實驗過,因為在spring裏面我不會用到request這個物件,我用spring裏面的SimpleFormController+POJO取代request的功能);另外的解法就是要在web.xml裏面加上filter,作法如下:
1.將tomcat預設網站裏面的一個class複製到網站的WEB-INF/classes/filters/下面,這個class的位置在webapps/examples/WEB-INF/classes/filters/下,一個叫作SetCharacterEncodingFilter的class檔案
2.設定web.xml,加上filter的設定,我的設定(節錄)如下:<filter>
<filter-name>Set Character Encoding</filter-name>
<filter-class>filters.SetCharacterEncodingFilter</filter-class>
<init-param>
<param-name>encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>Set Character Encoding</filter-name>
<url-pattern>*.jsp</url-pattern>
</filter-mapping>以上url-pattern的部份請自行依照現況修改,不要照抄。
3.重新啟動tomcat,應該就可以正常的傳遞UTF-8的中文了。
完成以上設定,理論上就可以從網頁上一路暢通到mysql資料庫裏面,UTF-8中文一切正常,從此過著幸福快樂的生活….
才怪!
經過這樣的設定,寫進mysql的資料依舊是亂碼,還好有log4j的加持,在層層的log中發現,確定jsp的form在傳遞過程中的中文是沒有問題的,也把要送進JDBCTemplate的SQL語法直接在command line下執行,也是可以正確的把資料更新到mysql裏面,那….問題出在哪裡?是jdbc?是mysql?還是c3p0?
於是又花了不少時間在找資料,但是很奇怪,找到的資料幾乎都是要c3p0搭配Hibernate,問題是我用不到Hibernate啊,好吧,既然找不到,我一個個去排除看看囉….
首先把c3p0還有JDBCTemplate都拿掉,直接使用jdbc執行–OK
接下來把JDBCTemplate加進去–OK
嗯,很好!
再把c3p0加進去就–出包了!?
原來是c3p0害的….嗎?難道我要換connection pool?
想想實在心有不甘,雖然有很多傳說c3p0在連線上依舊有不少問題,但是要換connection pool的話我又要掉進設定檔的圈套裡去,眼看快要下班了,乾脆死馬當活馬醫,反正電腦裏面有裝postgresql,拿來試試看也好,果不其然,試起來的效果還真是好,完整的中文進去也是完整的出來,根本看不到有什麼亂碼,這下好了,問題到底在哪裡….?是c3p0?還是mysql?
最後只能下個毫無研究精神的結論:
把mysql換掉,用postgresql吧!
如果有哪位高人知道其中奧妙,還請不吝指正,小弟也很想知道這個問題的答案呀~~
jdbc:mysql://localhost/some_db?useUnicode=yes&characterEncoding=UTF-8
基本上,mysql 的 jdbc 連線字串,要加上 unicode 的設定
這是早期從 4.x 就有的東西~~
試試看
另外 如果你用了 Spring,可以用 spring-mvc 中的org.springframework.web.filter.CharacterEncodingFilter
基本上 request 的 characterEncoding 設定是可以不用自己寫程式的~~~
用法可以參考 javadoc
希望還來的及幫的到忙
其實不管是不是使用jdbc,就算是使用php去連線mysql都是要加上編碼與UTF-8的設定(之前的慘痛經驗),所以之前一直都和mysql相處愉快,但是這次特別奇怪,只要把c3p0加進去就會出問題,不使用c3p0的時候就是完全OK的,一點亂碼都沒有,所以我才會弄的焦頭爛額,索性跳槽到PostgreSQL (沒想到P牌的DB意外的好用XD)
至於網頁編碼部份,可能是我被網路上的地雷炸暈了,難得找到一個可以用的辦法就當作救生圈死抓不放,至於spring-mvc的方法我還沒試過,感謝你提供的資訊囉m(_*_)m