本文主讲 数据库的安全性,欢迎阅读~
数据库的一大特点是数据共享
数据共享必然带来数据库的安全性问题
数据库系统中的数据共享不能是无条件的共享
数据库的安全性:
保护数据库以防止不合法使用所造成的数据泄露、更改或破坏
· 系统安全保护措施是否有效是数据库系统主要的性能指标之一
1 . 数据库的不安全因素
① 非授权用户对数据库的恶意存取和破坏
猎取用户名和用户口令,然后假冒合法用户偷取、修改甚至破坏用户数据。
② 数据库中重要或敏感的数据被泄露
黑客和敌对分子千方百计盗窃数据库中的重要数据,一些机密信息被暴露。
③ 安全环境的脆弱性
数据库安全性与计算机系统安全性紧密联系(计算机硬件、操作系统、网络等安全性)
2 . 安全标准简介
CC(Common Criteria):2008年,CC V3.1 ISO/IEC15408-2008
CC评估等级分为EAL1、EAL2、EAL3、EAL4、EAL5、EAL6和EAL7共七个等级,等级越高,表示通过认证需要满足的安全保证要求越多,系统的安全特性越可靠。
国际标准化组织(International Organization for Standardization,ISO)
非法使用数据库的情况:
① 编写合法程序绕过DBMS及其授权机制
② 直接(或编写应用程序)执行非授权操作
③ 通过多次合法查询数据库从中推导出一些保密数据
计算机系统中,安全措施是一级一级层层设置的:
① 用户标识鉴定用户身份,合法用户准许进入系统
② 数据库管理系统还要进行存取控制,只允许用户执行合法操作
③ 操作系统有自己的保护措施
④ 数据以密文形式存储到数据库中
(ps:数据以密文形式存储在数据库中,即使前三层被攻破,最后看到的是密文的话,是比较有安全性的)
数据库安全性控制的常用方法:
用户标识和鉴定、存取控制、视图、审计、数据加密
① 静态口令鉴别
静态口令一般由用户自己设定,这些口令是静态不变的(例如自己设置的各种登陆密码即静态口令)
② 动态口令鉴别
口令是动态变化的,每次鉴别时均需使用动态产生的新口令登录数据库管理系统,即采用一次一密的方法(例如有的地方每次登陆需要手机短信验证,每次发的验证码就是动态口令~)
③ 生物特征鉴别
通过生物特征进行认证的技术,生物特征如人脸、指纹等(现在这个技术比较普遍啦,很多智能手机上都有指纹识别和人脸识别)
④ 智能卡鉴别
智能卡是一种不可复制的硬件,内置集成电路的芯片,具有硬件加密功能(例如:IC银行卡,IC卡是以芯片作为介质的银行卡,与磁条卡相比,芯片卡安全性高,卡内敏感数据难以被复制)
存取控制机制组成:
用户权限定义和合法权检查机制一起组成了DBMS的存取控制子系统
— — — — — — — — — — — — — — — — — — — — — — — —
常用存取控制方法:
通过 SQL 的GRANT
语句和REVOKE
语句实现
定义用户存取权限:定义用户可以在哪些数据库对象上进行哪些操作
关系数据库系统中存取控制对象:
(ps:ALL PRIVLEGES
即全部权限)
① GRANT 授予
GRANT <权限>[,<权限>]...
ON <对象类型> <对象名>[,<对象类型> <对象名>]…
TO <用户>[,<用户>]...
[WITH GRANT OPTION];
WITH GRANT OPTION子句:
指定:可以再授予
没有指定:不能传播
语义:将对指定操作对象的指定操作权限授予指定的用户(即写了WITH GRANT OPTION
的话,TO之后的用户能继续传播相应的权限)
— — — — — — — — — — — — — — — — — — — — — — — —
这里举例需要用到很多用户,所以咱们先来新建几个用户:
关于如何创建登录名和用户,在查阅了大量资料和自己实践后,我写了一篇博客(做了基础的讲解和示范):SQL Server 创建登录名和用户名【详细介绍】
这里我采用如下格式在STUDENT数据库下创建了U1~U7用户及对应的登录名:
CREATE LOGIN U1 WITH PASSWORD = 'henry626626', DEFAULT_DATABASE = STUDENT;
CREATE USER U1 FOR LOGIN U1;
用以下SQL语句可查看当前数据库下的所有用户:
exec sp_helpuser;
好了~创建成功啦,接下来一大波例子来袭
— — — — — — — — — — — — — — — — — — — — — — — —
来看例 1: 把查询Student表权限授给用户U1:
GRANT SELECT
ON TABLE Student
TO U1;
不是,这第一个例子就这么不友好吗……
这里T-SQL中是不支持上面的标准SQL的写法的,将TABLE
去掉后方能正常运行:
GRANT SELECT
ON Student
TO U1;
如下图查看用户U1确实被授予了查询Student表的权限:
来看例 2: 把对Student表和Course表的全部权限授予用户U2和U3:
GRANT ALL PRIVILIGES
ON TABLE Student, Course
TO U2, U3;
-- 有了刚才的经验教训我去掉了TABLE
GRANT ALL PRIVILIGES
ON Student, Course
TO U2, U3;
emmm,这……(T-SQL和标准SQL要不干脆干一架算了)
因为提示的是"PRIVILIGES"附近有语法错误,所以我查看了SQL官方文档:GRANT (Transact-SQL),发现T-SQL中是有PRIVILEGES
这个参数的,其解释是:包含此参数是为了符合 ISO 标准。 请不要更改 ALL 的行为。emm(人类迷惑行为?,诶,等等我的单词好像写错了,是PRIVILEGES
)
然后有如下图中的报错,原来是因为ON后面只能跟一个对象,所以我将其拆分成了两个SQL语句:
GRANT ALL PRIVILEGES
ON Student
TO U2, U3
GRANT ALL PRIVILEGES
ON Course
TO U2, U3
这会儿提示的是:ALL 权限已不再推荐使用,并且只保留用于兼容性目的。它并不表示对实体定义了 ALL 权限。
官方文档中对参数ALL有以下讲解,很不错!
很明显,这里的例子中安全对象是表Student和Course,所以授予了U2和U3相应的权限(这里以U2为例查看)
来看例 3: 把对表SC的查询权限授予所有用户:
GRANT SELECT
ON TABLE SC
TO PUBLIC;
-- T-SQL如下
GRANT SELECT
ON SC
TO PUBLIC;
这里的PUBLIC
即表示授权给所有的用户~
来看例 4: 把查询Student表和修改学生学号的权限授给用户U4:
GRANT UPDATE(Sno), SELECT
ON TABLE Student
TO U4;
-- T-SQL如下
GRANT UPDATE(Sno), SELECT
ON Student
TO U4;
注意: 在对属性列授权时必须明确指出相应属性列名 ,如这里授予修改学生学号的权限,但是如果不加(Sno)
那就成了授予修改整个表的权限了,,啥都能改,这不行哈
来看例 5: 把对表SC的INSERT权限授予U5用户,并允许他再将此权限授予其他用户:
GRANT INSERT
ON TABLE SC
TO U5
WITH GRANT OPTION;
-- T-SQL如下
GRANT INSERT
ON SC
TO U5
WITH GRANT OPTION;
加上WITH GRANT OPTION
后,U5不仅拥有了对表SC的INSERT权限,还可以传播此权限
来看例 6: 使用登录名U5登录后执行如下语句(因为在一个数据库中登录名和用户名是一一对应的,所以登录U5后切换至STUDENT数据库进行如下操作实验),将权限授予给U6:
(ps:登录名必须映射到数据库用户才能连接到数据库。 一个登录名可以作为不同用户映射到不同的数据库,但在每个数据库中只能作为一个用户进行映射
)
GRANT INSERT
ON TABLE SC
TO U6
WITH GRANT OPTION;
-- T-SQL如下
GRANT INSERT
ON SC
TO U6
WITH GRANT OPTION;
GRANT INSERT
ON SC
TO U7;
因为没有WITH GRANT OPTION
,所以U7不能再传播此权限!!用登录名U7登录之后执行以下语句,系统报错:无法对 对象 'SC' 执行 查找,因为它不存在,或者您没有所需的权限
,显然STUDENT数据库中是有SC表的,所以原因是U7不能传播该权限
— — — — — — — — — — — — — — — — — — — — — — — —
② REVOKE 回收
语句的一般格式为:
REVOKE <权限>[,<权限>]...
ON <对象类型> <对象名>[,<对象类型><对象名>]…
FROM <用户>[,<用户>]...[CASCADE | RESTRICT];
来看例 1: 把用户U4修改学生学号的权限收回:
REVOKE UPDATE(Sno)
ON TABLE Student
FROM U4;
-- T-SQL如下
REVOKE UPDATE(Sno)
ON Student
FROM U4;
U4修改学生学号的权限UPDATE(Sno)
已成功收回~
来看例 2: 收回所有用户对表SC的查询权:
REVOKE SELECT
ON TABLE SC
FROM PUBLIC;
-- T-SQL如下
REVOKE SELECT
ON SC
FROM PUBLIC;
来看例 3: 把用户U5对SC表的INSERT权限收回:
REVOKE INSERT
ON TABLE SC
FROM U5 CASCADE ;
-- T-SQL如下
REVOKE INSERT
ON SC
FROM U5 CASCADE ;
因为U5还将该权限传播给了U6和U7,所以将U5的INSERT权限收回的时候应该使用CASCADE(级联收回),否则拒绝执行该语句
如果U6或U7还从其他用户处获得对SC表的INSERT权限,则他们仍具有此权限,系统只收回直接或间接从U5处获得的权限。如下如U6的该权限还从dbo获得,所以当收回U5授予的权限之后,他仍然具有对SC表的INSERT权限。
执行上面的SQL语句后:
角色(ROLE):被命名的一组与数据库操作相关的权限
角色是权限的集合。可以为一组具有相同权限的用户创建一个角色(所以在修改权限等的操作时对角色ROLE修改即可,不用再去麻烦地对每一个用户修改)
它的优点是:简化授权的过程
— — — — — — — — — — — — — — — —
1.角色的创建
CREATE ROLE <角色名>
2.给角色授权
GRANT <权限>[,<权限>]…
ON <对象类型>对象名
TO <角色>[,<角色>]…
3.将一个角色授予其他的角色或用户
GRANT <角色1>[,<角色2>]…
TO <角色3>[,<用户1>]…
[WITH ADMIN OPTION]
ps:该语句把角色授予某用户,或授予另一个角色,授予者是角色的创建者或拥有在这个角色上的ADMIN OPTION(即授予者能传播该权限)
指定了WITH ADMIN OPTION
则获得某种权限的角色或用户还可以把这种权限授予其他角色(能继续传播该权限)
一个角色的权限:直接授予这个角色的全部权限 + 其他角色授予这个角色的全部权限(这和上面例子中用户权限可以叠加起来(来自很多用户授予)是一样的,即这里某个角色的权限可以来自很多角色)
4.角色权限的收回
REVOKE <权限>[,<权限>]…
ON <对象类型> <对象名>
FROM <角色>[,<角色>]…
用户可以回收角色的权限,从而修改角色拥有的权限
REVOKE执行者是:①角色的创建者;②拥有在这个(些)角色上的ADMIN OPTION
来看例 1: 通过角色来实现将一组权限授予一个用户:
步骤如下:
1)首先创建一个角色 R1
CREATE ROLE R1;
2)然后使用GRANT语句,使角色R1拥有Student表的 SELECT、UPDATE、INSERT权限
GRANT SELECT, UPDATE, INSERT
ON TABLE Student
TO R1;
-- T-SQL
GRANT SELECT, UPDATE, INSERT
ON Student
TO R1;
(ps:这里UPDATE和SELECT的权限在图中看不到,需要把滚动条拉到下面,我就不截图啦)
3)将这个角色授予夏雨,夏雪,夏冰雹。使他们具有角色R1所包含的全部权限
(首先,需要创建夏雨,夏雪,夏冰雹玲这三个用户,因为这里只是需要用于做角色的实验,所以我就不新建登录名啦~ 能让他们能被授予权限就ok,实在想创建登录名的小伙伴看我上面讲解用户时写的就行~)
GRANT R1
TO 夏雨, 夏雪, 夏冰雹;
emmm,T-SQL中不支持此写法,官方文档CREATE ROLE (Transact-SQL)中有相关介绍:
附上链接:ALTER ROLE (Transact-SQL)
所以咱们可以通过下面的SQL语句来为角色R1添加成员,相当于为成员授予了角色R1拥有的权限:
ALTER ROLE R1 ADD MEMBER 夏雨;
ALTER ROLE R1 ADD MEMBER 夏雪;
ALTER ROLE R1 ADD MEMBER 夏冰雹;
(ps:需要注意的是,一条SQL语句只能添加一个角色!!)
4) 可以一次性通过R1来回收夏雨的这3个权限
REVOKE R1
FROM 夏雨;
同样的因为T-SQL不支持此写法,所以我们通过删除角色成员的方式来达到回收其权限的目的
ALTER ROLE R1 DROP MEMBER 夏雨;
GRANT DELETE
ON TABLE Student
TO R1;
-- T-SQL
GRANT DELETE
ON Student
TO R1;
使角色R1在原来的基础上增加了Student表的删除权限
来看例 3:
REVOKE SELECT
ON TABLE Student
FROM R1;
-- T-SQL
REVOKE SELECT
ON Student
FROM R1;
使R1减少了SELECT权限
— — — — — — — — — — — — — — — — — — — — — — — —
自主存取控制缺点: 可能存在数据的“无意泄露”
原因:这种机制仅仅通过对数据的存取权限来进行安全控制,而数据本身并无安全性标记
(自主存取控制能够通过授权机制有效地控制其他用户对敏感数据的存取。但是由于用户对数据的存取权限是“自主”的,用户可以自由地决定将数据的存取权限授予何人、决定是否也将“授权”的权限授予别人。在这种授权机制下,仍可能存在数据的“无意泄露”)
解决:对系统控制下的所有主客体实施强制存取控制策略
强制存取控制(MAC):
· 保证更高程度的安全性
· 用户不能直接感知或进行控制
· 适用于对数据有严格而固定密级分类的部门:军事部门、政府部门
在强制存取控制中,数据库管理系统所管理的全部实体被分为主体和客体两大类
· 主体是系统中的活动实体,即:数据库管理系统所管理的实际用户
· 客体是系统中的被动实体,即:文件、基本表、索引、视图
敏感度标记(Label): 对于主体和客体,DBMS为它们每个实例(值)指派一个敏感度标记(Label)
敏感度标记分成若干级别:
绝密(Top Secret,TS)
机密(Secret,S)
可信(Confidential,C)
公开(Public,P)
TS>=S>=C>=P
主体的敏感度标记称为许可证级别(Clearance Level)
客体的敏感度标记称为密级(Classification Level)
强制存取控制规则:
(1)仅当主体的许可证级别大于或等于客体的密级时,该主体才能读相应的客体
(2)仅当主体的许可证级别小于或等于客体的密级时,该主体才能写相应的客体
简单记作:向下读,向上写
就比如,某个TS(绝密)密级的主体把一个密级为TS的数据恶意地降为P(公开),然后把它写回。这样原来是TS密级的数据大家都可以读到了,这样就导致了TS密级数据的泄露
另一方面,如果许可证级别大于客体的密级能写的话也很可怕,因为上级(领导)能在大家不知道的情况下随意修改,这,,,肯定是不行的
至于为什么等于,是因为自己写的东西自己肯定也要能看到吖,不然自己写完就看不到了,写错了或是想再看看也没办法了,no way,,,
把要保密的数据对无权存取这些数据的用户隐藏起来,对数据提供一定程度的安全保护
视图机制间接地实现支持存取谓词的用户权限定义
来看例子: 建立计算机系学生的视图,把对该视图的SELECT权限授于夏雨,把该视图上的所有操作权限授于夏冰雹:
-- 先建立计算机系学生的视图CS_Student
CREATE VIEW CS_Student
AS
SELECT *
FROM Student
WHERE Sdept = 'CS';
-- 在视图上进一步定义存取权限
GRANT SELECT
ON CS_Student
TO 夏雨;
GRANT ALL PRIVILIGES
ON CS_Student
TO 夏冰雹;
什么是“存取谓词”?
我的理解是,存取谓词是能直接对数据进行操作(增删改查)的谓词,需要系统能支持给用户定义相关的存取谓词的权限,在不支持存取谓词的系统中,可以先建立相关视图,然后在视图上进一步定义存取权限。
为什么要用视图间接实现,直接用基本表不可以么?
emmm,可以为不同的用户定义不同的视图,把数据对象限制在一定的范围内,也就是说,通过视图机制把要保密的数据对无权存取这些数据的用户隐藏起来,对数据提供一定程度的安全保护(不想让他看到的数据就不定义在视图里,这相对于直接给他看基本表要安全很多)
什么是审计:
审计功能的可选性:
· 审计很费时间和空间
· DBA可以打开或关闭审计功能
· 审计功能主要用于安全性要求较高的部门
AUDIT语句和NOAUDIT语句:
AUDIT
语句:设置审计功能
NOAUDIT
语句:取消审计功能
来看例 1: 对修改SC表结构或修改SC表数据的操作进行审计:
AUDIT ALTER, UPDATE
ON SC;
这里T-SQL是不支持这样写的,具体写法暂时没搞明白,待弄清楚之后第一时间回来更新补充上~
先附上官方文档:SQL Server 审核(数据库引擎),惭愧惭愧,没看明白这个官方文档
来看例 2: 取消对SC表的一切审计:
NOAUDIT ALTER, UPDATE
ON SC;
数据加密: 防止数据库中数据在存储和传输中失密的有效手段
加密的基本思想: 根据一定的算法将原始数据—明文(Plain text)变换为不可直接识别的格式—密文(Cipher text)
加密方法: ①存储加密;②传输加密
— — — — — — — — — — — — — — — — — —
存储加密:
透明存储加密
①内核级加密保护方式,对用户完全透明
②将数据在写到磁盘时对数据进行加密,授权用户读取数据时再对其进行解密
③数据库的应用程序不需要做任何修改,只需在创建表语句中说明需加密的字段即可
内核级加密方法: 性能较好,安全完备性较高
非透明存储加密:通过多个加密函数实现
传输加密(结合计算机网络学习,我暂时还没学习相关内容,所以这里就只是写个大概,嘻嘻):
那 关于数据库安全性 部分到这里也就结束啦,感谢你耐心地阅读~
如有不恰当的地方,望提出指正~
咱们下期 见~