KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > blojsom > plugin > nofollow > NoFollowPlugin


1 /**
2  * Copyright (c) 2003-2006, David A. Czarnecki
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  * Redistributions of source code must retain the above copyright notice, this list of conditions and the
9  * following disclaimer.
10  * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the
11  * following disclaimer in the documentation and/or other materials provided with the distribution.
12  * Neither the name of "David A. Czarnecki" and "blojsom" nor the names of its contributors may be used to
13  * endorse or promote products derived from this software without specific prior written permission.
14  * Products derived from this software may not be called "blojsom", nor may "blojsom" appear in their name,
15  * without prior written permission of David A. Czarnecki.
16  *
17  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
18  * CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
19  * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
20  * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
21  * EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
22  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
23  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
24  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
26  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
27  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
29  * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30  */

31 package org.blojsom.plugin.nofollow;
32
33 import org.apache.commons.logging.Log;
34 import org.apache.commons.logging.LogFactory;
35 import org.blojsom.blog.Blog;
36 import org.blojsom.blog.Comment;
37 import org.blojsom.blog.Entry;
38 import org.blojsom.blog.Trackback;
39 import org.blojsom.plugin.Plugin;
40 import org.blojsom.plugin.PluginException;
41 import org.blojsom.util.BlojsomUtils;
42
43 import javax.servlet.http.HttpServletRequest JavaDoc;
44 import javax.servlet.http.HttpServletResponse JavaDoc;
45 import java.util.Iterator JavaDoc;
46 import java.util.Map JavaDoc;
47 import java.util.regex.Matcher JavaDoc;
48 import java.util.regex.Pattern JavaDoc;
49
50 /**
51  * NoFollow plugin adds support for the rel="nofollow" attribute on links added
52  * to comments and trackbacks.
53  *
54  * @author David Czarnecki
55  * @version $Id: NoFollowPlugin.java,v 1.2 2006/03/20 22:50:50 czarneckid Exp $
56  * @since blojsom 3.0
57  */

58 public class NoFollowPlugin implements Plugin {
59
60     private Log _logger = LogFactory.getLog(NoFollowPlugin.class);
61
62     private static final String JavaDoc HYPERLINK_REGEX = "<a\\s([^>]*\\s*href\\s*=[^>]*)>";
63     private static final String JavaDoc ATTRIBUTE_REGEX = "[^=[\\p{Space}]]*\\s*=\\s*\"[^\"]*\"|[^=[\\p{Space}]]*\\s*=\\s*'[^']*'|[^=[\\p{Space}]]*\\s*=[^[\\p{Space}]]*";
64     private static final String JavaDoc NOFOLLOW_REGEX = "\\s*nofollow\\s*";
65     private static final String JavaDoc REL_ATTR_REGEX = "rel\\s*=";
66     private static final String JavaDoc REL_NOFOLLOW = " rel=\"nofollow\"";
67
68     /**
69      * Construct a new instance of the NoFollow plugin
70      */

71     public NoFollowPlugin() {
72     }
73
74     /**
75      * Initialize this plugin. This method only called when the plugin is instantiated.
76      *
77      * @throws org.blojsom.plugin.PluginException
78      * If there is an error initializing the plugin
79      */

80     public void init() throws PluginException {
81     }
82
83     /**
84      * Take a string and add rel="nofollow" attributes to the &lt;a href/&gt; links
85      * if they are not already on the links.
86      *
87      * @param text Text to look for hyperlinks
88      * @return Text with rel="nofollow" attributes added to the hyperlinks
89      */

90     protected String JavaDoc noFollowFy(String JavaDoc text) {
91         if (BlojsomUtils.checkNullOrBlank(text)) {
92             return text;
93         }
94         
95         StringBuffer JavaDoc updatedText = new StringBuffer JavaDoc();
96
97         Pattern JavaDoc hyperlinkPattern = Pattern.compile(HYPERLINK_REGEX, Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.UNICODE_CASE | Pattern.DOTALL);
98         Matcher JavaDoc hyperlinkMatcher = hyperlinkPattern.matcher(text);
99
100         Pattern JavaDoc attributePattern = Pattern.compile(ATTRIBUTE_REGEX, Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.UNICODE_CASE | Pattern.DOTALL);
101         Pattern JavaDoc relAttrPattern = Pattern.compile(REL_ATTR_REGEX, Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.UNICODE_CASE | Pattern.DOTALL);
102         Pattern JavaDoc noFollow = Pattern.compile(NOFOLLOW_REGEX, Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.UNICODE_CASE | Pattern.DOTALL);
103
104         Matcher JavaDoc noFollowMatcher;
105         Matcher JavaDoc attributeMatcher;
106
107         int lastIndex = 0;
108         while (hyperlinkMatcher.find()) {
109             updatedText.append(text.substring(lastIndex, hyperlinkMatcher.start()));
110             String JavaDoc link = hyperlinkMatcher.group();
111             attributeMatcher = attributePattern.matcher(link);
112
113             StringBuffer JavaDoc updatedLink = new StringBuffer JavaDoc();
114             boolean shouldAddAttr = true;
115
116             while (attributeMatcher.find()) {
117                 String JavaDoc attr = attributeMatcher.group();
118
119                 Matcher JavaDoc relAttrMatcher = relAttrPattern.matcher(attr);
120                 while (relAttrMatcher.find()) {
121                     noFollowMatcher = noFollow.matcher(attr);
122                     if (!noFollowMatcher.matches()) {
123                         int indexOfQuote = attr.lastIndexOf("\"");
124                         if (indexOfQuote != -1) {
125                             attr = attr.substring(0, indexOfQuote) + " nofollow\"";
126                             shouldAddAttr = false;
127                         }
128                     }
129                 }
130
131                 updatedLink.append(attr);
132             }
133
134             if (shouldAddAttr) {
135                 updatedLink.append(REL_NOFOLLOW);
136             }
137
138             updatedLink.append((">"));
139             updatedText.append(updatedLink);
140             lastIndex = hyperlinkMatcher.end();
141         }
142
143         updatedText.append(text.substring(lastIndex));
144
145         return updatedText.toString();
146     }
147
148     /**
149      * Process the blog entries
150      *
151      * @param httpServletRequest Request
152      * @param httpServletResponse Response
153      * @param blog {@link Blog} instance
154      * @param context Context
155      * @param entries Blog entries retrieved for the particular request
156      * @return Modified set of blog entries
157      * @throws PluginException If there is an error processing the blog entries
158      */

159     public Entry[] process(HttpServletRequest JavaDoc httpServletRequest, HttpServletResponse JavaDoc httpServletResponse, Blog blog, Map JavaDoc context, Entry[] entries) throws PluginException {
160         for (int i = 0; i < entries.length; i++) {
161             Entry entry = entries[i];
162
163             Iterator JavaDoc commentsIterator = entry.getComments().iterator();
164             String JavaDoc commentText;
165             while (commentsIterator.hasNext()) {
166                 Comment blogComment = (Comment) commentsIterator.next();
167
168                 commentText = blogComment.getComment();
169                 commentText = noFollowFy(commentText);
170                 blogComment.setComment(commentText);
171             }
172
173             Iterator JavaDoc trackbacksIterator = entry.getTrackbacks().iterator();
174             String JavaDoc trackbackText;
175             while (trackbacksIterator.hasNext()) {
176                 Trackback trackback = (Trackback) trackbacksIterator.next();
177
178                 trackbackText = trackback.getExcerpt();
179                 trackbackText = noFollowFy(trackbackText);
180                 trackback.setExcerpt(trackbackText);
181             }
182         }
183
184         return entries;
185     }
186
187     /**
188      * Perform any cleanup for the plugin. Called after {@link #process}.
189      *
190      * @throws PluginException If there is an error performing cleanup for this plugin
191      */

192     public void cleanup() throws PluginException {
193     }
194
195     /**
196      * Called when BlojsomServlet is taken out of service
197      *
198      * @throws PluginException If there is an error in finalizing this plugin
199      */

200     public void destroy() throws PluginException {
201     }
202 }
Popular Tags