【云小课】EI第29课 大数据时代的隐私利器-GaussDB(DWS)数据脱敏

背景信息

大数据时代的到来,大数据、云计算和人工智能等新技术应用不断深化,为数据的深度挖掘及分析提供了强有力的支撑,大数据中蕴含的巨大价值被逐步挖掘出来。然而,一系列信息泄露事件的曝光,使得数据安全越来越受到广泛的关注。各国各地区逐步建立健全和完善数据安全与隐私保护相关法律法规,提供用户隐私保护的法律保障。如何加强技术层面的数据安全和隐私保护,是对数据仓库产品提出的要求,也是数据安全建设最有效的办法。

GaussDB(DWS)产品8.1.1版本发布数据脱敏特性,支持指定用户范围内列级敏感数据的脱敏功能,具有灵活、高效、透明、友好等优点。使得敏感及隐私信息不被泄露,提高了对敏感及私密数据的保护,极大地增强了产品的数据安全能力。


云小课封面.jpg

什么是数据脱敏

数据脱敏(Data Masking),即屏蔽敏感数据,对某些敏感信息(比如,身份证号、手机号、卡号、客户姓名、客户地址、邮箱地址、银行账号、密码类等等 )通过脱敏规则进行数据的变形,实现隐私数据的可靠保护。

业界常见的脱敏规则有,替换、重排、加密、截断、掩码,用户也可以根据期望的脱敏算法自定义脱敏规则。

什么是数据脱敏.png

良好的数据脱敏实施,需要遵循两个原则:第一,尽可能地为脱敏后的应用,保留脱敏前的有意义信息;第二,最大程度地防止黑客进行破解。

数据脱敏分为静态数据脱敏动态数据脱敏。静态数据脱敏,是数据的“搬移并仿真替换”,是将数据抽取进行脱敏处理后,下发给下游环节,随意取用和读写的,脱敏后数据与生产环境相隔离,满足业务需求的同时保障生产数据库的安全。动态数据脱敏,在访问敏感数据的同时实时进行脱敏处理,可以为不同角色、不同权限、不同数据类型执行不同的脱敏方案,从而确保返回的数据可用而安全。下图为一个简单的静态脱敏和动态脱敏示例,可以看出两者的不同。

动态脱敏.png

GaussDB (DWS)的数据脱敏功能,摒弃业务应用层脱敏依赖性高、代价大等痛点,将数据脱敏内化为数据库产品自身的安全能力,提供了一套完整、安全、灵活、透明、友好的数据脱敏解决方案,属于动态数据脱敏。用户识别敏感字段后,基于目标字段,绑定内置脱敏函数,即可创建脱敏策略。脱敏策略(Redaction Policy)与表对象是一一对应的。一个脱敏策略包含表对象、生效条件、脱敏列-脱敏函数对三个关键要素,是该表对象上所有脱敏列的集合,不同字段可以根据数据特征采用不同的脱敏函数。当且仅当生效条件为真时,查询语句才会触发敏感数据的脱敏,而脱敏过程是内置在SQL引擎内部实现的,对生成环境用户是透明不可见的。


数据脱敏功能.png

数据脱敏如何使用

第一步:创建脱敏策略需确定受限制用户角色

动态数据脱敏,是在查询语句执行过程中,根据生效条件是否满足,实现实时的脱敏处理。生效条件,通常是针对当前用户角色的判断。敏感数据的可见范围,即是针对不同用户预设的。系统管理员,具有最高权限,任何时刻对任何表的任何字段都可见。

第二步:识别和梳理具体业务场景的敏感字段。

敏感信息依赖于实际业务场景和安全维度,以自然人为例,用户个体的敏感字段包括:姓名、身份证号、手机号、邮箱地址等等;在银行系统,作为客户,可能还涉及银行卡号、过期时间、支付密码等等;在公司系统,作为员工,可能还涉及薪资、教育背景等;在医疗系统,作为患者,可能还涉及就诊信息等等。

第三步:确定脱敏列需要绑定的脱敏函数。

产品内置一系列常见的脱敏函数接口,可以针对不同数据类型和数据特征,指定参数,从而达到不一样的脱敏效果。脱敏函数可采用如下三种内置接口,同时支持自定义脱敏函数。三种内置脱敏函数能够涵盖大部分场景的脱敏效果,不推荐使用自定义脱敏函数。

  • MASK_NONE:不作脱敏处理,仅内部测试用。

  • MASK_FULL:全脱敏成固定值。

  • MASK_PARTIAL:使用指定的脱敏字符对脱敏范围内的内容做部分脱敏。

不同脱敏列可以采用不同的脱敏函数。比如,手机号通常显示后四位尾号,前面用"*"替换;金额统一显示为固定值0,等等。

数据脱敏使用示例

以某公司员工表emp,表的属主用户alice以及用户matu、july为例,简单介绍数据脱敏的使用过程。其中,表emp包含员工的姓名、手机号、邮箱、发薪卡号、薪资等隐私数据,用户alice是人力资源经理,用户matu和july是普通职员。假设表、用户及用户对表emp的查看权限均已就绪。

  1. 创建脱敏策略mask_emp,仅允许alice查看员工所有信息,matu和july对发薪卡号、薪资均不可见。字段card_no是数值类型,采用MASK_FULL全脱敏成固定值0;字段card_string是字符类型,采用MASK_PARTIAL按指定的输入输出格式对原始数据作部分脱敏;字段salary是数值类型,采用数字9部分脱敏倒数第二位前的所有数位值。

    postgres=# CREATE REDACTION POLICY mask_emp ON emp WHEN (current_user != 'alice')
    ADD COLUMN card_no WITH mask_full(card_no),
    ADD COLUMN card_string WITH mask_partial(card_string, 'VVVVFVVVVFVVVVFVVVV','VVVV-VVVV-VVVV-VVVV','#',1,12), 
    ADD COLUMN salary WITH mask_partial(salary, '9', 1, length(salary) - 2);
    切换到matu和july,查看员工表emp。
    postgres=> SET ROLE matu PASSWORD 'Gauss@123';
    postgres=> SELECT * FROM emp;
     id | name |  phone_no   | card_no |     card_string     |        email         |   salary   |      birthday       
    ----+------+-------------+---------+---------------------+----------------------+------------+---------------------
      1 | anny | 13420002340 |       0 | ####-####-####-1234 | smithWu@163.com      | 99999.9990 | 1999-10-02 00:00:00
      2 | bob  | 18299023211 |       0 | ####-####-####-3456 | 66allen_mm@qq.com    |  9999.9990 | 1989-12-12 00:00:00
      3 | cici | 15512231233 |         |                     | jonesishere@sina.com |            | 1992-11-06 00:00:00
    (3 rows)
    postgres=> SET ROLE july PASSWORD 'Gauss@123';
    postgres=> SELECT * FROM emp;
     id | name |  phone_no   | card_no |     card_string     |        email         |   salary   |      birthday       
    ----+------+-------------+---------+---------------------+----------------------+------------+---------------------
      1 | anny | 13420002340 |       0 | ####-####-####-1234 | smithWu@163.com      | 99999.9990 | 1999-10-02 00:00:00
      2 | bob  | 18299023211 |       0 | ####-####-####-3456 | 66allen_mm@qq.com    |  9999.9990 | 1989-12-12 00:00:00
      3 | cici | 15512231233 |         |                     | jonesishere@sina.com |            | 1992-11-06 00:00:00
    (3 rows)
  2. 由于工作调整,matu进入人力资源部参与公司招聘事宜,也对员工所有信息可见,修改策略生效条件。

    postgres=> ALTER REDACTION POLICY mask_emp ON emp WHEN(current_user NOT IN ('alice', 'matu'));

    切换到用户matu和july,重新查看员工表emp。

    postgres=> SET ROLE matu PASSWORD 'Gauss@123';
    postgres=> SELECT * FROM emp;
     id | name |  phone_no   |     card_no      |     card_string     |        email         |   salary   |      birthday       
    ----+------+-------------+------------------+---------------------+----------------------+------------+---------------------
      1 | anny | 13420002340 | 1234123412341234 | 1234-1234-1234-1234 | smithWu@163.com      | 10000.0000 | 1999-10-02 00:00:00
      2 | bob  | 18299023211 | 3456345634563456 | 3456-3456-3456-3456 | 66allen_mm@qq.com    |  9999.9900 | 1989-12-12 00:00:00
      3 | cici | 15512231233 |                  |                     | jonesishere@sina.com |            | 1992-11-06 00:00:00
    (3 rows)
    postgres=> SET ROLE july PASSWORD 'Gauss@123';
    postgres=> SELECT * FROM emp;
     id | name |  phone_no   | card_no |     card_string     |        email         |   salary   |      birthday       
    ----+------+-------------+---------+---------------------+----------------------+------------+---------------------
      1 | anny | 13420002340 |       0 | ####-####-####-1234 | smithWu@163.com      | 99999.9990 | 1999-10-02 00:00:00
      2 | bob  | 18299023211 |       0 | ####-####-####-3456 | 66allen_mm@qq.com    |  9999.9990 | 1989-12-12 00:00:00
      3 | cici | 15512231233 |         |                     | jonesishere@sina.com |            | 1992-11-06 00:00:00
    (3 rows)
  3. 员工信息phone_no、email和birthday也是隐私数据,更新脱敏策略mask_emp,新增三个脱敏列。

    postgres=> ALTER REDACTION POLICY mask_emp ON emp ADD COLUMN phone_no WITH mask_partial(phone_no, '*', 4);
    postgres=> ALTER REDACTION POLICY mask_emp ON emp ADD COLUMN email WITH mask_partial(email, '*', 1, position('@' in email));
    postgres=> ALTER REDACTION POLICY mask_emp ON emp ADD COLUMN birthday WITH mask_full(birthday);

    切换到用户july,查看员工表emp。

    postgres=> SET ROLE july PASSWORD 'Gauss@123';
    postgres=> SELECT * FROM emp;
     id | name |  phone_no   | card_no |     card_string     |        email         |   salary   |      birthday       
    ----+------+-------------+---------+---------------------+----------------------+------------+---------------------
      1 | anny | 134******** |       0 | ####-####-####-1234 | ********163.com      | 99999.9990 | 1970-01-01 00:00:00
      2 | bob  | 182******** |       0 | ####-####-####-3456 | ***********qq.com    |  9999.9990 | 1970-01-01 00:00:00
      3 | cici | 155******** |         |                     | ************sina.com |            | 1970-01-01 00:00:00
    (3 rows)
  4. 考虑用户交互的友好性,GaussDB (DWS) 提供系统视图redaction_policies和redaction_columns,方便用户直接查看更多脱敏信息。

    postgres=> SELECT * FROM redaction_policies;
     object_schema | object_owner | object_name | policy_name |            expression             | enable | policy_description 
    ---------------+--------------+-------------+-------------+-----------------------------------+--------+--------------------
     public        | alice        | emp         | mask_emp    | ("current_user"() = 'july'::name) | t      | 
    (1 row)
    postgres=> SELECT object_name, column_name, function_info FROM redaction_columns;
     object_name | column_name |                                             function_info                                             
    -------------+-------------+-------------------------------------------------------------------------------------------------------
     emp         | card_no     | mask_full(card_no)
     emp         | card_string | mask_partial(card_string, 'VVVVFVVVVFVVVVFVVVV'::text, 'VVVV-VVVV-VVVV-VVVV'::text, '#'::text, 1, 12)
     emp         | email       | mask_partial(email, '*'::text, 1, "position"(email, '@'::text))
     emp         | salary      | mask_partial(salary, '9'::text, 1, (length((salary)::text) - 2))
     emp         | birthday    | mask_full(birthday)
     emp         | phone_no    | mask_partial(phone_no, '*'::text, 4)
    (6 rows)
  5. 突然某一天,公司内部可共享员工信息时,直接删除表emp的脱敏策略mask_emp即可。

    postgres=> DROP REDACTION POLICY mask_emp ON emp;

GaussDB(DWS)数据脱敏优势

  • 一套简单、易用的数据脱敏策略语法。
  • 一系列可覆盖常见隐私数据脱敏效果的、灵活配置的内置脱敏函数。
  • 一个完备、便捷的脱敏策略应用方案,使得原始语句在执行过程中可以实时、透明、高效地实现脱敏。

GaussDB(DWS)充分满足客户业务场景的数据脱敏诉求,支持常见隐私数据的脱敏效果,实现敏感数据的可靠保护。

了解更多华为云数据仓库GaussDB(DWS),请点击这里


(完)