不能坐視了!Oracle資料庫varchar2欄位擴容,每月總有那麼一兩次。----- 優秀的程式應總是儘可能地規避問題

来源:https://www.cnblogs.com/buguge/p/17995321
-Advertisement-
Play Games

優秀的程式應該儘可能地規避問題。因此,以後在服務商系統里,當定義包含漢字的欄位時,使用 nvarchar2,而非 varchar2。 因此,在服務商系統作為我司系統的小眾系統的背景下,Oracle的技術特性我們不一一曉知是可以理解和接受的。而如何在不一一曉知這些技術特性的情況下,能夠規避這些技術特性... ...


Oracle資料庫varchar2欄位擴容-始末

今天,有後端小伙伴提了個sql工單。對我司服務商系統Oracle資料庫的一個mer_name欄位擴容。

alter table T_MER_SETTLE modify mer_name VARCHAR2(100)

審批前,我查了一下當前這個mer_name欄位的長度是 VARCHAR2(64)。

基於對我司客戶名稱的長度通常不超過64字的瞭解,我下意識里感到奇怪:莫非存在長度超過64個文字的客戶名稱?這種情況應該很少吧?什麼公司的名字能有這麼長呢?

 

然後,我找當事人來詢問。他言說,當時開發需求時,看到企業表裡的mer_name是varchar2(100),就沿襲使用varchar2了,加上對系統里企業名稱長度通常不會超過64個漢字的認識,就把新表的mer_name定義為varchar2(64)。 今天生產環境的告警顯示,在向這個T_MER_SETTLE表插入數據時出現“欄位值超長”持久化失敗的bug,這才得知Oracle的varchar2(64)與mysql的varchar(64)不同,mysql的varchar(64)能存最多64個字元,而Oracle的varchar2(64)則不同。在資料庫字元集是UTF-8的情況下,varchar2在存漢字時,是每個漢字占3個位元組。也就是說,這個varchar2(64)最多可以存64/3=21個漢字。

 

本著解決問題優先的原則,我審批了sql工單並執行sql。

 

優秀的程式應該儘可能地規避問題

欄位擴容,這是我們日常開發中經常遇到的小事。我們服務商系統類似對varchar2欄位擴容的案例,幾乎每月都發生。那麼,針對這個欄位擴容,大家有沒有琢磨過,我們如何在開發時就能規避呢?

優秀的程式應該儘可能地規避問題。我們來複盤一下這個事情。

有必要先說明一個情況,我司絕大多數系統以mysql資料庫為主,服務商系統是其中唯一一個使用Oracle資料庫的小眾系統。並且,服務商系統的日常維護或需求迭代較少,由我們技術團隊中的三個同學抽一部分精力兼管。 因此,大家對Oracle資料庫瞭解得並不多,相比mysql,就少多了。

好,繼續來複盤。
開發人員不瞭解varchar2這個技術點,憑著mysql資料庫經驗和對業務的瞭解,定義了  mer_name VARCHAR2(64) 。
我在審批時,也不瞭解varcahr2這個技術點,就去反問開發同學。同樣,其他同學,也未必清楚Oracle的varchar2這個數據類型的細節。

 

那麼,如何規避呢?

無藥可救了嗎?

不!

我們事後瞭解到,Oracle的nvarchar2不區分字元類型,它將漢字、全形符號與數字、字母、半形符號等均視為一個字元。也就是說,nvarchar2(64)表示可存最大64個字元。註意這裡不是位元組,而是字元。 包括 數字、字母、符號、以及漢字。同時,在存儲含有文字的欄位時,Oracle開發規範里建議使用nvarchar2取代varchar2。

因此,我們可以做什麼?

將資料庫里的mer_name的數據類型全部改為nvarchar2,以及其他的這種varchar2欄位類型使用不當的欄位。

這以後,服務商系統再有迭代開發時,開發者CV時,就不會(或很少)再有varchar2的mer_name了,樂觀一點講,再出現因varchar2數據類型使用不當而導致“欄位值超長”持久化失敗的bug就會扼殺在搖籃里。

 

【附】Oracle數據類型varchar2與nvarchar2

  1. varchar - Oracle不建議使用varchar類型(我在DBeaver中新建varchar欄位時自動建成了varchar2,無論是所見即所得的操作方式,還是執行DDL方式)
  2. varchar2 - varchar2(20) 表示可存最大20個位元組長度的字元串。 數字/字母/半形符號 占一個位元組。 對於全形符號或漢字,則要看字元集,GBK的話,一個漢字占2個位元組;UTF-8的話,一個漢字占3個位元組。
  3. nvarchar - Oracle中沒有nvarchar這個數據類型
  4. nvarchar2 - nvarchar2(20) 表示可存最大20個字元。註意這裡不是位元組了,而是字元。 包括 數字、字母、符號、以及漢字。每個字元占2個位元組存儲。
 
  • varchar2是Oracle提供的特定數據類型,Oracle可以保證varchar2在任何版本中該數據類型都可以向上或向下相容。
  • nvarchar2雖然更占空間,但是它有更好的相容性。尤其是當欄位包含漢字的情況下,推薦使用nvarchar2。  - - - - - - - - 我們服務商系統Oracle資料庫里,對於mer_name等包含漢字的欄位,大家往往沿襲使用varchar2(100甚至更大),我們在新建表裡涉及到這個欄位時,有開發者會誤以為Oracle的varchar2與mysql里的varchar相同,我們mysql應用里約定mer_name是varchar(32) ,就在Oracle庫里定義成了 varchar2(32) ,結果,服務商系統在生產運行過程中,出現插入mer_name因欄位值超長而持久化資料庫失敗。 - - - - - - - - 優秀的程式應總是儘可能地規避問題。因此,以後在服務商系統里,當定義包含漢字的欄位時,使用 nvarchar2,而非 varchar2。 因此,在服務商系統作為我司系統的小眾系統的背景下,Oracle的技術特性我們不一一曉知是可以理解和接受的。而如何在不一一曉知這些技術特性的情況下,能夠規避這些技術特性帶來的bug,需要我們引起思考和實踐摸索。
 

 【附】欄位值超長,程式異常截圖↓

 


當看到一些不好的代碼時,會發現我還算優秀;當看到優秀的代碼時,也才意識到持續學習的重要!--buguge
本文來自博客園,轉載請註明原文鏈接:https://www.cnblogs.com/buguge/p/17995321



您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 2024年1月2日,北京白鯨開源科技有限公司(以下簡稱"白鯨開源")榮幸宣佈,白鯨開源旗下產品 WhaleStudio V2.4 已成功通過與麒麟軟體有限公司旗下的銀河麒麟高級伺服器操作系統產品的相容性測試。 麒麟軟體有限公司的銀河麒麟高級伺服器操作系統(飛騰版)V10和銀河麒麟高級伺服器操作系統( ...
  • 本文介紹瞭如何通過子查詢優化深度分頁查詢,以減少回表操作帶來的性能損耗。傳統的深度分頁查詢往往會面臨嚴重的性能問題,尤其在處理大量數據時更是如此。 ...
  • 本文介紹了在雲上環境的雙集群(不跨Region不跨VPC)後臺手動部署並使用細粒度容災的主要步驟,使得用戶能快速方便得搭建起細粒度容災。 ...
  • MySQL Shell 8.0.32 for GreatSQL編譯二進位包 構建MySQL Shell 8.0.32 for GreatSQL 0. 寫在前面 之前已經寫過一篇前傳 MySQL Shell 8.0.32 for GreatSQL編譯安裝,最近再次編譯MySQL Shell二進位包時, ...
  • 北京時間2024年2月20日,中國領先的開源技術公司,白鯨開源科技有限公司(以下簡稱"白鯨開源")榮幸宣佈,該公司獲得了第六屆 "年度金猿季大型主題策劃活動" 頒發的 "2023大數據產業年度最具投資價值" 獎項。這一殊榮是對白鯨開源在大數據領域取得的卓越成就和突出貢獻的認可。 金猿季推動產業升級 ...
  • 本文深度解析MySQL的COUNT(1), COUNT(*),COUNT(列)計數方式,強調COUNT(*)的廣泛應用與InnoDB存儲引擎的優化。通過性能比較,揭示COUNT(id)在索引下的性能,通過技術細節揭示MySQL查詢優化器的工作原理,最終總結適用場景,為讀者提供計數方式選擇的指導。 ...
  • 目錄MongoDB創建一張表用法示例資料分享系列文章clickhouse系列文章 MongoDB MongoDB 引擎是只讀表引擎,允許從遠程 MongoDB 集合中讀取數據(SELECT查詢)。引擎只支持非嵌套的數據類型。不支持 INSERT 查詢。 創建一張表 CREATE TABLE [IF ...
  • 工商銀行和華為雲牽頭,並聯合7家金融機構共同編製的《金融行業開放平臺資料庫轉型白皮書》榮獲2023年度十佳課題。 ...
一周排行
    -Advertisement-
    Play Games
  • 1、預覽地址:http://139.155.137.144:9012 2、qq群:801913255 一、前言 隨著網路的發展,企業對於信息系統數據的保密工作愈發重視,不同身份、角色對於數據的訪問許可權都應該大相徑庭。 列如 1、不同登錄人員對一個數據列表的可見度是不一樣的,如數據列、數據行、數據按鈕 ...
  • 前言 上一篇文章寫瞭如何使用RabbitMQ做個簡單的發送郵件項目,然後評論也是比較多,也是準備去學習一下如何確保RabbitMQ的消息可靠性,但是由於時間原因,先來說說設計模式中的簡單工廠模式吧! 在瞭解簡單工廠模式之前,我們要知道C#是一款面向對象的高級程式語言。它有3大特性,封裝、繼承、多態。 ...
  • Nodify學習 一:介紹與使用 - 可樂_加冰 - 博客園 (cnblogs.com) Nodify學習 二:添加節點 - 可樂_加冰 - 博客園 (cnblogs.com) 介紹 Nodify是一個WPF基於節點的編輯器控制項,其中包含一系列節點、連接和連接器組件,旨在簡化構建基於節點的工具的過程 ...
  • 創建一個webapi項目做測試使用。 創建新控制器,搭建一個基礎框架,包括獲取當天日期、wiki的請求地址等 創建一個Http請求幫助類以及方法,用於獲取指定URL的信息 使用http請求訪問指定url,先運行一下,看看返回的內容。內容如圖右邊所示,實際上是一個Json數據。我們主要解析 大事記 部 ...
  • 最近在不少自媒體上看到有關.NET與C#的資訊與評價,感覺大家對.NET與C#還是不太瞭解,尤其是對2016年6月發佈的跨平臺.NET Core 1.0,更是知之甚少。在考慮一番之後,還是決定寫點東西總結一下,也回顧一下.NET的發展歷史。 首先,你沒看錯,.NET是跨平臺的,可以在Windows、 ...
  • Nodify學習 一:介紹與使用 - 可樂_加冰 - 博客園 (cnblogs.com) Nodify學習 二:添加節點 - 可樂_加冰 - 博客園 (cnblogs.com) 添加節點(nodes) 通過上一篇我們已經創建好了編輯器實例現在我們為編輯器添加一個節點 添加model和viewmode ...
  • 前言 資料庫併發,數據審計和軟刪除一直是數據持久化方面的經典問題。早些時候,這些工作需要手寫複雜的SQL或者通過存儲過程和觸發器實現。手寫複雜SQL對軟體可維護性構成了相當大的挑戰,隨著SQL字數的變多,用到的嵌套和複雜語法增加,可讀性和可維護性的難度是幾何級暴漲。因此如何在實現功能的同時控制這些S ...
  • 類型檢查和轉換:當你需要檢查對象是否為特定類型,並且希望在同一時間內將其轉換為那個類型時,模式匹配提供了一種更簡潔的方式來完成這一任務,避免了使用傳統的as和is操作符後還需要進行額外的null檢查。 複雜條件邏輯:在處理複雜的條件邏輯時,特別是涉及到多個條件和類型的情況下,使用模式匹配可以使代碼更 ...
  • 在日常開發中,我們經常需要和文件打交道,特別是桌面開發,有時候就會需要載入大批量的文件,而且可能還會存在部分文件缺失的情況,那麼如何才能快速的判斷文件是否存在呢?如果處理不當的,且文件數量比較多的時候,可能會造成卡頓等情況,進而影響程式的使用體驗。今天就以一個簡單的小例子,簡述兩種不同的判斷文件是否... ...
  • 前言 資料庫併發,數據審計和軟刪除一直是數據持久化方面的經典問題。早些時候,這些工作需要手寫複雜的SQL或者通過存儲過程和觸發器實現。手寫複雜SQL對軟體可維護性構成了相當大的挑戰,隨著SQL字數的變多,用到的嵌套和複雜語法增加,可讀性和可維護性的難度是幾何級暴漲。因此如何在實現功能的同時控制這些S ...