在 Spring Boot 中从 FTP 发送和接收文件

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/42107640/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-08 01:20:12  来源:igfitidea点击:

Send and receive files from FTP in Spring Boot

springspring-bootspring-integrationftps

提问by russellhoff

I'm new to Spring Framework and, indeed, I'm learning and using Spring Boot. Recently, in the app I'm developing, I made Quartz Scheduler work, and now I want to make Spring Integration work there: FTP connection to a server to write and read files from.

我是 Spring Framework 的新手,事实上,我正在学习和使用Spring Boot。最近,在我正在开发的应用程序中,我让 Quartz Scheduler 工作,现在我想让 Spring Integration 在那里工作:FTP 连接到服务器以写入和读取文件。

What I want is really simple (as I've been able to do so in a previous java application). I've got two Quartz Jobs scheduled to fired in different times daily: one of them reads a file from a FTP server and another one writes a file to a FTP server.

我想要的非常简单(因为我已经能够在以前的 Java 应用程序中这样做)。我有两个 Quartz 作业计划在每天的不同时间触发:其中一个从 FTP 服务器读取文件,另一个将文件写入 FTP 服务器。

I'll detail what I've developed so far.

我将详细介绍到目前为止我开发的内容。

@SpringBootApplication
@ImportResource("classpath:ws-config.xml")
@EnableIntegration
@EnableScheduling
public class MyApp extends SpringBootServletInitializer {

    @Autowired
    private Configuration configuration;

    //...

    @Bean
    public DefaultFtpsSessionFactory  myFtpsSessionFactory(){
        DefaultFtpsSessionFactory sess = new DefaultFtpsSessionFactory();
        Ftp ftp = configuration.getFtp();
        sess.setHost(ftp.getServer());
        sess.setPort(ftp.getPort());
        sess.setUsername(ftp.getUsername());
        sess.setPassword(ftp.getPassword());
        return sess;
    }

}

The following class I've named it as a FtpGateway, as follows:

我将以下类命名为 FtpGateway,如下所示:

@Component
public class FtpGateway {

    @Autowired
    private DefaultFtpsSessionFactory sess;

    public void sendFile(){
        // todo
    }

    public void readFile(){
        // todo
    }

}

I'm reading thisdocumentation to learn to do so. Spring Integration's FTP seems to be event driven, so I don't know how can I execute either of the sendFile() and readFile() from by Jobs when the trigger is fired at an exact time.

我正在阅读文档以学习这样做。Spring Integration 的 FTP 似乎是事件驱动的,所以我不知道如何在确切的时间触发触发器时执行 Jobs 的 sendFile() 和 readFile() 中的任一个。

The documentation tells me somethingabout using Inbound Channel Adapter (to read files from a FTP?), Outbound Channel Adapter (to write files to a FTP?) and Outbound Gateway (to do what?):

该文件告诉我一些关于使用入站通道适配器,出站通道适配器(写入文件到FTP?)和出站网关(做什么?)(从FTP读取文件?):

Spring Integration supports sending and receiving files over FTP/FTPS by providing three client side endpoints: Inbound Channel Adapter, Outbound Channel Adapter, and Outbound Gateway. It also provides convenient namespace-based configuration options for defining these client components.

Spring Integration 通过提供三个客户端端点来支持通过 FTP/FTPS 发送和接收文件:入站通道适配器、出站通道适配器和出站网关。它还为定义这些客户端组件提供了方便的基于命名空间的配置选项。

So, I haven't got it clear as how to follow.

所以,我还不清楚如何遵循。

Please, could anybody give me a hint?

拜托,有人可以给我一个提示吗?

Thank you!

谢谢!

EDIT:

编辑

Thank you @M. Deinum. First, I'll try a simple task: read a file from the FTP, the poller will run every 5 seconds. This is what I've added:

谢谢@M。迪努姆。首先,我将尝试一个简单的任务:从 FTP 读取文件,轮询器将每 5 秒运行一次。这是我添加的内容:

@Bean
public FtpInboundFileSynchronizer ftpInboundFileSynchronizer() {
    FtpInboundFileSynchronizer fileSynchronizer = new FtpInboundFileSynchronizer(myFtpsSessionFactory());
    fileSynchronizer.setDeleteRemoteFiles(false);
    fileSynchronizer.setPreserveTimestamp(true);
    fileSynchronizer.setRemoteDirectory("/Entrada");
    fileSynchronizer.setFilter(new FtpSimplePatternFileListFilter("*.csv"));
    return fileSynchronizer;
}


@Bean
@InboundChannelAdapter(channel = "ftpChannel", poller = @Poller(fixedDelay = "5000"))
public MessageSource<File> ftpMessageSource() {
    FtpInboundFileSynchronizingMessageSource source = new FtpInboundFileSynchronizingMessageSource(inbound);
    source.setLocalDirectory(new File(configuracion.getDirFicherosDescargados()));
    source.setAutoCreateLocalDirectory(true);
    source.setLocalFilter(new AcceptOnceFileListFilter<File>());
    return source;
}

@Bean
@ServiceActivator(inputChannel = "ftpChannel")
public MessageHandler handler() {
    return new MessageHandler() {

        @Override
        public void handleMessage(Message<?> message) throws MessagingException {
            Object payload = message.getPayload();
            if(payload instanceof File){
                File f = (File) payload;
                System.out.println(f.getName());
            }else{
                System.out.println(message.getPayload());
            }
        }

    };
}

Then, when the app is running, I put a new csv file intro "Entrada" remote folder, but the handler() method isn't run after 5 seconds... I'm doing something wrong?

然后,当应用程序运行时,我在“Entrada”远程文件夹中放入了一个新的 csv 文件,但是 5 秒后没有运行 handler() 方法......我做错了什么?

回答by Mr Nobody

Please add @Scheduled(fixedDelay = 5000)over your poller method.

请在您的轮询方法上添加@Scheduled(fixedDelay = 5000)

回答by Swarit Agarwal

You should use SPRING BATCHwith tasklet. It is far easier to configure bean, crone time, input source with existing interfaces provided by Spring.

您应该将SPRING BATCH与 tasklet 一起使用。使用 Spring 提供的现有接口配置 bean、克隆时间、输入源要容易得多。

https://www.baeldung.com/introduction-to-spring-batch

https://www.baeldung.com/introduction-to-spring-batch

Above example is annotation and xml based both, you can use either.

上面的例子是基于注解和 xml 的两者,你可以使用任何一个。

Other benefitTake use of listeners and parallel steps. This framework can be used in Reader - Processor - Writer manner as well.

其他好处利用监听器和并行步骤。该框架也可以以 Reader - Processor - Writer 的方式使用。