001 /**
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements. See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License. You may obtain a copy of the License at
008 *
009 * http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017 package org.apache.camel.component.file.remote;
018
019 import java.io.IOException;
020 import java.io.InputStream;
021
022 import org.apache.camel.Exchange;
023 import org.apache.commons.net.ftp.FTPClient;
024
025 public class FtpProducer extends RemoteFileProducer<RemoteFileExchange> {
026
027 private FtpEndpoint endpoint;
028 private FTPClient client;
029 private boolean loggedIn;
030
031 public FtpProducer(FtpEndpoint endpoint, FTPClient client) {
032 super(endpoint);
033 this.endpoint = endpoint;
034 this.client = client;
035 }
036
037 public void process(Exchange exchange) throws Exception {
038 if (log.isTraceEnabled()) {
039 log.trace("Processing " + endpoint.getConfiguration());
040 }
041
042 try {
043 connectIfNecessary();
044
045 if (!loggedIn) {
046 String message = "Could not connect/login to " + endpoint.getConfiguration();
047 log.warn(message);
048 throw new FtpOperationFailedException(client.getReplyCode(), client.getReplyString(), message);
049 }
050
051 process(endpoint.createExchange(exchange));
052 } catch (Exception e) {
053 loggedIn = false;
054 if (isStopping() || isStopped()) {
055 // if we are stopping then ignore any exception during a poll
056 log.warn("Producer is stopping. Ignoring caught exception: "
057 + e.getClass().getCanonicalName() + " message: " + e.getMessage());
058 } else {
059 log.warn("Exception occured during processing: "
060 + e.getClass().getCanonicalName() + " message: " + e.getMessage());
061 disconnect();
062 // Rethrow to signify that we didn't poll
063 throw e;
064 }
065 }
066 }
067
068 protected void connectIfNecessary() throws IOException {
069 if (!client.isConnected() || !loggedIn) {
070 if (log.isDebugEnabled()) {
071 log.debug("Not connected/logged in, connecting to " + remoteServer());
072 }
073 loggedIn = FtpUtils.connect(client, endpoint.getConfiguration());
074 if (!loggedIn) {
075 return;
076 }
077 }
078
079 log.info("Connected and logged in to " + remoteServer());
080 }
081
082 public void disconnect() throws IOException {
083 loggedIn = false;
084 if (log.isDebugEnabled()) {
085 log.debug("Disconnecting from " + remoteServer());
086 }
087 FtpUtils.disconnect(client);
088 }
089
090 public void process(RemoteFileExchange exchange) throws Exception {
091 InputStream payload = exchange.getIn().getBody(InputStream.class);
092 try {
093 String fileName = createFileName(exchange.getIn(), endpoint.getConfiguration());
094
095 int lastPathIndex = fileName.lastIndexOf('/');
096 if (lastPathIndex != -1) {
097 String directory = fileName.substring(0, lastPathIndex);
098 if (!FtpUtils.buildDirectory(client, directory)) {
099 log.warn("Couldn't build directory: " + directory + " (could be because of denied permissions)");
100 }
101 }
102
103 boolean success = client.storeFile(fileName, payload);
104 if (!success) {
105 String message = "Error sending file: " + fileName + " to: " + remoteServer();
106 throw new FtpOperationFailedException(client.getReplyCode(), client.getReplyString(), message);
107 }
108
109 log.info("Sent: " + fileName + " to: " + remoteServer());
110 } finally {
111 if (payload != null) {
112 payload.close();
113 }
114 }
115 }
116
117 }