2017-03-27 15 views
0

私は、Spring SFTP Outboundゲートウェイを使用し、GET操作を実行するコードを書いています。全体の構成はJAVA(XMLなし)です。 私は、最大10セッションを許可するキャッシング・セッション・ファクトリを作成しました。これにより、GET要求が複数回になって10を超えると、GET要求の開始に失敗します。Spring SFTP Outbound Gateway:Java ConfigでGET後にセッションを閉じるには?

私はドキュメントを読んで、操作後にセッションを終了するように書かれていましたが、JAVA設定でこのセッションを終了する方法を知ることができませんでしたか?

@org.springframework.integration.annotation.MessagingGateway 
public interface FileOperationGateway { 
    @Gateway(requestChannel = "sftpChannelDownload") 
    InputStream downloadFromSftp(Message<Boolean> message); 

} 



@Bean 
public SessionFactory<LsEntry> sftpSessionFactory() { 
    DefaultSftpSessionFactory factory = new DefaultSftpSessionFactory(true); 
    factory.setHost(SFTP_HOST); 
    factory.setPort(SFTP_PORT); 
    factory.setUser(SFTP_USERNAME); 
    factory.setPassword(SFTP_PASSWORD); 
    factory.setAllowUnknownKeys(true); 
    return new CachingSessionFactory<LsEntry>(factory); 
} 

/** 
* Bean for Caching the session 
* 
*/ 

@Bean 
@Autowired 
public CachingSessionFactory<LsEntry> cachingSessionFactory(SessionFactory<LsEntry> sftpSessionFactory) { 
    CachingSessionFactory<LsEntry> cachingSessionFactory = new CachingSessionFactory<>(sftpSessionFactory, 10); 
    cachingSessionFactory.setSessionWaitTimeout(SFTP_SESSION_TIMEOUT); 
    return cachingSessionFactory; 
} 

/** 
* Bean for Remote File Template 
* 
* @return 
* @throws Exception 
*/ 

@Bean 
@Autowired 
public RemoteFileTemplate<LsEntry> remoteFileTemplateDesigner(CachingSessionFactory<LsEntry> csf) throws Exception { 
    ExpressionParser expressionParser = new SpelExpressionParser(); 
    Expression expression = expressionParser.parseExpression("'" + SFTP_LOCATION + "'"); 
    SftpRemoteFileTemplate rft = new SftpRemoteFileTemplate(csf); 
    rft.setRemoteDirectoryExpression(expression); 
    rft.setRemoteFileSeparator("/"); 
    rft.setFileNameGenerator((msg) -> { 
     Timestamp timestamp = new Timestamp(System.currentTimeMillis()); 
     Instant instant = timestamp.toInstant(); 
     String fileNameFromHeader = msg.getHeaders().get(FileOperationConstants.FILE_HEADER_KEY).toString(); 
     String newFileName; 
     if (fileNameFromHeader.lastIndexOf("/") != -1) { 
      newFileName = fileNameFromHeader.substring(fileNameFromHeader.lastIndexOf("/")); 
     } else if (fileNameFromHeader.lastIndexOf("\\") != -1) { 
      newFileName = fileNameFromHeader.substring(fileNameFromHeader.lastIndexOf("\\")); 
     } else 
      newFileName = fileNameFromHeader; 

     String fileNameOnly = newFileName.substring(0, newFileName.lastIndexOf(".")); 
     String fileType = newFileName.substring(newFileName.lastIndexOf(".") + 1); 
     return (fileNameOnly + "__" + instant.toString() + "." + fileType); 
    }); 
    rft.afterPropertiesSet(); 
    return rft; 
} 

@Bean 
@Autowired 
@ServiceActivator(inputChannel = "sftpChannelDownload") 
public SftpOutboundGatewaySpec downloadHandler(RemoteFileTemplate<LsEntry> rft) { 
    SftpOutboundGatewaySpec sogs = Sftp.outboundGateway(rft, FileOperationConstants.FILE_DOWNLOAD_COMMAND, 
      FileOperationConstants.FILE_DOWNLOAD_EXPRESSION); 
    sogs.options(Option.STREAM); 
    return sogs; 
} 

****** UPDATE:******

私は@messageEndpointで新しいクラスを作成し、その中に閉鎖可能セッションコードを配置。

@Gateway(requestChannel = "sftpCloseSession") 
void closeSession(Message<InputStream> msg); 

@MessagingGateway注釈付きクラスでこの行を置いた

@MessageEndpoint 
public class FileOperationCloseSessionMessageHandler { 

    @ServiceActivator(inputChannel = "sftpCloseSession") 
    public void closeSession(Message<Boolean> msg) throws IOException { 

     Closeable closeable = new IntegrationMessageHeaderAccessor(msg).getCloseableResource(); 
     if (closeable != null) { 
      closeable.close(); 
     } 
    } 
} 

そしてサービスからゲートウェイメソッドを呼び出した:私は、私のサービスクラス(ここで、iは、ストリームを消費した)。これは、働いていたから、このハンドラを呼び出しクラス:

Message<InputStream> msg = msgGateway.downloadFromSftp(message); 
    InputStream is = msg.getPayload(); 
    msgGateway.closeSession(msg); 

答えて

0

sogs.options(Option.STREAM)。

ファイルをストリーミングすると、ストリーミングが終了した後にセッションを終了する責任があります。これはthe documentationで説明されています。

リモートファイルをストリームとして使用する場合、ストリームが消費された後にセッションを閉じる必要があります。便宜のために、セッションがIntegrationMessageHeaderAccessor.CLOSEABLE_RESOURCEヘッダに設けられている、便利な方法はIntegrationMessageHeaderAccessor上に設けられている。そのようなファイル分割及びストリームトランスとして

Closeable closeable = new IntegrationMessageHeaderAccessor(message).getCloseableResource(); 
if (closeable != null) { 
    closeable.close(); 
} 

Frameworkコンポーネントが自動的に後にセッションを終了しますデータが転送されます。

+0

こんにちはゲイリー、返信ありがとうございます。私はすでに、この「閉鎖可能な」コードを使ってセッションを閉じることができることを知っていましたが、問題はどこでどのように使用するのでしょうか?私は新しい@serviceActivatorメソッドを作成し、これを配置する必要がありますか?あなたはコードで見せていただけますか? –

+0

解決策を見つけて更新しました。ありがとう。 –

関連する問題