You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@click.apache.org by sa...@apache.org on 2009/06/18 23:49:22 UTC
svn commit: r786301 - in /incubator/click/trunk/click: documentation/docs/
extras/src/org/apache/click/extras/gae/
Author: sabob
Date: Thu Jun 18 21:49:21 2009
New Revision: 786301
URL: http://svn.apache.org/viewvc?rev=786301&view=rev
Log:
added Google App Engine support. CLK-560
Added:
incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/
incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/GoogleAppEngineListener.java
incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItem.java
incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItemFactory.java
incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileUploadService.java
Modified:
incubator/click/trunk/click/documentation/docs/roadmap-changes.html
Modified: incubator/click/trunk/click/documentation/docs/roadmap-changes.html
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/documentation/docs/roadmap-changes.html?rev=786301&r1=786300&r2=786301&view=diff
==============================================================================
--- incubator/click/trunk/click/documentation/docs/roadmap-changes.html (original)
+++ incubator/click/trunk/click/documentation/docs/roadmap-changes.html Thu Jun 18 21:49:21 2009
@@ -147,6 +147,14 @@
</div>
<ul style="padding: 0em; margin-left:0em;margin-bottom: 2em">
<li class="change">
+ Added support for <a class="external" target="_blank" href="http://code.google.com/appengine/docs/java/overview.html">Google App Engine</a>,
+ a free Java hosting environment from Google. This provides an ideal
+ environment for students and startups to quickly host their Click
+ applications online. See <a href="extras-api/org/apache/click/extras/gae/GoogleAppEngineListener.html">GoogleAppEngineListener</a>
+ for details
+ [<a target="_blank" href="https://issues.apache.org/jira/browse/CLK-560">560</a>].
+ </li>
+ <li class="change">
Added new Calendar popup to DateField. This Calendar popup uses
<a target="_blank" class="external" href="http://code.google.com/p/calendardateselect/">Calendar Date Select</a>
which is based on the Prototype JavaScript library.
Added: incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/GoogleAppEngineListener.java
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/GoogleAppEngineListener.java?rev=786301&view=auto
==============================================================================
--- incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/GoogleAppEngineListener.java (added)
+++ incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/GoogleAppEngineListener.java Thu Jun 18 21:49:21 2009
@@ -0,0 +1,162 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.click.extras.gae;
+
+import javax.servlet.ServletContextEvent;
+import javax.servlet.ServletContextListener;
+
+import ognl.OgnlRuntime;
+
+/**
+ * Provides Google App Engine (GAE) support for Click applications.
+ * <p/>
+ * To deploy Click applications to GAE, you need to set the
+ * <tt>GoogleAppEngineListener</tt> listener in your <tt>web.xml</tt>:
+ *
+ * <pre class="codeHtml">
+ * <?xml version="1.0" encoding="utf-8"?>
+ * <web-app xmlns="http://java.sun.com/xml/ns/javaee" version="2.5">
+ *
+ * <listener>
+ * <listener-class><span class="red">org.apache.click.extras.gae.GoogleAppEngineListener</span></listener-class>
+ * </listener>
+ *
+ * <servlet>
+ * <servlet-name>ClickClickServlet</servlet-name>
+ * <servlet-class>net.sf.clickclick.ClickClickServlet</servlet-class>
+ * <load-on-startup>0</load-on-startup>
+ * </servlet>
+ * <servlet-mapping>
+ * <servlet-name>ClickClickServlet</servlet-name>
+ * <url-pattern>*.htm</url-pattern>
+ * </servlet-mapping>
+ * </web-app> </pre>
+ *
+ * You also need to configure GAE to exclude <tt>*.htm</tt> files from being
+ * served as static resources. Also you should enable <tt>http-session</tt>
+ * support. You set these changes in the GAE file <tt>war/WEB-INF/appengine-web.xml</tt>:
+ *
+ * <pre class="codeHtml">
+ * <?xml version="1.0" encoding="utf-8"?>
+ * <appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
+ * <application>myapp</application>
+ * <version>1</version>
+ *
+ * <!-- Configure java.util.logging -->
+ * <system-properties>
+ * <property name="java.util.logging.config.file" value="WEB-INF/logging.properties"/>
+ * </system-properties>
+ *
+ * <!-- Enable HttpSession usage -->
+ * <<span class="blue">sessions-enabled</span>><span class="red">true</span></<span class="blue">sessions-enabled</span>>
+ *
+ * <!-- Exclude *.htm files from being served as static files by GAE,
+ * because the *.htm extension is mapped to ClickServlet. -->
+ * <static-files>
+ * <<span class="blue">exclude</span> path="<span class="red">**.htm</span>" />
+ * </static-files>
+ *
+ * </appengine-web-app> </pre>
+ *
+ * <h3>File Uploads</h3>
+ *
+ * GAE does not allow web application to write to files on disk. This poses a
+ * problem for the {@link org.apache.click.control.FileField} control that
+ * depends on <a class="external" target="_blank" href="http://commons.apache.org/fileupload/">Commons FileUpload</a>
+ * which stores uploaded files on disk. To work around this limitation Click
+ * provides the {@link MemoryFileUploadService} which stores uploaded files in
+ * memory.
+ * <p/>
+ * Below is an example configuration of a {@link MemoryFileUploadService}:
+ *
+ * <pre class="prettyprint">
+ * <click-app charset="UTF-8">
+ * <pages package="com.myapp.pages"/>
+ * <mode value="production"/>
+ *
+ * <file-upload-service classname="org.apache.click.extras.gae.MemoryFileUploadService">
+ * <!-- Set the total request maximum size to 10mb (10 x 1024 x 1024 = 10485760).
+ * The default request upload size is unlimited. -->
+ * <property name="sizeMax" value="10485760"/>
+ *
+ * <!-- Set the maximum individual file size to 2mb (2 x 1024 x 1024 = 2097152).
+ * The default file upload size is unlimited. -->
+ * <property name="fileSizeMax" value="2097152"/>
+ * </file-upload-service>
+ * </click-app> </pre>
+ *
+ * <h3>Performance Filter</h3>
+ *
+ * If you use Click's {@link org.apache.click.extras.filter.PerformanceFilter}
+ * you should also exclude the following static files from GAE, so that
+ * PerformanceFilter can set their <tt>expiry headers</tt>:
+ * <tt>*.css</tt>, <tt>*.js</tt>, <tt>*.png</tt> and <tt>*.gif</tt>. For example:
+ *
+ * <pre class="codeHtml">
+ * <?xml version="1.0" encoding="utf-8"?>
+ * <appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
+ *
+ * ...
+ *
+ * <!-- Exclude the following files from being served as static files by GAE,
+ * as they will be processed by Click's PerformanceFilter. -->
+ * <static-files>
+ * <<span class="blue">exclude</span> path="<span class="red">**.htm</span>" />
+ * <<span class="blue">exclude</span> path="<span class="red">**.css</span>" />
+ * <<span class="blue">exclude</span> path="<span class="red">**.js</span>" />
+ * <<span class="blue">exclude</span> path="<span class="red">**.png</span>" />
+ * <<span class="blue">exclude</span> path="<span class="red">**.gif</span>" />
+ * </static-files>
+ *
+ * </appengine-web-app> </pre>
+ *
+ * @author Bob Schellink
+ */
+public class GoogleAppEngineListener implements ServletContextListener {
+
+ /**
+ * Creates a default GoogleAppEngineListener.
+ */
+ public GoogleAppEngineListener() {
+ }
+
+ /**
+ * This method does nothing.
+ *
+ * @param servletContextEvent the event class for notifications about
+ * changes to the servlet context
+ */
+ public void contextDestroyed(ServletContextEvent servletContextEvent) {
+ }
+
+ /**
+ * Sets the Ognl Runtime SecurityManager to <tt>null</tt> so as not to
+ * interfere with Google App Engine (GAE). GAE provides its own strict
+ * SecurityManager which clashes with Ognl security checks.
+ *
+ * <pre class="prettyprint">
+ * OgnlRuntime.setSecurityManager(null); </pre>
+ *
+ * @param servletContextEvent the event class for notifications about
+ * changes to the servlet context
+ */
+ public void contextInitialized(ServletContextEvent servletContextEvent) {
+ OgnlRuntime.setSecurityManager(null);
+ }
+}
Added: incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItem.java
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItem.java?rev=786301&view=auto
==============================================================================
--- incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItem.java (added)
+++ incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItem.java Thu Jun 18 21:49:21 2009
@@ -0,0 +1,318 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.click.extras.gae;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.File;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.io.UnsupportedEncodingException;
+
+import java.util.Map;
+import org.apache.commons.fileupload.FileItem;
+import org.apache.commons.fileupload.FileItemHeaders;
+import org.apache.commons.fileupload.FileItemHeadersSupport;
+import org.apache.commons.fileupload.ParameterParser;
+
+/**
+ * Provides an In-Memory FileItem implementation which represents a file or
+ * form item that was received within a <tt>multipart/form-data</tt> POST
+ * request.
+ * <p/>
+ * This FileItem implementation can safely be used with Google App Engine (GAE)
+ * since the file content is not written to disk.
+ * <p/>
+ * The MemoryFileItem is based on the
+ * <a class="external" target="_blank" href="http://commons.apache.org/fileupload/">Commons FileUpload</a>
+ * project.
+ *
+ * @author Bob Schellink
+ */
+public class MemoryFileItem implements FileItem, FileItemHeadersSupport {
+
+ // -------------------------------------------------------------- Constants
+
+ /**
+ * Default content charset to be used when no explicit charset
+ * parameter is provided by the sender. Media subtypes of the
+ * "text" type are defined to have a default charset value of
+ * "ISO-8859-1" when received via HTTP.
+ */
+ public static final String DEFAULT_CHARSET = "ISO-8859-1";
+
+ // -------------------------------------------------------------- Variables
+
+ /**
+ * The name of the form field as provided by the browser.
+ */
+ private String fieldName;
+
+ /**
+ * The content type passed by the browser, or null if not defined.
+ */
+ private String contentType;
+
+ /**
+ * Whether or not this item is a simple form field.
+ */
+ private boolean isFormField;
+
+ /**
+ * The original filename in the user's filesystem.
+ */
+ private String fileName;
+
+ /**
+ * The file items headers.
+ */
+ private FileItemHeaders headers;
+
+ /**
+ * The file item's uploaded content.
+ */
+ private ByteArrayOutputStream content;
+
+ // ----------------------------------------------------------- Constructors
+
+ /**
+ * Constructs a new MemoryFileItem for the given fieldName, contentType
+ * isFormField and fileName parameters.
+ *
+ * @param fieldName the name of the form field as provided by the browser
+ * @param contentType the content type passed by the browser
+ * @param isFormField specifies whether or not this item is a simple form field
+ * @param fileName the original filename in the user's filesystem
+ */
+ public MemoryFileItem(String fieldName, String contentType, boolean isFormField,
+ String fileName) {
+
+ this.fieldName = fieldName;
+ this.contentType = contentType;
+ this.isFormField = isFormField;
+ this.fileName = fileName;
+ this.content = new ByteArrayOutputStream();
+ }
+
+ // --------------------------------------------------------- Public Methods
+
+ /**
+ * This method does nothing since the file is stored in memory only.
+ */
+ public void delete() {
+ }
+
+ /**
+ * Returns the contents of the file item as an array of bytes.
+ *
+ * @return the contents of the file item as an array of bytes
+ */
+ public byte[] get() {
+ return content.toByteArray();
+ }
+
+ /**
+ * Returns the content type passed by the browser or null if not defined.
+ *
+ * @return the content type passed by the browser or null if not defined
+ */
+ public String getContentType() {
+ return contentType;
+ }
+
+ /**
+ * Returns the name of the field in the multipart form corresponding to
+ * this file item.
+ *
+ * @return the name of the form field
+ */
+ public String getFieldName() {
+ return fieldName;
+ }
+
+ /**
+ * Sets the field name used to reference this file item.
+ *
+ * @param fieldName the name of the form field
+ */
+ public void setFieldName(String fieldName) {
+ this.fieldName = fieldName;
+ }
+
+ /**
+ * Determines whether or not a <tt>FileItem</tt> instance represents
+ * a simple form field.
+ *
+ * @return true if the instance represents a simple form field; false if it
+ * represents an uploaded file
+ */
+ public boolean isFormField() {
+ return isFormField;
+ }
+
+ /**
+ * Specifies whether or not a <tt>FileItem</tt> instance represents
+ * a simple form field.
+ *
+ * @param isFormField true if the instance represents a simple form field;
+ * false if it represents an uploaded file
+ */
+ public void setFormField(boolean isFormField) {
+ this.isFormField = isFormField;
+ }
+
+ /**
+ * Returns an {@link java.io.InputStream InputStream} that can be used to
+ * retrieve the contents of the file.
+ *
+ * @return an {@link java.io.InputStream InputStream} that can be used to
+ * retrieve the contents of the file
+ * @throws IOException if an error occurs
+ */
+ public InputStream getInputStream() throws IOException {
+ return new ByteArrayInputStream(get());
+ }
+
+ /**
+ * Returns the original filename in the client's filesystem, as provided by
+ * the browser (or other client software). In most cases, this will be the
+ * base file name, without path information. However, some clients, such as
+ * Internet Explorer, do include path information.
+ * <p/>
+ * You can easily remove the path information with the following snippet:
+ *
+ * <pre class="prettyprint">
+ * String fileName = fileItem.getName();
+ * if (fileName != null) {
+ * filename = FilenameUtils.getName(filename);
+ * } </pre>
+ *
+ * @return the original filename in the client's filesystem.
+ */
+ public String getName() {
+ return fileName;
+ }
+
+ /**
+ * Returns an {@link java.io.OutputStream OutputStream} that can be used for
+ * storing the contents of the file.
+ *
+ * @return an {@link java.io.OutputStream OutputStream} that can be used
+ * for storing the contensts of the file
+ * @throws IOException if an error occurs
+ */
+ public OutputStream getOutputStream() throws IOException {
+ return content;
+ }
+
+ /**
+ * Returns the size of the file item, in bytes.
+ *
+ * @return the size of the file item, in bytes
+ */
+ public long getSize() {
+ return content.size();
+ }
+
+ /**
+ * Returns the contents of the file as a String, using the default
+ * character encoding. This method uses {@link #get()} to retrieve the
+ * contents of the file.
+ *
+ * @return the contents of the file, as a string.
+ */
+ public String getString() {
+ byte[] rawdata = get();
+ String charset = getCharSet();
+ if (charset == null) {
+ charset = DEFAULT_CHARSET;
+ }
+ try {
+ return new String(rawdata, charset);
+ } catch (UnsupportedEncodingException e) {
+ return new String(rawdata);
+ }
+ }
+
+ /**
+ * Returns the contents of the file as a String, using the specified
+ * encoding. This method uses {@link #get()} to retrieve the contents of the
+ * file.
+ *
+ * @param charset the charset to use
+ * @return the contents of the file, as a string
+ * @throws UnsupportedEncodingException if the requested character
+ * encoding is not available.
+ */
+ public String getString(final String charset)
+ throws UnsupportedEncodingException {
+ return new String(get(), charset);
+ }
+
+ /**
+ * Provides a hint as to whether or not the file contents will be read
+ * from memory. This method always returns true.
+ *
+ * @return true to indicate that the file contents will be read from memory
+ */
+ public boolean isInMemory() {
+ return true;
+ }
+
+ /**
+ * This method does nothing since the file is stored in memory only.
+ *
+ * @param file the File into which the uploaded item should be stored
+ * @throws Exception if an error occurs
+ */
+ public void write(File file) throws Exception {
+ }
+
+ /**
+ * Returns the file item headers.
+ *
+ * @return the file items headers
+ */
+ public FileItemHeaders getHeaders() {
+ return headers;
+ }
+
+ /**
+ * Sets the file item headers.
+ *
+ * @param headers the file items headers
+ */
+ public void setHeaders(FileItemHeaders headers) {
+ this.headers = headers;
+ }
+
+ /**
+ * Returns the content charset passed by the agent or null if not defined.
+ *
+ * @return The content charset passed by the agent or null if not defined
+ */
+ public String getCharSet() {
+ ParameterParser parser = new ParameterParser();
+ parser.setLowerCaseNames(true);
+ // Parameter parser can handle null input
+ Map params = parser.parse(getContentType(), ';');
+ return (String) params.get("charset");
+ }
+}
Added: incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItemFactory.java
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItemFactory.java?rev=786301&view=auto
==============================================================================
--- incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItemFactory.java (added)
+++ incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileItemFactory.java Thu Jun 18 21:49:21 2009
@@ -0,0 +1,49 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.click.extras.gae;
+
+import org.apache.commons.fileupload.FileItem;
+import org.apache.commons.fileupload.FileItemFactory;
+
+/**
+ * Provides a FileItemFactory implementation that creates {@link MemoryFileItem}
+ * instances which always keep their content in memory.
+ *
+ * @author Bob Schellink
+ */
+public class MemoryFileItemFactory implements FileItemFactory {
+
+ /**
+ * Create a new {@link MemoryFileItem} instance from the supplied parameters.
+ *
+ * @param fieldName the name of the form field
+ * @param contentType the content type of the form field
+ * @param isFormField true if this is a plain form field, false otherwise
+ * @param fileName the name of the uploaded file, if any, as supplied by the
+ * browser or other client
+ * @return the newly created file item
+ */
+ public FileItem createItem(String fieldName, String contentType,
+ boolean isFormField, String fileName) {
+
+ FileItem result =
+ new MemoryFileItem(fieldName, contentType, isFormField, fileName);
+ return result;
+ }
+}
Added: incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileUploadService.java
URL: http://svn.apache.org/viewvc/incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileUploadService.java?rev=786301&view=auto
==============================================================================
--- incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileUploadService.java (added)
+++ incubator/click/trunk/click/extras/src/org/apache/click/extras/gae/MemoryFileUploadService.java Thu Jun 18 21:49:21 2009
@@ -0,0 +1,67 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.click.extras.gae;
+
+import javax.servlet.http.HttpServletRequest;
+import org.apache.click.service.CommonsFileUploadService;
+import org.apache.commons.fileupload.FileItemFactory;
+
+/**
+ * Provides an Apache Commons In-Memory FileUploadService class.
+ * <p/>
+ * This service creates an {@link MemoryFileItemFactory} for creating
+ * {@link MemoryFileItem In-Memory FileItem instances} which content is never
+ * written to disk.
+ * <p/>
+ * This service is recommended to be used with Google App Engine (GAE) which
+ * doesn't allow Web Application access to disk.
+ * <p/>
+ * To use this service in your GAE applications, add the following to your
+ * <tt>click.xml</tt> config:
+ *
+ * <pre class="prettyprint">
+ * <file-upload-service classname="org.apache.click.extras.gae.MemoryFileUploadService">
+ * <!-- Set the total request maximum size to 10mb (10 x 1024 x 1024 = 10485760). -->
+ * <property name="sizeMax" value="10485760"/>
+ *
+ * <!-- Set the maximum individual file size to 2mb (2 x 1024 x 1024 = 2097152). -->
+ * <property name="fileSizeMax" value="2097152"/>
+ * </file-upload-service> </pre>
+ *
+ * To prevent users from uploading exceedingly large files you can configure
+ * MemoryFileUploadService through the properties {@link #setSizeMax(long)} and
+ * {@link #setFileSizeMax(long)}, as demonstrated above.
+ * <p/>
+ * <b>Please note:</b> Google App Engine further restricts the size of file
+ * uploads as well. Currently the limit is 10MB.
+ *
+ * @author Bob Schellink
+ */
+public class MemoryFileUploadService extends CommonsFileUploadService {
+
+ /**
+ * Create and return a new {@link MemoryFileItemFactory} instance.
+ *
+ * @param request the servlet request
+ * @return a new MemoryFileItemFactory instance
+ */
+ public FileItemFactory createFileItemFactory(HttpServletRequest request) {
+ return new MemoryFileItemFactory();
+ }
+}