有的時候我們資料庫設(shè)計可能不會完全和程式碼語言一致,例如我們會在資料庫的每一張表前面加上一個特定的前綴用來區(qū)分,在BeetlSQL中將程式碼Pojo的名稱和資料庫Table名稱對應(yīng)起來是使用NameConversion來轉(zhuǎn)換的,BeetlSQL內(nèi)建了DefaultNameConversion、UnderlinedNameConversion和JPANameConversion等轉(zhuǎn)換器基本上可以滿足絕大部分的要求的,今天就來給大家示範(fàn)一下如何自訂NameConversion。
前言
要了解本文的內(nèi)容,首先你需要先了解Beetl和BeetlSQL這兩個項目,它們是來自於國人@閒·大賦嘔心瀝血精心打造的Java模板引擎和Java數(shù)據(jù)庫全功能Dao,而且目前官方已經(jīng)提供了Beetl和BeetlSQL與市面上各種主流MVC框架的整合方案
我不敢說Beetl比JSP、FreeMarker、Velocity等大家熟知的一些模板引擎怎麼說的好,但是我想說以我個人的使用經(jīng)驗來做對比,Beetl絕對不會比它們差,BeetlSQL更是不會比Hibernate和MyBatis等差
如果有興趣想了解一下Beetl和BeetlSQL,可以訪問Beetl官方論壇查閱詳情。
何不給Beetl一個機會來證明Beetl自己,更是給你自己一個學(xué)習(xí)工作嘗試的機會,說不定你就和我一樣一不留神就愛上了它。
正文
本文討論的是使用BeetlSQL自動產(chǎn)生Pojo物件時,透過自訂轉(zhuǎn)換器移除映射表名前綴的問題。
先看一組開發(fā)遇到的情況:
假定目前有個項目beetl在資料庫設(shè)計的時候,所有的表名都有一個項目前綴bt_,即所有的表都以bt_開頭,如bt_user、 bt_role、bt_user_role,看到這樣的表名設(shè)計我們可能第一想到的是使用UnderlinedNameConversion來進行轉(zhuǎn)化,於是乎:
bt_user-> BtUser
bt_role -> BtRole
肯定跟我一樣是不能接受這樣的命名的,所以我們需要自己定義一個NameConversion來進行轉(zhuǎn)換,去除掉Table生成Pojo時自動加上的Bt前綴NameConversion中核心的幾個方法getPropertyName、getColName、getTableName、 getClassName,根據(jù)方法名稱和參數(shù)很容易理解@Overridepublic String getTableName(Class<?> c) { //遵循BeetlSQL規(guī)范,@Table擁有最高優(yōu)先級 Table table = (Table)c.getAnnotation(Table.class); if(table!=null){ return table.name(); } //UserRole -> user_role String tableName = StringKit.enCodeUnderlined(c.getSimpleName()); //user_role -> bt_user_role return "bt_"+tableName; }@Overridepublic String getClassName(String tableName){ //假定所有表都是以bt_開頭 //bt_user_role -> user_role tableName = tableName.substring(tableName.indexOf("_")+1); //user_role -> userRole String clsName = StringKit.deCodeUnderlined(tableName); //userRole -> UserRole return StringKit.toUpperCaseFirstOne(clsName); }就這樣輕鬆的完成的整個資料庫的表名去前綴。 事與願違! ! ! 往往我們可能還會遇到更特殊的情況,以下讓我們再來看一組開發(fā)可能遇到的情況:目前有一個項目,裡面有一些使用者的資料表(如User),後臺管理的資料表(如Admin)和先前使用者與後臺公共的資料表(如City),然後在開發(fā)時為了做區(qū)分,分別為不同的功能模組的表加上了不同的前綴,最後我們的表名可能是:usr_user 、mgr_admin和base_city這樣的形式,這時候我們再用上面的方式統(tǒng)一去前綴再統(tǒng)一加前綴肯定是行不通的,畢竟前綴不一樣你去掉前綴後是很難直接還原的。 最初我遇到這樣的問題,第一個想法是,讓BeetlSQL反向生成Pojo的時候,去除前綴然後自動給所有的Pojo加上@Table的註解,例如例子中的usr_user、mgr_admin和base_city三張表最後可能產(chǎn)生以下形式:usr_user -> @Table(name="usr_user") Usermgr_admin -> @Table(name="mgr_admin") Adminbase_citybase -> @Table(name="m_city_city" ) City
理想是豐滿的,現(xiàn)實是骨感的。在QQ上與作者溝通遇到這種情況時的解決方案時發(fā)現(xiàn)可能會出現(xiàn)這樣的情況: 前臺用戶使用的數(shù)據(jù)表可能是 usr_user,而后臺管理員也屬于用戶呀,因此可能后臺管理員的數(shù)據(jù)表為mgr_user,最后這樣會導(dǎo)致兩個類沖突了,生成代碼的時候可能會被覆蓋一個類,是有問題的。好在機智如我~遇到這樣的根據(jù)功能模塊給不同的表加上不同的前綴,我們在Java程序開發(fā)時也經(jīng)常會使用不同的包名來區(qū)分不同的模塊,我可以將不同前綴的實體放到對應(yīng)的包下面,還原表名的時候讀取一下包名即可反向解析出表名,下面是我的具體實現(xiàn):
@Overridepublic String getClassName(String tableName){ //為了安全起見,做了個判斷,理論上項目數(shù)據(jù)庫設(shè)計好了應(yīng)該是無需判斷直接截取所有前綴 //usr_user_role -> user_role if(tableName.matches("^(usr_|base_|mgr_).*")){ tableName = tableName.substring(tableName.indexOf("_")+1); } //user_role -> UserRole String clsName = StringKit.deCodeUnderlined(tableName); return StringKit.toUpperCaseFirstOne(clsName); }@Overridepublic String getTableName(Class<?> c) { Table table = (Table)c.getAnnotation(Table.class); if(table!=null){ return table.name(); } //獲取Package 最后一層 xxx.pojo.usr -> Usr String pkg = c.getPackage().getName(); pkg = pkg.substring(pkg.lastIndexOf(".")+1); pkg = Character.toUpperCase(pkg.charAt(0))+pkg.substring(1); //Usr+User -> UsrUser -> usr_user return StringKit.enCodeUnderlined(pkg+c.getSimpleName()); }
然后在使用BeetlSQL反向生成Pojo的時候,使用Filter將數(shù)據(jù)表分門別類的生成到不同的包下面
//記得初始化SQLManager時要使用自己寫好的NameConvertionSQLManager sql = initSQLManager(); GenConfig config = new GenConfig(); sql.genALL("xxxx.pojo.usr", config, new GenFilter(){ @Override public boolean accept(String tableName) { return tableName.startsWith("usr_"); } }); sql.genALL("xxxx.pojo.mgr", config, new GenFilter(){ @Override public boolean accept(String tableName) { return tableName.startsWith("mgr_"); } }); sql.genALL("xxxx.pojo.base", config, new GenFilter(){ @Override public boolean accept(String tableName) { return tableName.startsWith("base_"); } });
最終會在項目中會生成以下Pojo
usr_user -> xxxx.pojo.usr.User.java
mgr_admin -> xxxx.pojo.mgr.Admin.java
base_city -> xxxx.pojo.base.City.java
即便是有類名沖突的,因為在不同的包下,所以也不會影響
就這樣一次輕松而又愉快的BeetlSQL自定義去除Pojo和表前綴被解決啦~
最后
之前所有項目的開發(fā)都是Jsp,幾乎沒使用過其他第三方模板庫,因為一次誤打誤撞讓我認識了Beetl,它的輕巧,它獨特的語法都深深的吸引了我,因為Beetl又讓我認識了BeetlSQL,抱著試一試的心態(tài)嘗試過之后總有一種把當(dāng)前項目(使用的Hibernate)推倒重來的沖動,雖然最后因為項目的工程量和工期原因,當(dāng)前的這個項目最終還是使用了Hibernate,但是我可以確定的是,在以后的開發(fā)道路上,如果允許,如果沒有能讓我更心動的通用Dao,BeetlSQL將會是我不二的選擇。
今天在這里分享這篇自定義NameConvertion的功能,其實并沒有多少技術(shù)含量,更多的是想做一次簡單的推廣,讓更多人知道Beetl,讓更多人愛上Beetl~

熱AI工具

Undress AI Tool
免費脫衣圖片

Undresser.AI Undress
人工智慧驅(qū)動的應(yīng)用程序,用於創(chuàng)建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Clothoff.io
AI脫衣器

Video Face Swap
使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱門文章

熱工具

記事本++7.3.1
好用且免費的程式碼編輯器

SublimeText3漢化版
中文版,非常好用

禪工作室 13.0.1
強大的PHP整合開發(fā)環(huán)境

Dreamweaver CS6
視覺化網(wǎng)頁開發(fā)工具

SublimeText3 Mac版
神級程式碼編輯軟體(SublimeText3)