alanhe421 / coding-note

note
3 stars 1 forks source link

关于ssh2-sftp-client #360

Open alanhe421 opened 2 years ago

alanhe421 commented 2 years ago

list返回文件项,具体参数如下

{
  "type": "-",
  "name": "admin1.pem",
  "size": 418,
  "modifyTime": 1651807713000,
  "accessTime": 1651807715000,
  "rights": {
    "user": "rw",
    "group": "r",
    "other": "r"
  },
  "owner": 0,
  "group": 0
} 
alanhe421 commented 2 years ago

list方法

list(data.path, /^[^.]/)
alanhe421 commented 2 years ago

filesize

返回为字节数,可以自行处理显示为表意的KB,MB之类单位

alanhe421 commented 2 years ago

filetype

alanhe421 commented 2 years ago

权限

{
      "type": "-",
      "name": "admin4.key",
      "size": 1679,
      "modifyTime": 1651807713000,
      "accessTime": 1651807715000,
      "rights": { "user": "rw", "group": "r", "other": "r" },
      "owner": 0,
      "group": 0
    }

owner,group字段返回值为ID

image

alanhe421 commented 2 years ago

下载文件

下载进度通过step函数可以获取,上传类似

this.sftpClient.fastGet(filePath, localPath, {
      concurrency: 64, // integer. Number of concurrent reads to use
      chunkSize: 32768, // integer. Size of each read in bytes
      step: function (total_transferred, chunk, total) {
        console.log('download step', total_transferred, chunk, total, 'percent:', (total_transferred / total * 100).toFixed(0), '%');
      }
    })

文件夹下载

注意,浏览器端JS可以实现多文件转ZIP包,但不支持在用户桌面创建文件夹。

alanhe421 commented 2 years ago

连接异常

 this.sftpClient.connect(this.config).catch(err => {
      console.log(`Error: ${err.message}`); // error message will include 'example-client'
    });
  1. ECONNRESET

image

alanhe421 commented 2 years ago

上传文件

  1. 重复文件会直接覆盖
  2. 默认给的权限是可读可写 0o666

上传下载文件可以限制下速度

https://github.com/theophilusx/ssh2-sftp-client/issues/259

put方法仅支持上传文件,针对文件夹会报错,需要使用对应API uploadDir

image

同时空文件支持上传

alanhe421 commented 2 years ago

取消

在下载或者上传大文件时,由于时间消耗太大,用户存在取消的需求

解决办法

手动断开连接,再重新建立连接。

https://github.com/theophilusx/ssh2-sftp-client/issues/292

alanhe421 commented 2 years ago

下载文件以流的形式直接传到另一台机器,去掉下载临时文件。

alanhe421 commented 2 years ago

sftp协议本身

https://www.ssh.com/academy/ssh/sftp

对于文件夹的上传下载,本质都是递归执行N次操作。因此递归执行解决上下载文件夹。

alanhe421 commented 1 year ago

stat文件信息获取

let stats = {
  mode: 33279, // integer representing type and permissions
  uid: 1000, // user ID
  gid: 985, // group ID
  size: 5, // file size
  accessTime: 1566868566000, // Last access time. milliseconds
  modifyTime: 1566868566000, // last modify time. milliseconds
  isDirectory: false, // true if object is a directory
  isFile: true, // true if object is a file
  isBlockDevice: false, // true if object is a block device
  isCharacterDevice: false, // true if object is a character device
  isSymbolicLink: false, // true if object is a symbolic link
  isFIFO: false, // true if object is a FIFO
  isSocket: false // true if object is a socket
};

关于mode

(rslt.mode& parseInt('777', 8)).toString(8)

https://www.martin-brennan.com/nodejs-file-permissions-fstat/

const RIGHTS_NUM_TO_STR = {
  7: 'rwx',
  6: 'rw-',
  5: 'r-x',
  4: 'r--',
  3: '-wx',
  2: '-w-',
  1: '--x',
  0: '---',
};

/**
 * 例如:16832=>700
 */
function handleFileModeRights(str) {
  return (str & parseInt('777', 8)).toString(8)
    .split('')
    .reduce((res, item) => {
      res += RIGHTS_NUM_TO_STR[+item];
      return res;
    }, '');
}

function handleShortRights(str) {
  const processRights = item => item.replace(/-/g, '');
  return str.match(/[a-z-]{3}/g)
    .reduce((res, item, index) => {
      if (index === 0) {
        res.user = processRights(item);
      }
      if (index === 1) {
        res.group = processRights(item);
      }
      if (index === 2) {
        res.other = processRights(item);
      }
      return res;
    }, {});
}

function handleLongRights(str) {
  return handleShortRights(str.substring(1));
}