changeset 859:3dcc52e17535

simplify multipart
author Franklin Schmidt <fschmidt@gmail.com>
date Wed, 21 Sep 2016 16:15:19 -0600
parents dbbd9c3f14f8
children 626815a4b19b
files src/luan/modules/http/HttpServicer.java src/org/eclipse/jetty/server/Request.java src/org/eclipse/jetty/util/MultiPartInputStream.java
diffstat 3 files changed, 9 insertions(+), 189 deletions(-) [+]
line wrap: on
line diff
--- a/src/luan/modules/http/HttpServicer.java	Wed Sep 21 15:02:19 2016 -0600
+++ b/src/luan/modules/http/HttpServicer.java	Wed Sep 21 16:15:19 2016 -0600
@@ -118,8 +118,7 @@
 		} else {  // multipart
 			try {
 				InputStream in = new BufferedInputStream(request.getInputStream());
-				final MultiPartInputStream mpis = new MultiPartInputStream(in,contentType,null,null);
-				mpis.setDeleteOnExit(true);
+				final MultiPartInputStream mpis = new MultiPartInputStream(in,contentType);
 				for( Part p : mpis.getParts() ) {
 					final MultiPartInputStream.MultiPart part = (MultiPartInputStream.MultiPart)p;
 					String name = part.getName();
--- a/src/org/eclipse/jetty/server/Request.java	Wed Sep 21 15:02:19 2016 -0600
+++ b/src/org/eclipse/jetty/server/Request.java	Wed Sep 21 16:15:19 2016 -0600
@@ -46,7 +46,6 @@
 import javax.servlet.AsyncEvent;
 import javax.servlet.AsyncListener;
 import javax.servlet.DispatcherType;
-import javax.servlet.MultipartConfigElement;
 import javax.servlet.RequestDispatcher;
 import javax.servlet.ServletContext;
 import javax.servlet.ServletException;
@@ -89,7 +88,6 @@
 import org.eclipse.jetty.util.LazyList;
 import org.eclipse.jetty.util.MultiException;
 import org.eclipse.jetty.util.MultiMap;
-import org.eclipse.jetty.util.MultiPartInputStream;
 import org.eclipse.jetty.util.StringUtil;
 import org.eclipse.jetty.util.URIUtil;
 import org.eclipse.jetty.util.UrlEncoded;
@@ -136,41 +134,6 @@
 	private static final Collection __defaultLocale = Collections.singleton(Locale.getDefault());
 	private static final int __NONE = 0, _STREAM = 1, __READER = 2;
 
-	public static class MultiPartCleanerListener implements ServletRequestListener
-	{
-
-		@Override
-		public void requestDestroyed(ServletRequestEvent sre)
-		{
-			//Clean up any tmp files created by MultiPartInputStream
-			MultiPartInputStream mpis = (MultiPartInputStream)sre.getServletRequest().getAttribute(__MULTIPART_INPUT_STREAM);
-			if (mpis != null)
-			{
-				ContextHandler.Context context = (ContextHandler.Context)sre.getServletRequest().getAttribute(__MULTIPART_CONTEXT);
-
-				//Only do the cleanup if we are exiting from the context in which a servlet parsed the multipart files
-				if (context == sre.getServletContext())
-				{
-					try
-					{
-						mpis.deleteParts();
-					}
-					catch (MultiException e)
-					{
-						sre.getServletContext().log("Errors deleting multipart tmp files", e);
-					}
-				}
-			}
-		}
-
-		@Override
-		public void requestInitialized(ServletRequestEvent sre)
-		{
-			//nothing to do, multipart config set up by ServletHolder.handle()
-		}
-		
-	}
-	
 	
 	/* ------------------------------------------------------------ */
 	public static Request getRequest(HttpServletRequest request)
@@ -219,8 +182,6 @@
 	private Buffer _timeStampBuffer;
 	private HttpURI _uri;
 	
-	private MultiPartInputStream _multiPartInputStream; //if the request is a multi-part mime
-	
 	/* ------------------------------------------------------------ */
 	public Request()
 	{
@@ -1389,8 +1350,6 @@
 		_parameters = null;
 		_paramsExtracted = false;
 		_inputState = __NONE;
-
-		_multiPartInputStream = null;
 	}
 
 	/* ------------------------------------------------------------ */
@@ -1834,63 +1793,13 @@
 	/* ------------------------------------------------------------ */
 	public Part getPart(String name) throws IOException, ServletException
 	{                
-		getParts();
-		return _multiPartInputStream.getPart(name);
+		throw new UnsupportedOperationException();
 	}
 
 	/* ------------------------------------------------------------ */
 	public Collection<Part> getParts() throws IOException, ServletException
 	{
-		if (getContentType() == null || !getContentType().startsWith("multipart/form-data"))
-			throw new ServletException("Content-Type != multipart/form-data");
-		
-		if (_multiPartInputStream == null)
-			_multiPartInputStream = (MultiPartInputStream)getAttribute(__MULTIPART_INPUT_STREAM);
-		
-		if (_multiPartInputStream == null)
-		{
-			MultipartConfigElement config = (MultipartConfigElement)getAttribute(__MULTIPART_CONFIG_ELEMENT);
-			
-			if (config == null)
-				throw new IllegalStateException("No multipart config for servlet");
-			
-			_multiPartInputStream = new MultiPartInputStream(getInputStream(), 
-															 getContentType(), config, 
-															 (_context != null?(File)_context.getAttribute("javax.servlet.context.tempdir"):null));
-			
-			setAttribute(__MULTIPART_INPUT_STREAM, _multiPartInputStream);
-			setAttribute(__MULTIPART_CONTEXT, _context);
-			Collection<Part> parts = _multiPartInputStream.getParts(); //causes parsing 
-			for (Part p:parts)
-			{
-				MultiPartInputStream.MultiPart mp = (MultiPartInputStream.MultiPart)p;
-				if (mp.getContentDispositionFilename() == null)
-				{
-					//Servlet Spec 3.0 pg 23, parts without filenames must be put into init params
-					String charset = null;
-					if (mp.getContentType() != null)
-						charset = MimeTypes.getCharsetFromContentType(new ByteArrayBuffer(mp.getContentType()));
-
-					ByteArrayOutputStream os = null;
-					InputStream is = mp.getInputStream(); //get the bytes regardless of being in memory or in temp file
-					try
-					{
-						os = new ByteArrayOutputStream();
-						IO.copy(is, os);
-						String content=new String(os.toByteArray(),charset==null?StringUtil.__UTF8:charset);   
-						getParameter(""); //cause params to be evaluated
-						getParameters().add(mp.getName(), content);
-					}
-					finally
-					{
-						IO.close(os);
-						IO.close(is);
-					}
-				}
-			}
-		}
-
-		return _multiPartInputStream.getParts();
+		throw new UnsupportedOperationException();
 	}
 
 	/* ------------------------------------------------------------ */
--- a/src/org/eclipse/jetty/util/MultiPartInputStream.java	Wed Sep 21 15:02:19 2016 -0600
+++ b/src/org/eclipse/jetty/util/MultiPartInputStream.java	Wed Sep 21 16:15:19 2016 -0600
@@ -43,7 +43,6 @@
 import java.util.StringTokenizer;
 import java.util.Base64;
 
-import javax.servlet.MultipartConfigElement;
 import javax.servlet.ServletException;
 import javax.servlet.http.Part;
 
@@ -61,18 +60,13 @@
 {
 	private static final Logger LOG = LoggerFactory.getLogger(MultiPartInputStream.class);
 
-	public static final MultipartConfigElement  __DEFAULT_MULTIPART_CONFIG = new MultipartConfigElement(System.getProperty("java.io.tmpdir"));
 	protected InputStream _in;
-	protected MultipartConfigElement _config;
 	protected String _contentType;
 	protected MultiMap<String> _parts;
-	protected File _tmpDir;
-	protected File _contextTmpDir;
-	protected boolean _deleteOnExit;
 	
 	
 	
-	public class MultiPart implements Part
+	public final class MultiPart implements Part
 	{
 		protected String _name;
 		protected String _filename;
@@ -82,7 +76,6 @@
 		protected String _contentType;
 		protected MultiMap<String> _headers;
 		protected long _size = 0;
-		protected boolean _temporary = true;
 
 		public MultiPart (String name, String filename) 
 		throws IOException
@@ -125,11 +118,6 @@
 		protected void write (int b)
 		throws IOException
 		{      
-			if (MultiPartInputStream.this._config.getMaxFileSize() > 0 && _size + 1 > MultiPartInputStream.this._config.getMaxFileSize())
-				throw new IllegalStateException ("Multipart Mime part "+_name+" exceeds max filesize");
-			
-			if (MultiPartInputStream.this._config.getFileSizeThreshold() > 0 && _size + 1 > MultiPartInputStream.this._config.getFileSizeThreshold() && _file==null)
-				createFile();
 			_out.write(b);   
 			_size ++;
 		}
@@ -137,12 +125,6 @@
 		protected void write (byte[] bytes, int offset, int length) 
 		throws IOException
 		{ 
-			if (MultiPartInputStream.this._config.getMaxFileSize() > 0 && _size + length > MultiPartInputStream.this._config.getMaxFileSize())
-				throw new IllegalStateException ("Multipart Mime part "+_name+" exceeds max filesize");
-			
-			if (MultiPartInputStream.this._config.getFileSizeThreshold() > 0 && _size + length > MultiPartInputStream.this._config.getFileSizeThreshold() && _file==null)
-				createFile();
-			
 			_out.write(bytes, offset, length);
 			_size += length;
 		}
@@ -150,9 +132,8 @@
 		protected void createFile ()
 		throws IOException
 		{
-			_file = File.createTempFile("MultiPart", "", MultiPartInputStream.this._tmpDir);
-			if (_deleteOnExit)
-				_file.deleteOnExit();
+			_file = File.createTempFile("MultiPart", null);
+			_file.deleteOnExit();
 			FileOutputStream fos = new FileOutputStream(_file);
 			BufferedOutputStream bos = new BufferedOutputStream(fos);
 			
@@ -253,36 +234,7 @@
 		 */
 		public void write(String fileName) throws IOException
 		{
-			if (_file == null)
-			{
-				_temporary = false;
-				
-				//part data is only in the ByteArrayOutputStream and never been written to disk
-				_file = new File (_tmpDir, fileName);
-
-				BufferedOutputStream bos = null;
-				try
-				{
-					bos = new BufferedOutputStream(new FileOutputStream(_file));
-					_bout.writeTo(bos);
-					bos.flush();
-				}
-				finally
-				{
-					if (bos != null)
-						bos.close();
-					_bout = null;
-				}
-			}
-			else
-			{
-				//the part data is already written to a temporary file, just rename it
-				_temporary = false;
-				
-				File f = new File(_tmpDir, fileName);
-				if (_file.renameTo(f))
-					_file = f;
-			}
+			throw new UnsupportedOperationException();
 		}
 		
 		/** 
@@ -303,7 +255,7 @@
 		 */
 		public void cleanUp() throws IOException
 		{
-			if (_temporary && _file != null && _file.exists())
+			if (_file != null && _file.exists())
 				_file.delete();
 		}
 		
@@ -337,17 +289,10 @@
 	 * @param config MultipartConfigElement 
 	 * @param contextTmpDir javax.servlet.context.tempdir
 	 */
-	public MultiPartInputStream (InputStream in, String contentType, MultipartConfigElement config, File contextTmpDir)
+	public MultiPartInputStream (InputStream in, String contentType)
 	{
 		_in = new ReadLineInputStream(in);
 	   _contentType = contentType;
-	   _config = config;
-	   _contextTmpDir = contextTmpDir;
-	   if (_contextTmpDir == null)
-		   _contextTmpDir = new File (System.getProperty("java.io.tmpdir"));
-	   
-	   if (_config == null)
-		   _config = new MultipartConfigElement(_contextTmpDir.getAbsolutePath());
 	}
 
 	/**
@@ -455,24 +400,6 @@
 		//if its not a multipart request, don't parse it
 		if (_contentType == null || !_contentType.startsWith("multipart/form-data"))
 			return;
- 
-		//sort out the location to which to write the files
-		
-		if (_config.getLocation() == null)
-			_tmpDir = _contextTmpDir;
-		else if ("".equals(_config.getLocation()))
-			_tmpDir = _contextTmpDir;
-		else
-		{
-			File f = new File (_config.getLocation());
-			if (f.isAbsolute())
-				_tmpDir = f;
-			else
-				_tmpDir = new File (_contextTmpDir, _config.getLocation());
-		}
-	  
-		if (!_tmpDir.exists())
-			_tmpDir.mkdirs();
 
 		String contentTypeBoundary = "";
 		int bstart = _contentType.indexOf("boundary=");
@@ -540,8 +467,6 @@
 					break;
 				
 				total += line.length();
-				if (_config.getMaxRequestSize() > 0 && total > _config.getMaxRequestSize())
-					throw new IllegalStateException ("Request exceeds maxRequestSize ("+_config.getMaxRequestSize()+")");
 
 				//get content-disposition and content-type
 				int c=line.indexOf(':',0);
@@ -649,8 +574,6 @@
 					while((c=(state!=-2)?state:partInput.read())!=-1)
 					{
 						total ++;
-						if (_config.getMaxRequestSize() > 0 && total > _config.getMaxRequestSize())
-							throw new IllegalStateException("Request exceeds maxRequestSize ("+_config.getMaxRequestSize()+")");
 						
 						state=-2;
 						
@@ -740,17 +663,6 @@
 			throw new IOException("Incomplete parts");
 	}
 	
-	public void setDeleteOnExit(boolean deleteOnExit)
-	{
-		_deleteOnExit = deleteOnExit;
-	}
-
-
-	public boolean isDeleteOnExit()
-	{
-		return _deleteOnExit;
-	}
-
 
 	/* ------------------------------------------------------------ */
 	private String value(String nameEqualsValue, boolean splitAfterSpace)