时间:2021-07-01 10:21:17 帮助过:2人阅读
-- Set up sample encryption database USE master; GO -- Set up a login IF SUSER_SID(‘User1‘) IS NOT NULL DROP LOGIN User1; CREATE LOGIN User1 WITH password = ‘3f@$fWDY3QvP&K0‘; GO IF DB_ID(‘EncryptionDB‘) IS NOT NULL DROP DATABASE EncryptionDB; CREATE DATABASE EncryptionDB; GO USE EncryptionDB; GO CREATE USER User1 FOR LOGIN User1; GO USE EncryptionDB; GO -- Databases do not have a master key by default, so you must create it before you can use it: CREATE MASTER KEY ENCRYPTION BY PASSWORD = ‘gK#3hbQKDFQY0oF‘; GOView Code
代码8.1 在EncryptionDB库中创建Database Master Key
Database Master Key存储两次:它首先被Service Master Key加密存储,然后被你提供的密码再次加密。你可以删除两者中的一个,但不能全删除。通常情况下不会操作它们。
作为对称密钥,Database Master Key在你使用前必须找开它。打开一个密钥加载到内存然后解密,然后就可以使用。因为服务器级的Service Master Key加密了Database Master Key,数据库能自动为你打开密钥,很少需要你显示的去打开。类似Service Master Key,你可以备份、还原、修改Database Master Key.
你将使用图8.1中的其他密钥来加密数据。箭头指示使用哪一个密钥来加密和保护其他的密钥。例如,你可以使用Database Master Key来加密证书或非对称密钥。证书和非对称密钥只能保护对称密钥。对称密钥可以通过证书、非对称密钥或其他对称密钥来保护。
密钥管理
图8.1显示了加密密钥的另一个方面:你可以使用另一个密钥或一个密码来创建密钥。这就是所谓的密钥管理,这是SQL Server能为你管理的一个主要服务。
Key management is the single hardest thing to get right about encryption。历史上充满了各种国家的秘密,当密钥被截取时/泄露。第二次世界大战期间,美国、英国和其他盟国把大量的资源投入到德国和日本使用的加密密钥,以使他们能够拦截和读取高度敏感的信息。在最近的一次,许多高安全的应用程序被攻破,因为攻击者能够找到在应用程序或在计算机上嵌入的密钥。分享秘密是很困难的。
如果选择使用密码你可以自己管理SQL Server加密密钥,然后你肩负着保管密钥的责任。大多数人不想这样做,因为它需要高度专业化的技术技能。但是,如果你想承担这个任务,只要你创建一个密钥时使用密码选项。密码基本上是密钥,你必须确保你可以将密钥保存在安全的位置,并在需要时将其安全传输。
但是你不需要处理这些细节,因为SQL Server将为你照顾密钥管理。它将为你加密新的密钥,使用你所指定的任何方法,并将数据存储为安全地存储任何其他敏感信息。
你有权管理钥匙,但没有一个很好的理由你不应该这样做。
加密数据
现在来看一个SQL Server中加密数据的例子。在这个场景,Customer表通常具有客户的常规信息。客户名称和所在城市,不是敏感数据,不需要加密;但是信用卡类型、帐号可能包含个人敏感信息,应该进行加密。
你将使用一个对称密钥来加密表中的数据,记住一个对称密钥需要一个证书或非对称密钥在数据库中保护。因此,首先使用代码8.2创建一个非对称密钥来保护对称密钥:
-- Create an asymmetric key to protect the new symmetric key CREATE ASYMMETRIC KEY User1AsymmetricKey AUTHORIZATION User1 WITH ALGORITHM = RSA_2048;
代码8.2 创建一个非对称密钥
这个非对称密钥叫做User1AsymmetricKey,被User1用户拥有。这个密钥使用2048位的RSA加密,这是非常强/复杂的加密算法。这类数据肯定是非常非常重要!
接着,使用代码8.3创建一个对称密钥User1SymmetricKey.本例中使用TRIPLE_DES算法,并且被刚才创建的非对称密钥保护:
-- Create a symmetric key, protected by the asymmetric key CREATE SYMMETRIC KEY User1SymmetricKey WITH ALGORITHM = TRIPLE_DES ENCRYPTION BY ASYMMETRIC KEY User1AsymmetricKey;
代码8.3 创建一个对称密钥
如果你想罗列数据库下的对称加密密钥,你可以使用sys.symmetric_keys目录视图来查看。代码8.4执行结果如图8.2所示。注意,因为Database Master Key是一个对称密钥,它也会出现在结果中。
-- List the symmetric keys in the database SELECT * FROM sys.symmetric_keys;
代码8.4 罗列数据库下的对称密钥
图8.2 sys.symmetric_keys目录视图返回结果
代码8.5是EncryptionDB数据库下Customer表的结构:
USE EncryptionDB; GO CREATE TABLE Customer ( CustId int, Name nvarchar(30), City varchar(20), CreditCardType varbinary(1000), CreditCardNumber varbinary(1000), Notes varbinary(4000)); GO -- Grant access on the table to user GRANT SELECT, INSERT ON Customer to User1;
代码8.5 创建Customer表
注意,因为最后三列将会保存加密后的binary类型数据而不是原始的string数据,因此列的类型设置成varbinary。列的长度依赖数据的大小以及算法。数据库有一个User1用户,对Customer表有SELECT和INSERT权限。
是时候加密一些数据并插入到数据库中。第一步使用代码8.6打开对称密钥,这一步引起SQL Server在内部存储查找密钥,确保用户有权限使用密钥,然后解密密钥到内存以准备使用:
OPEN SYMMETRIC KEY User1SymmetricKey DECRYPTION BY ASYMMETRIC KEY User1AsymmetricKey;
代码8.6 打开对称密钥
数据加密使用T-SQL语句EncryptByKey函数,使用唯一的GUID区分密钥。你可以使用Key_GUID函数检索GUID而不是直接传送数值。否则,代码8.7是一个普通的T-SQL插入语句:
INSERT INTO Customer VALUES (1, ‘Sally Roe‘, ‘Chatinika‘, EncryptByKey(Key_GUID(‘User1SymmetricKey‘), ‘Visa‘), EncryptByKey(Key_GUID(‘User1SymmetricKey‘), ‘1234-5678-9009-8765‘), EncryptByKey(Key_GUID(‘User1SymmetricKey‘), ‘One of our best customers. Treat like royalty.‘));
代码8.7 插入加密数据
最后一步使用代码8.8关闭对称密钥。它会从内存中移除密钥并释放资源。只要你不需要加密了就应该尽快关闭密钥,因为把它留在内存可能会被攻击者利用。
CLOSE SYMMETRIC KEY User1SymmetricKey;
代码8.8 关闭对称密钥
提示:如果你要使用密钥在一个单独批处理中加密或解密大量的数据,可以它先打开着。打开和关闭密钥需要处理时间的。但是当你完成的时候,别忘了把它关上!
现在运行一个查询语句查看表中的数据,如图8.3所示。你可以看到在CustId、Name、City列数据没有加密,但是在加密列文本是随机binary数据。你的数据是安全的!
图8.3 表中存储的加密数据
表中的数据是没有价值的,除非有一个方法来检索它。本例中你需要使用一个常规查询语句,并且使用DecryptByKey函数来解密数据。这个函数返回varbinary数据,因为加密数据可能是任何数据类型。因此要检索原始文本需要你对DecryptByKey函数结果进行转换。
OPEN SYMMETRIC KEY User1SymmetricKey DECRYPTION BY ASYMMETRIC KEY User1AsymmetricKey; SELECT CustID, Name, City, CONVERT(VARCHAR, DecryptByKey(CreditCardType)) AS CardType, CONVERT(VARCHAR, DecryptByKey(CreditCardNumber)) AS CardNumber, CONVERT(VARCHAR, DecryptByKey(Notes)) AS Notes FROM Customer; CLOSE SYMMETRIC KEY User1SymmetricKey;
代码8.9 打开密钥然后执行查询语句
图8.4 解密数据结果
-- *** Encryption Catalog Views *** -- ******************************** -- Existing keys SELECT * FROM sys.certificates; SELECT * FROM sys.asymmetric_keys; SELECT * FROM sys.symmetric_keys; SELECT * FROM sys.database_principals; SELECT * FROM sys.key_encryptions; SELECT * FROM sys.crypt_properties; -- Information about keys -- Returns a row for each symmetric key encryption specified using the ENCRYPTION BY clause of the CREATE SYMMETRIC KEY statement. SELECT * FROM sys.key_encryptions; -- Returns one row for each cryptographic property associated with a securable SELECT * FROM sys.crypt_properties; -- *** Clean up *** -- **************** USE master; GO IF SUSER_SID(‘User1‘) IS NOT NULL DROP LOGIN User1; IF DB_ID(‘EncryptionDB‘) IS NOT NULL DROP DATABASE EncryptionDB; GOView Code
总结
SQL Server的数据加密功能为你的数据提供额外的保护层,让你在深度防御。SQL Server攻击者必须攻破网络安全、服务器安全、SQL Server实例的安全性、以及数据库的安全来获得你的数据。然后,与胜利如此接近,他们必须处理强加密的数据才能为其所用。结合强大的数据库安全性,充分利用细粒度的权限以对主体需要访问的数据提供最小特权,你可以为最敏感的数据建立强大的保护。
第八篇 SQL Server安全数据加密
标签: