Apache优化之权限控制

Apache优化之权限控制

前言

在linux系统中最让人头疼的就是这权限问题,有时候,我们服务启动失败了,说不准就是这文件的权限、属主或者属组出了问题,由此可见,权限是真的让人又爱又恨。我们还是要好好学习Apache的访问控制,毕竟现在的网站安全这一块是非常重要的。

权限控制

1.场景举例

企业IT管理员一般都能为系统定义角色,给用户分配角色。这就是最常见的基于角色访问控制。场景举例:

1、给张三赋予“人力资源经理”角色,“人力资源经理”具有“查询员工”、“添加员工”、“修改员工”和“删除员工”权限。此时张三能够进入系统,则可以进行这些操作;

2、去掉李四的“人力资源经理”角色,此时李四就不能够进入系统进行这些操作了。

以上举例,局限于功能访问权限。还有一些更加丰富、更加细腻的权限管理。比如:

1、因为张三是北京分公司的“人力资源经理”,所以他能够也只能够管理北京分公司员工和北京分公司下属的子公司(海淀子公司、朝阳子公司、西城子公司、东城子公司等)的员工;

2、因为王五是海淀子公司的“人力资源经理”,所以他能够也只能够管理海淀子公司的员工;

3、普通审查员审查财务数据的权限是:在零售行业审核最高限额是¥50万,在钢铁行业最高限额是¥1000万;高级审查员不受该限额限制;

4、ATM取款每次取款额不能超过¥5000元,每天取款总额不能超过¥20000元。

这些权限管理和数据(可以统称为资源)直接相关,又称为数据级权限管理、细粒度权限管理或者内容权限管理。

3.分类

从控制力度来看,可以将权限管理分为两大类:

1、功能级权限管理;

2、数据级权限管理。

从控制方向来看,也可以将权限管理分为两大类:

1、从系统获取数据,比如查询订单、查询客户资料;

2、向系统提交数据,比如删除订单、修改客户资料。

4.概念

用户身份认证,根本就不属于权限管理范畴。用户身份认证,是要解决这样的问题:用户告诉系统“我是谁”,系统就问用户凭什么证明你就是“谁”呢?对于采用用户名、密码验证的系统,那么就是出示密码。当用户名和密码匹配,则证明当前用户是谁;对于采用指纹等系统,则出示指纹;对于硬件Key等刷卡系统,则需要刷卡。

密码加密,是隶属用户身份认证领域,不属于权限管理范畴。

系统管理,一般是系统的一个模块。而且该模块一般还含有权限管理子模块。因此,很多人误认为权限管理系统只是系统的一个小小的子模块。系统管理里面的权限管理模块,只是一个操作界面,让企业IT管理员能够设置角色等安全策略。系统背后还有很多权限验证逻辑,这些都并不属于该模块。总体来说,该模块相当于给权限管理模块提供了一些数据,比如:张三是人力资源经理等。

更多混淆概念,请参考:《对权限管理认识的一些误区》。

5.技术实现

按照权限管理的力度,逐步介绍权限管理实现技术。

5.1功能权限管理技术实现

功能权限管理技术,一般就使用基于角色访问控制

RBAC权限模型RBAC权限模型

权限设置

一般来说,系统提供如下功能:

1、角色管理界面,由用户定义角色,给角色赋权限;

2、用户角色管理界面,由用户给系统用户赋予角色。

3、一些优秀系统,还支持用户定义权限,这样新增功能的时候,可以将需要保护的功能添加到系统。

这里,我们谈谈Spring Security框架。它将访问角色固化到程序代码里面。那么这种控制就相当于由软件开发人员完成,而不是最终用户。这从实施角度来看,是完全错误的。更多阅读,可以查看《Spring Security优劣之我见》。

5.2权限验证

功能级的权限验证逻辑非常简单。查看该当前登录用户的角色是否包含该功能的权限。如果有,则表示有权访问,否则表示无权访问。

对于WEB系统,一般定义一个Filter就可以完成权限验证,无需在各个程序入口进行权限判断。程序伪代码如下:

// 获取访问功能

String url=request.getRequestPath();

// 进行权限验证

User user=request.getSession().get(“user”);

boolean permit=PrivilegeManager.permit( user, url );

if( permit ) {

chain.doFilter( request, response );

} else {

// 可以转到提示界面

}

5.3数据级权限管理技术实现

目前,数据级权限管理领域,一直没有统一的技术。大体上,软件开发人员采用如下技术:

1、硬编码,也就是将这种逻辑以if/else等形式与业务代码耦合在一起,这种情况居多;

2、使用规则引擎,也有一些企业将这种逻辑以规则形式提出来,并使用规则引擎解析规则;

3、使用第三方专业软件,有开源中间件Ralasafe [1] ;开源框架Spring Security [2] ;商业产品Oracle Entitlements Server,IBM Tivoli Access Manager,UPMS通用用户权限系统等。

硬编码形式弊端是非常显然的。耦合性强,难以测试;系统组件复用率低;系统后期改动代价非常大,牵一发而动全身

使用规则引擎可以解决很多问题,学习难度尚可。但规则引擎并不是专业用于权限管理的,所以对于复杂一些的权限管理,就显得力不从心。

Ralasafe和Oracle、IBM的商业产品一样,都是中间件形式。对应用系统和应用数据库结构没有要求。都有管理界面进行直接操控管理,而且都能在线进行测试。相比较,Ralasafe还可以控制查询权限(即从系统查询订单、查询客户等),Oracle、IBM的商业产品没有这方面功能;从产品学习难度来看,Ralasafe只要有一些IT经验,就能快速上手;Oracle、IBM产品即使是专业人员,也难以掌握。

Spring Security是框架,需要对你的应用系统进行改动,你的系统必须在该框架进行设计编写。它只是帮助开发人员将权限提取出来了,但数据级权限还需要开发人员开发Voter。而且配置工作巨大,难以测试。

虽然上述提到的产品,都是Java产品。但Ralasfe和Oracle、IBM的商业产品,以中间件形式,可以部署在独立服务器上,使用web service等方式与非Java系统交互。

6.实施

6.1功能级权限控制

这是很多系统都能做到的。让系统使用者(一企业IT管理员)定义角色,给用户分配角色。成功实施该步骤,用户能在功能级进行权限管理。整个过程无需软件开发商参与。

6.2部分预定义好的数据级权限

有些复杂一点的系统,提供了一些规则和管理界面,可以让系统使用者(一般是企业IT管理员)输入规则参数。比如普通审查员审查财务数据的金额区间,勾选某用户能够查询哪些组织机构的订单数据。

这是给企业提供了部分控制数据级权限的能力。但该能力还非常弱,仅限于已定义好的策略,不能适应安全策略变化。而,企业需求肯定会随着业务发展、时间推移,发生变化。比如:普通审查员审查区间由原来的单一设置区间,改为按照行业、按照地域来设置不同的区间。用户查询订单不仅和组织机构有关,还和订单业务领域(体育、食品等)有关。当这些需求发生的时候,企业还要求助于软件开发商进行修改。

6.3企业完全掌控安全策略

企业完整掌控安全策略,应该包括2个方面内容:1,功能级权限管理完全自我掌控;2,数据级权限管理完全自我掌控。实现这方面需要,还需要考虑企业的IT能力:IT能力没有软件开发商强,而且权限管理涉及整个系统安全,关系重大。因此软件必须是这样的:1,图形化、集中管理的,便于企业管理;2,可在线测试的,定制策略后在不影响业务的情况下,进行测试,确保无误。

目前,就Ralasafe和Oracle、IBM产品满足要求

7.注意问题

不良的权限管理系统,必然留下系统漏洞权限由紧密分散,转换为集中专业管理之机。很多软件可以轻松通过URL侵入、SQL注入等模式,轻松越权获得未授权数据。甚至对系统数据进行修改、删除,造成巨大损失。

很多系统,尤其是采用硬编码方式的系统,存在权限逻辑与业务代码紧密耦合,同时又分散在系统各个地方。系统漏洞势必非常多,而且随着系统不断修改,漏洞逐步增多。 好的系统,应该将权限逻辑集中起来,由专业的安全引擎进行设置、解析。业务逻辑调用安全引擎,获得权限结果,不再使用非专业模式。

实验步骤

1.策略禁止访问

1.到虚拟主机的配置文件里,对虚拟主机的配置文件进行修改

[root@localhost ~]# cd /etc/httpd/conf/extra/
[root@localhost extra]# ls
vhosts.conf
[root@localhost extra]# vim vhosts.conf
<VirtualHost 192.168.73.143:80>
    DocumentRoot "/var/www/html/hello"
    ErrorLog "logs/www.hello.com.error_log"
    CustomLog "logs/www.hello.com.access_log" common
    <Directory "/var/www/html/">
      <RequireAll>
        Require not ip 192.168.73.150  //我们这里是禁止win10主机的ip地址
        Require all granted
      </RequireAll>
    </Directory>
</VirtualHost>

<VirtualHost 192.168.73.154:80>
    DocumentRoot "/var/www/html/hello02"
    ErrorLog "logs/www.hello02.com.error_log"
    CustomLog "logs/www.hello02.com.access_log" common
    <Directory "/var/www/html/">
    Require all granted
    </Directory>
</VirtualHost>

#<VirtualHost *:80>
#    DocumentRoot "/var/www/html/world"
#    ServerName www.world.com
#    ErrorLog "logs/www.world.com.error_log"
#    CustomLog "logs/www.world.com.access_log" common
#    <Directory "/var/www/html/">
#    Require all granted
#    </Directory>
#</VirtualHost>
#
#<VirtualHost *:8080>
#    DocumentRoot "/var/www/html/world02"
#    ServerName www.world.com
#    ErrorLog "logs/www.world02.com.error_log"
#    CustomLog "logs/www.world02.com.access_log" common
#    <Directory "/var/www/html/">
#    Require all granted
#    </Directory>
#</VirtualHost>

2.重启httpd服务,并在win10主机的浏览器里面进行测试

[root@localhost extra]# systemctl restart httpd

在这里插入图片描述

这就说明我们在虚拟主机里面的限制生效了

在这里插入图片描述

2.身份认证功能

1.创建身份认证

[root@localhost extra]# htpasswd -c /etc/httpd/conf/pwd test01
New password:                       //密码创建,我这里设的是abc1234
Re-type new password: 
Adding password for user test01
[root@localhost extra]# cd ..
[root@localhost conf]# ls
extra  httpd.conf  magic  pwd
[root@localhost conf]# cat pwd
test01:$apr1$7x0YrzY2$YYr386gt0FY0EUbRpEngE0
[root@localhost conf]# htpasswd /etc/httpd/conf/pwd test02
New password: 
Re-type new password: 
Adding password for user test02
[root@localhost conf]# cat pwd
test01:$apr1$7x0YrzY2$YYr386gt0FY0EUbRpEngE0
test02:$apr1$NReef8Dz$cp1ppgOjCRtpfL39ifcKN.

2.修改虚拟主机的主配置文件

[root@localhost conf]# vim extra/vhosts.conf 
<VirtualHost 192.168.73.143:80>
    DocumentRoot "/var/www/html/hello"
    ErrorLog "logs/www.hello.com.error_log"
    CustomLog "logs/www.hello.com.access_log" common
    <Directory "/var/www/html/">
      <RequireAll>
        Require not ip 192.168.73.150  
        Require all granted
      </RequireAll>
    </Directory>
</VirtualHost>

<VirtualHost 192.168.73.154:80>
    DocumentRoot "/var/www/html/hello02"
    ErrorLog "logs/www.hello02.com.error_log"
    CustomLog "logs/www.hello02.com.access_log" common
    <Directory "/var/www/html/">
      AuthName "DocumentRoot"
      AuthType Basic
      AuthUserFile /etc/httpd/conf/pwd
      Require valid-user
    </Directory>
</VirtualHost>

#<VirtualHost *:80>
#    DocumentRoot "/var/www/html/world"
#    ServerName www.world.com
#    ErrorLog "logs/www.world.com.error_log"
#    CustomLog "logs/www.world.com.access_log" common
#    <Directory "/var/www/html/">
#    Require all granted
#    </Directory>
#</VirtualHost>
#
#<VirtualHost *:8080>
#    DocumentRoot "/var/www/html/world02"
#    ServerName www.world.com
#    ErrorLog "logs/www.world02.com.error_log"
#    CustomLog "logs/www.world02.com.access_log" common
#    <Directory "/var/www/html/">
#    Require all granted
#    </Directory>
#</VirtualHost>

3.重启服务

[root@localhost conf]# systemctl restart httpd
[root@localhost conf]# systemctl stop firewalld
[root@localhost conf]# setenforce 0

4.在win10主机里面进行测试

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

发布了95 篇原创文章 · 获赞 39 · 访问量 6147

猜你喜欢

转载自blog.csdn.net/double_happy111/article/details/103523890