View Javadoc
1   /**
2    * This file is part of Waarp Project.
3    *
4    * Copyright 2009, Frederic Bregier, and individual contributors by the @author tags. See the
5    * COPYRIGHT.txt in the distribution for a full listing of individual contributors.
6    *
7    * All Waarp Project is free software: you can redistribute it and/or modify it under the terms of
8    * the GNU General Public License as published by the Free Software Foundation, either version 3 of
9    * the License, or (at your option) any later version.
10   *
11   * Waarp is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even
12   * the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
13   * Public License for more details.
14   *
15   * You should have received a copy of the GNU General Public License along with Waarp . If not, see
16   * <http://www.gnu.org/licenses/>.
17   */
18  package org.waarp.gateway.ftp;
19  
20  import java.io.FileWriter;
21  import java.io.IOException;
22  import java.io.OutputStreamWriter;
23  import java.io.Writer;
24  import java.sql.Timestamp;
25  
26  import org.waarp.common.command.ReplyCode;
27  import org.waarp.common.database.DbPreparedStatement;
28  import org.waarp.common.database.exception.WaarpDatabaseNoConnectionException;
29  import org.waarp.common.database.exception.WaarpDatabaseSqlException;
30  import org.waarp.common.file.filesystembased.FilesystemBasedFileParameterImpl;
31  import org.waarp.common.utility.WaarpStringUtils;
32  import org.waarp.ftp.core.file.FtpDir;
33  import org.waarp.gateway.ftp.config.FileBasedConfiguration;
34  import org.waarp.gateway.ftp.control.ExecBusinessHandler;
35  import org.waarp.gateway.ftp.data.FileSystemBasedDataBusinessHandler;
36  import org.waarp.gateway.ftp.database.DbConstant;
37  import org.waarp.gateway.ftp.database.data.DbTransferLog;
38  
39  
40  
41  /**
42   * Program to export log history from database to a file and optionally
43   * purge exported entries.
44   *
45   * @author Bruno Carlin
46   *
47   */
48  public class LogExport {
49      /**
50       * Command Flags
51       */
52      private static boolean purge = false;
53      private static boolean correctOnly = false;
54      private static String destinationPath = null;
55      protected static Timestamp start;
56      protected static Timestamp stop;
57  
58      /**
59       * Internal pointer to the destination writer object
60       */
61      private static Writer destinationWriter = null;
62  
63      /**
64       * Internal pointer to the configuration
65       */
66      private static FileBasedConfiguration config;
67  
68      /**
69       * Usage for the command
70       */
71      private static String usage = "Need at least the configuration file as first argument then optionally\n"
72          + "    -correctOnly      Only exports successful transfers\n"
73          + "    -purge            Purge exported transfers\n"
74          + "    -out [filepath|-] The path to the file created\n"
75          + "                      Use '-' for stdout\n"
76          + "    -start timestamp  in format yyyyMMddHHmmssSSS possibly truncated and where one of ':-. ' can be separators\n"
77          + "    -stop timestamp   in same format than start\n";
78  
79      /**
80       * Verifies command line arguments and initialize internals (mainly config)
81       *
82       * @param  args command line arguments
83       * @return the result of the initialization. if an error occured at
84       *         this stage, return value will be false
85       */
86      protected static boolean initialize(String[] args) {
87          if (!getParams(args)) {
88              return false;
89          }
90  
91          config = new FileBasedConfiguration(
92              ExecGatewayFtpServer.class, ExecBusinessHandler.class,
93              FileSystemBasedDataBusinessHandler.class,
94              new FilesystemBasedFileParameterImpl());
95  
96          if (!config.setConfigurationServerFromXml(args[0])) {
97              System.err.println("Bad main configuration");
98              if (DbConstant.gatewayAdmin != null) {
99                  DbConstant.gatewayAdmin.close();
100             }
101             return false;
102         }
103 
104         FileBasedConfiguration.fileBasedConfiguration = config;
105 
106         return setDestinationWriter();
107     }
108 
109     /**
110      * Creates and sets destinationWriter according to the following logic
111      * based on the value of the '-out' command line argument:
112      * - if no value is given, a default path is computed (the same as
113      *   online export, i.e. in [data directory]/[admin name])
114      * - if the value '-' is given,
115      *   destinationWriter is the standard output (System.out)
116      * - if any other value is given, then it is considered as the path to
117      *   the destination file
118      *
119      * @return a bollean indicating the success in opening the Writer.
120      */
121     public static boolean setDestinationWriter() {
122         if (destinationPath == null) {
123             destinationPath = config.getBaseDirectory() +
124                 FtpDir.SEPARATOR + config.ADMINNAME + FtpDir.SEPARATOR +
125                 config.HOST_ID + "_logs_" + System.currentTimeMillis()
126                 + ".xml";
127         }
128 
129         if (destinationPath.equalsIgnoreCase("-")) {
130             destinationWriter = new OutputStreamWriter(System.out);
131         } else {
132             try {
133                 destinationWriter = new FileWriter(destinationPath);
134             } catch (IOException e) {
135                 System.err.println("Cannot open out file " + destinationPath);
136                 return false;
137             }
138         }
139         return true;
140     }
141 
142     /**
143      * Parses command line arguments
144      * @param  args command line arguments to parse
145      * @return      [description]
146      */
147     static protected boolean getParams(String[] args) {
148         if (args.length < 1) {
149             System.err.println(usage);
150             return false;
151         }
152 
153         for (int i = 1; i < args.length; i++) {
154             if (args[i].equalsIgnoreCase("-purge")) {
155                 purge = true;
156             } else if (args[i].equalsIgnoreCase("-correctOnly")) {
157                 correctOnly = true;
158             } else if (args[i].equalsIgnoreCase("-out")) {
159                 i++;
160                 if (i >= args.length
161                         || (args[i].charAt(0) == '-' && args[i].length() > 1)) {
162                     System.err.println("Error: -out needs a value.\n\n" + usage);
163                     return false;
164                 }
165                 destinationPath = args[i].trim();
166             } else if (args[i].equalsIgnoreCase("-start")) {
167                 i++;
168                 if (i >= args.length
169                         || (args[i].charAt(0) == '-' && args[i].length() > 1)) {
170                     System.err.println("Error: -start needs a value.\n\n" + usage);
171                     return false;
172                 }
173                 start = WaarpStringUtils.fixDate(args[i]);
174             } else if (args[i].equalsIgnoreCase("-stop")) {
175                 i++;
176                 if (i >= args.length
177                         || (args[i].charAt(0) == '-' && args[i].length() > 1)) {
178                     System.err.println("Error: -stop needs a value.\n\n" + usage);
179                     return false;
180                 }
181                 stop = WaarpStringUtils.fixDate(args[i]);
182             }
183         }
184         return true;
185     }
186 
187     /**
188      * Main logic for the command.
189      * @return      an error message or null
190      */
191     protected static String run() {
192         ReplyCode status = null;
193         if (correctOnly) {
194             status = ReplyCode.REPLY_226_CLOSING_DATA_CONNECTION;
195         }
196 
197         DbPreparedStatement preparedStatement = null;
198         try {
199             preparedStatement = DbTransferLog.getLogPrepareStament(
200                 DbConstant.gatewayAdmin.getSession(), start, stop, status);
201 
202         } catch (WaarpDatabaseNoConnectionException e) {
203             return "An error occured while connecting to the database: "
204                 + e.getMessage();
205 
206         } catch (WaarpDatabaseSqlException e) {
207             return "An error occured with the database: " + e.getMessage();
208         }
209 
210         return DbTransferLog.saveDbTransferLogFile(preparedStatement,
211             destinationWriter, purge);
212     }
213 
214     /**
215      * Command Entry point
216      * @param args command line arguments
217      */
218     public static void main(String[] args) {
219         try {
220             if (!initialize(args)) {
221                 System.exit(1);
222             }
223 
224             String message = run();
225 
226             if (message.contains("successfully")) {
227                 System.exit(0);
228             } else {
229                 System.err.println(message);
230                 System.exit(1);
231             }
232 
233         } finally {
234             if (DbConstant.gatewayAdmin != null) {
235                 DbConstant.gatewayAdmin.close();
236             }
237         }
238     }
239 }