spring integration sftp mainframe:写文件失败;嵌套异常为3:权限被拒绝

时间:2014-09-16 19:36:15

标签: java sftp spring-integration jsch mainframe

我正在尝试使用spring integration sftp:outbound-gateway将文件sft到大型机: 这是配置:

<sftp:outbound-gateway id="putGateway"
        session-factory="sftpSessionFactory"
        request-channel="sftpFileInputChannel"      
        command="put"       
        expression="payload"    
        remote-directory="${remote.upload.directory}"     
        remote-filename-generator-expression="'${remote.upload.filename}'"      
        use-temporary-file-name="false"
        reply-channel="replayFromPutSftpChannel"/>

,其中

remote.upload.filename.credit.fmpl=/!DTS4.UP.G3TRF.S60304
remote.upload.directory=/

我得到例外:

Caused by: org.springframework.integration.MessagingException: Failed to write to '//!DTS4.UP.G3TRF.S60304' while uploading the file
    at org.springframework.integration.file.remote.RemoteFileTemplate.sendFileToRemoteDirectory(RemoteFileTemplate.java:392)
    at org.springframework.integration.file.remote.RemoteFileTemplate.access$500(RemoteFileTemplate.java:56)
    at org.springframework.integration.file.remote.RemoteFileTemplate$1.doInSession(RemoteFileTemplate.java:213)
    ... 46 more
Caused by: org.springframework.core.NestedIOException: failed to write file; nested exception is 3: Permission denied
    at org.springframework.integration.sftp.session.SftpSession.write(SftpSession.java:158)
    at org.springframework.integration.file.remote.RemoteFileTemplate.sendFileToRemoteDirectory(RemoteFileTemplate.java:385)
    ... 48 more
Caused by: 3: Permission denied
    at com.jcraft.jsch.ChannelSftp.throwStatusError(ChannelSftp.java:2629)
    at com.jcraft.jsch.ChannelSftp._put(ChannelSftp.java:545)
    at com.jcraft.jsch.ChannelSftp.put(ChannelSftp.java:491)
    at com.jcraft.jsch.ChannelSftp.put(ChannelSftp.java:454)
    at org.springframework.integration.sftp.session.SftpSession.write(SftpSession.java:155)

如果我使用sftp客户端从命令行上传,则以下工作:

put filename //!DTS4.UP.G3TRF.S60304

但是通过Spring集成,它没有。 服务器,我试图sftp到:IBM z / OS大型机。

如果您知道如何解决问题,请提供帮助。

谢谢你, 安娜

2 个答案:

答案 0 :(得分:0)

  

为什么我收到“com.jcraft.jsch.ChannelSftp.throwStatusError(ChannelSftp.java:2297)”中的“权限被拒绝”

     

我们收到此错误,因为在某些sftp服务器上“/”表示用户主目录的根目录,但在其他服务器上它实际上意味着用户显然没有写入权限的服务器根目录。当用户尝试编写的目录不存在时,我们也在某些sftp服务器上收到了这个。

另一个问题:

  

我也遇到了SFTP的问题,并且发现在ftp服务器名称或地址右侧框中的File Writer FTP的参数中,你必须放置你要去的文件夹的完全限定路径将文件放入。否则MIRTH SFTP会尝试将目录更改为/并获得权限被拒绝。   例如。 sftp:// 111.222.333.444 / foldera / folderb / folderc /

     

要了解foldera / folderb / folderc /应该使用哪种SFTP客户端(不是MIRTH),当它连接时,它应该显示你所在的文件夹的路径。

     

这对我有用。

那么,您的SFTP路径以/开头的问题。来自ChannelSftp.put的代码:

dst=remoteAbsolutePath(dst);
...
private String remoteAbsolutePath(String path) throws SftpException{
   if(path.charAt(0)=='/') return path;
   String cwd=getCwd();
   if(cwd.endsWith("/")) return cwd+path;
   return cwd+"/"+path;
}

尝试在开始时弄清楚如何避免/

答案 1 :(得分:0)

跟进Artem所指出的内容,例如在sFTP传输到云Axway sFTP服务器时,我被告知当前工作目录为“ /”

首先,我使用了终端sftp客户端:

$ sftp username@mft-xxx.axwaycloud.com
sftp> pwd
Remote working directory: /

这不是根目录/,而是chroot目录,因此我无法确定绝对路径是什么。下面的代码字符串ftpRemoteDestinationPath =“ /” + tempFile.getName();在这种情况下仍然有效:

    if (tempFile.exists()) {

        try {
            axwaySftpRemoteFileTemplate.execute((SessionCallback<ChannelSftp.LsEntry, Void>) session -> {

                String ftpRemoteDestinationPath = "/" + tempFile.getName();

                logger.info("FTP local file residing on server: [" + tempFile.getAbsolutePath() + "]");

                InputStream targetStream = new FileInputStream(tempFile);

                logger.debug("sftp uploading file: [" + tempFile.getName() + "] using channel connected to an sftp server :[" + session.getClientInstance().toString() + "]");
                session.write(targetStream, ftpRemoteDestinationPath);

                return null;
            });

        } catch (Exception e) {
            logger.error("Could not send file per SFTP: " + e);

            throw new SomeRuntimeSftpException("Error FTPing file " + tempFile.getAbsolutePath() + " " + e.getMessage());
        }
        finally {
            tempFile.delete();
        }
    }