001package lucee.runtime.net.ftp;
002
003import java.io.IOException;
004import java.io.InputStream;
005import java.io.OutputStream;
006import java.net.InetAddress;
007import java.net.Socket;
008import java.net.SocketException;
009
010import org.apache.commons.net.ftp.FTPFile;
011
012public abstract class AFTPClient {
013
014        public final static int FILE_TYPE_BINARY=1;
015        public final static int FILE_TYPE_TEXT=2;
016        
017        public static AFTPClient getInstance(boolean secure, InetAddress host, int port, String username, String password, String fingerprint, boolean stopOnError) throws SocketException, IOException {
018                AFTPClient client=secure?new SFTPClientImpl():new FTPClientImpl();
019                client.init(host, port, username, password, fingerprint, stopOnError);
020                return client;
021        }
022
023        /**
024     * Renames a remote file.
025     * <p>
026     * @param from  The name of the remote file to rename.
027     * @param to    The new name of the remote file.
028     * @return True if successfully completed, false if not.
029     * @exception FTPConnectionClosedException
030     *      If the FTP server prematurely closes the connection as a result
031     *      of the client being idle or some other reason causing the server
032     *      to send FTP reply code 421.  This exception may be caught either
033     *      as an IOException or independently as itself.
034     * @exception IOException  If an I/O error occurs while either sending a
035     *      command to the server or receiving a reply from the server.
036         * @throws FTPException 
037     */
038    public abstract boolean rename(String from, String to) throws IOException;
039
040        /***
041     * Returns the integer value of the reply code of the last FTP reply.
042     * You will usually only use this method after you connect to the
043     * FTP server to check that the connection was successful since
044     * <code> connect </code> is of type void.
045     * <p>
046     * @return The integer value of the reply code of the last FTP reply.
047     ***/
048    public abstract int getReplyCode();
049
050            /***
051     * Returns the entire text of the last FTP server response exactly
052     * as it was received, including all end of line markers in NETASCII
053     * format.
054     * <p>
055     * @return The entire text from the last FTP response as a String.
056     ***/
057    public abstract String getReplyString();
058
059    /**
060     * Change the current working directory of the FTP session.
061     * <p>
062     * @param pathname  The new current working directory.
063     * @return True if successfully completed, false if not.
064     * @exception FTPConnectionClosedException
065     *      If the FTP server prematurely closes the connection as a result
066     *      of the client being idle or some other reason causing the server
067     *      to send FTP reply code 421.  This exception may be caught either
068     *      as an IOException or independently as itself.
069     * @exception IOException  If an I/O error occurs while either sending a
070     *      command to the server or receiving a reply from the server.
071     */
072    public abstract boolean changeWorkingDirectory(String pathname) throws IOException;
073
074        /**
075     * Creates a new subdirectory on the FTP server in the current directory
076     * (if a relative pathname is given) or where specified (if an absolute
077     * pathname is given).
078     * <p>
079     * @param pathname The pathname of the directory to create.
080     * @return True if successfully completed, false if not.
081     * @exception FTPConnectionClosedException
082     *      If the FTP server prematurely closes the connection as a result
083     *      of the client being idle or some other reason causing the server
084     *      to send FTP reply code 421.  This exception may be caught either
085     *      as an IOException or independently as itself.
086     * @exception IOException  If an I/O error occurs while either sending a
087     *      command to the server or receiving a reply from the server.
088     */
089    public abstract boolean makeDirectory(String pathname) throws IOException;
090
091            /**
092     * Using the default system autodetect mechanism, obtain a
093     * list of file information for the current working directory
094     * or for just a single file.
095     * <p>
096     * This information is obtained through the LIST command.  The contents of
097     * the returned array is determined by the<code> FTPFileEntryParser </code>
098     * used.
099     * <p>
100     * @param pathname  The file or directory to list.  Since the server may
101     *                  or may not expand glob expressions, using them here
102     *                  is not recommended and may well cause this method to
103     *                  fail.
104     *                  Also, some servers treat a leading '-' as being an option.
105     *                  To avoid this interpretation, use an absolute pathname
106     *                  or prefix the pathname with ./ (unix style servers).
107     *                  Some servers may support "--" as meaning end of options,
108     *                  in which case "-- -xyz" should work.
109     *
110     * @return The list of file information contained in the given path in
111     *         the format determined by the autodetection mechanism
112     * @exception FTPConnectionClosedException
113     *                   If the FTP server prematurely closes the connection
114     *                   as a result of the client being idle or some other
115     *                   reason causing the server to send FTP reply code 421.
116     *                   This exception may be caught either as an IOException
117     *                   or independently as itself.
118     * @exception IOException
119     *                   If an I/O error occurs while either sending a
120     *                   command to the server or receiving a reply
121     *                   from the server.
122     * @exception org.apache.commons.net.ftp.parser.ParserInitializationException
123     *                   Thrown if the parserKey parameter cannot be
124     *                   resolved by the selected parser factory.
125     *                   In the DefaultFTPEntryParserFactory, this will
126     *                   happen when parserKey is neither
127     *                   the fully qualified class name of a class
128     *                   implementing the interface
129     *                   org.apache.commons.net.ftp.FTPFileEntryParser
130     *                   nor a string containing one of the recognized keys
131     *                   mapping to such a parser or if class loader
132     *                   security issues prevent its being loaded.
133     */
134    public abstract FTPFile[] listFiles(String pathname) throws IOException;
135
136    /**
137     * Removes a directory on the FTP server (if empty).
138     * <p>
139     * @param pathname  The pathname of the directory to remove.
140     * @param recursive  if true it also can delete 
141     * @return True if successfully completed, false if not.
142     * @exception FTPConnectionClosedException
143     *      If the FTP server prematurely closes the connection as a result
144     *      of the client being idle or some other reason causing the server
145     *      to send FTP reply code 421.  This exception may be caught either
146     *      as an IOException or independently as itself.
147     * @exception IOException  If an I/O error occurs while either sending a
148     *      command to the server or receiving a reply from the server.
149     */
150    public abstract boolean removeDirectory(String pathname) throws IOException;
151
152        /**
153     * Sets the file type to be transferred.  This should be one of
154     * <code> FTP.ASCII_FILE_TYPE </code>, <code> FTP.BINARY_FILE_TYPE</code>,
155     * etc.  The file type only needs to be set when you want to change the
156     * type.  After changing it, the new type stays in effect until you change
157     * it again.  The default file type is <code> FTP.ASCII_FILE_TYPE </code>
158     * if this method is never called.
159     * <br>
160     * The server default is supposed to be ASCII (see RFC 959), however many
161     * ftp servers default to BINARY. <b>To ensure correct operation with all servers,
162     * always specify the appropriate file type after connecting to the server.</b>
163     * <br>
164     * <p>
165     * <b>N.B.</b> currently calling any connect method will reset the type to
166     * FTP.ASCII_FILE_TYPE.
167     * @param fileType The <code> _FILE_TYPE </code> constant indcating the
168     *                 type of file.
169     * @return True if successfully completed, false if not.
170     * @exception FTPConnectionClosedException
171     *      If the FTP server prematurely closes the connection as a result
172     *      of the client being idle or some other reason causing the server
173     *      to send FTP reply code 421.  This exception may be caught either
174     *      as an IOException or independently as itself.
175     * @exception IOException  If an I/O error occurs while either sending a
176     *      command to the server or receiving a reply from the server.
177     */
178    public abstract boolean setFileType(int fileType) throws IOException;
179
180        /**
181     * Retrieves a named file from the server and writes it to the given
182     * OutputStream.  This method does NOT close the given OutputStream.
183     * If the current file type is ASCII, line separators in the file are
184     * converted to the local representation.
185     * <p>
186     * Note: if you have used {@link #setRestartOffset(long)},
187     * the file data will start from the selected offset.
188     * @param remote  The name of the remote file.
189     * @param local   The local OutputStream to which to write the file.
190     * @return True if successfully completed, false if not.
191     * @exception FTPConnectionClosedException
192     *      If the FTP server prematurely closes the connection as a result
193     *      of the client being idle or some other reason causing the server
194     *      to send FTP reply code 421.  This exception may be caught either
195     *      as an IOException or independently as itself.
196     * @exception org.apache.commons.net.io.CopyStreamException
197     *      If an I/O error occurs while actually
198     *      transferring the file.  The CopyStreamException allows you to
199     *      determine the number of bytes transferred and the IOException
200     *      causing the error.  This exception may be caught either
201     *      as an IOException or independently as itself.
202     * @exception IOException  If an I/O error occurs while either sending a
203     *      command to the server or receiving a reply from the server.
204     */
205    public abstract boolean retrieveFile(String remote, OutputStream local) throws IOException;
206
207        /**
208     * Stores a file on the server using the given name and taking input
209     * from the given InputStream.  This method does NOT close the given
210     * InputStream.  If the current file type is ASCII, line separators in
211     * the file are transparently converted to the NETASCII format (i.e.,
212     * you should not attempt to create a special InputStream to do this).
213     * <p>
214     * @param remote  The name to give the remote file.
215     * @param local   The local InputStream from which to read the file.
216     * @return True if successfully completed, false if not.
217     * @exception FTPConnectionClosedException
218     *      If the FTP server prematurely closes the connection as a result
219     *      of the client being idle or some other reason causing the server
220     *      to send FTP reply code 421.  This exception may be caught either
221     *      as an IOException or independently as itself.
222     * @exception org.apache.commons.net.io.CopyStreamException
223     *      If an I/O error occurs while actually
224     *      transferring the file.  The CopyStreamException allows you to
225     *      determine the number of bytes transferred and the IOException
226     *      causing the error.  This exception may be caught either
227     *      as an IOException or independently as itself.
228     * @exception IOException  If an I/O error occurs while either sending a
229     *      command to the server or receiving a reply from the server.
230     */
231    public abstract boolean storeFile(String remote, InputStream local) throws IOException;
232
233        /**
234     * Deletes a file on the FTP server.
235     * <p>
236     * @param pathname   The pathname of the file to be deleted.
237     * @return True if successfully completed, false if not.
238     * @exception FTPConnectionClosedException
239     *      If the FTP server prematurely closes the connection as a result
240     *      of the client being idle or some other reason causing the server
241     *      to send FTP reply code 421.  This exception may be caught either
242     *      as an IOException or independently as itself.
243     * @exception IOException  If an I/O error occurs while either sending a
244     *      command to the server or receiving a reply from the server.
245     */
246    public abstract boolean deleteFile(String pathname) throws IOException;
247
248        /**
249     * Returns the pathname of the current working directory.
250     * <p>
251     * @return The pathname of the current working directory.  If it cannot
252     *         be obtained, returns null.
253     * @exception FTPConnectionClosedException
254     *      If the FTP server prematurely closes the connection as a result
255     *      of the client being idle or some other reason causing the server
256     *      to send FTP reply code 421.  This exception may be caught either
257     *      as an IOException or independently as itself.
258     * @exception IOException  If an I/O error occurs while either sending a
259     *      command to the server or receiving a reply from the server.
260     */
261    public abstract String printWorkingDirectory() throws IOException;
262
263        public abstract String getPrefix();
264
265        /**
266     * @return The remote address to which the client is connected.
267     * Delegates to {@link Socket#getInetAddress()}
268     * @throws NullPointerException if the socket is not currently open
269     */
270    public abstract InetAddress getRemoteAddress();
271
272        /**
273     * Returns true if the client is currently connected to a server.
274     * <p>
275     * Delegates to {@link Socket#isConnected()}
276     * @return True if the client is currently connected to a server,
277     *         false otherwise.
278     */
279    public abstract boolean isConnected();
280    
281    /***
282     * A convenience method to send the FTP QUIT command to the server,
283     * receive the reply, and return the reply code.
284     * <p>
285     * @return The reply code received from the server.
286     * @exception FTPConnectionClosedException
287     *      If the FTP server prematurely closes the connection as a result
288     *      of the client being idle or some other reason causing the server
289     *      to send FTP reply code 421.  This exception may be caught either
290     *      as an IOException or independently as itself.
291     * @exception IOException  If an I/O error occurs while either sending the
292     *      command or receiving the server reply.
293     ***/
294    public abstract int quit() throws IOException;
295    
296    /**
297     * Closes the connection to the FTP server and restores
298     * connection parameters to the default values.
299     * <p>
300     * @exception IOException If an error occurs while disconnecting.
301     */
302    public abstract void disconnect() throws IOException;
303    
304    /**
305     * timeout in milli seconds
306     * @param timeout
307     */
308    public abstract void setTimeout(int timeout);
309    
310
311    /**
312     * Returns the current data connection mode (one of the
313     * <code> _DATA_CONNECTION_MODE </code> constants.
314     * <p>
315     * @return The current data connection mode (one of the
316     * <code> _DATA_CONNECTION_MODE </code> constants.
317     */
318    public abstract int getDataConnectionMode();
319
320    /**
321     * Set the current data connection mode to
322     * <code> PASSIVE_LOCAL_DATA_CONNECTION_MODE </code>.  Use this
323     * method only for data transfers between the client and server.
324     * This method causes a PASV (or EPSV) command to be issued to the server
325     * before the opening of every data connection, telling the server to
326     * open a data port to which the client will connect to conduct
327     * data transfers.  The FTPClient will stay in
328     * <code> PASSIVE_LOCAL_DATA_CONNECTION_MODE </code> until the
329     * mode is changed by calling some other method such as
330     * {@link #enterLocalActiveMode  enterLocalActiveMode() }
331     * <p>
332     * <b>N.B.</b> currently calling any connect method will reset the mode to
333     * ACTIVE_LOCAL_DATA_CONNECTION_MODE.
334     */
335    public abstract void enterLocalPassiveMode();
336    
337    /**
338     * Set the current data connection mode to
339     * <code>ACTIVE_LOCAL_DATA_CONNECTION_MODE</code>.  No communication
340     * with the FTP server is conducted, but this causes all future data
341     * transfers to require the FTP server to connect to the client's
342     * data port.  Additionally, to accommodate differences between socket
343     * implementations on different platforms, this method causes the
344     * client to issue a PORT command before every data transfer.
345     */
346    public abstract void enterLocalActiveMode();
347    
348    public abstract void init(InetAddress host, int port, String username, String password, String fingerprint, boolean stopOnError) throws SocketException, IOException;
349    
350    
351    /**
352     * Opens a Socket connected to a remote host at the specified port and
353     * originating from the current host at a system assigned port.
354     * Before returning, {@link #_connectAction_  _connectAction_() }
355     * is called to perform connection initialization actions.
356     * <p>
357     * @param host  The remote host.
358     * @param port  The port to connect to on the remote host.
359     * @exception SocketException If the socket timeout could not be set.
360     * @exception IOException If the socket could not be opened.  In most
361     *  cases you will only want to catch IOException since SocketException is
362     *  derived from it.
363     * @throws FTPException 
364     */
365    public abstract void connect() throws SocketException, IOException;
366    
367    /***
368     * Determine if a reply code is a positive completion response.  All
369     * codes beginning with a 2 are positive completion responses.
370     * The FTP server will send a positive completion response on the final
371     * successful completion of a command.
372     * <p>
373     * @param reply  The reply code to test.
374     * @return True if a reply code is a postive completion response, false
375     *         if not.
376     ***/
377    public abstract boolean isPositiveCompletion();
378
379        public abstract boolean directoryExists(String pathname) throws IOException;
380}