Return-Path: Delivered-To: apmail-incubator-jspwiki-commits-archive@minotaur.apache.org Received: (qmail 92870 invoked from network); 6 Mar 2009 23:31:37 -0000 Received: from hermes.apache.org (HELO mail.apache.org) (140.211.11.2) by minotaur.apache.org with SMTP; 6 Mar 2009 23:31:37 -0000 Received: (qmail 34338 invoked by uid 500); 6 Mar 2009 23:31:37 -0000 Delivered-To: apmail-incubator-jspwiki-commits-archive@incubator.apache.org Received: (qmail 34319 invoked by uid 500); 6 Mar 2009 23:31:37 -0000 Mailing-List: contact jspwiki-commits-help@incubator.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: jspwiki-dev@incubator.apache.org Delivered-To: mailing list jspwiki-commits@incubator.apache.org Received: (qmail 34302 invoked by uid 99); 6 Mar 2009 23:31:37 -0000 Received: from athena.apache.org (HELO athena.apache.org) (140.211.11.136) by apache.org (qpsmtpd/0.29) with ESMTP; Fri, 06 Mar 2009 15:31:37 -0800 X-ASF-Spam-Status: No, hits=-2000.0 required=10.0 tests=ALL_TRUSTED X-Spam-Check-By: apache.org Received: from [140.211.11.4] (HELO eris.apache.org) (140.211.11.4) by apache.org (qpsmtpd/0.29) with ESMTP; Fri, 06 Mar 2009 23:31:28 +0000 Received: by eris.apache.org (Postfix, from userid 65534) id C4B2A2388999; Fri, 6 Mar 2009 23:31:07 +0000 (UTC) Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Subject: svn commit: r751135 [2/3] - in /incubator/jspwiki/trunk: ./ src/WebContent/ src/WebContent/WEB-INF/ src/WebContent/WEB-INF/classes/ src/WebContent/WEB-INF/classes/templates/ src/WebContent/scripts/ src/WebContent/templates/default/ src/WebContent/templ... Date: Fri, 06 Mar 2009 23:31:05 -0000 To: jspwiki-commits@incubator.apache.org From: ajaquith@apache.org X-Mailer: svnmailer-1.0.8 Message-Id: <20090306233107.C4B2A2388999@eris.apache.org> X-Virus-Checked: Checked by ClamAV on apache.org Modified: incubator/jspwiki/trunk/src/WebContent/WEB-INF/classes/templates/default_zh_CN.properties URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/WEB-INF/classes/templates/default_zh_CN.properties?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/WEB-INF/classes/templates/default_zh_CN.properties (original) +++ incubator/jspwiki/trunk/src/WebContent/WEB-INF/classes/templates/default_zh_CN.properties Fri Mar 6 23:31:03 2009 @@ -43,10 +43,6 @@ diff.goback=\u8fd4\u56de {0} \u6216 {1} diff.versionhistory={0} \u9875\u9762\u4fe1\u606f diff.nodiff=\u6ca1\u6709\u5dee\u5f02\u3002 -# EditContent.jsp - -edit.locked=\u7528\u6237 {0} \u5df2\u5f00\u59cb\u7f16\u8f91\u8be5\u9875\u9762\uff0c\u4f46\u8fd8\u672a\u4fdd\u5b58\u3002\u6211\u4e0d\u4f1a\u963b\u6b62\u60a8\u7f16\u8f91\u8be5\u9875\u9762\uff0c\u4f46\u662f\u8981\u77e5\u9053\u5176\u4ed6\u4eba\u53ef\u80fd\u4f1a\u5f88\u70e6\u3002\u7b49\u5f85\u9501\u5b9a\u8fc7\u671f\u6216\u522b\u4eba\u505c\u6b62\u7f16\u8f91\uff0c\u8fd9\u6837\u4f1a\u6bd4\u8f83\u793c\u8c8c\u3002\u9501\u5b9a\u4f1a\u5728 {1} \u5206\u949f\u540e\u8fc7\u671f\u3002 -edit.restoring=\u5c06\u6062\u590d\u7248\u672c {0}\u3002\u5355\u51fb\u201c\u4fdd\u5b58\u201d\u6765\u8fdb\u884c\u6062\u590d\u3002\u4e5f\u53ef\u4ee5\u5728\u6062\u590d\u9875\u9762\u524d\u8fdb\u884c\u7f16\u8f91\u3002 edit.tab.attachments=\u9644\u4ef6 edit.tab.help=\u5e2e\u52a9 edit.tab.edit=\u7f16\u8f91 @@ -98,8 +94,8 @@ group.tab=\u67e5\u770b\u7ec4 #replaced by grp.deletegroup.confirm -#group.areyousure=Are you sure you want to permanently delete group "{0}"? \ -# Users might not be able to access pages whose ACLS contain this group. \\n\\n \ +#group.areyousure=Are you sure you want to permanently delete group "{0}"? \ +# Users might not be able to access pages whose ACLS contain this group. \\n\\n \ # If you click OK, the group will be removed immediately. group.doesnotexist=\u8be5\u7ec4\u4e0d\u5b58\u5728\u3002 group.createsuggestion=\u4e3a\u4ec0\u4e48\u4e0d {0} @@ -376,18 +372,10 @@ # 0 : Application Name # 1 : Page name view.title.view={0}\uff1a{1} -# The built-in editors also have their localized strings in this file. - -editor.plain.name=\u60a8\u7684\u540d\u79f0(N) -editor.plain.remember=\u662f\u5426\u8bb0\u4f4f\u6211\u7684\u4fe1\u606f\uff1f editor.plain.email=\u4e3b\u9875\u6216\u7535\u5b50\u90ae\u4ef6(M) -editor.plain.save.submit=\u4fdd\u5b58 editor.plain.save.title=\u4fdd\u5b58 [ s ] -editor.plain.preview.submit=\u9884\u89c8 editor.plain.preview.title=\u9884\u89c8 [ v ] -editor.plain.cancel.submit=\u53d6\u6d88 editor.plain.cancel.title=\u53d6\u6d88\u7f16\u8f91\u3002\u60a8\u6240\u505a\u7684\u66f4\u6539\u5c06\u4e22\u5931\u3002[ q ] -editor.plain.changenote=\u66f4\u6539\u6ce8\u91ca editor.commentsignature=\u6ce8\u91ca\u7b7e\u540d editor.plain.toolbar=\u5de5\u5177\u680f editor.plain.find=\u67e5\u627e @@ -407,9 +395,6 @@ editor.plain.smartpairs.title=\u81ea\u52a8\u8f93\u5165\u6210\u5bf9\u7684\u7b26\u53f7 () [] {} <> "" '' editor.plain.tabcompletion=Tab \u5b8c\u6210\uff08\u5173\u952e\u5b57 + Tab\uff09 editor.plain.tabcompletion.title=\u5c06\u5173\u952e\u5b57\u81ea\u52a8\u6269\u5c55\u4e3a Wiki \u6807\u8bb0 -#editor.plain.editassist=Edit Assist -#editor.plain.editassist.title=Toggle Edit Assist buttons -editor.plain.sneakpreview=\u62a2\u5148\u9884\u89c8 editor.plain.sneakpreview.title=\u62a2\u5148\u9884\u89c8\u3002\u5728\u6587\u672c\u6846\u5916\u9762\u70b9\u51fb\u53ef\u4ee5\u5237\u65b0\u62a2\u5148\u9884\u89c8\u533a\u57df\u3002 editor.plain.tbLink.title=\u94fe\u63a5 - \u63d2\u5165 Wiki \u94fe\u63a5 editor.plain.tbH1.title=h1 - \u63d2\u5165\u6807\u9898\u6837\u5f0f1 Modified: incubator/jspwiki/trunk/src/WebContent/WEB-INF/web.xml URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/WEB-INF/web.xml?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/WEB-INF/web.xml (original) +++ incubator/jspwiki/trunk/src/WebContent/WEB-INF/web.xml Fri Mar 6 23:31:03 2009 @@ -96,13 +96,6 @@ This is new in 2.4. This defines a servlet filter which filters all requests. --> - - WikiServletFilter /attach/* @@ -147,17 +140,6 @@ - - Modified: incubator/jspwiki/trunk/src/WebContent/Wiki.jsp URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/Wiki.jsp?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/Wiki.jsp (original) +++ incubator/jspwiki/trunk/src/WebContent/Wiki.jsp Fri Mar 6 23:31:03 2009 @@ -1,8 +1,15 @@ <%@ taglib uri="http://jakarta.apache.org/jspwiki.tld" prefix="wiki" %> <%@ taglib uri="http://stripes.sourceforge.net/stripes.tld" prefix="s" %> - + + <%-- If wiki page is current, allow search engines to spider it --%> + + + + + + Modified: incubator/jspwiki/trunk/src/WebContent/scripts/jspwiki-edit.js URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/scripts/jspwiki-edit.js?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/scripts/jspwiki-edit.js (original) +++ incubator/jspwiki/trunk/src/WebContent/scripts/jspwiki-edit.js Fri Mar 6 23:31:03 2009 @@ -496,7 +496,7 @@ var ta = this.textarea, isOn = checkbox.checked; - $('sneakpreview').empty(); + $('livepreview').empty(); ta.removeEvents('preview'); Wiki.prefs.set('autopreview',isOn); @@ -506,7 +506,7 @@ }, refreshPreview: function(){ - var preview = $('sneakpreview'); + var preview = $('livepreview'); $('previewSpin').show(); new Ajax( Wiki.TemplateUrl + "/AJAXPreview.jsp?page="+Wiki.PageName, { Modified: incubator/jspwiki/trunk/src/WebContent/templates/default/AttachmentTab.jsp URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/templates/default/AttachmentTab.jsp?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/templates/default/AttachmentTab.jsp (original) +++ incubator/jspwiki/trunk/src/WebContent/templates/default/AttachmentTab.jsp Fri Mar 6 23:31:03 2009 @@ -27,7 +27,7 @@

- + @@ -35,8 +35,13 @@ + + + - + @@ -53,7 +58,6 @@

+
+
-
Copied: incubator/jspwiki/trunk/src/WebContent/templates/default/DefaultLayout.jsp (from r746887, incubator/jspwiki/trunk/src/WebContent/templates/default/ViewLayout.jsp) URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/templates/default/DefaultLayout.jsp?p2=incubator/jspwiki/trunk/src/WebContent/templates/default/DefaultLayout.jsp&p1=incubator/jspwiki/trunk/src/WebContent/templates/default/ViewLayout.jsp&r1=746887&r2=751135&rev=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/templates/default/ViewLayout.jsp (original) +++ incubator/jspwiki/trunk/src/WebContent/templates/default/DefaultLayout.jsp Fri Mar 6 23:31:03 2009 @@ -1,29 +1,144 @@ <%@ taglib uri="http://jakarta.apache.org/jspwiki.tld" prefix="wiki" %> +<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> <%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %> <%@ taglib uri="http://stripes.sourceforge.net/stripes.tld" prefix="s" %> +<%@ page import="org.apache.wiki.WikiContext" %> +<%@ page import="org.apache.wiki.action.WikiContextFactory" %> +<%-- + This file contains the default layout used by all JSPWiki 3 pages. + The default layout contains the HTML doctype declaration, header, + and page layout. It can be customized in the following ways: + + 1) Top-level JSPs can define default components, as defined by + Stripes elements. Named components + that can be overridden include: + + head.title : The HTML page title, which will be rendered + in the element. Default=wiki: pagename + stylesheet : Link tags to external stylesheets. Default=blank + inlinecss : Inline stylesheets. Default=blank + script : JavaScript <script> elements. Default=blank + jslocalizedstrings : Localized scripts for JavaScript + functions. Default=blank + jsfunction : JavaScript functions. Default=blank + head.meta.robots : Search engine options. Default=noindex,nofollow + content : The page contents. Default=blank + + 2) DefaultLayout injects additional JSPs that are meant to be + customized. These include: + + commonheader.jsp : A "local header" that can contain company logos + or other markup. Default=blank + +--%> <s:layout-definition> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <title> + <%-- + + Title: by default, use the "view page" title + --%> + <s:layout-component name="head.title"> <fmt:message key="view.title.view"> <fmt:param><wiki:Variable var="ApplicationName" /></fmt:param> <fmt:param><wiki:PageName/></fmt:param> </fmt:message> + </s:layout-component> - - - - - - - - - + <%-- + + CSS stylesheets + --%> + + <%-- put this at the top, to avoid double load when not yet cached --%> + + + + + + <%-- + + Links to favicon and common pages + --%> + + + + + <%-- ie6 needs next line --%> + + <%-- + + Support for the universal edit button + (www.universaleditbutton.org) + --%> + + + + + + + <%-- + + Skins: extra stylesheets, extra javascript + --%> + + + + + <%-- + + JavaScript + --%> + + + + + + <%-- + + JavaScript: localized strings and functions + --%> + + <%-- + + Meta tags + --%> + + + + + + <%--unusual pagename--%> + <%--pagename without blanks--%> + + + + <%-- + + Search engines: by default, page is not indexed or followed + --%> + + + + <%-- + + RSS Feed discovery + --%> + + + + + - +
Modified: incubator/jspwiki/trunk/src/WebContent/templates/default/EditContent.jsp URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/templates/default/EditContent.jsp?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/templates/default/EditContent.jsp (original) +++ incubator/jspwiki/trunk/src/WebContent/templates/default/EditContent.jsp Fri Mar 6 23:31:03 2009 @@ -1,7 +1,8 @@ +<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> +<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %> <%@ taglib uri="http://jakarta.apache.org/jspwiki.tld" prefix="wiki" %> +<%@ taglib uri="http://stripes.sourceforge.net/stripes.tld" prefix="s" %> <%@ page import="org.apache.wiki.*" %> -<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %> -<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> <%@ page import="javax.servlet.jsp.jstl.fmt.*" %> <%@ page import="org.apache.wiki.action.WikiContextFactory" %> <% @@ -11,51 +12,28 @@ if( attCount != 0 ) attTitle += " (" + attCount + ")"; %> - + + - -
- - - - -
-
- - -
- - - -
-
- - - -
+ + + + - - - - - - - - + + - + - - -
- - EditPageHelp - -
-
+ + +
+ + EditPageHelp + +
+
\ No newline at end of file Modified: incubator/jspwiki/trunk/src/WebContent/templates/default/PreviewContent.jsp URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/templates/default/PreviewContent.jsp?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/templates/default/PreviewContent.jsp (original) +++ incubator/jspwiki/trunk/src/WebContent/templates/default/PreviewContent.jsp Fri Mar 6 23:31:03 2009 @@ -1,24 +1,51 @@ +<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> +<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %> <%@ taglib uri="http://jakarta.apache.org/jspwiki.tld" prefix="wiki" %> +<%@ taglib uri="http://stripes.sourceforge.net/stripes.tld" prefix="s" %> +<%@ page import="org.apache.wiki.filters.SpamFilter" %> <%@ page import="org.apache.wiki.ui.EditorManager" %> -<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %> <%@ page import="javax.servlet.jsp.jstl.fmt.*" %> -<%-- Inserts page content for preview. --%> - - -
- - -
- -
- <%=EditorManager.getEditedText(pageContext)%> -
- -
- -
+ + +
+ +
+ + -
+ + +

+ <%-- Edit.jsp & Comment.jsp rely on these being found. So be careful, if you make changes. --%> + + + + + + + +

+
+ + + + + + +
+ +
+ +
+ ${wikiActionBean.text} +
+ +
+ +
+ +
\ No newline at end of file Modified: incubator/jspwiki/trunk/src/WebContent/templates/default/editors/plain.jsp URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/templates/default/editors/plain.jsp?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/templates/default/editors/plain.jsp (original) +++ incubator/jspwiki/trunk/src/WebContent/templates/default/editors/plain.jsp Fri Mar 6 23:31:03 2009 @@ -1,220 +1,163 @@ -<%@ page language="java" import="java.util.*" pageEncoding="UTF-8" %> -<%@ taglib uri="http://jakarta.apache.org/jspwiki.tld" prefix="wiki" %> -<%@ page import="org.apache.wiki.*" %> -<%@ page import="org.apache.wiki.auth.*" %> -<%@ page import="org.apache.wiki.auth.permissions.*" %> -<%@ page import="org.apache.wiki.tags.*" %> -<%@ page import="org.apache.wiki.filters.SpamFilter" %> -<%@ page import="org.apache.wiki.ui.*" %> -<%@ page import="org.apache.wiki.rpc.*" %> -<%@ page import="org.apache.wiki.rpc.json.*" %> -<%@ page import="org.apache.wiki.api.WikiPage" %> <%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %> <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> -<%@ taglib uri="http://stripes.sourceforge.net/stripes.tld" prefix="stripes" %> -<%@ page import="org.apache.wiki.action.WikiContextFactory" %> +<%@ taglib uri="http://jakarta.apache.org/jspwiki.tld" prefix="wiki" %> +<%@ taglib uri="http://stripes.sourceforge.net/stripes.tld" prefix="s" %> +<%@ page import="org.apache.wiki.filters.SpamFilter" %> <%@ page import="org.apache.wiki.util.TextUtil" %> <%-- This is a plain editor for JSPWiki. --%> -<% - WikiContext context = WikiContextFactory.findContext( pageContext ); - WikiEngine engine = context.getEngine(); - - String contextPath = request.getContextPath(); - - TemplateManager.addResourceRequest( context, "script", contextPath + "/scripts/jspwiki-edit.js" ); - TemplateManager.addResourceRequest( context, "script", contextPath + "/scripts/posteditor.js" ); - String usertext = EditorManager.getEditedText( pageContext ); -%> - - <%-- this is a new page, check if we're cloning --%> -<% - String clone = request.getParameter( "clone" ); - if( clone != null ) - { - WikiPage p = engine.getPage( clone ); - if( p != null ) - { - AuthorizationManager mgr = engine.getAuthorizationManager(); - PagePermission pp = new PagePermission( p, PagePermission.VIEW_ACTION ); - - try - { - if( mgr.checkPermission( context.getWikiSession(), pp ) ) - { - usertext = engine.getPureText( p ); - } - } - catch( Exception e ) { /*log.error( "Accessing clone page "+clone, e );*/ } - } - } -%> - -<% - if( usertext == null ) - { - usertext = engine.getPureText( context.getPage() ); - } -%> - -<% if( usertext == null ) usertext = ""; %> - -
<%-- Required for IE6 on Windows --%> - -
- - <%-- Edit.jsp relies on these being found. So be careful, if you make changes. --%> -

- - - <%=SpamFilter.insertInputFields( pageContext )%> - - - - -

- <%-- This following field is only for the SpamFilter to catch bots which are just randomly filling all fields and submitting. - Normal user should never see this field, nor type anything in it. --%> -
Authentication code:
- -<%--FIXME - - - - - - ---%> - - - - -
-    - - - FIXME
-
+ + + <%-- Edit.jsp relies on these being found. So be careful, if you make changes. --%> +

+ + + <%=SpamFilter.insertInputFields( pageContext )%> + + + + + + + + + + + + + +

+ + <%-- This following field is only for the SpamFilter to catch bots which are just + randomly filling all fields and submitting. Normal user should never see this field, + nor type anything in it. --%> +
Authentication code:
+ + <%-- Fields for changenote, renaming etc. --%> + + + + + +
+ + + +
+ + <%-- Toolbar --%> +

- - link - h1 - h2 - h3 - - - bold - italic - mono - sup - sub - strike - - - br - hr - pre - code - dl - - - toc - tab - table - img - quote - sign - - - - - - - -
- - - - -
-
- -
- -
-
- - -
- -

- - - /> - -

-

- - -

-
-
- - - -
- /> - - -
-
+ + link + h1 + h2 + h3 + + + bold + italic + mono + sup + sub + strike + + + br + hr + pre + code + dl + + + toc + tab + table + img + quote + sign + + + + + + + +
+ + <%-- Toolbar extras --%> + + + <%-- Search bar --%> + +
+
+ + <%-- You knew this would be here somewhere. Yes, it's the textarea where the user + actually edits stuff. --%> +
+ +
+
+ + +
+ +

+ + + + +

+

+ + +

+
+
+ +
+ + + + +
+
+ +
\ No newline at end of file Modified: incubator/jspwiki/trunk/src/WebContent/templates/default/jspwiki.css URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/templates/default/jspwiki.css?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/templates/default/jspwiki.css (original) +++ incubator/jspwiki/trunk/src/WebContent/templates/default/jspwiki.css Fri Mar 6 23:31:03 2009 @@ -1177,14 +1177,14 @@ /* +++ 475 PreviewContent - "This is a preview" comment +++ */ -#sneakpreviewheader { +#livepreviewheader { clear:both; font-size:110%; background-color:#ddd; padding:0.5em; margin:0.5em 0; } -#sneakpreview { +#livepreview { } #previewcontent { } Modified: incubator/jspwiki/trunk/src/WebContent/templates/default/skins/OrderedList/skin.css URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/templates/default/skins/OrderedList/skin.css?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/templates/default/skins/OrderedList/skin.css (original) +++ incubator/jspwiki/trunk/src/WebContent/templates/default/skins/OrderedList/skin.css Fri Mar 6 23:31:03 2009 @@ -350,10 +350,10 @@ } /* +++ 475 PageContent.jsp +++ */ -#sneakpreviewheader { +#livepreviewheader { background-color:#3f464a; } -#sneakpreview { +#livepreview { background:transparent !important; } /* +++ 475 PreviewContent - "This is a preview" comment +++ */ Modified: incubator/jspwiki/trunk/src/WebContent/templates/default/skins/Smart/skin.css URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/WebContent/templates/default/skins/Smart/skin.css?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/WebContent/templates/default/skins/Smart/skin.css (original) +++ incubator/jspwiki/trunk/src/WebContent/templates/default/skins/Smart/skin.css Fri Mar 6 23:31:03 2009 @@ -275,7 +275,7 @@ color:white; padding:0.5em 0.25em; } -#sneakpreviewheader { +#livepreviewheader { background-color:#fff7c0; } Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/action/AbstractPageActionBean.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/action/AbstractPageActionBean.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/action/AbstractPageActionBean.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/action/AbstractPageActionBean.java Fri Mar 6 23:31:03 2009 @@ -30,10 +30,9 @@ * process {@link org.apache.wiki.api.WikiPage} objects bound to the * page request parameter. In particular, this subclass contains * special processing logic that ensures that, the page - * properties of this object and its related - * {@link org.apache.wiki.WikiContext} are set to the same value. When - * {@link #setPage(WikiPage)} is called by, for example, the Stripes controller, - * the underlying + * properties of this object and its related {@link org.apache.wiki.WikiContext} + * are set to the same value. When {@link #setPage(WikiPage)} is called by, for + * example, the Stripes controller, the underlying * {@link org.apache.wiki.ui.stripes.WikiActionBeanContext#setPage(WikiPage)} * method is called also. */ @@ -55,10 +54,14 @@ * Sets the WikiPage property for this ActionBean, and also sets the * WikiActionBeanContext's page property to the same value by calling * {@link org.apache.wiki.ui.stripes.WikiActionBeanContext#setPage(WikiPage)}. + * Note that because of the {@link Validate} annotation, the + * page field will be required by any executing event handler + * method. To change this property, subclasses should override this method + * and supply a Validate( required = false ) annotation. * * @param page the wiki page. */ - @Validate( required = false ) + @Validate( required = true ) public void setPage( WikiPage page ) { m_page = page; Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/action/DeleteActionBean.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/action/DeleteActionBean.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/action/DeleteActionBean.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/action/DeleteActionBean.java Fri Mar 6 23:31:03 2009 @@ -108,15 +108,6 @@ } /** - * {@inheritDoc} - */ - @Validate( required = true ) - public void setPage( WikiPage page ) - { - super.setPage( page ); - } - - /** * Sets the version to delete. If not set, all versions of the page or * attachment will be deleted. * Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/action/EditActionBean.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/action/EditActionBean.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/action/EditActionBean.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/action/EditActionBean.java Fri Mar 6 23:31:03 2009 @@ -21,26 +21,88 @@ package org.apache.wiki.action; +import java.io.IOException; +import java.security.Principal; +import java.util.List; + import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpSession; -import org.apache.wiki.WikiContext; +import net.sourceforge.stripes.action.*; +import net.sourceforge.stripes.controller.LifecycleStage; +import net.sourceforge.stripes.validation.LocalizableError; +import net.sourceforge.stripes.validation.Validate; +import net.sourceforge.stripes.validation.ValidationErrors; + +import org.apache.wiki.*; +import org.apache.wiki.api.WikiException; +import org.apache.wiki.api.WikiPage; import org.apache.wiki.auth.permissions.PagePermission; +import org.apache.wiki.filters.RedirectException; import org.apache.wiki.filters.SpamFilter; -import org.apache.wiki.ui.EditorManager; +import org.apache.wiki.htmltowiki.HtmlStringToWikiTranslator; +import org.apache.wiki.log.Logger; +import org.apache.wiki.log.LoggerFactory; import org.apache.wiki.ui.stripes.HandlerPermission; +import org.apache.wiki.ui.stripes.WikiActionBeanContext; import org.apache.wiki.ui.stripes.WikiRequestContext; - -import net.sourceforge.stripes.action.*; - +import org.apache.wiki.workflow.DecisionRequiredException; +import org.jdom.JDOMException; @HttpCache( allow = false ) -@UrlBinding( "/Edit.jsp" ) public class EditActionBean extends AbstractPageActionBean { - @HandlesEvent("comment") - @HandlerPermission(permissionClass=PagePermission.class, target="${page.qualifiedName}", actions=PagePermission.COMMENT_ACTION) - @WikiRequestContext("comment") + private static final Logger log = LoggerFactory.getLogger( EditActionBean.class ); + + private String m_author = null; + + private String m_spamhash = null; + + private String m_text = null; + + private String m_changeNote = null; + + private boolean m_append = false; + + private boolean m_captcha = false; + + private boolean m_remember = true; + + private String m_htmlPageText = null; + + private boolean m_livePreview = false; + + private String m_link = null; + + /** + * Event handler method that cancels any locks the user possesses for the current wiki page, + * and redirects the user to the {@link ViewActionBean} "view" handler. + * @return the redirect + */ + @DontValidate + @HandlesEvent( "cancel" ) + @HandlerPermission( permissionClass = PagePermission.class, target = "${page.qualifiedName}", actions = PagePermission.EDIT_ACTION ) + @WikiRequestContext( "cancel" ) + public Resolution cancel() + { + String pagereq = m_page.getName(); + log.debug( "Cancelled editing " + pagereq ); + + // Cancel page lock + HttpSession session = getContext().getRequest().getSession(); + WikiEngine engine = getContext().getEngine(); + PageLock lock = (PageLock) session.getAttribute( "lock-" + pagereq ); + if( lock != null ) + { + engine.getPageManager().unlockPage( lock ); + session.removeAttribute( "lock-" + pagereq ); + } + return new RedirectResolution( ViewActionBean.class ).addParameter( "page", pagereq ); + } + + @HandlesEvent( "comment" ) + @HandlerPermission( permissionClass = PagePermission.class, target = "${page.qualifiedName}", actions = PagePermission.COMMENT_ACTION ) + @WikiRequestContext( "comment" ) public Resolution comment() { return null; @@ -61,17 +123,176 @@ } @DefaultHandler + @DontValidate @HandlesEvent( "edit" ) @HandlerPermission( permissionClass = PagePermission.class, target = "${page.qualifiedName}", actions = PagePermission.EDIT_ACTION ) @WikiRequestContext( "edit" ) public Resolution edit() { - return null; + WikiActionBeanContext wikiContext = getContext(); + HttpServletRequest request = wikiContext.getRequest(); + HttpSession session = request.getSession(); + Principal user = wikiContext.getCurrentUser(); + String pagereq = m_page.getName(); + + log.info( "Editing page " + pagereq + ". User=" + user.getName() + ", host=" + request.getRemoteAddr() ); + + // If page is locked, make sure we tell the user + List messages = wikiContext.getMessages(); + WikiEngine engine = wikiContext.getEngine(); + PageManager mgr = engine.getPageManager(); + PageLock lock = mgr.getCurrentLock( m_page ); + if( lock != null ) + { + messages.add( new LocalizableMessage( "edit.locked", lock.getLocker(), lock.getTimeLeft() ) ); + } + + // If user is not editing the latest one, tell user also + ValidationErrors errors = getContext().getValidationErrors(); + WikiPage latest = engine.getPage( m_page.getName() ); + if( latest.getVersion() != m_page.getVersion() ) + { + errors.addGlobalError( new LocalizableError( "edit.restoring", m_page.getVersion() ) ); + } + + // Attempt to lock the page. + lock = mgr.lockPage( m_page, user.getName() ); + if( lock != null ) + { + session.setAttribute( "lock-" + pagereq, lock ); + } + + // Load the page text + m_text = engine.getPureText( m_page ); + + return new ForwardResolution( "/Edit.jsp" ); + } + + /** + * Returns whether the edited text should be appended to the page. + * + * @return true if text should be appended; + * false otherwise (the default). + */ + public boolean getAppend() + { + return m_append; + } + + /** + * Returns the author. + * + * @return the author + */ + public String getAuthor() + { + return m_author; + } + + /** + * Returns whether a CAPTCHA is being used for editing. + * + * @return true if a CAPTCHA is in use; false + * otherwise. + */ + public boolean getCaptcha() + { + return m_captcha; + } + + /* + * Returns the changenote for this upload. + */ + public String getChangenote() + { + return m_changeNote; + } + + /** + * Returns the HTML page text. + * + * @return the HTML page text + */ + public String getHtmlPageText() + { + return m_htmlPageText; + } + + /** + * Returns the link. + * + * @return the link + */ + public String getLink() + { + return m_link; + } + + /** + * Returns true if the "live preview" feature is turned on; + * false otherwise + * + * @return the "live preview" setting + */ + public boolean getLivePreview() + { + return m_livePreview; + } + + /** + * Returns the flag indicating whether the author name should be remembered. + * + * @return the remember-me flag + */ + public boolean getRemember() + { + return m_remember; } /** - * Event that extracts the current state of the edited page from the HTTP - * session and redirects the user to the previewer JSP. + * Returns the edited text. + * + * @return the text + */ + public String getText() + { + return m_text; + } + + /** + * Initializes default values. Also looks up the correct spam hash field, as determined by + * {@link SpamFilter#getHashFieldName(HttpServletRequest)}. + + */ + @After( stages = LifecycleStage.BindingAndValidation ) + public void initDefaultValues() + { + HttpServletRequest request = getContext().getRequest(); + + // Look up and set spam hash field name for this particular edit + String hashParam = SpamFilter.getHashFieldName( request ); + m_spamhash = request.getParameter( hashParam ); + if( m_spamhash != null ) + { + m_spamhash = m_spamhash.trim(); + } + + // Set author: prefer authenticated/asserted principals first + WikiSession wikiSession = getContext().getWikiSession(); + if( wikiSession.isAsserted() || wikiSession.isAuthenticated() ) + { + m_author = wikiSession.getUserPrincipal().getName(); + } + + // Otherwise, if author not bound, check session + else if( m_author == null ) + { + m_author = wikiSession.getUserPrincipal().getName(); + } + } + + /** + * Event that the user to the preview display JSP. * * @return a forward resolution back to the preview page. */ @@ -80,15 +301,202 @@ @WikiRequestContext( "preview" ) public Resolution preview() { - WikiContext context = getContext(); - HttpServletRequest request = context.getHttpRequest(); + log.debug( "Previewing " + m_page.getName() ); + return new ForwardResolution( "/Preview.jsp" ); + } + + @HandlesEvent( "save" ) + @HandlerPermission( permissionClass = PagePermission.class, target = "${page.qualifiedName}", actions = PagePermission.EDIT_ACTION ) + @WikiRequestContext( "save" ) + public Resolution save() throws WikiException + { + WikiSession wikiSession = getContext().getWikiSession(); + HttpServletRequest request = getContext().getHttpRequest(); HttpSession session = request.getSession(); + WikiContext wikiContext = getContext(); + WikiEngine engine = getContext().getEngine(); + String pagereq = m_page.getName(); + + log.info( "Saving page " + m_page.getName() + ". UserPrincipal=" + wikiSession.getUserPrincipal().getName() + ", Author=" + + m_author + ", Host=" + getContext().getRequest().getRemoteAddr() ); + + // Check for session expiration + Resolution r = SpamFilter.checkHash( this ); + if( r != null ) + { + return r; + } + + // FIXME: I am not entirely sure if the JSP page is the + // best place to check for concurrent changes. It certainly + // is the best place to show errors, though. + String h = SpamFilter.getSpamHash( m_page, request ); + + // Someone changed the page while we were editing it! + if( !h.equals( m_spamhash ) ) + { + log.info( "Page changed, warning user." ); + return new RedirectResolution( PageModifiedActionBean.class, "conflict" ).addParameter( "page", pagereq ); + } + + // + // We expire ALL locks at this moment, simply because someone has + // already broken it. + // + PageLock lock = engine.getPageManager().getCurrentLock( m_page ); + engine.getPageManager().unlockPage( lock ); + session.removeAttribute( "lock-" + pagereq ); + + // Set author information and other metadata + WikiPage modifiedPage = (WikiPage) wikiContext.getPage().clone(); + modifiedPage.setAuthor( m_author ); + + // If this is an append, add it to the page. + // If a full edit, replace the previous contents. + try + { + wikiContext.setPage( modifiedPage ); + + if( m_captcha ) + { + wikiContext.setVariable( "captcha", Boolean.TRUE ); + session.removeAttribute( "captcha" ); + } + + if( m_append ) + { + StringBuffer pageText = new StringBuffer( engine.getText( pagereq ) ); + pageText.append( m_text ); + engine.saveText( wikiContext, pageText.toString() ); + } + else + { + engine.saveText( wikiContext, m_text ); + } + } + catch( DecisionRequiredException ex ) + { + return new RedirectResolution( ViewActionBean.class, "view" ).addParameter( "page", "ApprovalRequiredForPageChanges" ); + } + catch( RedirectException ex ) + { + // Should work, but doesn't + wikiContext.getWikiSession().addMessage( ex.getMessage() ); // FIXME: + session.setAttribute( "message", ex.getMessage() ); + session.setAttribute( SpamFilter.getHashFieldName( request ), m_spamhash ); + return new RedirectResolution( ex.getRedirect() ).flash( this ); + } - request.setAttribute( EditorManager.ATTR_EDITEDTEXT, session.getAttribute( EditorManager.REQ_EDITEDTEXT ) ); + return new RedirectResolution( ViewActionBean.class, "view" ).addParameter( "page", pagereq ); + } - String lastchange = SpamFilter.getSpamHash( context.getPage(), request ); - request.setAttribute( "lastchange", lastchange ); + /** + * Sets a flag indicating that new page text should be appended to the old + * text. + * + * @param true if text should be appended; false + * otherwise (the default). + */ + @Validate( required = false ) + public void setAppend( boolean append ) + { + m_append = append; + } - return new ForwardResolution( "/Preview.jsp" ); + /** + * Sets the author. + * + * @param author the author + */ + @Validate( required = false ) + public void setAuthor( String author ) + { + m_author = author; } + + /** + * Sets a flag indicating that CAPTCHA should be used for editing. + * + * @param captcha true if a CAPTCHA is in use; + * false otherwise. + */ + @Validate( required = false ) + public void setCaptcha( boolean captcha ) + { + m_captcha = captcha; + } + + /** + * Sets the changenote for this upload; usually a short comment. + * + * @param changenote the change note + */ + @Validate( required = false ) + public void setChangenote( String changenote ) + { + m_changeNote = changenote; + } + + /** + * Sets the HTML page text, which will be translated into wiki text by + * {@link HtmlStringToWikiTranslator}. Calling this method causes + * {@link #setText(String)} to be called, with the translated text supplied. + * + * @param the HTML to translate + * @throws JDOMException if the HTML cannot be translated + * @throws IOException if the HtmlStringToWikiTranslator cannot translated + * the text + */ + @Validate( required = false ) + public void setHtmlPageText( String html ) throws IOException, JDOMException + { + m_htmlPageText = html; + m_text = new HtmlStringToWikiTranslator().translate( html, getContext() ); + } + + /** + * Sets the link. + * + * @param link the link + */ + @Validate( required = false ) + public void setLink( String link ) + { + m_link = link; + } + + /** + * Returns true if the "live preview" feature is turned on; + * false otherwise + * + * @param livePreview the "live preview" setting + */ + @Validate( required = false ) + public void setLivePreview( boolean livePreview ) + { + m_livePreview = livePreview; + } + + /** + * Sets the flag indicating that the author name should be remembered. + * + * @param remember the remember-me flag + */ + @Validate( required = false ) + public void setRemember( boolean remember ) + { + m_remember = remember; + } + + /** + * Sets the edited text. + * + * @param text the text + */ + @Validate( required = true ) + public void setText( String text ) + { + m_text = text; + } + } Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/action/RenameActionBean.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/action/RenameActionBean.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/action/RenameActionBean.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/action/RenameActionBean.java Fri Mar 6 23:31:03 2009 @@ -23,21 +23,23 @@ import javax.servlet.http.HttpServletRequest; +import net.sourceforge.stripes.action.HandlesEvent; +import net.sourceforge.stripes.action.RedirectResolution; +import net.sourceforge.stripes.action.Resolution; +import net.sourceforge.stripes.action.UrlBinding; +import net.sourceforge.stripes.validation.LocalizableError; +import net.sourceforge.stripes.validation.Validate; +import net.sourceforge.stripes.validation.ValidationErrors; +import net.sourceforge.stripes.validation.ValidationMethod; + import org.apache.wiki.WikiEngine; import org.apache.wiki.api.WikiException; -import org.apache.wiki.api.WikiPage; import org.apache.wiki.auth.permissions.PagePermission; import org.apache.wiki.log.Logger; import org.apache.wiki.log.LoggerFactory; import org.apache.wiki.ui.stripes.HandlerPermission; import org.apache.wiki.ui.stripes.WikiRequestContext; -import net.sourceforge.stripes.action.HandlesEvent; -import net.sourceforge.stripes.action.RedirectResolution; -import net.sourceforge.stripes.action.Resolution; -import net.sourceforge.stripes.action.UrlBinding; -import net.sourceforge.stripes.validation.*; - /** *

@@ -138,16 +140,6 @@ } /** - * Sets the page. - * @param page the wiki page. - */ - @Validate( required = true ) - public void setPage( WikiPage page ) - { - super.setPage( page ); - } - - /** * Sets the new name for the page, which will be set when the * {@link #rename()} handler is executed. * Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/action/UploadActionBean.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/action/UploadActionBean.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/action/UploadActionBean.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/action/UploadActionBean.java Fri Mar 6 23:31:03 2009 @@ -21,26 +21,52 @@ package org.apache.wiki.action; +import java.io.IOException; +import java.io.InputStream; +import java.security.Principal; import java.util.List; +import net.sourceforge.stripes.action.FileBean; +import net.sourceforge.stripes.action.HandlesEvent; +import net.sourceforge.stripes.action.RedirectResolution; +import net.sourceforge.stripes.action.Resolution; +import net.sourceforge.stripes.validation.LocalizableError; +import net.sourceforge.stripes.validation.Validate; +import net.sourceforge.stripes.validation.ValidationErrors; +import net.sourceforge.stripes.validation.ValidationMethod; + +import org.apache.wiki.WikiContext; +import org.apache.wiki.WikiEngine; +import org.apache.wiki.api.WikiException; +import org.apache.wiki.api.WikiPage; +import org.apache.wiki.attachment.Attachment; +import org.apache.wiki.attachment.AttachmentManager; import org.apache.wiki.auth.permissions.PagePermission; +import org.apache.wiki.content.WikiName; +import org.apache.wiki.i18n.InternationalizationManager; import org.apache.wiki.log.Logger; import org.apache.wiki.log.LoggerFactory; +import org.apache.wiki.providers.ProviderException; import org.apache.wiki.ui.stripes.HandlerPermission; import org.apache.wiki.ui.stripes.WikiRequestContext; -import net.sourceforge.stripes.action.FileBean; -import net.sourceforge.stripes.action.HandlesEvent; -import net.sourceforge.stripes.action.Resolution; -import net.sourceforge.stripes.action.UrlBinding; - -@UrlBinding( "/Upload.jsp" ) -public class UploadActionBean extends AbstractActionBean +public class UploadActionBean extends AbstractPageActionBean { - private Logger log = LoggerFactory.getLogger( UploadActionBean.class ); + private static final Logger log = LoggerFactory.getLogger( UploadActionBean.class ); private List m_newAttachments; + private String m_changeNote = null; + + /** + * Returns the new attachments uploaded by the user. + * @return the new files to attach + */ + public List getNewAttachments() + { + return m_newAttachments; + } + /** * Sets the set of new attachments that should be saved when the * {@link #upload()} event is executed. @@ -53,17 +79,157 @@ } /** + * Sets the changenote for this upload; usually a short comment. + * + * @param changenote the change note + */ + @Validate( required = false ) + public void setChangenote( String changenote ) + { + m_changeNote = changenote; + } + + /* + * Returns the changenote for this upload. + */ + public String getChangenote() + { + return m_changeNote; + } + + /** * Handler method that uploads a new attachment to the ViewActionBean. * - * @return {@link Resolution} + * @return */ @HandlesEvent( "upload" ) - @HandlerPermission( permissionClass = PagePermission.class, target = "${page.qualifiedName}", actions = PagePermission.VIEW_ACTION ) + @HandlerPermission( permissionClass = PagePermission.class, target = "${page.qualifiedName}", actions = PagePermission.UPLOAD_ACTION ) @WikiRequestContext( "upload" ) - public Resolution upload() + public Resolution upload() throws Exception + { + for( FileBean attachment : m_newAttachments ) + { + if ( attachment != null ) + { + executeUpload( attachment ); + log.debug( "Executed upload; " + m_newAttachments.size() + " attachments found." ); + } + } + + return new RedirectResolution( ViewActionBean.class, "attachments" ).addParameter( "page", m_page.getName() ); + } + + @ValidationMethod + public void validateFileType( ValidationErrors errors ) { - log.debug( "Executed upload; " + m_newAttachments.size() + " attachments found." ); - return null; + AttachmentManager mgr = getContext().getEngine().getAttachmentManager(); + for ( FileBean attachment : m_newAttachments ) + { + if ( attachment != null ) + { + // Clean the file name before validating + String filename = attachment.getFileName(); + try + { + filename = AttachmentManager.cleanFileName( filename ); + } + catch( WikiException e ) + { + // Error message returns the i18n key name + errors.add( "newAttachments", new LocalizableError( e.getMessage(), filename ) ); + } + + if ( !mgr.isFileTypeAllowed( filename ) ) + { + errors.add( "newAttachments", new LocalizableError( "attach.bad.filetype", filename ) ); + } + } + } + } + + /** + * Uploads a single FileBean to the AttachmentManager. This method assumes + * that the user has permissions to do so; handler method callers should use + * the {@link HandlerPermission} annotation to force permission checks. + * + * @param filebean the FileBean containing the file to be uploaded + * @return true if upload results in the creation of a new + * page; false otherwise + * @throws IOException If there is a problem in the upload. + * @throws ProviderException If there is a problem in the backend. + */ + private boolean executeUpload( FileBean filebean ) throws Exception + { + boolean created = false; + WikiContext context = getContext(); + WikiEngine engine = context.getEngine(); + AttachmentManager mgr = engine.getAttachmentManager(); + + // Get the file name, size etc from the FileBean + InputStream data = filebean.getInputStream(); + String filename = filebean.getFileName(); + int contentLength = (int)filebean.getSize(); + + // Cleanse the file name + filename = AttachmentManager.cleanFileName( filename ); + log.debug( "file=" + filename ); + + // Get the name of the user uploading the file + Principal user = context.getCurrentUser(); + + // + // Check whether we already have this kind of a page. + // If the "page" parameter already defines an attachment + // name for an update, then we just use that file. + // Otherwise we create a new attachment, and use the + // filename given. Incidentally, this will also mean + // that if the user uploads a file with the exact + // same name than some other previous attachment, + // then that attachment gains a new version. + // + + Attachment att = mgr.getAttachmentInfo( context.getPage().getName() ); + + if( att == null ) + { + String contentType = "application/octet-stream"; // FIXME: This is not a good guess + WikiName path = context.getPage().getQualifiedName().resolve(filename); + att = engine.getContentManager().addPage( path, contentType ); + created = true; + } + att.setSize( contentLength ); + + if( user != null ) + { + att.setAuthor( user.getName() ); + } + + if( m_changeNote != null && m_changeNote.length() > 0 ) + { + att.setAttribute( WikiPage.CHANGENOTE, m_changeNote ); + } + + try + { + engine.getAttachmentManager().storeAttachment( att, data ); + } + catch( ProviderException pe ) + { + // this is a kludge, the exception that is caught here contains + // the i18n key + // here we have the context available, so we can + // internationalize it properly : + throw new ProviderException( context.getBundle( InternationalizationManager.CORE_BUNDLE ) + .getString( pe.getMessage() ) ); + } + + // Close the stream and delete the filebean, since we're done with it + data.close(); + filebean.delete(); + + log.info( "User " + user + " uploaded attachment to " + m_page.getName() + " called " + filename + ", size " + att.getSize() ); + + return created; } } Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/action/ViewActionBean.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/action/ViewActionBean.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/action/ViewActionBean.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/action/ViewActionBean.java Fri Mar 6 23:31:03 2009 @@ -23,6 +23,7 @@ import net.sourceforge.stripes.action.*; import net.sourceforge.stripes.controller.LifecycleStage; +import net.sourceforge.stripes.validation.Validate; import net.sourceforge.stripes.validation.ValidationError; import net.sourceforge.stripes.validation.ValidationErrors; @@ -192,6 +193,17 @@ } /** + * {@inheritDoc}. This method overrides the superclass method + * by disabling validation of the page field. + */ + @Override + @Validate( required = false ) + public void setPage( WikiPage page ) + { + super.setPage( page ); + } + + /** * Sets the name to rename the page to * * @param renameTo the page name to use Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/Attachment.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/Attachment.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/Attachment.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/Attachment.java Fri Mar 6 23:31:03 2009 @@ -20,8 +20,6 @@ */ package org.apache.wiki.attachment; -import java.io.InputStream; - import org.apache.wiki.api.WikiPage; /** Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/AttachmentManager.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/AttachmentManager.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/AttachmentManager.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/AttachmentManager.java Fri Mar 6 23:31:03 2009 @@ -40,6 +40,7 @@ import org.apache.wiki.log.Logger; import org.apache.wiki.log.LoggerFactory; import org.apache.wiki.providers.ProviderException; +import org.apache.wiki.util.TextUtil; import com.opensymphony.oscache.base.Cache; import com.opensymphony.oscache.base.NeedsRefreshException; @@ -80,6 +81,16 @@ private WikiEngine m_engine; /** + * List of attachment types which are allowed. + */ + private String[] m_allowedPatterns; + + /** + * List of attachment types which are forbidden. + */ + private String[] m_forbiddenPatterns; + + /** * Creates a new AttachmentManager. Note that creation will never fail, * but it's quite likely that attachments do not function. *

@@ -96,6 +107,7 @@ public AttachmentManager( WikiEngine engine, Properties props ) { m_engine = engine; + initFileRestrictions(); } /** @@ -376,7 +388,7 @@ * disabled. * @throws ProviderException If the provider fails for some reason. */ - public List getVersionHistory( String attachmentName ) + public List getVersionHistory( String attachmentName ) throws ProviderException { return m_engine.getContentManager().getVersionHistory( WikiName.valueOf(attachmentName) ); @@ -407,14 +419,14 @@ } /** - * Validates the filename and makes sure it is legal. It trims and splits - * and replaces bad characters. + * Cleans an attachment filename by trimming and replacing bad characters. + * If a file path is supplied, only the trailing file name will be returned. * - * @param filename + * @param filename the filename to cleanse * @return A validated name with annoying characters replaced. * @throws WikiException If the filename is not legal (e.g. empty) */ - static String validateFileName( String filename ) + public static String cleanFileName( String filename ) throws WikiException { if( filename == null || filename.trim().length() == 0 ) @@ -457,4 +469,69 @@ return filename; } + + /** + * Determines whether a supplied attachment is allowed to be + * uploaded, based on the file name. The list of files types allowed for uploading + * are contained in jspwiki.properties property + * {@link #PROP_ALLOWEDEXTENSIONS}. The list of denied file types are + * contained in {@link #PROP_FORDBIDDENEXTENSIONS}. If an extension is + * included in both lists, the forbidden list wins. + * @param name the proposed file name + * @return true if a supplied attachment file name is + * allowed to be uploaded; false otherwise. + */ + public boolean isFileTypeAllowed( String name ) + { + if( name == null || name.length() == 0 ) return false; + + name = name.toLowerCase(); + + for( int i = 0; i < m_forbiddenPatterns.length; i++ ) + { + if( name.endsWith(m_forbiddenPatterns[i]) && m_forbiddenPatterns[i].length() > 0 ) + return false; + } + + for( int i = 0; i < m_allowedPatterns.length; i++ ) + { + if( name.endsWith(m_allowedPatterns[i]) && m_allowedPatterns[i].length() > 0 ) + return true; + } + + return m_allowedPatterns.length == 0; + } + + private void initFileRestrictions() + { + Properties props = m_engine.getWikiProperties(); + + String allowed = TextUtil.getStringProperty( props, + AttachmentManager.PROP_ALLOWEDEXTENSIONS, + null ); + + if( allowed != null && allowed.length() > 0 ) + { + m_allowedPatterns = allowed.toLowerCase().split("\\s"); + } + else + { + m_allowedPatterns = new String[0]; + } + + String forbidden = TextUtil.getStringProperty( props, + AttachmentManager.PROP_FORDBIDDENEXTENSIONS, + null ); + + if( forbidden != null && forbidden.length() > 0 ) + { + m_forbiddenPatterns = forbidden.toLowerCase().split("\\s"); + } + else + { + m_forbiddenPatterns = new String[0]; + } + + log.debug( "AttachmentManager initialized with allowed/denied file patterns." ); + } } Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/AttachmentServlet.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/AttachmentServlet.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/AttachmentServlet.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/attachment/AttachmentServlet.java Fri Mar 6 23:31:03 2009 @@ -666,7 +666,7 @@ try { - filename = AttachmentManager.validateFileName( filename ); + filename = AttachmentManager.cleanFileName( filename ); } catch( WikiException e ) { Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/filters/SpamFilter.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/filters/SpamFilter.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/filters/SpamFilter.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/filters/SpamFilter.java Fri Mar 6 23:31:03 2009 @@ -32,11 +32,15 @@ import javax.servlet.jsp.PageContext; import net.sf.akismet.Akismet; +import net.sourceforge.stripes.action.RedirectResolution; +import net.sourceforge.stripes.action.Resolution; import org.apache.commons.jrcs.diff.*; import org.apache.commons.jrcs.diff.myers.MyersDiff; import org.apache.commons.lang.time.StopWatch; import org.apache.wiki.*; +import org.apache.wiki.action.ViewActionBean; +import org.apache.wiki.action.WikiActionBean; import org.apache.wiki.action.WikiContextFactory; import org.apache.wiki.api.ModuleData; import org.apache.wiki.api.WikiPage; @@ -46,6 +50,7 @@ import org.apache.wiki.log.LoggerFactory; import org.apache.wiki.providers.ProviderException; import org.apache.wiki.ui.EditorManager; +import org.apache.wiki.ui.stripes.WikiActionBeanContext; import org.apache.wiki.util.FileUtil; import org.apache.wiki.util.TextUtil; @@ -1111,6 +1116,39 @@ return hash != null ? hash : c_hashName; } + /** + *

This method checks if the hash value is still valid, i.e. if it exists at all. This + * can occur in two cases: either this is a spam bot which is not adaptive, or it is + * someone who has been editing one page for too long, and their session has expired.

+ *

If the hash is not valid, this method returns a Stripes + * {@link net.sourceforge.stripes.action.RedirectResolution} that directs + * users to wiki page "SessionExpired" and logs the incident in the spam log + * (it may or may not be spam, but it's rather likely that it is).

+ *

If the hash is valid, this method simply returns null.

+ *

Other than the differences in the method parameters and return syntax, this + * method operates in every other respect identically to + * {@link #checkHash(WikiContext, PageContext)}

+ * + * @param actionBean the WikiActionBean representing the editing activity and page. + * @return null if hash is okay, or a RedirectResolution if not. + * @since 3.0 + */ + public static final Resolution checkHash( WikiActionBean actionBean ) + { + WikiActionBeanContext context = actionBean.getContext(); + String hashName = getHashFieldName( context.getRequest() ); + + if( context.getRequest().getParameter(hashName) == null ) + { + Change change = getChange( context, EditorManager.getEditedText( context.getRequest() ) ); + + log( context, REJECT, "MissingHash", change.m_change ); + + return new RedirectResolution( ViewActionBean.class, "view" ).addParameter( "name", "SessionExpired"); + } + + return null; + } /** * This method checks if the hash value is still valid, i.e. if it exists at all. This Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/tags/IncludeResourcesTag.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/tags/IncludeResourcesTag.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/tags/IncludeResourcesTag.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/tags/IncludeResourcesTag.java Fri Mar 6 23:31:03 2009 @@ -28,7 +28,7 @@ * tiny marker into the stream, and then a ServletFilter will take * care of the actual inclusion. * - * +* @deprecated use the Stripes layout-component tags instead */ public class IncludeResourcesTag extends WikiTagBase { Modified: incubator/jspwiki/trunk/src/java/org/apache/wiki/tags/RequestResourceTag.java URL: http://svn.apache.org/viewvc/incubator/jspwiki/trunk/src/java/org/apache/wiki/tags/RequestResourceTag.java?rev=751135&r1=751134&r2=751135&view=diff ============================================================================== --- incubator/jspwiki/trunk/src/java/org/apache/wiki/tags/RequestResourceTag.java (original) +++ incubator/jspwiki/trunk/src/java/org/apache/wiki/tags/RequestResourceTag.java Fri Mar 6 23:31:03 2009 @@ -27,6 +27,7 @@ * any of the request types defined there. * * @see TemplateManager + * @deprecated use the Stripes layout-component tags instead */ public class RequestResourceTag extends WikiTagBase {