【问题标题】:Masking data after a particular word up to next word in oracle将特定单词之后的数据屏蔽到oracle中的下一个单词
【发布时间】:2022-01-20 21:56:51
【问题描述】:

我在屏蔽下面描述的数据时遇到了问题 --

Input Output
1. CC# S2345-567 Match 2345 This is String ************** Match 2345 This is String
2. My Self CC P457-238 This is Data My Self *********** This is Data
3. My Card is CC 457829 My Card is *********
4. This is the CC# 42357 This is the my records This is the ********* This is the my records .

我能够通过使用以下查询来屏蔽第 3 和第 4 个条件 --

SELECT CASE 
       WHEN start_pos1 > 0 
       THEN SUBSTR( col, 1, start_pos1 - 1) 
            || RPAD('*', end_pos1 - start_pos1, '*') 
            || SUBSTR(col, end_pos1) 
       ELSE col 
       END AS col_new 
FROM   ( 
  SELECT col, 
         REGEXP_INSTR( col, 'CC([. # -]*\d+)+', 1, 1, 0, NULL) AS start_pos1, 
         REGEXP_INSTR( col, 'CC([. # -]*\d+)+', 1, 1, 1, NULL) AS end_pos1
 FROM  Table 
);

任何人都可以为上述第一个和第二个条件提供帮助吗?

【问题讨论】:

  • 我们需要更精确的规则来屏蔽您的数据,以便在此处给出答案。
  • CC 或 CC# 后的下一个字母数字或数字可以被屏蔽,字母数字单词可以包含一个字符。例如 CC# S2345-567 匹配 2345 这是字符串 ---- ************** 匹配 2345 这是字符串 我的自我 CC P457-238 这是数据 ----- 我的自我 *********** 这是数据
  • 作为注释,一般来说,not 使用 CC 文本的确切原始宽度可能会更好。这样做的原因是,放弃长度可能仍然会泄露关键信息,例如使用的信用卡类型是什么。

标签: oracle


【解决方案1】:

在这里尝试使用REGEXP_REPLACE

SELECT col,
       REGEXP_REPLACE(col, 'CC#?[[:space:]]+\S+', '********') AS col_masked
FROM yourTable;

【讨论】:

  • 您的查询对上述字符串运行良好。但对于下面它是失败的 ex - 1. CC# F38967 是 data 。由于 CC# 和 F38967 之间有多个空格,它按原样显示。
  • @EX08 请检查更新的答案。
  • 这将屏蔽“ABCC 不应被屏蔽”。
【解决方案2】:

你需要匹配数字前的字母字符:

SELECT col,
       CASE 
       WHEN start_pos1 > 0 
       THEN SUBSTR( col, 1, start_pos1 - 1) 
            || RPAD('*', end_pos1 - start_pos1, '*') 
            || SUBSTR(col, end_pos1) 
       ELSE col 
       END AS col_new 
FROM   ( 
  SELECT col, 
         REGEXP_INSTR( col, 'CC#?\s+[A-Z]?\d+([. -]*\d+)*', 1, 1, 0, NULL) AS start_pos1, 
         REGEXP_INSTR( col, 'CC#?\s+[A-Z]?\d+([. -]*\d+)*', 1, 1, 1, NULL) AS end_pos1
  FROM  table_name
);

其中,对于您的示例数据:

CREATE TABLE table_name (col) AS
SELECT 'CC# S2345-567 Match 2345 This is String' FROM DUAL UNION ALL
SELECT 'My Self CC P457-238 This is Data' FROM DUAL UNION ALL
SELECT 'My Card is CC 457829' FROM DUAL UNION ALL
SELECT 'This is the CC# 42357' FROM DUAL UNION ALL
SELECT 'The ABCC should not be masked' FROM DUAL;

输出:

COL COL_NEW
CC# S2345-567 Match 2345 This is String ************* Match 2345 This is String
My Self CC P457-238 This is Data My Self *********** This is Data
My Card is CC 457829 My Card is *********
This is the CC# 42357 This is the *********
The ABCC should not be masked The ABCC should not be masked

db小提琴here

【讨论】:

  • 请注意,隐藏信用卡号的确切原始宽度可能是一个问题,因为它可能会泄露有关 CC 的一些信息(例如,它是哪个提供商等)。
  • 感谢您的帮助
【解决方案3】:

另一种选择:

WITH cteData
  AS (SELECT col, REGEXP_SUBSTR(col, 'CC#? [A-Z]?[-0-9]+') AS MATCH_DATA
        FROM table_name)
SELECT col, MATCH_DATA, REPLACE(col, MATCH_DATA, RPAD('*', LENGTH(MATCH_DATA), '*'))
  FROM cteData

db<>fiddle here

(非常感谢@MT0 提供示例数据:-)

【讨论】:

    猜你喜欢
    • 2017-07-26
    • 1970-01-01
    • 2022-01-21
    • 2020-09-15
    • 1970-01-01
    • 2022-01-04
    • 2020-03-09
    • 2021-08-01
    • 1970-01-01
    相关资源
    最近更新 更多