基於hessian的文件傳輸 (轉)

基於hessian的文件傳輸html

一般文件傳輸建議仍是經過 ftp ,只有當 ftp 知足不了需求時,才考慮 hessian 的傳輸方案。java

Hessian 傳文件的應用場景有好比兩臺須要傳輸文件的服務器之間的網絡狀況限制比較嚴格,不容許 ftp 或新開端口之類;兩臺服務器之間傳文件必須通過一臺中間機器中轉。還有就是得到比 ftp 傳輸更大的靈活性。上面的一些應用場景,都是在項目裏實際遇到的。服務器

Hessian 是不支持 File 的直接傳輸的,因此採起的方案是將 File 讀到 byte[] 再用 hessian 傳輸。
  
不過最新的
 hessian4.0 已經支持 InputStream 做爲參數或返回值進行傳輸。網絡

說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif    public  String uploadStream(String filename, InputStream data)
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedBlockStart.gif    
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif        HessianInerface hessianInerface 
 =  (HessianInerface) getHessianInterface();
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif        
 return  hessianInerface.uploadStream(filename, data);
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedBlockEnd.gif    }
jvm


可是以上2中方法都會有個問題,就是當文件比較大的時候,會報java.lang.OutOfMemoryErrorui

基於 byte[] 的方法的解決辦法是將大的文件分紅一小塊一小塊進行傳輸。url

說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif   public  String uploadSingleFiles(File file)
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedBlockStart.gif    
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif        String logicPath 
 =   "" ;
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif        InputStream is 
 =   null ;
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif        
 try 
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif         
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif            
 byte [] buffer  =   null ;
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif            HessianInerface hessianInerface 
 =  (HessianInerface) getHessianInterface();
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif            is 
 =   new  FileInputStream(file);
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif            
 long  size  =  file.length();
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif            
 long  perSize  =  onePerSize;
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif            
 if  (size  >  onePerSize)
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif            
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                
 long  index  =  size  /  perSize;
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                
 if  (size  >  perSize  *  index)
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif                
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                    index 
 =  index  +   1 ;
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif                }
 
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif 
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                
 for  ( long  j  =   1 ; j  <=  index; j ++ )
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif                
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                    
 long  curPerSize  =  perSize;
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                    
 if  (j  ==  index)
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif                    
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                        curPerSize 
 =  size  -  perSize  *  (j  -   1 );
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif                    }
 
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif 
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                    buffer 
 =   new   byte [( int ) curPerSize];
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                    is.read(buffer);
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                    
 if  (j  ==   1 )
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif                    
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                        logicPath 
 =  hessianInerface.uploadSingleBigFile(buffer,
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                                file.getName(), 
 false );
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif                    }
   else 
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif                     
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                        logicPath 
 =  hessianInerface.uploadSingleBigFile(buffer,
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                                file.getName(), 
 true );
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif                    }
 
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif 
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif                }
 
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif 
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif            }
   else 
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif             
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                buffer 
 =   new   byte [is.available()];
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                is.read(buffer);
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                logicPath 
 =  hessianInerface.uploadSingleFile(buffer, file
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif                        .getName());
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif            }
 
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif 
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif        }
   catch  (IOException e)
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif        
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif            
 throw   new  RuntimeException(e);
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif        }
   finally 
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockStart.gif         
 {
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif            IOUtils.closeQuietly(is);
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedSubBlockEnd.gif        }
 
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif 
說明: http://www.blogjava.net/Images/OutliningIndicators/InBlock.gif        
 return  logicPath;
說明: http://www.blogjava.net/Images/OutliningIndicators/ExpandedBlockEnd.gif    }
 
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
spa



基於 InputStream 的解決辦法,最初想法講 InputStream 分塊讀出傳輸,不過沒成功,若是誰成功,請告訴我一聲。.net

總結,若是 jvm 的內存設置比較大, InputStream 的方式是能夠直接傳輸的,而 byte[] 的方式超過必定的大小就報錯,在個人機器上大概 20M 左右。因此基於 byte[] 的分塊傳輸是目前比較合理的解決辦法。htm

代碼比較多,我就不一一帖出了,在最後放出下載的連接,在服務端的實現類請根據本身的需求稍微修改下就能運行起來。

使用方法示例以下 :

說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif HessianClient cl  =   new  HessianClient();
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif cl.setHessianserviceurl(
 http://127.0.0.1:80/hessianService );
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif 
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif            
 long  onePerSize  =   2080000 ;
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif          cl.setOnePerSize(onePerSize);
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif         File file1 
 =   new  File( " d:\\tddownload\\CJT.rar " );
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif        cl.uploadSingleFiles(file1)  ;
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif 
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif        File ff
 =    cl.downloadSingleBigFile( 23884L , " 中文9999.rar " )  ;
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif
說明: http://www.blogjava.net/Images/OutliningIndicators/None.gif

 

代碼還能夠繼續完善的地方,好比加入文件的完整性校驗,壓縮傳輸等。
代碼下載地址:
http://www.blogjava.net/Files/magicdoom/hessianTransferFile.rar

相關文章
相關標籤/搜索