001/*
002 * Copyright (c) 2009 The openGion Project.
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *     http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
013 * either express or implied. See the License for the specific language
014 * governing permissions and limitations under the License.
015 */
016package org.opengion.fukurou.transfer;
017
018import java.io.BufferedOutputStream;
019import java.io.File;
020import java.io.FileOutputStream;
021import java.io.IOException;
022import java.io.InputStream;
023import java.io.OutputStream;
024
025import org.opengion.fukurou.db.Transaction;
026import org.opengion.fukurou.util.Closer;
027import org.opengion.fukurou.util.StringUtil;
028import org.opengion.fukurou.util.URLConnect;
029
030/**
031 * 伝送要求に対してファイルを取得し、ローカルサーバーに保存します。
032 *
033 * この実行方法は、読取方法がHTTP受信(ファイル一覧)(HTTP_FILELIST)のみ使用することができます。
034 * HTTP受信(ファイル一覧)により取得されたファイル一覧の各ファイルに対して、URL接続を行い、
035 * 実行対象で指定された保存先にファイルを保存します。
036 *
037 * @og.group 伝送システム
038 *
039 * @version  5.0
040 * @author   Hiroki.Nakamura
041 * @since    JDK1.6
042 */
043public class TransferExec_FILEGET implements TransferExec {
044
045        // リモートコントロールサーブレット
046        protected static final String REMOTE_SERVLET = "servlet/remoteControl";
047
048        /**
049         * ファイルに書込みします。
050         *
051         * @param vals 伝送データ(配列)
052         * @param config 伝送設定オブジェクト
053         * @param tran トランザクションオブジェクト
054         */
055        @Override
056        public void execute( final String[] vals, final TransferConfig config, final Transaction tran ) {
057                if( vals == null || vals.length == 0 ) { return; }
058
059                String kbRead = config.getKbRead();
060                if( !"HTTP_FILELIST".equals( kbRead ) ) {
061                        String errMsg = "実行方法(ファイル取得(FILEGET))を利用する場合、"
062                                                        + "読取方法はHTTP受信(ファイル一覧)(HTTP_FILELIST)を指定して下さい。"
063                                                        + "KBREAD=[" + kbRead + "]";
064                        throw new RuntimeException( errMsg );
065                }
066
067                String[] readObjArr = StringUtil.csv2Array( config.getReadObj(), ' ' );
068                if( readObjArr[0] == null || readObjArr[0].length() == 0 ) {
069                        String errMsg = "受信元基準ディレクトリが取得できません。[READOBJ=" + config.getReadObj() + "]";
070                        throw new RuntimeException( errMsg );
071                }
072                File remoteFileDir = new File( readObjArr[0] );
073
074                String hostPort = readObjArr[1];
075                if( hostPort == null || hostPort.length() == 0 ) {
076                        String errMsg = "受信ホスト名が取得できません。[READOBJ=" + config.getReadObj() + "]";
077                        throw new RuntimeException( errMsg );
078                }
079
080                String saveBasePath = new File( config.getExecObj() ).getAbsolutePath();
081
082                for( String val : vals ) {
083                        String saveFileName = null;
084                        if( remoteFileDir.isDirectory() ) {
085                                // 読取元がディレクトリの場合は、保存基準ディレクトリに相対パス名を付加して保存
086                                saveFileName = saveBasePath + val.replace( remoteFileDir.getAbsolutePath(), "" );
087                        }
088                        else {
089                                // 読取元がファイルの場合は、保存基準ディレクトリ+ファイル名で保存
090                                String fileName = new File( val ).getName();
091                                saveFileName = saveBasePath + File.separatorChar + fileName;
092                        }
093
094                        File saveFile = new File( saveFileName );
095                        File parent = saveFile.getParentFile();
096                        if( !parent.exists() && !parent.mkdirs() ) {
097                                String errMsg = "保存ディレクトリの作成に失敗しました。file=[" + saveFileName + "]";
098                                throw new RuntimeException( errMsg );
099                        }
100
101                        URLConnect conn = null;
102                        InputStream is = null;
103                        OutputStream os = null;
104                        try {
105                                String url = hostPort + REMOTE_SERVLET + "?file=" + StringUtil.urlEncode( val );
106
107                                conn = new URLConnect( url, TransferConfig.HTTP_AUTH_USER_PASS );
108                                if( config.getProxyHost() != null && config.getProxyHost().length() > 0 ) {
109                                        conn.setProxy( config.getProxyHost(),config.getProxyPort() );
110                                }
111
112                                conn.setCharset( "UTF-8" );
113                                conn.connect();
114                                is = conn.getInputStream();
115
116                                os = new BufferedOutputStream( new FileOutputStream( saveFileName ) );
117                                byte buf[] = new byte[4096];
118                                int len = 0;
119                                while( ( len = is.read( buf ) ) != -1 ) {
120                                        os.write( buf, 0 ,len );
121                                }
122                                os.flush();
123                        }
124                        catch( IOException ex ) {
125                                String errMsg = "ファイル取得時にエラーが発生しました。file=[" + val + "]";
126                                throw new RuntimeException( errMsg, ex );
127                        }
128                        finally {
129                                Closer.ioClose( os );
130                                Closer.ioClose( is );
131
132                                if( conn != null ) { conn.disconnect(); }
133                        }
134                }
135        }
136}