当本地目录包含任何内容时,SFTP入站通道适配器不会复制文件

时间:2014-06-25 18:29:49

标签: java spring spring-integration

我正在尝试使用Spring Batch Integration和我已构建的Spring Batch程序,但此时我只是试图在Spring IO和{{3}的帮助下获得Spring Integration的工作示例}}

我已经自定义了示例程序,可以将远程目录中的所有文件一次性复制到本地,以及其他一些细微的更改。该程序运行得非常好,但是当我正在复制的本地目录没有内容时,工作。

我尝试重命名文件并运行程序,但问题仍然存在。即使本地目录具有隐藏的.DS_Store文件,程序也不会复制内容,即来自远程(SFTP)目录的文件。我想尝试一些场景:

  1. 即使存在隐藏文件也要复制文件
  2. 覆盖名称相同的文件
  3. 仅复制文件的子集,即仅复制尚未使用相同名称的文件
  4. 原谅我的无知,我似乎错过了在 标签上设置一些属性。

    我的XML文件大致如下:

    <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xmlns:int="http://www.springframework.org/schema/integration"
        xmlns:int-sftp="http://www.springframework.org/schema/integration/sftp"
        xmlns:task="http://www.springframework.org/schema/task"
        xmlns:context="http://www.springframework.org/schema/context"
        xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
            http://www.springframework.org/schema/integration http://www.springframework.org/schema/integration/spring-integration.xsd
            http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task.xsd
            http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
            http://www.springframework.org/schema/integration/sftp http://www.springframework.org/schema/integration/sftp/spring-integration-sftp.xsd">
    
        <context:property-placeholder location="classpath:user.properties"/>
    
        <bean id="sftpSessionFactory" class="org.springframework.integration.sftp.session.DefaultSftpSessionFactory">
            <property name="host" value="${host}"/>
            <property name="port" value="22"/>
            <property name="user" value="${user}"/>
        <property name="password" value="${password}"/>
        </bean>
    
        <int-sftp:inbound-channel-adapter id="sftpInbondAdapter"
                channel="receiveChannel"
                session-factory="sftpSessionFactory"
                local-directory="file:${local.directory}"
                remote-directory="${remote.directory}"
                auto-create-local-directory="true"
                delete-remote-files="false"
                filename-pattern="*.txt">
            <int:poller max-messages-per-poll="-1" fixed-rate="1000" />
        </int-sftp:inbound-channel-adapter>
    
        <int:channel id="receiveChannel">
            <int:queue/>
        </int:channel>
    
    </beans>
    

    这是测试计划:

    public class SftpInboundReceiveSampleTest {
    
        @Test
        public void runDemo(){
            ApplicationContext context = new ClassPathXmlApplicationContext("/META-INF/spring/integration/SftpInboundReceiveSample-context.xml", this.getClass());
            PollableChannel localFileChannel = context.getBean("receiveChannel", PollableChannel.class);
            System.out.println("Received first file message: " + localFileChannel.receive());
        }
    }
    

    更新 操作系统:Mac OS X 10.9.3 Spring Integration版本:4.0.0.RELEASE 记录:Spring Example on GITHUB

1 个答案:

答案 0 :(得分:1)

之前已经报道过,如果本地目录不为空,则不会复制文件,但我不会在代码中看到这是如何可能的,我们从未能够重现该问题。我不记得前一个问题的结果。

所以:

  1. 应该只是工作 - 你能打开DEBUG日志记录,看它是否提供任何线索?另请注明操作系统和Spring Integration版本。
  2. 始终复制文件(默认情况下)并覆盖本地版本;但是,如果该文件已由该应用程序实例处理(默认本地过滤器为AcceptOnceFileListFilter),则它们不会生成消息。自3.0起,您可以将local-filter设置为AcceptAllFileListFilter以始终生成消息 - 但是您需要在处理文件时删除该文件,以避免在每个文件中反复发现该文件轮询。或者,使用存储lastModified日期的FileSystemPersistentAcceptOnceFileListFilter以及文件名,以便检测文件是否已更改。
  3. 为了防止提取重复文件(无论#2如何),请使用代理{a} filename-pattern和{{CompositeFileListFilter的{​​{1}}代替SftpPersistentAcceptOnceFileListFilter 1}};只有在通过两个过滤器时才会获取该文件。
  4. PS:我刚刚在OS X上运行了一个测试目录SftpSimplePatternFileListFilter,其中bar有一个/Users/foo/bar,它运行得很好。

    编辑:

    这是我的配置,执行1,2和3 ...

    .DS_Store

    请注意<int-sftp:inbound-channel-adapter id="sftpInbondAdapter" channel="receiveChannel" session-factory="sftpSessionFactory" local-directory="/Users/.../Development/tmp" remote-directory="foo" auto-create-local-directory="true" delete-remote-files="false" filter="filter"> <int:poller fixed-rate="1000" max-messages-per-poll="1"/> </int-sftp:inbound-channel-adapter> <int:channel id="receiveChannel"> <int:queue/> </int:channel> <bean id="filter" class="org.springframework.integration.file.filters.CompositeFileListFilter"> <constructor-arg> <list> <bean class="org.springframework.integration.sftp.filters.SftpPersistentAcceptOnceFileListFilter"> <constructor-arg> <bean class="org.springframework.integration.metadata.PropertiesPersistingMetadataStore" /> </constructor-arg> <constructor-arg value="foo" /> </bean> <bean class="org.springframework.integration.sftp.filters.SftpSimplePatternFileListFilter"> <constructor-arg value="*.txt" /> </bean> </list> </constructor-arg> </bean> ... // logs showing existing present files sent to the channel ... 16:44:54.465 WARN [task-scheduler-3][com.jcraft.jsch] Permanently added '10.0.0.3' (RSA) to the list of known hosts. 16:45:06.372 DEBUG [task-scheduler-3][org.springframework.integration.sftp.inbound.SftpInboundFileSynchronizer] 2 files transferred 16:45:12.704 DEBUG [task-scheduler-3][org.springframework.integration.endpoint.SourcePollingChannelAdapter] Received no Message during the poll, returning 'false' 16:45:40.056 DEBUG [task-scheduler-4][org.springframework.integration.sftp.inbound.SftpInboundFileSynchronizer] 0 files transferred 2 files transferred

    我在日志中看不到0 files transferred的任何日志。请注意,我必须在测试应用程序中进行睡眠 - 如果您使用相同的应用程序;如果文件已经存在,它会在同步任何文件之前终止;在那里放一个SftpInboundFileSynchronizer来阻止它终止。