zoukankan      html  css  js  c++  java
  • oracle label security(OLS)相关主体流程整理

    一个OLS简单应用场景, 下面的列子将实现这样的功能:

    1. 创建4个level, 级别从高到低依次为: top, high, middle, low;
    2. 给stu表上所有数据添加标签;
    3. 如果用户被赋予第一个标签, 则能查看所有带标签数据;
    4. 如果用户被赋予第二个标签, 则能查看对应级别及其以下的数据;
    5. 用户在授权范围内调整会话label, 重新查看数据;

    步骤:

    1. 准备2个账户, quzq和us1, quzq用来创建table及赋权label, us1用来作为特权账户给数据添加label:

    create user quzq identified by lala123;

    grant connect, resource, dba to quzq;

    create user us1 identified by lala123;

    grant connect, resource, dba to us1;

    1. 使用quzq账户创建stu表, 并添加数据:

    create table stu(s1 nvarchar2(10));

    insert into stu values(1);

    insert into stu values(2);

    insert into stu values(3);

    insert into stu values(4);

    1. 连接lbacsys账户创建policy及其组件(此处创建了上面所说的4个level)

    exec sa_sysdba.create_policy('my_policy', 'ols_name','ALL_CONTROL');          # 创建policy, 参数详见下方ols使用的3个阶段

    exec sa_components.create_level('my_policy', 100, 'low', 'low_level');                # 创建policy的level组件

    exec sa_components.create_level('my_policy', 200, 'middle', 'middle_level');

    exec sa_components.create_level('my_policy', 300, 'high', 'high_level');

    exec sa_components.create_level('my_policy', 400, 'top', 'top_level');

    1. 创建label

    exec sa_label_admin.create_label('my_policy',40000,'top',true);

    exec sa_label_admin.create_label('my_policy',30000,'high',true);

    exec sa_label_admin.create_label('my_policy',20000,'middle',true);

    exec sa_label_admin.create_label('my_policy',10000,'low',true);

    1. 应用policy到table

    exec sa_policy_admin.apply_table_policy('my_policy','quzq','stu');

    此时使用quzq和us1账户分别查看stu表结果如下:

    image.png

    image.png

    查看表结构,如下:

    image.png

    1. 给quzq用户赋权第一个label, 再次查看数据:

    exec sa_user_admin.set_user_labels('my_policy','quzq','top');

    重新登录查看结果如下:

    image.png

    1. 使用lbacsys给us1账户赋特权, 绕开OLS验证, 重新登录us1账户查看数据, 并给数据行添加label

    execute sa_user_admin.set_user_privs('my_policy','us1','FULL');

    image.png

    1. 再次使用quzq账户查看stu表:

    image.png

    1. 使用lbacsys账户给quzq用户赋权第二个标签, 登录quzq账户再次查看stu表:

    exec sa_user_admin.set_user_labels('my_policy','quzq','high');

    image.png

    1. 用户端在权限范围内修改会话的label, 再次查看stu表:

    上一步的赋权用户label中第三个参数指定了用户的最高label为high, 最低默认为low, 会话label默认也是high,

    所以当前用户的权限范围可在low, middle和high中随意指定, 而不能指定成范围之外的top:

    exec sa_session.set_label('my_policy','top');

    image.png

    1. 使用当前会话进行insert操作:

    image.png

    OLS使用流程可拆分为3个阶段, 以下通过对这3个阶段的描述来说明OLS的使用

    一.定义阶段

        定义阶段包含定义policy及其组件,以及使用定义好的组件来创建label, 如下:

        1.创建policy

    语法: exec sa_sysdba.create_policy(policy_name, 'ols_name','');

    说明: policy是使用OLS的基础, 其相当于个容器, 该容器内包含有3个组件, 分别为level, compartment和group;

    参数: policy_name参数用来给policy命名, policy的名称必须是唯一的;

      column_name参数用于定义将policy应用到table时, 表中生成的label列名;

      default_options参数用于设定默认的策略控制选项, 如将policy应用到table时不指定控制选项, 则此默认值生效;

        2.在policy中创建level

    语法: exec sa_components.create_level(policy_name, level_num, short_name, long_name);

    说明: level是policy中的必有组件, 其具有层级关系, level个数无明确限制, 但level_num必须唯一;

    参数: policy_name参数用于指定该level属于哪个policy的组件;

      level_num参数取值0-9999, 数值越大表示其层级越高, 同一个policy中level_num值唯一;

      short_name参数用于给level设定简写名称, level被引用时使用该名称;

      long_name参数用于给level设定全名;

        3.在policy中创建compartment

    语法: exec sa_components.create_compartment(policy_name, comp_num, short_name, long_name);

    说明: compartment是可选组件, 没有级别或层级的区分, 个数无明确限制, 但comp_num必须唯一;

    参数: policy_name参数用于指定该compartment属于哪个policy的组件;

      comp_num参数取值0-9999, 数值大小只影响显示时的排序, 同一个policy中comp_num值唯一;

      short_name参数用于给compartment设定简写名称, compartment被引用时使用该名称;

      long_name参数用于给compartment设定全名;

        4.在policy中创建group

    语法: sa_components.create_group(policy_name, group_num, short_name, long_name, parent_name);

    说明: group是可选组件, 有子集或父集区分, 个数无明确限制, 但group_num必须唯一;

    参数: policy_name参数用于指定该group属于哪个policy的组件;

      group_num参数取值0-9999, 数值大小只影响显示时的排序, 同一个policy中group_num值唯一;

      short_name参数用于给group设定简写名称, group被引用时使用该名称;

      long_name参数用于给group设定全名;

      parent_name参数用户指定该group的父集, 该参数可选;

        5.创建label

    语法: exec sa_label_admin.create_label(policy_name, label_tag, label_value, data_label);

    说明: label有两方面用处, 一方面用于表中数据行, 另一方面用于赋给用户; 用于控制用户能访问到的数据;

    参数: policy_name参数用于指定生成哪个policy的label;

      label_tag参数取值0-99999999,数值大小只影响显示时的排序,表中数据行添加label后会显示该值;

      label_value参数使用policy中的level,compartment,group来生成, 如: 'level:compartment:group';

      data_label参数取值为布尔型, TRUE表示该label可用于数据行;

    二.应用阶段

        包含: 将policy应用到table或schema上, 将label赋给用户, 将表中原有数据添加label, 如下:

        1.将policy应用到table或schema(此处以应用到table来说明)

    语法: exec sa_policy_admin.apply_table_policy(policy_name, schema_name, table_name, table_options,

      label_function, predicate);

    说明: 将policy成功应用到table上, 所有访问该table的用户都获取不到任何数据, 对表的所有想要的控制也是在

      这个阶段设定的, 通过table_options的参数选项来实现,. 前3个参数是必选的.

    参数: policy_name参数用于指定将被应用的policy名称;

      schema_name参数用于指定用户schema;

      table_name参数用于指定给哪张表添加policy;

      table_options参数用于设定对表的控制项, oracle提供有10个选项, 可按需选取;

      label_function参数用于设定生成label的函数;

      predicate参数配合options选项为READ_CONTROL时使用;

        2.将label赋给用户

    将label赋给用户oracle提供有两类方法: 一类是按照组件给用户赋权, 一类是通过label string给用户赋权;

    1.按照组件的赋权:

        1).赋权level给用户

        语法: exec sa_user_admin.set_levels(policy_name, user_name, max_level, min_level, def_level, row_level);

        说明: 可单独赋权level给用户;

        参数: policy_name参数用于指定生效的policy;

    user_name参数用于指定赋给哪个用户;

    max_level参数设置该用户能操控的最高level等级;

    min_level参数设置该用户能操控的最低level等级;

    def_level参数设置该用户默认的session所使用的level等级;

    row_level参数设置该用户缺省insert操作时默认使用的level;

        2).赋权compartment给用户:

        语法:  exec sa_user_admin.set_compartments(policy_name, user_name, read_comps, write_comps,def_comps, row_comps );

        说明: 必须在赋权level给用户的基础上赋权compartment, 不能单独赋权compartment给用户;

        参数: policy_name参数用于指定生效的policy;

    user_name参数用于指定赋给哪个用户;

    read_comps参数可指定多个以逗号分隔的compartment;

    write_comps参数默认为null, null时以read_comps为准;

    def_comps参数默认为null, null时以read_comps为准, 设定时必须是read_comps的子集;

    row_comps参数默认为null, null时以def_comps为准, 设定时必须是write_comps和def_comps的子集;

        3).赋权group给用户:

        语法: exec sa_user_admin.set_groups(policy_name, user_name, read_groups, write_groups, def_groups,row_groups);

        说明: 不能单独赋权group给用户, 必须是在赋权level的基础上才行;

        参数: policy_name参数用于指定生效的policy;

            user_name参数用于指定赋给哪个用户;

    read_groups参数可指定多个以逗号分隔的group;

    write_groups参数默认为null, null时以read_groups为准;

    def_groups参数默认为null, null时以read_groups为准, 设定时必须是read_groups的子集;

    row_groups参数默认null, null时以def_groups为准, 设定时必须是write_groups和def_groups的子集;

    2.通过label string给用户赋权:

    语法: exec sa_user_admin.set_user_labels(policy_name, user_name, max_read_label, max_write_label,min_write_label, def_label, row_label);

    说明: label string赋权是结合了policy中所有组件, 以字符形式的一种赋权, 两种赋权任选其一即可.

    参数: policy_name参数用于指定生效的policy;

            user_name参数用于指定赋给哪个用户;

      max_read_label参数用于指定最大的read权限的label, 如: 'l : c : g1, g2';

      max_write_label参数默认null, null时以max_read_label为准;

      min_write_label参数默认null, null时为最低level, 无compartment和group;

      def_label参数取值必须是max_read_label的子集, null时以max_read_label为准;

      row_label参数指定默认的行label, 必须是max_write_label和def_label的子集;

    3.为表中已有数据行添加label(可选操作, 视场景选用)

    table上应用policy后,有且只有数据行label和用户label能匹配上的数据才能被访问到, 默认没有label的数据行永

    远无法被访问. 如对表应用policy之前,表中就存有数据的场景, 在应用policy后需要为这部分数据添加label.

    1).普通用户的特权管理:

    语法: exec sa_user_admin.set_user_privs(policy_name, user_name, privileges);

    说明: policy应用到table后, 普通用户在不赋权label时无法无法操控数据库, 要为原有数据添加label只能使用特权来绕过OLS的认证.

    参数: policy_name参数用于指定特权对哪个policy生效;

      user_name参数用于指定对哪个用户授权;

      privileges参数用于指定授予什么样的特权, 此参数的取值oracle提供有7个选项, 可控制不同的特权范围;

    2).特权设置成功即可绕开OLS相应的验证, 以update形式给数据添加label:

    update stu set OLS_CNAME=CHAR_TO_LABEL('my_policy','internal:fin,hr:west,east');

    三.使用阶段

        1.用户在权限范围内自定义session label

    说明: 在给用户设置label时, 设定有用户默认的初始化连接数据库的label, 也设定有用户的最大和最小label.

             session label的取值决定着用户所能操作的数据范围, 某些场景需要在权限范围内调高或调低session权限;

    语法: exec sa_session.set_label(policy_name, label);

    参数: policy_name参数用于指定policy名称;

             label参数用于设定当前session使用的label, 此处取值不能超出设定的最高和最低label范围;

        2.用户在权限范围内自定义row label

    说明: 在给用户设置label时, 设定有用户默认的row label. row babel用于insert时不指定label值时的默认使用值,

              在使用某些table_options选项来限制table时, row label的权限不能高于session label.

    语法: exec sa_session.set_row_label(policy_name, label);

    参数: policy_name参数用于指定policy名称;

             label参数用于设定不指定label时的insert默认值, 此处取值不能超出设定的最高和最低label范围;

    总结:

    1. 以上为使用OLS的主体流程描述, 不包含所有的OLS功能.
    2. OLS使用过程中比较复杂的地方在应用policy到table时的table_options选项,不同选项控制着不同的OLS行为,也会影响着各种给用户赋权label时的参数选定, 以及用户使用过程中自定义的session label和row label的取值. 去理解单独的某个功能或参数的取值没有意义, 需要结合OLS整个流程中的上下文环境去设定合适的场景.
    3. OLS相关视图如下:

    查看创建的policy:               select * from dba_sa_policies;

    查看创建的level:                 select * from dba_sa_levels;

    查看创建的compartments:  select * from dba_sa_compartments;

    查看创建的groups:             select * from dba_sa_groups;

    查看创建的labels:               select * from dba_sa_labels;

    查看table上的policy:          select * from dba_sa_table_policies;

    查看用户的label:                select * from dba_sa_user_labels;

    查看当前session label:       select sa_session.label('MY_POLICY') from dual;

    查看当前row label:            select sa_session.row_label('MY_POLICY') from dual;

    1. policy中level, compartment, group对数据进行逻辑分类的三个维度:

    image.png

  • 相关阅读:
    沉默
    抱冰握火
    数据库原理-SQL查询语句
    简单算法的实现——集合
    团队总结
    个人作业----项目测试
    团队项目-Beta冲刺
    团队项目-Alpha版本发布1
    团队项目-----系统设计 认真不马虎队
    团队项目----需求分析 认真不马虎队
  • 原文地址:https://www.cnblogs.com/quzq/p/11953399.html
Copyright © 2011-2022 走看看