Log4j filter to mask Payment Card numbers (PCI DSS)

According to PCI DSS (Payment Card Industry Data Security Standard) your application must not store payment card numbers. This requirement includes database, files and logs. The following filter will allow you to mask card numbers in your logs on the fly, so even if you accidentally turned debug mode on for network communication, you can be confident that your data is PCI compliant.

Log4j allows you to configure PatternLayout that processes your log records. The idea is simple, out filter would match payment card numbers and replace them with masked values. Card number is usually a number of 15-19 digits.

I am going to use regular expression to match possible card numbers and replace them with masked values. I leave unmasked the beginning (6 digits) and the ending (4 digits), replacing the middle part with text. So, instead of 123456789012345678, I will get 123456<HIDDEN>5678 in my logs.

The following class implements PatternLayout with overriden format() method that does filtering:

package vozis.logger;

import java.util.regex.Matcher;
import java.util.regex.Pattern;
import org.apache.log4j.Logger;
import org.apache.log4j.PatternLayout;
import org.apache.log4j.spi.LoggingEvent; /**
* Credit Card Filtering Layout
* @author sergej.sizov
*/
public class CreditCardFilteringLayout extends PatternLayout { private static final String MASKCARD = "$1<HIDDEN>$2";
private static final Pattern PATTERNCARD =
Pattern.compile("([0-9]{6})[0-9]{0,9}([0-9]{4})"); @Override
public String format(LoggingEvent event) {
if (event.getMessage() instanceof String) {
String message = event.getRenderedMessage(); Matcher matcher = PATTERNCARD.matcher(message); if (matcher.find()) {
String maskedMessage = matcher.replaceAll(MASKCARD); Throwable throwable =
event.getThrowableInformation() != null ?
event.getThrowableInformation().getThrowable() : null; LoggingEvent maskedEvent = new LoggingEvent(
event.fqnOfCategoryClass,
Logger.getLogger(event.getLoggerName()),
event.timeStamp,
event.getLevel(),
maskedMessage,
throwable); return super.format(maskedEvent);
}
} return super.format(event); }
}

Then we need to configure Log4j to use CreditCardFilteringLayout. You need to override layout property for every appender in log4j.properties as it is shown below:

    log4j.appender.stdout=org.apache.log4j.ConsoleAppender
log4j.appender.stdout.Target=System.out
log4j.appender.stdout.layout=vozis.logger.CreditCardFilteringLayout
log4j.appender.stdout.layout.ConversionPattern=%d{HH:mm:ss} %-5p %c{1} - %m%n
log4j.appender.stdout.Threshold=info log4j.appender.TEMP=org.apache.log4j.RollingFileAppender
log4j.appender.TEMP.File=temp.log
log4j.appender.TEMP.MaxFileSize=5MB
log4j.appender.TEMP.MaxBackupIndex=1
log4j.appender.TEMP.layout=vozis.logger.CreditCardFilteringLayout
log4j.appender.TEMP.layout.ConversionPattern=%-5p %d{yyyy-MM-dd HH:mm:ss,SSS} %C{1}:%M(line %L) - %m%n

This idea can be used not only for credit card numbers, but also for Social Security number (SSN) or any other data that you consider sensitive. The benefit of this solution is that it is a one place change and it is easier than checking every logger.log() invocation in your application.

Log4j 密码屏蔽的更多相关文章

  1. paip.Log4j配置不起作用的解决

    paip.Log4j配置不起作用的解决 1.jar包里的log4j配置 看累挂jar,真的有个" webservices-rt.jar\com\sun\org\apache\xml\inte ...

  2. 超大 Cookie 拒绝服务攻击

    有没有想过,如果网站的 Cookie 特别多特别大,会发生什么情况? 不多说,马上来试验一下: for (i = 0; i < 20; i++) document.cookie = i + '= ...

  3. zkSNARK 零知识验证

    参考文献 ZCash7篇,有社区翻译版,但还是推荐看原汁原味的     https://z.cash/blog/snark-explain.html Vitalik3篇,小天才作者我就不介绍了,这三篇 ...

  4. linux下输入密码不回显

    这几天在做一个登陆的程序,需要将输入的密码屏蔽掉,自己百度,找到了两种方法,先贴下第一种方法, #include<stdio.h> #include<unistd.h> int ...

  5. 通过游戏学python 3.6 第一季 第九章 实例项目 猜数字游戏--核心代码--猜测次数--随机函数和屏蔽错误代码--优化代码及注释--简单账号密码登陆--账号的注册查询和密码的找回修改--锁定账号--锁定次数--菜单功能'menufile

      通过游戏学python 3.6 第一季 第九章 实例项目 猜数字游戏--核心代码--猜测次数--随机函数和屏蔽错误代码--优化代码及注释--简单账号密码登陆--账号的注册查询和密码的找回修改--锁 ...

  6. 通过游戏学python 3.6 第一季 第八章 实例项目 猜数字游戏--核心代码--猜测次数--随机函数和屏蔽错误代码--优化代码及注释--简单账号密码登陆--账号的注册查询和密码的找回修改--锁定账号--锁定次数

    通过游戏学python 3.6 第一季 第八章 实例项目 猜数字游戏--核心代码--猜测次数--随机函数和屏蔽错误代码--优化代码及注释--简单账号密码登陆--账号的注册查询和密码的找回修改--锁定账 ...

  7. 通过游戏学python 3.6 第一季 第七章 实例项目 猜数字游戏--核心代码--猜测次数--随机函数和屏蔽错误代码--优化代码及注释--简单账号密码登陆--账号的注册查询和密码的找回修改--锁定账号

    #猜数字--核心代码--猜测次数--随机函数和屏蔽错误代码---优化代码及注释--简单账号密码登陆--账号的注册查询和密码的找回修改--锁定账号 #猜数字--核心代码--猜测次数--随机函数和屏蔽错误 ...

  8. 通过游戏学python 3.6 第一季 第六章 实例项目 猜数字游戏--核心代码--猜测次数--随机函数和屏蔽错误代码--优化代码及注释--简单账号密码登陆--账号的注册查询和密码的找回修改 可复制直接使用 娱乐 可封装 函数

    #猜数字--核心代码--猜测次数--随机函数和屏蔽错误代码---优化代码及注释--简单账号密码登陆--账号的注册查询和密码的找回修改 #猜数字--核心代码--猜测次数--随机函数和屏蔽错误代码---优 ...

  9. 通过游戏学python 3.6 第一季 第五章 实例项目 猜数字游戏--核心代码--猜测次数--随机函数和屏蔽错误代码--优化代码及注释--简单账号密码登陆 可复制直接使用 娱乐 可封装 函数

    #猜数字--核心代码--猜测次数--随机函数和屏蔽错误代码---优化代码及注释--账号密码登陆 #!usr/bin/env python #-*-coding:utf-8-*- #QQ12411129 ...

随机推荐

  1. 自己动手写缓存Version1

    实现一个最简单最主要的缓存系统. using System; using System.Data; using System.Configuration; using System.Web; usin ...

  2. windows API 实现截图

    參考:http://bbs.csdn.net/topics/330154355 #include "stdio.h" #include "windows.h" ...

  3. 浅谈 Underscore.js 中 _.throttle 和 _.debounce 的差异

    Underscore.js是一个很精干的库,压缩后只有5.2KB.它提供了几十种函数式编程的方法,弥补了标准库的不足,大大方便了JavaScript的编程. 本文仅探讨Underscore.js的两个 ...

  4. linux+nginx+tomcat负载均衡,实现session同步

    linux+nginx+tomcat负载均衡,实现session同步 花了一个上午的时间研究nginx+tomcat的负载均衡测试,集群环境搭建比较顺利,但是session同步的问题折腾了几个小时才搞 ...

  5. 新型信用卡MasterPass

    Xsolla与masterpass合作.提供新型支付方式 "电子支付的未来在这里. "在万事达卡宣布发行一种全新的被称为MasterPass的支付解决方式的两年后.从2014年底開 ...

  6. linux-memory-buffer-vs-cache

    http://stackoverflow.com/questions/6345020/linux-memory-buffer-vs-cache

  7. android开发之使用上下文菜单

    android中的上下文菜单类似于PC上的鼠标右键单击,不同的是android上没有鼠标这一概念,更谈不上右键单击,在android中,一般是长按某个View,调出上下文菜单.与OptionsMenu ...

  8. PHP正值表达式

    一个正值表达式是有四部分组成分别是 1.定界符 //是最常用的定界符 其实除了数组字母下划线以外其他的什么都可以作为定界符 2.原子:最小的一个匹配单位 放在定界符中  在一个正值表达式中至少要有一个 ...

  9. Linux Bash终端快捷键小结

    Ctrl + A  定位至行首 Ctrl + E  定位至行尾 Ctrl + U  向前删除至行首 Ctrl + K  向后删除至行尾 Ctrl + L  清屏

  10. Scala中class和object的区别

    1.class scala的类和C#中的类有点不一样,诸如: 声明一个未用priavate修饰的字段 var age,scala编译器会字段帮我们生产一个私有字段和2个公有方法get和set ,这和C ...