The road rain is like snow. Are you frozen? -- Slightly, I am a keyword filter.

Source: Internet
Author: User

Keyword filtering is required in recent projects. configure a filter to filter only POST requests. Don't talk nonsense, code up.

1 package cn.com. phone. servlet. filter; 2 3 import java. io. IOException; 4 import java. io. unsupportedEncodingException; 5 import java. lang. reflect. invocationTargetException; 6 import java. lang. reflect. method; 7 import java.net. URLDecoder; 8 import java. util. enumeration; 9 import java. util. map; 10 11 import javax. servlet. filter; 12 import javax. servlet. filterChain; 13 import javax. servlet. filterConfig; 14 import javax. servlet. servletException; 15 import javax. servlet. servletRequest; 16 import javax. servlet. servletResponse; 17 import javax. servlet. http. httpServletRequest; 18 import javax. servlet. http. httpServletResponse; 19 20 import cn.com. phone. utils. consts. consts; 21 import cn.com. phone. utils. log. printLog; 22 import cn.com. phone. utils. utils. keywordFilterService; 23 24/** 25 * keyword Filter 26 * @ author nyp2 */28 public class KeywordFilter implements Filter {29 30 @ Override31 public void destroy () {32 PrintLog. printInfoLog (getClass (), 33 Consts. debugdefine. response); 34} 35 36 @ SuppressWarnings ("unchecked") 37 @ Override38 public void doFilter (ServletRequest request, ServletResponse response, 39 FilterChain filterchain) throws IOException, UnsupportedEncodingException, servletException {40 HttpServletRequest req = (HttpServletRequest) request; 41 HttpServletResponse res = (HttpServletResponse) response; 42 // http Protocol 43 PrintLog. printInfoLog (getClass (), req. getProtocol (); 44 // Request Method 45 PrintLog. printInfoLog (getClass (), req. getMethod (); 46 if (req. getMethod (). equals ("POST") {47 req. setCharacterEncoding ("UTF-8"); 48 Enumeration e = req. getParameterNames (); // obtain the names of all request parameters, and assemble 49 Map = req by enumeration. getParameterMap (); 50 Method method = null; 51 52 try {53 method = map. getClass (). getMethod ("setLocked", 54 new Class [] {boolean. class}); 55 method. invoke (map, new Object [] {new Boolean (false)}); 56} catch (Exception e1) {57 e1.printStackTrace (); 58} 59 60 while (e. hasMoreElements () {61 String par = (String) e. nextElement (); // obtain the parameter names and obtain the parameter value 62 String value = req. getParameter (par); 63 URLDecoder. decode (value, "UTF-8"); 64 String tempvalue = new String (value. getBytes ("iso-8859-1"), "UTF-8"); 65 // call the keyword Filter Method 66 String newvalue = KeywordFilterService. getFilterString (67 tempvalue, "*"); 68 map. put (par, newvalue); 69} 70} 71 filterchain. doFilter (req, res); 72} 73 74 @ Override75 public void init (FilterConfig arg0) throws ServletException {76 PrintLog77. printInfoLog (getClass (), Consts. debugdefine. serlvetfilterinits); 78} 79 80}

The code for keyword filtering is as follows:

Package cn.com. phone. utils. utils; import java. util. arrayList; import java. util. hashMap; import java. util. iterator; import java. util. map; import java. util. set; import cn.com. phone. jdbc. DBoperation; public class KeywordFilterService {private static final char endTag = (char) (1); // keyword Terminator @ SuppressWarnings ("unchecked") private static Map <Character, hashMap> filterMap = new HashMap <Character, HashMap> (102 4); private static java. util. list <HashMap> key_list_map = new ArrayList <HashMap> (); private static java. util. list key_list = new ArrayList (); static {String SQL = "SELECT * FROM KEYWORD"; key_list_map = DBoperation. queryForObjectList (DBoperation. getConn (), null, SQL); init (); System. out. println ("key_list_map =" + key_list_map) ;}@ SuppressWarnings ("unchecked") public static void init () {for (Map m Ap: key_list_map) {key_list.add (map. get ("name");} for (Object filterWord: key_list) {char [] charArray = filterWord. toString (). trim (). toCharArray (); int len = charArray. length; if (len> 0) {Map <Character, HashMap> subMap = filterMap; for (int I = 0; I <len-1; I ++) {Map <Character, HashMap> obj = subMap. get (charArray [I]); if (obj = null) {// new index, add HashMap int size = (int) Math. max (2, 16/ Math. pow (2, I); HashMap <Character, HashMap> subMapTmp = new HashMap <Character, HashMap> (size); subMap. put (charArray [I], subMapTmp); subMap = subMapTmp;} else {// The index already has subMap = obj ;}}// process the Map of the last Character <Character, hashMap> obj = subMap. get (charArray [len-1]); if (obj = null) {// new index, add HashMap, and set the terminator int size = (int) Math. max (2, 16/Math. pow (2, len-1); HashMap <Character, HashMap> subMapT Mp = new HashMap <Character, HashMap> (size); subMapTmp. put (endTag, null); subMap. put (charArray [len-1], subMapTmp);} else {// The index already exists. Set the terminator obj. put (endTag, null) ;}}// returns whether to include the words to be filtered. If the keyword matches the shortest, return the result @ SuppressWarnings ("unchecked ") public static boolean isHasFilterWord (String info) {if (info = null | info. length () = 0) {return false;} char [] charArray = info. toCharArray (); int len = charA Rray. length; for (int I = 0; I <len; I ++) {int index = I; Map <Character, HashMap> sub = filterMap. get (charArray [index]); while (sub! = Null) {if (sub. containsKey (endTag) {// return true after the match ends;} else {index ++; if (index> = len) {// return false after the string ends;} sub = sub. get (charArray [index]) ;}} return false ;}// filter and replace the keywords contained in the string with the specified string, then return the replaced String // try to match the longest keyword and replace @ SuppressWarnings ("unchecked") public static String getFilterString (String info, String replaceTag) {if (info = null | info. length () = 0 | replaceTag = null | replaceTag. length () = 0) {return info;} char [] charArray = info. toCharArray (); int len = charArray. length; String newInfo = ""; int I = 0; while (I <len) {int end =-1; int index; Map <Character, HashMap> sub = filterMap; for (index = I; index <len; index ++) {sub = sub. get (charArray [index]); if (sub = null) {// The matching fails. Replace the longest matched character with if (end =-1) {// no matching keyword newInfo + = charArray [I]; I ++; break ;} else {// Replace the longest matching string with the specific character for (int j = I; j <= end; j ++) {newInfo + = replaceTag ;} I = end + 1; break;} else {if (sub. containsKey (endTag) {// match end = index ;}}if (index >=len) {// string ends if (end =-1) {// no matching keyword newInfo + = charArray [I]; I ++;} else {// Replace the longest matching string with a specific character for (int j = I; j <= end; j ++) {newInfo + = replaceTag;} I = end + 1 ;}} return newInfo ;}}

In practice, the thought of filtering keywords is to filter and process the request parameter values one by one, and finally obtain the filtered values. The problem is, how can we ensure that the old duty can be replaced by the new value after the request parameter value is taken out for processing? I even thought about getting the request header Request Path and parameters combined with the filtered parameter value through an existing request to re-initiate a request. That's ridiculous, right. In fact, Httprequest provides a getParameterMap () method to obtain a Map object named KEY with the parameter VALUE as VALUE. Then, you can directly set a new VALUE through put. But this is not complete yet. If this is the case, an exception is thrown as follows:

Yes, ParameterMap is locked. In fact, we can obtain the source code through decompilation and find that the original surface of ParameterMap is org. apache. catalina. util. parameterMap, which is not a HashMap object we normally use, but inherited from it, and when we set a value for it through put, it will first determine whether it is locked, and by default, it is locked. It is understandable that if a network request can modify the request content at will, the risk of data transmission is inevitable. Source code excerpt is as follows:

Public Object put (Object key, Object value) {if (locked) // first checks whether the current Object is locked. The default lock throw new IllegalStateException (sm. getString ("parameterMap. locked "); else return super. put (key, value);} public void setLocked (boolean locked) {this. locked = locked ;}

We cannot modify the source code, but since there is a setLocked method, it is easier to solve this problem through reflection. As follows:

 

Map map = req. getParameterMap (); try {Method method = map. getClass (). getMethod ("setLocked", new Class [] {boolean. class}); method. invoke (map, new Object [] {new Boolean (false)}); // sets the current ParameterMap Object to unlocked through reflection.
} Catch (Exception e1) {e1.printStackTrace ();} map. put (par, newvalue); // newvalue is the processed value.

 

 

Certificate --------------------------------------------------------------------------------------------------------------------------------------------------------------

Forgive me for having to indulge in my life and love your code and silence

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.