使用tinyint(1) 用來存儲枚舉時候的坑
場景描述:
公司某個系統分別在dev,test等多個環境進行部署,但是某一天在聯調過程中發現dev環境的很多地方的枚舉值無法正常顯示 均為null。但是在其他多個環境,均能正常顯示。有點懵逼,然后開啟排查模式ing....
問題排查
-
保證在dev,test環境發布同樣的分支
結果:test環境ok,dev環境任然異常-->排除代碼問題
-
在dev環境,本地 使用同一個數據庫查詢
結果:本地環境ok,dev環境任然異常-->排除數據問題
-
找運維臨時開放遠程debug端口
本地遠程debug,果真枚舉顯示null異常--->確定是開發環境的問題
3.1 去私服上下載剛打包的項目jar 本地引用后使用
結果:顯示正常 -->排除部署的jar包問題
3.2 去開發環境機器上獲取相關配置文件進行對比
結果:配置文件存在差異。修復差異后重新部署 ->dev環境顯示正常
問題出現的根源:原先我司xxx系統是dev,test 將相關的配置文件打包至jar中,使用項目中的配置文件。最近由運維團隊統一管理配置文件。運維小伙伴在維護dev配置文件時候,dev相關的配置未與代碼中保持一致(dev環境缺少 tinyInt1isBit=false)。
事后詳細學習下tinyInt1isBit=false 的作用
JAVA數據類型 和 MYSQL的數據類型轉換,要注意tinyInt 類型,且存儲長度為1的情況。
先看下mysql官網的介紹
java.lang.Boolean if the configuration property tinyInt1isBit is set to true (the default) and the storage size is 1, or java.lang.Integer if not.
tinyInt(1) 只用來代表Boolean含義的字段,且0代表False,1代表True。如果要存儲多個數值,則定義為tinyInt(N), N>1。例如 tinyInt(2)
項目中需要使用枚舉時候(0:默認,1:成功,2:失敗,3:異常,4:未知錯誤...),有兩種方式可以正常展示枚舉
方式1:
JDBC的URL增加 tinyInt1isBit=false參數,注意參數名區分大小寫,否則不生效
jdbc:mysql://${ucmha.proxy1_2.host}/${db.mysql.db}?tinyInt1isBit=false
方式2:
一定要用tinyint就增加長度(tinyInt(N), N>1 比如tinyint(4))
實測分析
場景1:tinyInt1isBit 使用默認值true and 使用tinyint(1)
#alter table tableA add COLUMN `return_type` tinyint(1) NOT NULL DEFAULT '0' COMMENT '狀態(0未審批 1審批通過 2審批拒絕 3 拒絕失敗 4 拒絕中)'; spring.datasource.url=jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=utf-8&allowMultiQueries=true&useAffectedRows=true
會發現實際java代碼中查詢實體后,對於枚舉值的展示均出現異常,顯示為 null
場景2:tinyInt1isBit 使用false and 使用tinyint(1)
#alter table tableA add COLUMN `return_type` tinyint(1) NOT NULL DEFAULT '0' COMMENT '狀態(0未審批 1審批通過 2審批拒絕 3 拒絕失敗 4 拒絕中)'; spring.datasource.url=jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=utf-8&allowMultiQueries=true&tinyInt1isBit=false&useAffectedRows=true
可正常顯示枚舉
場景3:tinyInt1isBit 使用默認值true and 使用tinyint(n) (n>1)
#alter table tableA add COLUMN `return_type` tinyint(2) NOT NULL DEFAULT '0' COMMENT '狀態(0未審批 1審批通過 2審批拒絕 3 拒絕失敗 4 拒絕中)'; spring.datasource.url=jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=utf-8&allowMultiQueries=true&useAffectedRows=true
tinyint(n) (n>1) 可正常顯示枚舉