001: /**
002: * Copyright (c) 2003-2007, David A. Czarnecki
003: * All rights reserved.
004: *
005: * Redistribution and use in source and binary forms, with or without
006: * modification, are permitted provided that the following conditions are met:
007: *
008: * Redistributions of source code must retain the above copyright notice, this list of conditions and the
009: * following disclaimer.
010: * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the
011: * following disclaimer in the documentation and/or other materials provided with the distribution.
012: * Neither the name of "David A. Czarnecki" and "blojsom" nor the names of its contributors may be used to
013: * endorse or promote products derived from this software without specific prior written permission.
014: * Products derived from this software may not be called "blojsom", nor may "blojsom" appear in their name,
015: * without prior written permission of David A. Czarnecki.
016: *
017: * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
018: * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
019: * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
020: * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
021: * EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
022: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
023: * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
024: * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
025: * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
026: * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
027: * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
028: * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
029: * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
030: */package org.blojsom.plugin.comment;
031:
032: import org.blojsom.blog.Blog;
033: import org.blojsom.blog.Entry;
034: import org.blojsom.plugin.PluginException;
035: import org.blojsom.plugin.comment.event.CommentResponseSubmissionEvent;
036: import org.blojsom.util.BlojsomUtils;
037: import org.blojsom.event.Listener;
038: import org.blojsom.event.Event;
039: import org.blojsom.event.EventBroadcaster;
040: import org.apache.commons.logging.Log;
041: import org.apache.commons.logging.LogFactory;
042:
043: import javax.servlet.http.HttpServletRequest;
044: import javax.servlet.http.HttpServletResponse;
045: import javax.servlet.http.HttpSession;
046: import java.util.HashMap;
047: import java.util.Map;
048: import java.util.Iterator;
049:
050: /**
051: * Math comment authenticator plugin
052: *
053: * @author David Czarnecki
054: * @version $Id: MathCommentAuthenticationPlugin.java,v 1.5 2007/01/17 02:35:08 czarneckid Exp $
055: * @since blojsom 3.0
056: */
057: public class MathCommentAuthenticationPlugin extends
058: CommentModerationPlugin implements Listener {
059:
060: private Log _logger = LogFactory
061: .getLog(MathCommentAuthenticationPlugin.class);
062:
063: private static final String MATH_COMMENT_MODERATION_ENABLED = "math-comment-moderation-enabled";
064: private static final String MATH_COMMENT_AUTHENTICATION_OPERATIONS_IP = "math-comment-authentication-operations";
065: private static final String MATH_COMMENT_AUTHENTICATION_BOUND_IP = "math-comment-authentication-bound";
066:
067: private static final int AVAILABLE_OPERATIONS = 3;
068: private static final int BOUND_DEFAULT = 10;
069:
070: public static final String BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_ANSWER = "BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_ANSWER";
071: public static final String BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_VALUE1 = "BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_VALUE1";
072: public static final String BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_VALUE2 = "BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_VALUE2";
073: public static final String BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_OPERATION = "BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_OPERATION";
074: public static final String BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_ANSWER_CHECK_PARAM = "mathAnswerCheck";
075: public static final String BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_STATUS_MESSAGE = "BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_STATUS_MESSAGE";
076:
077: private EventBroadcaster _eventBroadcaster;
078:
079: /**
080: * Math comment authenticator plugin
081: */
082: public MathCommentAuthenticationPlugin() {
083: }
084:
085: /**
086: * Set the {@link EventBroadcaster} to use
087: *
088: * @param eventBroadcaster {@link EventBroadcaster}
089: */
090: public void setEventBroadcaster(EventBroadcaster eventBroadcaster) {
091: _eventBroadcaster = eventBroadcaster;
092: }
093:
094: /**
095: * Initialize this plugin. This method only called when the plugin is instantiated.
096: *
097: * @throws PluginException If there is an error initializing the plugin
098: */
099: public void init() throws PluginException {
100: super .init();
101:
102: _eventBroadcaster.addListener(this );
103: }
104:
105: /**
106: * Process the blog entries
107: *
108: * @param httpServletRequest Request
109: * @param httpServletResponse Response
110: * @param blog {@link Blog} instance
111: * @param context Context
112: * @param entries Blog entries retrieved for the particular request
113: * @return Modified set of blog entries
114: * @throws PluginException If there is an error processing the blog entries
115: */
116: public Entry[] process(HttpServletRequest httpServletRequest,
117: HttpServletResponse httpServletResponse, Blog blog,
118: Map context, Entry[] entries) throws PluginException {
119: HttpSession httpSession = httpServletRequest.getSession();
120:
121: int bound = BOUND_DEFAULT;
122: int availableOperations = AVAILABLE_OPERATIONS;
123: String boundProperty = blog
124: .getProperty(MATH_COMMENT_AUTHENTICATION_BOUND_IP);
125: String availableOperationsProperty = blog
126: .getProperty(MATH_COMMENT_AUTHENTICATION_OPERATIONS_IP);
127:
128: if (!BlojsomUtils.checkNullOrBlank(boundProperty)) {
129: try {
130: bound = Integer.parseInt(boundProperty);
131: } catch (NumberFormatException e) {
132: }
133: }
134:
135: if (!BlojsomUtils.checkNullOrBlank(availableOperationsProperty)) {
136: try {
137: availableOperations = Integer
138: .parseInt(availableOperationsProperty);
139: if (availableOperations < 1
140: || availableOperations > AVAILABLE_OPERATIONS) {
141: availableOperations = AVAILABLE_OPERATIONS;
142: } else {
143: availableOperations -= 1;
144: }
145: } catch (NumberFormatException e) {
146: }
147: }
148:
149: int operation = (int) (Math.random() * (availableOperations + 1));
150: int value1 = (int) (Math.random() * bound);
151: int value2 = (int) (Math.random() * bound);
152: int answer;
153:
154: answer = getAnswerForOperation(value1, value2, operation);
155:
156: httpSession.setAttribute(
157: BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_VALUE1, new Integer(
158: value1));
159: httpSession.setAttribute(
160: BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_VALUE2, new Integer(
161: value2));
162: httpSession.setAttribute(
163: BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_ANSWER, new Integer(
164: answer));
165: httpSession.setAttribute(
166: BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_OPERATION,
167: getOperatorForOperation(operation));
168:
169: return entries;
170: }
171:
172: /**
173: * Simple check to see if comment moderation is enabled
174: * <p/>
175: * @param httpServletRequest Request
176: * @param httpServletResponse Response
177: * @param blog {@link Blog} instance
178: * @param context Context
179: * @param entries Blog entries retrieved for the particular request
180: * @throws org.blojsom.plugin.PluginException
181: * If there is an error in moderating a comment
182: */
183: protected void moderateComment(
184: HttpServletRequest httpServletRequest,
185: HttpServletResponse httpServletResponse, Blog blog,
186: Map context, Entry[] entries) throws PluginException {
187: if ("true".equalsIgnoreCase(blog
188: .getProperty(COMMENT_MODERATION_ENABLED))
189: && "true".equalsIgnoreCase(blog
190: .getProperty(MATH_COMMENT_MODERATION_ENABLED))) {
191: HttpSession httpSession = httpServletRequest.getSession();
192:
193: if ("y".equalsIgnoreCase(httpServletRequest
194: .getParameter(CommentPlugin.COMMENT_PARAM))
195: && blog.getBlogCommentsEnabled().booleanValue()) {
196: String mathAnswerCheck = BlojsomUtils
197: .getRequestValue(
198: BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_ANSWER_CHECK_PARAM,
199: httpServletRequest);
200:
201: boolean passedCheck = false;
202: if (httpSession
203: .getAttribute(BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_ANSWER) != null) {
204: Integer mathAnswer = (Integer) httpSession
205: .getAttribute(BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_ANSWER);
206:
207: try {
208: int mathAnswerCheckValue = Integer
209: .parseInt(mathAnswerCheck);
210: int originalMathAnswerValue = mathAnswer
211: .intValue();
212:
213: if (mathAnswerCheckValue == originalMathAnswerValue) {
214: passedCheck = true;
215: }
216: } catch (NumberFormatException e) {
217: }
218: }
219:
220: Map commentMetaData;
221: if (context
222: .containsKey(CommentPlugin.BLOJSOM_PLUGIN_COMMENT_METADATA)) {
223: commentMetaData = (Map) context
224: .get(CommentPlugin.BLOJSOM_PLUGIN_COMMENT_METADATA);
225: } else {
226: commentMetaData = new HashMap();
227: }
228:
229: if (!passedCheck) {
230: commentMetaData
231: .put(
232: CommentPlugin.BLOJSOM_PLUGIN_COMMENT_METADATA_DESTROY,
233: Boolean.TRUE);
234: httpServletRequest
235: .setAttribute(
236: BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_STATUS_MESSAGE,
237: "Failed math comment authentication check.");
238: } else {
239: commentMetaData
240: .put(
241: CommentModerationPlugin.BLOJSOM_COMMENT_MODERATION_PLUGIN_APPROVED,
242: Boolean.TRUE.toString());
243: httpServletRequest
244: .setAttribute(
245: BLOJSOM_MATH_AUTHENTICATOR_PLUGIN_STATUS_MESSAGE,
246: "Passed math comment authentication check.");
247: }
248:
249: context.put(
250: CommentPlugin.BLOJSOM_PLUGIN_COMMENT_METADATA,
251: commentMetaData);
252: }
253: }
254: }
255:
256: /**
257: * Return the result from the specified operation where 0 = addition, 1 = subtraction, 2 = multiplication
258: *
259: * @param value1 Value 1
260: * @param value2 Value 2
261: * @param operation Operation where 0 = addition, 1 = subtraction, 2 = multiplication
262: * @return Value of operation
263: */
264: protected int getAnswerForOperation(int value1, int value2,
265: int operation) {
266: int answer;
267:
268: switch (operation) {
269: case 0: {
270: answer = value1 + value2;
271: break;
272: }
273: case 1: {
274: answer = value1 - value2;
275: break;
276: }
277: case 2: {
278: answer = value1 * value2;
279: break;
280: }
281: default: {
282: answer = value1 + value2;
283: }
284: }
285:
286: return answer;
287: }
288:
289: /**
290: * Return the appropriate operator for the operation
291: *
292: * @param operation Operation where 0 = addition, 1 = subtraction, 2 = multiplication
293: * @return + for addition, - for subtraction, and * for multiplication
294: */
295: protected String getOperatorForOperation(int operation) {
296: switch (operation) {
297: case 0: {
298: return "+";
299: }
300: case 1: {
301: return "-";
302: }
303: case 2: {
304: return "*";
305: }
306: default: {
307: return "+";
308: }
309: }
310: }
311:
312: /**
313: * Handle an event broadcast from another component
314: *
315: * @param event {@link Event} to be handled
316: */
317: public void handleEvent(Event event) {
318: }
319:
320: /**
321: * Process an event from another component
322: *
323: * @param event {@link Event} to be handled
324: */
325: public void processEvent(Event event) {
326: if (event instanceof CommentResponseSubmissionEvent) {
327: CommentResponseSubmissionEvent commentResponseSubmissionEvent = (CommentResponseSubmissionEvent) event;
328:
329: try {
330: HashMap context = new HashMap();
331: moderateComment(commentResponseSubmissionEvent
332: .getHttpServletRequest(),
333: commentResponseSubmissionEvent
334: .getHttpServletResponse(),
335: commentResponseSubmissionEvent.getBlog(),
336: context,
337: new Entry[] { commentResponseSubmissionEvent
338: .getEntry() });
339:
340: if (context
341: .containsKey(CommentPlugin.BLOJSOM_PLUGIN_COMMENT_METADATA)) {
342: // Grab the comment metadata and populate the metadata for the current submission
343: Map operationMetadata = (Map) context
344: .get(CommentPlugin.BLOJSOM_PLUGIN_COMMENT_METADATA);
345: Map commentMetadata = commentResponseSubmissionEvent
346: .getMetaData();
347:
348: Iterator keys = operationMetadata.keySet()
349: .iterator();
350: while (keys.hasNext()) {
351: Object key = keys.next();
352: commentMetadata.put(key.toString(),
353: operationMetadata.get(key).toString());
354: }
355: }
356: } catch (PluginException e) {
357: if (_logger.isErrorEnabled()) {
358: _logger.error(e);
359: }
360: }
361: }
362: }
363: }
|