從一個簡單的約束看規範性的SQL腳本對資料庫運維的影響

来源:http://www.cnblogs.com/wy123/archive/2017/09/07/7492063.html
-Advertisement-
Play Games

之前提到了約束的一些特點,看起來也沒什麼大不了的問題,http://www.cnblogs.com/wy123/p/7350265.html以下以實際生產運維中遇到的一個問題來說明規範的重要性。 如下是一個簡單的建表腳本,錶面上看起來並沒有什麼問題。其中創建了3個約束,一個主鍵約束,一個唯一約束,一 ...


 

之前提到了約束的一些特點,看起來也沒什麼大不了的問題,http://www.cnblogs.com/wy123/p/7350265.html
以下以實際生產運維中遇到的一個問題來說明規範的重要性。


如下是一個簡單的建表腳本,錶面上看起來並沒有什麼問題。
其中創建了3個約束,一個主鍵約束,一個唯一約束,一個預設值約束,該腳本執行起來沒有任何問題。

USE Test
GO

if exists(select 1 from sys.tables where name = 'TestConstraint')
    drop table dbo.TestConstraint
GO

create table dbo.TestConstraint
(
    id int primary key,
    name varchar(100) unique,
    createdate date default getdate()
)
GO

 

如下是上述建表腳本執行之後生成的約束信息,可以看到生成的約束都是按照一定規則+隨機字元生成的約束名字。
實話說這不是我們想要的命名方式,之前提到過,我們不願意看到資料庫中存在非預期或者說是隨機的命名信息.
當然不僅僅是強迫症的原因,非要看到一個規範的命名。

隨著需求的變更,需要修改一個欄位的類型,當執行修改欄位類型的腳本的時候,發現報錯了,原因是欄位上有一個約束,如果想要修改欄位類型,就要先刪除這個約束。

   

既然無法直接修改欄位類型,那麼就刪除該約束,再重定義欄位類型,也是沒有問題的。

  

  但是問題就出在這裡,變更腳本的執行肯定是從開發環境開始修改,然後測試,然後再上測試環境,測試通過,最後才上生產環境執行。
  這裡沒辦法保證,在開發環境寫完的腳本,可以直接在測試環境執行,可以在生產環境執行。
  整個流程基本上是自動化執行的,腳本也是通用性執行的,如果中間改來改去,是不是要浪費很多無所謂的時間。
  難不成開發環境寫一個,測試環境寫一個,生產環境寫一個?並且需要一個一個用SSMS打開或者通過系統表來查看具體環境中欄位上約束的名稱?
  某些情況下,對於某些敏感的生產資料庫,不是輕易就可以訪問的。
  當然有人說老子可以隨時連上生產庫,隨時可以通過SSMS圖形界面進行操作,這種情況例外不討論。
    此種情況顯然是不太符合規範的,並且是增加了無所謂的工作量,我想有價值的工作絕不是做這些毫無意義的重覆性勞動吧。

 

 

要想規避此類情況,就要從建表開始,建表的過程中就執行規範的名字,然後這個建表腳本不管在哪個環境,生成的約束都是指定的名字。
在上述修改欄位類型的情況下,寫的腳本就可以通用在各個環境中了。

USE Test
GO

if exists(select 1 from sys.tables where name = 'TestConstraint')
    drop table dbo.TestConstraint
GO
--不要在建表的時候指定約束,這樣會生成隨機的約束名字
create table dbo.TestConstraint
(
    id int not null,
    name varchar(100) ,
    createdate date 
)
GO

--主鍵約束
alter table dbo.TestConstraint
    add constraint [PK_TestConstraint] primary key  clustered (id)  
GO

--唯一約束
alter table dbo.TestConstraint
    add constraint [UQ_TestConstraint_name] unique(name)  
GO

--預設值約束
alter table dbo.TestConstraint
add constraint [DF_TestConstraint_createdate] DEFAULT GETDATE() FOR createdate
GO

當然在修改欄位類型的腳本為了嚴謹期間,也要做到可以重覆執行,以下僅為示例,總之就是要儘可能規範性和嚴謹性,以減少無所謂的麻煩。

if exists(select 1 from sys.default_constraints where name = 'DF_TestConstraint_createdate')
begin
    alter table dbo.TestConstraint
    drop constraint DF_TestConstraint_createdate
end
go

alter table TestConstraint
alter column createdate datetime
GO

alter table dbo.TestConstraint
add constraint DF_TestConstraint_createdate DEFAULT GETDATE() FOR createdate
GO

 

資料庫從安裝,到對外開發使用,到後期的運維,甚至到退役,有一系列的規範性操作。
本文僅從建表時候約束這個個非常小的方面,來說明規範性對開發以及運維工作的影響。
一屋不掃可以掃天下,規範無小事,資料庫也不例外,
說到規範,很多人不屑,認為可有可無,比如說破嘴皮子的三範式,
有人拿著“適度冗餘”來逃避三範式,覺得“適度冗餘”是一個時髦+時尚+牛逼+鄙視呆板的一種設計,
對於關係資料庫,違反三範式的“適度冗餘”一旦考慮的不夠周全,遇到數據的不一致性,就算你死了,你自己去修複數據吧。

以上“改欄位”一句話看起來簡單,遇到這種事,背後一系列操蛋性的操作,如果經常有類似的問題,工作的價值又在哪裡呢?
從最基本的規範就可以看出來一個團隊的工作風格和技術能力。

 

 


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

-Advertisement-
Play Games
更多相關文章
  • Mysql建庫語句(導出的): DROP TABLE IF EXISTS `tablename`; CREATE TABLE `tablename` ( `C_DI_CDE` varchar(40) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL, /*My ...
  • 在hdfs集群上,需要向Hdfs寫入文件,控制台會輸出以下錯誤信息: Caused by: org.apache.hadoop.ipc.RemoteException(org.apache.hadoop.security.AccessControlException): Permission den ...
  • 前陣子遇到一個很是棘手的問題,監控系統DPA發現某個自定義標量函數被調用的次數非常高,高到一個離譜的程度。然後在Troubleshooting這個問題的時候,確實遇到了一些問題讓我很是糾結,下文是解決問題過程的一點思索和嘗試,如果你有更好的思路和解決方法,也請多多指教。 DPA可以監控到該函數每小時... ...
  • Mysql中的常用函數: 1.字元串函數: (1).合併字元串 concat():// concat('M','y',"SQL",'5.5');== MySQL5.5//當傳入的參數有一個值為NULL,返回的結果值為NULL concat_ws();// 指定分隔符插入到字元串中:concat_ws ...
  • 關於oracle with as用法 with as語法–針對一個別名with tmp as (select * from tb_name) –針對多個別名with tmp as (select * from tb_name), tmp2 as (select * from tb_name2), t ...
  • mysql中配置ssl_key、ssl-cert、ssl-ca的路徑及建立ssl連接 ...
  • Mac上MySQL在沒有my.cnf情況自建cnf解決資料庫編碼問題。 ...
  • 什麼是競態問題? 假設有一個計數器,首先當前值自增長,然後獲取到自增長之後的當前值。自增長後的值有可能被有些操作用來當做唯一性標識,因此併發的操作不能允許取得相同的值。 為什麼不能使用使用UPDATE語句更新計數器,然後SELECT語句獲取自增長後的當前值?問題在於併發的操作有可能獲取到相同的計數器 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...