从Java / J2EE应用程序将文件上载到SharePoint

我们需要从Java / J2EE应用程序向SharePoint上载大文件(最多200 MB)。

我们知道有一些现成的SharePoint Web服务允许将文件上传到SharePoint。 但是,我们主要担心的是并发用户上传文件会发生什么。 例如,在调用SharePoint发送该数据之前,我们需要为Java服务器(应用程序服务器)上的每个用户读取200 MB文件。 即使有5个并发用户,所消耗的内存大约为1 GB,并且CPU使用率也可能很高。 在这种情况下,是否有任何建议如何处理服务器内存,文件上传的并发性?

我认为一种选择可能是使用像Flash / Flex这样的技术,它们之间不需要其他服务器(Java应用服务器) – 但是,想知道如何在J2EE服务器中实现这一点?

HTTP://servername/sitename/_vti_bin/copy.asmx

谢谢

好的..所以这就是我的理解:

  • 您正在尝试使用Sharepoint Copy服务
  • 此服务要求流在Soap信封中进行base64编码。
  • 由于文件大小很大,因此SOAP请求大小变得庞大并需要更多内存

我可以想到两个选择:

  1. 我不太了解sharepoint,如果有可能提供要上传的文件的位置而不是发送字节,那么你可以将文件ftp / sftp发送到sharepoint服务器,然后使用文件的位置调用webservice。

  2. 在Java中,而不是使用开箱即用的api for SOAP消息,编写自定义api。 当用户上传文件时,将其另存为base64编码文件。 然后你的自定义api将创建一个soap消息并流式传输而不是将所有内容加载到内存中。

对于选项2:尝试是否可以将文件内容作为soap附件发送。 如果你想将它作为消息的一部分发送,它会变得有点复杂。

试试看。 我不确定是否有效。

SharePoint支持用于读取/写入文件的WebDAV协议。

您可以使用许多不需要在内存中加载完整文件的WebDAV库。

这是解决方案

import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.IOException; import java.net.Authenticator; import java.net.PasswordAuthentication; import java.security.cert.CertificateException; import javax.net.ssl.TrustManager; import javax.net.ssl.X509TrustManager; import javax.security.cert.X509Certificate; import javax.xml.ws.Holder; import org.apache.cxf.configuration.jsse.TLSClientParameters; import org.apache.cxf.configuration.security.AuthorizationPolicy; import org.apache.cxf.endpoint.Client; import org.apache.cxf.frontend.ClientProxy; import org.apache.cxf.interceptor.LoggingInInterceptor; import org.apache.cxf.interceptor.LoggingOutInterceptor; import org.apache.cxf.jaxws.JaxWsProxyFactoryBean; import org.apache.cxf.transport.http.HTTPConduit; import org.apache.cxf.transports.http.configuration.HTTPClientPolicy; import com.microsoft.schemas.sharepoint.soap.copy.CopyResultCollection; import com.microsoft.schemas.sharepoint.soap.copy.CopySoap; import com.microsoft.schemas.sharepoint.soap.copy.DestinationUrlCollection; import com.microsoft.schemas.sharepoint.soap.copy.FieldInformation; import com.microsoft.schemas.sharepoint.soap.copy.FieldInformationCollection; import com.microsoft.schemas.sharepoint.soap.copy.FieldType; public class Upload { private static String username = "yourusrename"; private static String password = "yourpassword"; private static String targetPath = "https://www.yoursite.target/filename"; private static String sourcePath = "file.txt"; private static String portUrl = "https://www.yoursite.com/_vti_bin/Copy.asmx"; private static CopySoap soapInstance; public static void main(String[] args) { activate(); CopySoap sqs = getInstance(); String url = targetPath; String sourceUrl = sourcePath; DestinationUrlCollection urls = new DestinationUrlCollection(); urls.getString().add(url); File file = null; byte[] content = null; try { FileInputStream fileStream = new FileInputStream(file = new File(sourceUrl)); ByteArrayOutputStream bos = new ByteArrayOutputStream(); byte[] buf = new byte[1024]; for (int readNum; (readNum = fileStream.read(buf)) != -1;) { bos.write(buf, 0, readNum); } content = bos.toByteArray(); } catch (FileNotFoundException e) { e.printStackTrace(); } catch (IOException ex) { ex.printStackTrace(); } FieldInformation titleInfo = new FieldInformation(); titleInfo.setDisplayName("testpage"); titleInfo.setType(FieldType.TEXT); titleInfo.setValue("Test Page"); FieldInformationCollection infos = new FieldInformationCollection(); infos.getFieldInformation().add(titleInfo); CopyResultCollection results = new CopyResultCollection(); Holder resultHolder = new Holder(results); Holder longHolder = new Holder(new Long(-1)); if (content != null) { sqs.copyIntoItems(sourceUrl, urls, infos, content, longHolder, resultHolder); } } private static void activate() { JaxWsProxyFactoryBean factory = new JaxWsProxyFactoryBean(); factory.setServiceClass(CopySoap.class); factory.setAddress(portUrl); factory.getInInterceptors().add(new LoggingInInterceptor()); factory.getOutInterceptors().add(new LoggingOutInterceptor()); soapInstance = (CopySoap) factory.create(); Authenticator.setDefault(new SPAuthenticator()); Client client = ClientProxy.getClient(soapInstance); HTTPConduit http = (HTTPConduit) client.getConduit(); HTTPClientPolicy httpClientPolicy = new HTTPClientPolicy(); httpClientPolicy.setConnectionTimeout(10000); httpClientPolicy.setAllowChunking(false); HTTPConduit conduit = (HTTPConduit) client.getConduit(); conduit.setClient(httpClientPolicy); TLSClientParameters tcp = new TLSClientParameters(); tcp.setTrustManagers(new TrustManager[] { (TrustManager) new TrustAllX509TrustManager() }); conduit.setTlsClientParameters(tcp); } public static CopySoap getInstance() { return soapInstance; } static class SPAuthenticator extends Authenticator { public PasswordAuthentication getPasswordAuthentication() { System.out.println("hitting SP with username and password for " + getRequestingScheme()); return (new PasswordAuthentication(username, password.toCharArray())); } } /** * This class allow any X509 certificates to be used to authenticate the * remote side of a secure socket, including self-signed certificates. */ public static class TrustAllX509TrustManager implements X509TrustManager { /** Empty array of certificate authority certificates. */ private static final X509Certificate[] acceptedIssuers = new X509Certificate[] {}; /** * Always trust for client SSL chain peer certificate chain with any * authType authentication types. * * @param chain * the peer certificate chain. * @param authType`enter * code here` the authentication type based on the client * certificate. */ public void checkClientTrusted(X509Certificate[] chain, String authType) { } /** * Always trust for server SSL chain peer certificate chain with any * authType exchange algorithm types. * * @param chain * the peer certificate chain. * @param authType * the key exchange algorithm used. */ public void checkServerTrusted(X509Certificate[] chain, String authType) { } /** * Return an empty array of certificate authority certificates which are * trusted for authenticating peers. * * @return a empty array of issuer certificates. */ public java.security.cert.X509Certificate[] getAcceptedIssuers() { return null; } @Override public void checkClientTrusted(java.security.cert.X509Certificate[] arg0, String arg1) throws CertificateException { // TODO Auto-generated method stub } @Override public void checkServerTrusted(java.security.cert.X509Certificate[] arg0, String arg1) throws CertificateException { // TODO Auto-generated method stub } } } 

可能是我错过了什么……但是当你让用户将文件上传到你的J2EE服务器时,你是不是首先将上传的内容写入临时目录然后将其流式传输到服务器?

当您将缓冲区立即写入磁盘时,您不会遇到内存限制的任何问题。

或采取对象

 @Autowired ServletContext c; byte[] bytes = file.getBytes(); String UPLOAD_FOLDEdR=c.getRealPath("/images"); Path path = Paths.get(UPLOAD_FOLDEdR+"/"+file.getOriginalFilename()); Files.write(path, bytes); String Pic_Name =file.getOriginalFilename() ;