/*\r
- * Copyright (C) 2001, 2002 The Mir-coders group\r
+ * Copyright (C) 2001, 2002 The Mir-coders group\r
*\r
* This file is part of Mir.\r
*\r
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA\r
*\r
* In addition, as a special exception, The Mir-coders gives permission to link\r
- * the code of this program with the com.oreilly.servlet library, any library\r
- * licensed under the Apache Software License, The Sun (tm) Java Advanced\r
- * Imaging library (JAI), The Sun JIMI library (or with modified versions of\r
- * the above that use the same license as the above), and distribute linked\r
- * combinations including the two. You must obey the GNU General Public\r
- * License in all respects for all of the code used other than the above\r
- * mentioned libraries. If you modify this file, you may extend this exception\r
- * to your version of the file, but you are not obligated to do so. If you do\r
- * not wish to do so, delete this exception statement from your version.\r
+ * the code of this program with any library licensed under the Apache Software License,\r
+ * The Sun (tm) Java Advanced Imaging library (JAI), The Sun JIMI library\r
+ * (or with modified versions of the above that use the same license as the above),\r
+ * and distribute linked combinations including the two. You must obey the\r
+ * GNU General Public License in all respects for all of the code used other than\r
+ * the above mentioned libraries. If you modify this file, you may extend this\r
+ * exception to your version of the file, but you are not obligated to do so.\r
+ * If you do not wish to do so, delete this exception statement from your version.\r
*/\r
\r
package mircoders.global;\r
\r
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.FileOutputStream;
-import java.util.Arrays;
-import java.util.Date;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.Random;
-import java.util.Vector;
-import javax.servlet.http.Cookie;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-
-import org.apache.commons.collections.ExtendedProperties;
-import gnu.regexp.RE;
-
-import mir.entity.Entity;
-import mir.log.LoggerWrapper;
-import mir.session.HTTPAdapters;
-import mir.session.Request;
-import mir.util.DateToMapAdapter;
-import mir.util.InternetFunctions;
-import mir.util.StringRoutines;
-import mircoders.entity.EntityComment;
-import mircoders.entity.EntityContent;
+import java.io.File;\r
+import java.io.FileNotFoundException;\r
+import java.io.FileOutputStream;\r
+import java.util.Arrays;\r
+import java.util.Date;\r
+import java.util.GregorianCalendar;\r
+import java.util.HashMap;\r
+import java.util.Iterator;\r
+import java.util.List;\r
+import java.util.Map;\r
+import java.util.Random;\r
+import java.util.Vector;\r
+import javax.servlet.http.Cookie;\r
+import javax.servlet.http.HttpServletResponse;\r
+\r
+import org.apache.commons.collections.ExtendedProperties;\r
+import mir.config.MirPropertiesConfiguration;\r
+import mir.entity.Entity;\r
+import mir.log.LoggerWrapper;\r
+import mir.session.Request;\r
+import mir.util.GeneratorFormatAdapters;\r
+import mir.util.StringRoutines;\r
+import mircoders.entity.EntityComment;\r
+import mircoders.entity.EntityContent;\r
+import mircoders.entity.EntityUsers;\r
import mircoders.localizer.MirAdminInterfaceLocalizer;\r
+import mircoders.localizer.MirAntiAbuseFilterType;\r
\r
\r
public class Abuse {\r
- private List filters;\r
+ private List filterRules;\r
+ private Map filterTypes;\r
+ private List filterTypeIds;\r
private int maxIdentifier;\r
private LoggerWrapper logger;\r
+ private LoggerWrapper adminUsageLogger;\r
private int logSize;\r
private boolean logEnabled;\r
private boolean openPostingDisabled;\r
private List log;\r
private String configFile = MirGlobal.config().getStringWithHome("Abuse.Config");\r
\r
+ private MirPropertiesConfiguration configuration;\r
\r
- private static final String IP_FILTER_TYPE="ip";\r
- private static final String REGEXP_FILTER_TYPE="regexp";\r
private static String cookieName=MirGlobal.config().getString("Abuse.CookieName");\r
private static int cookieMaxAge = 60*60*MirGlobal.config().getInt("Abuse.CookieMaxAge");\r
\r
public Abuse() {\r
logger = new LoggerWrapper("Global.Abuse");\r
- filters = new Vector();\r
+ adminUsageLogger = new LoggerWrapper("AdminUsage");\r
+ filterRules = new Vector();\r
maxIdentifier = 0;\r
log = new Vector();\r
\r
+ try {\r
+ configuration = MirPropertiesConfiguration.instance();\r
+ }\r
+ catch (Throwable e) {\r
+ throw new RuntimeException("Can't get configuration: " + e.getMessage());\r
+ }\r
+\r
logSize = 100;\r
logEnabled = false;\r
articleBlockAction = "";\r
openPostingDisabled = false;\r
cookieOnBlock = false;\r
\r
- load();\r
- }\r
+ try {\r
+ filterTypes = new HashMap();\r
+ filterTypeIds = new Vector();\r
\r
- public boolean checkIpFilter(String anIpAddress) {\r
- synchronized (filters) {\r
- Iterator i = filters.iterator();\r
+ Iterator i = MirGlobal.localizer().openPostings().getAntiAbuseFilterTypes().iterator();\r
\r
while (i.hasNext()) {\r
- Filter filter = (Filter) i.next();\r
-\r
- try {\r
- if ( (filter.getType().equals(IP_FILTER_TYPE)) &&\r
- InternetFunctions.isIpAddressInNetwork(anIpAddress, filter.getExpression())) {\r
- logger.debug("ip match on " + filter.getExpression());\r
- return true;\r
- }\r
- }\r
- catch (Throwable t) {\r
- logger.warn("error while checking ip address " + anIpAddress + " over network " + filter.expression + ": " + t.getMessage());\r
- }\r
+ MirAntiAbuseFilterType filterType = (MirAntiAbuseFilterType) i.next();\r
+ filterTypes.put(filterType.getName(), filterType);\r
+ filterTypeIds.add(filterType.getName());\r
}\r
-\r
- return false;\r
}\r
- }\r
-\r
- private boolean checkRegExpFilter(Entity anEntity) {\r
- synchronized (filters) {\r
- Iterator i = filters.iterator();\r
-\r
- while (i.hasNext()) {\r
- Filter filter = (Filter) i.next();\r
-\r
- if (filter.getType().equals(REGEXP_FILTER_TYPE)) {\r
- try {\r
- RE regularExpression = new RE(filter.getExpression());\r
-\r
- Iterator j = anEntity.getFields().iterator();\r
- while (j.hasNext()) {\r
- String field = anEntity.getValue( (String) j.next());\r
-\r
- if (field != null && regularExpression.isMatch(field.toLowerCase())) {\r
- logger.debug("regexp match on " + filter.getExpression());\r
- return true;\r
- }\r
- }\r
- }\r
- catch (Throwable t) {\r
- logger.warn("error while checking entity with regexp " + filter.getExpression() + ": " + t.getMessage());\r
- }\r
- }\r
- }\r
-\r
- return false;\r
+ catch (Throwable t) {\r
+ throw new RuntimeException("Can't get filter types: " + t.getMessage());\r
}\r
+\r
+ load();\r
}\r
\r
private void setCookie(HttpServletResponse aResponse) {\r
return false;\r
}\r
\r
- public void checkComment(EntityComment aComment, Request aRequest, HttpServletResponse aResponse) {\r
- try {\r
- long time = System.currentTimeMillis();\r
- String address = "0.0.0.0";\r
- String browser = "unknown";\r
- Cookie[] cookies = {};\r
+ FilterRule findMatchingFilter(Entity anEntity, Request aRequest) {\r
+ Iterator iterator = filterRules.iterator();\r
\r
- HttpServletRequest request = null;\r
+ while (iterator.hasNext()) {\r
+ FilterRule rule = (FilterRule) iterator.next();\r
\r
- if (aRequest instanceof HTTPAdapters.HTTPParsedRequestAdapter) {\r
- request = ((HTTPAdapters.HTTPParsedRequestAdapter) aRequest).getRequest();\r
- }\r
- else if (aRequest instanceof HTTPAdapters.HTTPRequestAdapter) {\r
- request = ((HTTPAdapters.HTTPRequestAdapter) aRequest).getRequest();\r
- }\r
- if (request!=null) {\r
- browser = (String) request.getHeader("User-Agent");\r
- address = request.getRemoteAddr();\r
- cookies = request.getCookies();\r
- }\r
+ if (rule.test(anEntity, aRequest))\r
+ return rule;\r
+ }\r
+\r
+ return null;\r
+ }\r
\r
- logComment(address, aComment.getId(), new Date(), browser);\r
+ public void checkComment(EntityComment aComment, Request aRequest, HttpServletResponse aResponse) {\r
+ logComment(aComment, aRequest);\r
+\r
+ try {\r
+ long time = System.currentTimeMillis();\r
\r
- MirAdminInterfaceLocalizer.MirSimpleEntityOperation operation = MirGlobal.localizer().adminInterface().simpleCommentOperationForName(commentBlockAction);\r
+ FilterRule filterRule = findMatchingFilter(aComment, aRequest);\r
\r
- if (checkCookie(Arrays.asList(cookies)) || checkIpFilter(address) || checkRegExpFilter(aComment)) {\r
- operation.perform(null, MirGlobal.localizer().dataModel().adapterModel().makeEntityAdapter("comment", aComment));\r
+ if (filterRule!=null) {\r
+ logger.debug("Match for " + filterRule.getType()+" rule '"+ filterRule.getExpression()+"'");\r
+ filterRule.setLastHit(new GregorianCalendar().getTime());\r
+ MirGlobal.performCommentOperation(null, aComment, filterRule.getCommentAction());\r
setCookie(aResponse);\r
+ save();\r
}\r
\r
logger.info("checkComment: " + (System.currentTimeMillis()-time) + "ms");\r
}\r
catch (Throwable t) {\r
+ t.printStackTrace(logger.asPrintWriter(logger.DEBUG_MESSAGE));\r
logger.error("Abuse.checkComment: " + t.toString());\r
}\r
}\r
\r
- public void checkArticle(EntityContent anArticle, HttpServletRequest aRequest, HttpServletResponse aResponse) {\r
+ public void checkArticle(EntityContent anArticle, Request aRequest, HttpServletResponse aResponse) {\r
+ logArticle(anArticle, aRequest);\r
+\r
try {\r
long time = System.currentTimeMillis();\r
\r
- logArticle(aRequest.getRemoteAddr(), anArticle.getId(), new Date(), (String) aRequest.getHeader("User-Agent"));\r
-\r
- MirAdminInterfaceLocalizer.MirSimpleEntityOperation operation = MirGlobal.localizer().adminInterface().simpleCommentOperationForName(commentBlockAction);\r
+ FilterRule filterRule = findMatchingFilter(anArticle, aRequest);\r
\r
- if (checkCookie(Arrays.asList(aRequest.getCookies())) || checkIpFilter(aRequest.getRemoteAddr()) || checkRegExpFilter(anArticle)) {\r
- operation.perform(null, MirGlobal.localizer().dataModel().adapterModel().makeEntityAdapter("content", anArticle));\r
+ if (filterRule!=null) {\r
+ logger.debug("Match for " + filterRule.getType() + " rule '" + filterRule.getExpression()+"'");\r
+ filterRule.setLastHit(new GregorianCalendar().getTime());\r
+ MirGlobal.performArticleOperation(null, anArticle, filterRule.getArticleAction());\r
setCookie(aResponse);\r
+ save();\r
}\r
\r
logger.info("checkArticle: " + (System.currentTimeMillis()-time) + "ms");\r
}\r
catch (Throwable t) {\r
+ t.printStackTrace(logger.asPrintWriter(logger.DEBUG_MESSAGE));\r
logger.error("Abuse.checkArticle: " + t.toString());\r
}\r
}\r
}\r
\r
public void setLogEnabled(boolean anEnabled) {\r
- logEnabled = anEnabled;\r
+ if (!configuration.getString("Abuse.DisallowIPLogging", "0").equals("1"))\r
+ logEnabled = anEnabled;\r
truncateLog();\r
}\r
\r
commentBlockAction = anAction;\r
}\r
\r
-\r
public List getLog() {\r
synchronized(log) {\r
- List result = new Vector();\r
+ try {\r
+ List result = new Vector();\r
+\r
+ Iterator i = log.iterator();\r
+ while (i.hasNext()) {\r
+ LogEntry logEntry = (LogEntry) i.next();\r
+ Map entry = new HashMap();\r
+\r
+ entry.put("ip", logEntry.getIpNumber());\r
+ entry.put("id", logEntry.getId());\r
+ entry.put("timestamp", new GeneratorFormatAdapters.DateFormatAdapter(logEntry.getTimeStamp(), MirPropertiesConfiguration.instance().getString("Mir.DefaultTimezone")));\r
+ if (logEntry.getIsArticle())\r
+ entry.put("type", "content");\r
+ else\r
+ entry.put("type", "comment");\r
+ entry.put("browser", logEntry.getBrowserString());\r
+\r
+ result.add(entry);\r
+ }\r
\r
- Iterator i = log.iterator();\r
- while (i.hasNext()) {\r
- LogEntry logEntry = (LogEntry) i.next();\r
- Map entry = new HashMap();\r
-\r
- entry.put("ip", logEntry.getIpNumber());\r
- entry.put("id", logEntry.getId());\r
- entry.put("timestamp", new DateToMapAdapter(logEntry.getTimeStamp()));\r
- if (logEntry.getIsArticle())\r
- entry.put("type", "content");\r
- else\r
- entry.put("type", "comment");\r
- entry.put("browser", logEntry.getBrowserString());\r
-\r
- result.add(entry);\r
+ return result;\r
+ }\r
+ catch (Throwable t) {\r
+ throw new RuntimeException(t.toString());\r
}\r
-\r
- return result;\r
}\r
}\r
\r
+ public void logComment(Entity aComment, Request aRequest) {\r
+ String ipAddress = aRequest.getHeader("ip");\r
+ String id = aComment.getId();\r
+ String browser = aRequest.getHeader("User-Agent");\r
+\r
+ logComment(ipAddress, id, new Date(), browser);\r
+ }\r
+\r
+ public void logArticle(Entity anArticle, Request aRequest) {\r
+ String ipAddress = aRequest.getHeader("ip");\r
+ String id = anArticle.getId();\r
+ String browser = aRequest.getHeader("User-Agent");\r
+\r
+ logArticle(ipAddress, id, new Date(), browser);\r
+ }\r
+\r
public void logComment(String anIp, String anId, Date aTimeStamp, String aBrowser) {\r
appendLog(new LogEntry(aTimeStamp, anIp, aBrowser, anId, false));\r
}\r
}\r
\r
public void load() {\r
- try {\r
- ExtendedProperties configuration = new ExtendedProperties();\r
-\r
+ synchronized (filterRules) {\r
try {\r
- configuration = new ExtendedProperties(configFile);\r
- }\r
- catch (FileNotFoundException e) {\r
- }\r
+ ExtendedProperties configuration = new ExtendedProperties();\r
\r
- getFilterConfig(filters, "abuse.filter", configuration);\r
+ try {\r
+ configuration = new ExtendedProperties(configFile);\r
+ }\r
+ catch (FileNotFoundException e) {\r
+ }\r
\r
- setOpenPostingDisabled(configuration.getString("abuse.openPostingDisabled", "0").equals("1"));\r
- setOpenPostingPassword(configuration.getString("abuse.openPostingPassword", "0").equals("1"));\r
- setCookieOnBlock(configuration.getString("abuse.cookieOnBlock", "0").equals("1"));\r
- setLogEnabled(configuration.getString("abuse.logEnabled", "0").equals("1"));\r
- setLogSize(configuration.getInt("abuse.logSize", 10));\r
- setArticleBlockAction(configuration.getString("abuse.articleBlockAction", ""));\r
- setCommentBlockAction(configuration.getString("abuse.commentBlockAction", ""));\r
- }\r
- catch (Throwable t) {\r
- throw new RuntimeException(t.toString());\r
+ getFilterConfig(filterRules, "abuse.filter", configuration);\r
+\r
+ setOpenPostingDisabled(configuration.getString("abuse.openPostingDisabled", "0").equals("1"));\r
+ setOpenPostingPassword(configuration.getString("abuse.openPostingPassword", "0").equals("1"));\r
+ setCookieOnBlock(configuration.getString("abuse.cookieOnBlock", "0").equals("1"));\r
+ setLogEnabled(configuration.getString("abuse.logEnabled", "0").equals("1"));\r
+ setLogSize(configuration.getInt("abuse.logSize", 10));\r
+ setArticleBlockAction(configuration.getString("abuse.articleBlockAction", ""));\r
+ setCommentBlockAction(configuration.getString("abuse.commentBlockAction", ""));\r
+ }\r
+ catch (Throwable t) {\r
+ throw new RuntimeException(t.toString());\r
+ }\r
}\r
}\r
+\r
public void save() {\r
- try {\r
- ExtendedProperties configuration = new ExtendedProperties();\r
+ synchronized (filterRules) {\r
+ try {\r
+ ExtendedProperties configuration = new ExtendedProperties();\r
\r
- setFilterConfig(filters, "abuse.filter", configuration);\r
+ setFilterConfig(filterRules, "abuse.filter", configuration);\r
\r
- configuration.addProperty("abuse.openPostingDisabled", getOpenPostingDisabled()?"1":"0");\r
- configuration.addProperty("abuse.openPostingPassword", getOpenPostingPassword()?"1":"0");\r
- configuration.addProperty("abuse.cookieOnBlock", getCookieOnBlock()?"1":"0");\r
- configuration.addProperty("abuse.logEnabled", getLogEnabled()?"1":"0");\r
- configuration.addProperty("abuse.logSize", Integer.toString(getLogSize()));\r
- configuration.addProperty("abuse.articleBlockAction", getArticleBlockAction());\r
- configuration.addProperty("abuse.commentBlockAction", getCommentBlockAction());\r
+ configuration.addProperty("abuse.openPostingDisabled", getOpenPostingDisabled() ? "1" : "0");\r
+ configuration.addProperty("abuse.openPostingPassword", getOpenPostingPassword() ? "1" : "0");\r
+ configuration.addProperty("abuse.cookieOnBlock", getCookieOnBlock() ? "1" : "0");\r
+ configuration.addProperty("abuse.logEnabled", getLogEnabled() ? "1" : "0");\r
+ configuration.addProperty("abuse.logSize", Integer.toString(getLogSize()));\r
+ configuration.addProperty("abuse.articleBlockAction", getArticleBlockAction());\r
+ configuration.addProperty("abuse.commentBlockAction", getCommentBlockAction());\r
\r
- configuration.save(new FileOutputStream(new File(configFile)), "Anti abuse configuration");\r
- }\r
- catch (Throwable t) {\r
- throw new RuntimeException(t.toString());\r
+ configuration.save(new FileOutputStream(new File(configFile)), "Anti abuse configuration");\r
+ }\r
+ catch (Throwable t) {\r
+ throw new RuntimeException(t.toString());\r
+ }\r
}\r
}\r
\r
public List getFilterTypes() {\r
- List result = new Vector();\r
+ try {\r
+ List result = new Vector();\r
+\r
+ Iterator i = filterTypeIds.iterator();\r
+ while (i.hasNext()) {\r
+ String id = (String) i.next();\r
\r
- Map entry = new HashMap();\r
- entry.put("resource", "ip");\r
- entry.put("id", IP_FILTER_TYPE);\r
- result.add(entry);\r
+ Map action = new HashMap();\r
+ action.put("resource", id);\r
+ action.put("identifier", id);\r
\r
- entry = new HashMap();\r
- entry.put("resource", "regexp");\r
- entry.put("id", REGEXP_FILTER_TYPE);\r
- result.add(entry);\r
+ result.add(action);\r
+ }\r
\r
- return result;\r
+ return result;\r
+ }\r
+ catch (Throwable t) {\r
+ throw new RuntimeException("can't get article actions");\r
+ }\r
}\r
\r
public List getArticleActions() {\r
}\r
\r
public List getFilters() {\r
- return getFiltersAsMaps(filters);\r
+ List result = new Vector();\r
+\r
+ synchronized(filterRules) {\r
+ Iterator i = filterRules.iterator();\r
+ while (i.hasNext()) {\r
+ FilterRule filter = (FilterRule) i.next();\r
+ result.add(filter.clone());\r
+ }\r
+ return result;\r
+ }\r
}\r
\r
- public void addFilter(String aType, String anExpression) {\r
- addFilter(filters, aType, anExpression);\r
+ public String addFilter(String aType, String anExpression, String aComments, String aCommentAction, String anArticleAction) {\r
+ return addFilter(aType, anExpression, aComments, aCommentAction, anArticleAction, null);\r
}\r
\r
- public void setFilter(String anIdentifier, String aType, String anExpression) {\r
- setFilter(filters, anIdentifier, aType, anExpression);\r
+ public String addFilter(String aType, String anExpression, String aComments, String aCommentAction, String anArticleAction, Date aListHit) {\r
+ return addFilter(filterRules, aType, anExpression, aComments, aCommentAction, anArticleAction, aListHit);\r
}\r
\r
- public void deleteFilter(String anIdentifier) {\r
- deleteFilter(filters, anIdentifier);\r
+ public FilterRule getFilter(String anId) {\r
+ synchronized (filterRules) {\r
+ FilterRule result = (FilterRule) findFilter(filterRules, anId);\r
+ if (result==null)\r
+ return result;\r
+ else\r
+ return (FilterRule) result.clone();\r
+ }\r
}\r
\r
- public void validateIpFilter(String anIdentifier, String anArticleAction, String aCommentAction) throws Exception {\r
+ public String setFilter(String anIdentifier, String aType, String anExpression, String aComments, String aCommentAction, String anArticleAction) {\r
+ return setFilter(filterRules, anIdentifier, aType, anExpression, aComments, aCommentAction, anArticleAction);\r
}\r
\r
- private List getFiltersAsMaps(List aFilters) {\r
- synchronized(aFilters) {\r
- List result = new Vector();\r
+ public void deleteFilter(String anIdentifier) {\r
+ deleteFilter(filterRules, anIdentifier);\r
+ }\r
\r
- Iterator i = aFilters.iterator();\r
- while (i.hasNext()) {\r
- Filter filter = (Filter) i.next();\r
- Map map = new HashMap();\r
+ private String addFilter(List aFilters, String aType, String anExpression, String aComments, String aCommentAction, String anArticleAction, Date aLastHit) {\r
+ MirAntiAbuseFilterType type = (MirAntiAbuseFilterType) filterTypes.get(aType);\r
\r
- map.put("id", filter.getId());\r
- map.put("expression", filter.getExpression());\r
- map.put("type", filter.getType());\r
+ if (type==null)\r
+ return "invalidtype";\r
\r
- result.add(map);\r
- }\r
- return result;\r
+ if (!type.validate(anExpression)) {\r
+ return "invalidexpression";\r
}\r
- }\r
\r
- private void addFilter(List aFilters, String aType, String anExpression) {\r
- Filter filter = new Filter();\r
+ FilterRule filter = new FilterRule();\r
\r
filter.setId(generateId());\r
filter.setExpression(anExpression);\r
filter.setType(aType);\r
+ filter.setComments(aComments);\r
+ filter.setArticleAction(anArticleAction);\r
+ filter.setCommentAction(aCommentAction);\r
+ filter.setLastHit(aLastHit);\r
\r
synchronized (aFilters) {\r
aFilters.add(filter);\r
}\r
+\r
+ return null;\r
}\r
\r
- private void setFilter(List aFilters, String anIdentifier, String aType, String anExpression) {\r
+ private String setFilter(List aFilters, String anIdentifier, String aType, String anExpression, String aComments, String aCommentAction, String anArticleAction) {\r
+ MirAntiAbuseFilterType type = (MirAntiAbuseFilterType) filterTypes.get(aType);\r
+\r
+ if (type==null)\r
+ return "invalidtype";\r
+\r
+ if (!type.validate(anExpression)) {\r
+ return "invalidexpression";\r
+ }\r
+\r
synchronized (aFilters) {\r
- Filter filter = findFilter(aFilters, anIdentifier);\r
+ FilterRule filter = findFilter(aFilters, anIdentifier);\r
\r
if (filter!=null) {\r
filter.setExpression(anExpression);\r
filter.setType(aType);\r
+ filter.setCommentAction(aCommentAction);\r
+ filter.setArticleAction(anArticleAction);\r
+ filter.setComments(aComments);\r
}\r
+\r
+ return null;\r
}\r
}\r
\r
- private Filter findFilter(List aFilters, String anIdentifier) {\r
+ private FilterRule findFilter(List aFilters, String anIdentifier) {\r
synchronized (aFilters) {\r
Iterator i = aFilters.iterator();\r
while (i.hasNext()) {\r
- Filter filter = (Filter) i.next();\r
+ FilterRule filter = (FilterRule) i.next();\r
\r
if (filter.getId().equals(anIdentifier)) {\r
return filter;\r
\r
private void deleteFilter(List aFilters, String anIdentifier) {\r
synchronized (aFilters) {\r
- Filter filter = findFilter(aFilters, anIdentifier);\r
+ FilterRule filter = findFilter(aFilters, anIdentifier);\r
\r
if (filter!=null) {\r
aFilters.remove(filter);\r
}\r
}\r
\r
- private static class Filter {\r
+ public class FilterRule {\r
private String identifier;\r
private String expression;\r
private String type;\r
+ private String comments;\r
+ private String articleAction;\r
+ private String commentAction;\r
+ private Date lastHit;\r
+\r
+ public FilterRule() {\r
+ expression = "";\r
+ type = "";\r
+ identifier = "";\r
+ comments = "";\r
+ articleAction = articleBlockAction;\r
+ commentAction = commentBlockAction;\r
+ lastHit = null;\r
+ }\r
\r
- public Filter() {\r
- expression="";\r
- type="";\r
- identifier="";\r
+ public Date getLastHit() {\r
+ return lastHit;\r
+ }\r
+\r
+ public void setLastHit(Date aDate) {\r
+ lastHit = aDate;\r
}\r
\r
public String getId() {\r
public void setType(String aType) {\r
type = aType;\r
}\r
+\r
+ public void setComments(String aComments) {\r
+ comments = aComments;\r
+ }\r
+\r
+ public String getComments() {\r
+ return comments;\r
+ }\r
+\r
+ public String getArticleAction() {\r
+ return articleAction;\r
+ }\r
+\r
+ public void setArticleAction(String anArticleAction) {\r
+ articleAction = anArticleAction;\r
+ }\r
+\r
+ public String getCommentAction() {\r
+ return commentAction;\r
+ }\r
+\r
+ public void setCommentAction(String aCommentAction) {\r
+ commentAction = aCommentAction;\r
+ }\r
+\r
+ public boolean test(Entity anEntity, Request aRequest) {\r
+ MirAntiAbuseFilterType filterType = (MirAntiAbuseFilterType) filterTypes.get(type);\r
+ try {\r
+ if (filterType != null)\r
+ return filterType.test(expression, anEntity, aRequest);\r
+ }\r
+ catch (Throwable t) {\r
+ logger.error("error while testing "+type+"-filter '"+expression+"'");\r
+ }\r
+\r
+ return false;\r
+ };\r
+\r
+ public Object clone() {\r
+ FilterRule result = new FilterRule();\r
+ result.setComments(getComments());\r
+ result.setExpression(getExpression());\r
+ result.setId(getId());\r
+ result.setType(getType());\r
+ result.setArticleAction(getArticleAction());\r
+ result.setCommentAction(getCommentAction());\r
+ result.setLastHit(getLastHit());\r
+\r
+ return result;\r
+ }\r
}\r
\r
private void setFilterConfig(List aFilters, String aConfigKey, ExtendedProperties aConfiguration) {\r
Iterator i = aFilters.iterator();\r
\r
while (i.hasNext()) {\r
- Filter filter = (Filter) i.next();\r
+ FilterRule filter = (FilterRule) i.next();\r
+\r
+ String filterconfig =\r
+ StringRoutines.replaceStringCharacters(filter.getType(), new char[] { '\\', ':'}, new String[] { "\\\\", "\\:"} ) + ":" +\r
+ StringRoutines.replaceStringCharacters(filter.getExpression(), new char[] { '\\', ':'}, new String[] { "\\\\", "\\:"} ) + ":" +\r
+ StringRoutines.replaceStringCharacters(filter.getArticleAction(), new char[] { '\\', ':'}, new String[] { "\\\\", "\\:"} ) + ":" +\r
+ StringRoutines.replaceStringCharacters(filter.getCommentAction(), new char[] { '\\', ':'}, new String[] { "\\\\", "\\:"} ) + ":" +\r
+ StringRoutines.replaceStringCharacters(filter.getComments(), new char[] { '\\', ':'}, new String[] { "\\\\", "\\:"}) + ":";\r
+\r
+ if (filter.getLastHit()!=null)\r
+ filterconfig = filterconfig + filter.getLastHit().getTime();\r
\r
- aConfiguration.addProperty(aConfigKey, filter.getType()+":"+filter.getExpression());\r
+ aConfiguration.addProperty(aConfigKey, filterconfig);\r
}\r
}\r
}\r
synchronized(aFilters) {\r
aFilters.clear();\r
\r
- Iterator i = Arrays.asList(aConfiguration.getStringArray(aConfigKey)).iterator();\r
+ if (aConfiguration.getStringArray(aConfigKey)!=null) {\r
\r
- while (i.hasNext()) {\r
- String filter = (String) i.next();\r
- List parts = StringRoutines.separateString(filter, ":");\r
+ Iterator i = Arrays.asList(aConfiguration.getStringArray(aConfigKey)).\r
+ iterator();\r
+\r
+ while (i.hasNext()) {\r
+ String filter = (String) i.next();\r
+ List parts = StringRoutines.splitStringWithEscape(filter, ':', '\\');\r
+ if (parts.size() == 2) {\r
+ parts.add(articleBlockAction);\r
+ parts.add(commentBlockAction);\r
+ parts.add("");\r
+ parts.add("");\r
+ }\r
+\r
+ if (parts.size() >= 5) {\r
+ Date lastHit = null;\r
+\r
+ if (parts.size()>=6) {\r
+ String lastHitString = (String) parts.get(5);\r
\r
- if (parts.size()==2) {\r
- addFilter( (String) parts.get(0), (String) parts.get(1));\r
+ try {\r
+ lastHit = new Date(Long.parseLong(lastHitString));\r
+ }\r
+ catch (Throwable t) {\r
+ }\r
+ }\r
+\r
+ addFilter( (String) parts.get(0), (String) parts.get(1), (String) parts.get(4), (String) parts.get(3), (String) parts.get(2), lastHit);\r
+ }\r
}\r
}\r
}\r
}\r
}\r
\r
+ public void logAdminUsage(EntityUsers aUser, String aDescription) {\r
+ try {\r
+ String user = "unknown (" + aUser.toString() +")";\r
+ if (user!=null)\r
+ user = aUser.getValue("login");\r
+ adminUsageLogger.info(user + ": " + aDescription);\r
+ }\r
+ catch (Throwable t) {\r
+ logger.error("Error while logging admin usage ("+aUser.toString()+", "+aDescription+"): " +t.toString());\r
+ }\r
+ }\r
}
\ No newline at end of file