爲了滿足安全性要求,我需要找到一種方法,在向開發人員提供數據庫之前,用唯一的隨機9位數字代替SSN。 SSN位於數據庫表的一列中。所述表格中可能有成千上萬的行。數字不需要連字符。我是一個初學SQL和一般編程的人。如何用SQL Server 2008R2中的9位隨機數替換SSN?
我一直無法爲我的特定需求找到解決方案。沒有什麼似乎很正確。但是,如果您知道我錯過的線索,請告訴我。
感謝您的幫助!
爲了滿足安全性要求,我需要找到一種方法,在向開發人員提供數據庫之前,用唯一的隨機9位數字代替SSN。 SSN位於數據庫表的一列中。所述表格中可能有成千上萬的行。數字不需要連字符。我是一個初學SQL和一般編程的人。如何用SQL Server 2008R2中的9位隨機數替換SSN?
我一直無法爲我的特定需求找到解決方案。沒有什麼似乎很正確。但是,如果您知道我錯過的線索,請告訴我。
感謝您的幫助!
這是一種方法。
我假設您已經擁有真實數據的備份,因爲此更新不可逆。
下面我假設你的表名是人名爲SSN您的SSN列。
UPDATE Person SET
SSN = CAST(LEFT(CAST(ABS(CAST(CAST(NEWID() as BINARY(10)) as int)) as varchar(max)) + '00000000',9) as int)
工作很好。我希望結果能夠滿足要求,但它看起來不錯並且非常容易。謝謝。 – user1901945
如果它們不必是隨機的,那麼可以用升序數值替換它們。否則,你必須生成一個隨機數。正如您可能已經發現的那樣,RAND函數只會爲每個查詢語句(選擇,更新等)生成一個值;解決此問題的方法是newid()函數,該函數將爲查詢生成的每行生成GUID(運行SELECT newid() from MyTable
以查看其工作原理)。將其包裝在校驗和()中以生成一個整數;通過1,000,000,000獲得SSN範圍內的值(0至999,999,999)的模數;假設你將它存儲爲一個char(9)前綴爲前導零。
下一個技巧是確保它對錶中所有值都是唯一的。這會變得棘手,我會通過設置一個帶有值的臨時表來填充它,然後複製它們。承租人現在...
DECLARE @DummySSN as table
(
PrimaryKey int not null
,NewSSN char(9) not null
)
-- Load initial values
INSERT @DummySSN
select
UserId
,right('000000000' + cast(abs(checksum(newid()))%1000000000 as varchar(9)), 9)
from Users
-- Check for dups
select NewSSN from @DummySSN group by NewSSN having count(*) > 1
-- Loop until values are unique
IF exists (SELECT 1 from @DummySSN group by NewSSN having count(*) > 1)
UPDATE @DummySSN
set NewSSN = right('000000000' + cast(abs(checksum(newid()))%1000000000 as varchar(9)), 9)
where NewSSN in (select NewSSN from @DummySSN group by NewSSN having count(*) > 1)
-- Check for dups
select NewSSN from @DummySSN group by NewSSN having count(*) > 1
這適用於我有一個小桌子,它應該爲一個大的工作。我沒有看到這變成一個無限循環,但即使如此,你可能想要添加一個檢查退出循環後說10迭代,
這裏假定SSN是表中唯一的一列。重複(兩行一個人)需要額外的處理。 –
'RAND'函數*可以*生成每行不同的值,假設你給它種子'SELECT RAND(num)AS orly FROM(SELECT 1 UNION ALL SELECT 500000)D(num);' – billinkc
很高興知道。如果源表中有唯一的代理鍵(如SSN),可以在這裏工作。安全純粹主義者可能會認爲這是一個可能的違規行爲,因爲您可能會從生成的值中反向設計原始值。 –
我已經運行了幾百萬測試在這和它似乎產生隨機(URN)9位數字(無前導零)。 我想不出一個更有效的方法來做到這一點。
SELECT CAST(FLOOR(RAND(CHECKSUM(NEWID())) * 900000000) + 100000000 AS BIGINT)
該測試使用;
;WITH Fn(N) AS
(
SELECT CAST(FLOOR(RAND(CHECKSUM(NEWID())) * 900000000) + 100000000 AS BIGINT)
UNION ALL
SELECT CAST(FLOOR(RAND(CHECKSUM(NEWID())) * 900000000) + 100000000 AS BIGINT)
FROM Fn
)
,Tester AS
(
SELECT TOP 5000000 *
FROM Fn
)
SELECT LEN(MIN(N))
,LEN(MAX(N))
,MIN(N)
,MAX(N)
FROM Tester
OPTION (MAXRECURSION 0)
沒有這麼快,但最簡單的...我加了一些點的...
DECLARE @tr NVARCHAR(40)
SET @tr = CAST(ROUND((888*RAND()+111),0) AS CHAR(3)) + '.' +
CAST(ROUND((8888*RAND()+1111),0) AS CHAR(4)) + '.' + CAST(ROUND((8888*RAND()+1111),0) AS
CHAR(4)) + '.' + CAST(ROUND((88*RAND()+11),0) AS CHAR(2))
PRINT @tr
如果要求混淆一個數據庫,那麼這將返回相同的獨特價值爲每個不同的SSN在任何表中保留輸出中的參照完整性,而不必查找和翻譯。
SELECT CAST(RAND(SSN)*999999999 AS INT)
,請告訴我們你的表結構(相關字段名稱和數據類型) – Tahbaza
是期望,開發人員將能夠解密的隨機數回到正確的SSN?或者,隨機數字是唯一的ID來標識用戶? – MadHenchbot
在這種情況下,不需要擁有SSN - 它是唯一的ID。將db提供給開發人員是爲了測試/調試目的,因此數據庫必須運行,但除非必要,否則必須編輯SSN(可能還有其他PII)。 – user1901945