本文目錄一覽:
java 上傳文件 問題
是通過數據流上傳嗎? 利用 B\S架構還是 C\S架構?
jsp文件上傳大多採用採用開源項目來簡化處理,這裡列出常用的兩個jar包的實現,並進行比較,說明他們的優缺點和應該注意的問題。
Commons FileUpload,可以在下載,這個包需要Commons IO的支持,可以在下載
com.oreilly.servlet,可以在下載
Commons FileUpload提供三種文件上傳處理方式,DiskFileUpload、ServletFileUpload和PortletFileUpload三種方式,其中DiskFileUpload已經在javadoc下已經被標記為過期的方法,建議用ServletFileUpload代替,而PortletFileUpload需要配合portlet-api來使用,所以這裡我們只介紹ServletFileUpload,並且這個也是最常用的。
com.oreilly.servlet也提供了三種文件上傳的處理方式,MultipartWrapper、MultipartRequest和MultipartParser三種方式,其中MultipartWrapper和MultipartRequest的用法基本相同,並且沒有MultipartRequest提供的操作多,所以這裡介紹MultipartRequest,MultipartParser和前兩者有些不同,可以用來處理某些特殊情況,例如表單中有兩個同名的文件上傳選擇框。
我們暫時稱三面三種文件上傳方式分別為:ServletFileUpload方式(MultipartTestServlet)、MultipartRequest方式(MultipartTestServlet2)、MultipartParser方式(MultipartTestServlet3)
代碼如下:
test.html
%@ page language=”java” import=”java.util.*” contentType=”text/html;charset=gbk” pageEncoding=”gbk”%
html
body
form action=”MultipartTestServlet” enctype=”multipart/form-data” method=”post”
input type=”text” name=”username” /br /
input type=”file” name=”myfile” /br/
input type=”file” name=”myfile” /br/
input type=”submit” /
/form
br/br/br/br/
form action=”MultipartTestServlet2″ enctype=”multipart/form-data” method=”post”
input type=”text” name=”username” /br /
input type=”file” name=”myfile” /br/
input type=”file” name=”myfile” /br/
input type=”submit” /
/form
br/br/br/br/
form action=”MultipartTestServlet3″ enctype=”multipart/form-data” method=”post”
input type=”text” name=”username” /br /
input type=”file” name=”myfile” /br/
input type=”file” name=”myfile” /br/
input type=”submit” /
/form
/body
/html
MultipartTestServlet.java
package com.bug.servlet;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileUpload;
import org.apache.commons.fileupload.FileUploadException;
import org.apache.commons.fileupload.RequestContext;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.commons.fileupload.servlet.ServletRequestContext;
public class MultipartTestServlet extends HttpServlet {
public MultipartTestServlet() {
super();
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
request.setCharacterEncoding(“gbk”);
RequestContext requestContext = new ServletRequestContext(request);
if(FileUpload.isMultipartContent(requestContext)){
DiskFileItemFactory factory = new DiskFileItemFactory();
factory.setRepository(new File(“c:/tmp/”));
ServletFileUpload upload = new ServletFileUpload(factory);
//upload.setHeaderEncoding(“gbk”);
upload.setSizeMax(2000000);
List items = new ArrayList();
try {
items = upload.parseRequest(request);
} catch (FileUploadException e1) {
System.out.println(“文件上傳發生錯誤” + e1.getMessage());
}
Iterator it = items.iterator();
while(it.hasNext()){
FileItem fileItem = (FileItem) it.next();
if(fileItem.isFormField()){
System.out.println(fileItem.getFieldName() + ” ” + fileItem.getName() + ” ” + new String(fileItem.getString().getBytes(“iso8859-1”), “gbk”));
}else{
System.out.println(fileItem.getFieldName() + ” ” +
fileItem.getName() + ” ” +
fileItem.isInMemory() + ” ” +
fileItem.getContentType() + ” ” +
fileItem.getSize());
if(fileItem.getName()!=null fileItem.getSize()!=0){
File fullFile = new File(fileItem.getName());
File newFile = new File(“c:/temp/” + fullFile.getName());
try {
fileItem.write(newFile);
} catch (Exception e) {
e.printStackTrace();
}
}else{
System.out.println(“文件沒有選擇 或 文件內容為空”);
}
}
}
}
}
}
MultipartTestServlet2.java
package com.bug.servlet;
import java.io.IOException;
import java.util.Enumeration;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import com.oreilly.servlet.MultipartRequest;
import com.oreilly.servlet.multipart.DefaultFileRenamePolicy;
public class MultipartTestServlet2 extends HttpServlet {
public MultipartTestServlet2() {
super();
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//request.setCharacterEncoding(“gbk”); 不起作用
System.out.println(“start “);
MultipartRequest multi = new MultipartRequest(request, “c:/tmp/”, 2*1024*1024, “gbk”, new DefaultFileRenamePolicy());
System.out.println(“start “);
Enumeration filesName = multi.getFileNames();
Enumeration paramsName = multi.getParameterNames();
while(paramsName.hasMoreElements()){
String paramName = (String) paramsName.nextElement();
System.out.println(multi.getParameter(paramName));
}
while(filesName.hasMoreElements()){
String fileName = (String) filesName.nextElement();
System.out.println(multi.getFilesystemName(fileName) + ” ” +
multi.getOriginalFileName(fileName) + ” ” +
multi.getContentType(fileName) + ” “);
if(multi.getFilesystemName(fileName)!=null !multi.getFilesystemName(fileName).equals(“”))
System.out.println(multi.getFile(fileName).toURI());
}
}
}
MultipartTestServlet3.java
package com.bug.servlet;
import java.io.File;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import com.oreilly.servlet.multipart.FilePart;
import com.oreilly.servlet.multipart.MultipartParser;
import com.oreilly.servlet.multipart.ParamPart;
import com.oreilly.servlet.multipart.Part;
public class MultipartTestServlet3 extends HttpServlet {
public MultipartTestServlet3() {
super();
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
MultipartParser mp = new MultipartParser(request, 2*1024*1024, false, false, “gbk”);
Part part;
while ((part = mp.readNextPart()) != null) {
String name = part.getName();
if (part.isParam()) {
ParamPart paramPart = (ParamPart) part;
String value = paramPart.getStringValue();
System.out.println(“param: name=” + name + “; value=” + value);
}
else if (part.isFile()) {
// it’s a file part
FilePart filePart = (FilePart) part;
String fileName = filePart.getFileName();
if (fileName != null) {
long size = filePart.writeTo(new File(“c:/tmp/”));
System.out.println(“file: name=” + name + “; fileName=” + fileName +
“, filePath=” + filePart.getFilePath() +
“, contentType=” + filePart.getContentType() +
“, size=” + size);
}
else {
System.out.println(“file: name=” + name + “; EMPTY”);
}
System.out.flush();
}
}
}
}
web.xml中加入
servlet
servlet-nameMultipartTestServlet/servlet-name
servlet-classcom.bug.servlet.MultipartTestServlet/servlet-class
/servlet
servlet
servlet-nameMultipartTestServlet2/servlet-name
servlet-classcom.bug.servlet.MultipartTestServlet2/servlet-class
/servlet
servlet
servlet-nameMultipartTestServlet3/servlet-name
servlet-classcom.bug.servlet.MultipartTestServlet3/servlet-class
/servlet
servlet-mapping
servlet-nameMultipartTestServlet/servlet-name
url-pattern/MultipartTestServlet/url-pattern
/servlet-mapping
servlet-mapping
servlet-nameMultipartTestServlet2/servlet-name
url-pattern/MultipartTestServlet2/url-pattern
/servlet-mapping
servlet-mapping
servlet-nameMultipartTestServlet3/servlet-name
url-pattern/MultipartTestServlet3/url-pattern
/servlet-mapping
問題1、中文問題:
三種凡是都可以通過自己的方法來設置encoding為gbk開處理和解決中文問題,包括初始化的時候傳入gbk作為參數,或是是初始化後通過setEncoding的方式來實現。
另外ServletFileUpload方式也可以通過request.setCharacterEncoding(“gbk”);的方式來實現,而其它兩種方式不支持這種方式。
問題2、文件大小限制
ServletFileUpload方式可以設置文件大小限制,也可以不用設置,例子中的upload.setSizeMax(2000000)就可以注釋掉。如果設置upload.setSizeMax(-1),表明不限制上傳的大小。文檔中沒有指明默認的限制的多少,我在不設置的情況下上傳了一個9M的東西,可以上傳,估計默認是不限制大小的。
而MultipartRequest方式和MultipartParser方式是必須設置文件的上傳文件的大小限制的,如果不設置,默認是1M的大小限制。
問題3、文件上傳發生錯誤
如果文件上傳過程中發生任何錯誤,或者是文件的大小超出了範圍,系統都將拋出錯誤。
ServletFileUpload方式在upload.parseRequest(request)時拋出錯誤
MultipartRequest方式在new MultipartRequest(。。。)時拋出錯誤
MultipartParser方式在new MultipartParser(。。。)時拋出錯誤
問題4、上傳同名文件時,他們保存到臨時目錄是的衝突問題
ServletFileUpload方式,不會有衝突,系統會把上傳得文件按照一定的規則重新命名,保證不會衝突
MultipartParser方式,會產生衝突,系統會把文件按照上傳時的文件名,保存到臨時目錄下,如果兩個用會同時上傳文件名相同的文件,那麼就可能會產生衝突,一方把另一方的臨時文件給替換了。
MultipartRequest方式,在初始化時如果提供了一個名稱轉換策略,就不會有衝突,如果不提桶,就會有衝突。在上面的例子中我們提供了一個new DefaultFileRenamePolicy()保證了文件名不會有衝突發生。
問題5:表單中有兩個同名的文件上傳選擇框,就像我們例子中的myfile一樣,每個表單中有兩個name=「myfile」的上傳框
ServletFileUpload方式,可以處理,可以分別得到他們各自的文件,
MultipartRequest方式,不可以處理,會發生衝突,會有一個上傳框的文件覆蓋了另外一個。
MultipartParser方式,可以處理,可以分別得到他們各自的文件,
備註:
代碼比較亂,主要是為了說明他們間的區別。他們的詳細地使用說明還是要參考他的javadoc和domo。
java如何實現文件上傳
public static int transFile(InputStream in, OutputStream out, int fileSize) {
int receiveLen = 0;
final int bufSize = 1000;
try {
byte[] buf = new byte[bufSize];
int len = 0;
while(fileSize – receiveLen bufSize)
{
len = in.read(buf);
out.write(buf, 0, len);
out.flush();
receiveLen += len;
System.out.println(len);
}
while(receiveLen fileSize)
{
len = in.read(buf, 0, fileSize – receiveLen);
System.out.println(len);
out.write(buf, 0, len);
receiveLen += len;
out.flush();
}
} catch (IOException e) {
// TODO 自動生成 catch 塊
e.printStackTrace();
}
return receiveLen;
}
這個方法從InputStream中讀取內容,寫到OutputStream中。
那麼發送文件方,InputStream就是FileInputStream,OutputStream就是Socket.getOutputStream.
接受文件方,InputStream就是Socket.getInputStream,OutputStream就是FileOutputStream。
就OK了。 至於存到資料庫里嘛,Oracle里用Blob。搜索一下,也是一樣的。從Blob能獲取一個輸出流。
java後台文件上傳到資源伺服器上
package com.letv.dir.cloud.util;import com.letv.dir.cloud.controller.DirectorWatermarkController;import org.slf4j.Logger;import org.slf4j.LoggerFactory;import java.io.*;import java.net.HttpURLConnection;import java.net.MalformedURLException;import java.net.URL;/** * Created by xijunge on 2016/11/24 0024. */public class HttpRequesterFile { private static final Logger log = LoggerFactory.getLogger(HttpRequesterFile.class); private static final String TAG = “uploadFile”; private static final int TIME_OUT = 100 * 1000; // 超時時間 private static final String CHARSET = “utf-8”; // 設置編碼 /** * 上傳文件到伺服器 * * @param file * 需要上傳的文件 * @param RequestURL * 文件伺服器的rul * @return 返迴響應的內容 * */ public static String uploadFile(File file, String RequestURL) throws IOException {
String result = null;
String BOUNDARY = “letv”; // 邊界標識 隨機生成 String PREFIX = “–“, LINE_END = “\r\n”;
String CONTENT_TYPE = “multipart/form-data”; // 內容類型 try {
URL url = new URL(RequestURL);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setReadTimeout(TIME_OUT);
conn.setConnectTimeout(TIME_OUT);
conn.setDoInput(true); // 允許輸入流 conn.setDoOutput(true); // 允許輸出流 conn.setUseCaches(false); // 不允許使用緩存 conn.setRequestMethod(“POST”); // 請求方式 conn.setRequestProperty(“Charset”, CHARSET); // 設置編碼 conn.setRequestProperty(“connection”, “keep-alive”);
conn.setRequestProperty(“Content-Type”, CONTENT_TYPE + “;boundary=” + BOUNDARY);
java怎麼實現上傳文件到伺服器
common-fileupload是jakarta項目組開發的一個功能很強大的上傳文件組件
下面先介紹上傳文件到伺服器(多文件上傳):
import javax.servlet.*;
import javax.servlet.http.*;
import java.io.*;
import java.util.*;
import java.util.regex.*;
import org.apache.commons.fileupload.*;
public class upload extends HttpServlet {
private static final String CONTENT_TYPE = “text/html; charset=GB2312”;
//Process the HTTP Post request
public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
response.setContentType(CONTENT_TYPE);
PrintWriter out=response.getWriter();
try {
DiskFileUpload fu = new DiskFileUpload();
// 設置允許用戶上傳文件大小,單位:位元組,這裡設為2m
fu.setSizeMax(2*1024*1024);
// 設置最多只允許在內存中存儲的數據,單位:位元組
fu.setSizeThreshold(4096);
// 設置一旦文件大小超過getSizeThreshold()的值時數據存放在硬碟的目錄
fu.setRepositoryPath(“c://windows//temp”);
//開始讀取上傳信息
List fileItems = fu.parseRequest(request);
// 依次處理每個上傳的文件
Iterator iter = fileItems.iterator();
//正則匹配,過濾路徑取文件名
String regExp=”.+////(.+)$”;
//過濾掉的文件類型
String[] errorType={“.exe”,”.com”,”.cgi”,”.asp”};
Pattern p = Pattern.compile(regExp);
while (iter.hasNext()) {
FileItem item = (FileItem)iter.next();
//忽略其他不是文件域的所有表單信息
if (!item.isFormField()) {
String name = item.getName();
long size = item.getSize();
if((name==null||name.equals(“”)) size==0)
continue;
Matcher m = p.matcher(name);
boolean result = m.find();
if (result){
for (int temp=0;tempERRORTYPE.LENGTH;TEMP++){
if (m.group(1).endsWith(errorType[temp])){
throw new IOException(name+”: wrong type”);
}
}
try{
//保存上傳的文件到指定的目錄
//在下文中上傳文件至資料庫時,將對這裡改寫
item.write(new File(“d://” + m.group(1)));
out.print(name+” “+size+””);
}
catch(Exception e){
out.println(e);
}
}
else
{
throw new IOException(“fail to upload”);
}
}
}
}
catch (IOException e){
out.println(e);
}
catch (FileUploadException e){
out.println(e);
}
}
}
現在介紹上傳文件到伺服器,下面只寫出相關代碼:
以sql2000為例,表結構如下:
欄位名:name filecode
類型: varchar image
資料庫插入代碼為:PreparedStatement pstmt=conn.prepareStatement(“insert into test values(?,?)”);
代碼如下:
。。。。。。
try{
這段代碼如果不去掉,將一同寫入到伺服器中
//item.write(new File(“d://” + m.group(1)));
int byteread=0;
//讀取輸入流,也就是上傳的文件內容
InputStream inStream=item.getInputStream();
pstmt.setString(1,m.group(1));
pstmt.setBinaryStream(2,inStream,(int)size);
pstmt.executeUpdate();
inStream.close();
out.println(name+” “+size+” “);
}
。。。。。。
這樣就實現了上傳文件至資料庫
java代碼怎樣實現自動上傳文件
java上傳這塊主要是位元組流的讀寫,建議採用第三方上傳組件來做,畢竟你這邊自己寫的效果性能沒有第三方優化,例如採用:apache開源的commons-fileupload.jar,具體怎麼使用你自己研究一下吧。
原創文章,作者:小藍,如若轉載,請註明出處:https://www.506064.com/zh-tw/n/233917.html