ssh2-sftp-client 2.4.3 → 2.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +55 -5
- package/package.json +5 -3
- package/src/index.js +179 -95
- package/test/append.js +112 -0
- package/test/checksum-tests.js +222 -0
- package/test/fastget.js +103 -0
- package/test/fastput.js +99 -0
- package/test/get.js +104 -0
- package/test/hooks/append-hooks.js +50 -0
- package/test/hooks/checksum-hooks.js +24 -0
- package/test/hooks/chmod-hooks.js +24 -0
- package/test/hooks/delete-hooks.js +27 -0
- package/test/hooks/exist-hooks.js +39 -0
- package/test/hooks/fastGet-hooks.js +63 -0
- package/test/hooks/fastPut-hooks.js +33 -0
- package/test/hooks/get-hooks.js +52 -0
- package/test/hooks/global-hooks.js +66 -0
- package/test/hooks/list-hooks.js +63 -0
- package/test/hooks/mkdir-hooks.js +18 -0
- package/test/hooks/put-hooks.js +24 -0
- package/test/hooks/rename-hooks.js +36 -0
- package/test/hooks/rmdir-hooks.js +34 -0
- package/test/hooks/stat-hooks.js +33 -0
- package/test/mocha.opts +1 -1
- package/test/put.js +114 -0
- package/test/testData/test-file1.txt +39999 -54
- package/test/testData/test-file2.txt.gz +0 -0
- package/test/utility-methods.js +363 -0
- package/test/index.js +0 -686
|
Binary file
|
|
@@ -0,0 +1,363 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
// smaller utility method tests
|
|
4
|
+
|
|
5
|
+
const chai = require('chai');
|
|
6
|
+
const expect = chai.expect;
|
|
7
|
+
const chaiSubset = require('chai-subset');
|
|
8
|
+
const chaiAsPromised = require('chai-as-promised');
|
|
9
|
+
const {join} = require('path');
|
|
10
|
+
const gHooks = require('./hooks/global-hooks');
|
|
11
|
+
const lHooks = require('./hooks/list-hooks');
|
|
12
|
+
const eHooks = require('./hooks/exist-hooks');
|
|
13
|
+
const sHooks = require('./hooks/stat-hooks');
|
|
14
|
+
const mHooks = require('./hooks/mkdir-hooks');
|
|
15
|
+
const rHooks = require('./hooks/rmdir-hooks');
|
|
16
|
+
const dHooks = require('./hooks/delete-hooks');
|
|
17
|
+
const cHooks = require('./hooks/chmod-hooks');
|
|
18
|
+
const rnHooks = require('./hooks/rename-hooks');
|
|
19
|
+
|
|
20
|
+
chai.use(chaiSubset);
|
|
21
|
+
chai.use(chaiAsPromised);
|
|
22
|
+
|
|
23
|
+
let hookSftp, sftp, sftpUrl, localUrl;
|
|
24
|
+
|
|
25
|
+
before('Global setup', function() {
|
|
26
|
+
return gHooks
|
|
27
|
+
.setup()
|
|
28
|
+
.then(testEnv => {
|
|
29
|
+
hookSftp = testEnv.hookSftp;
|
|
30
|
+
sftp = testEnv.sftp;
|
|
31
|
+
sftpUrl = testEnv.sftpUrl;
|
|
32
|
+
localUrl = testEnv.localUrl;
|
|
33
|
+
return true;
|
|
34
|
+
})
|
|
35
|
+
.catch(err => {
|
|
36
|
+
throw new Error(err.message);
|
|
37
|
+
});
|
|
38
|
+
});
|
|
39
|
+
|
|
40
|
+
after('Global shutdown', function() {
|
|
41
|
+
return gHooks
|
|
42
|
+
.closeDown()
|
|
43
|
+
.then(() => {
|
|
44
|
+
return true;
|
|
45
|
+
})
|
|
46
|
+
.catch(err => {
|
|
47
|
+
throw new Error(err.message);
|
|
48
|
+
});
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
describe('list method tests', () => {
|
|
52
|
+
before('List test setup hook', function() {
|
|
53
|
+
return lHooks.listSetup(hookSftp, sftpUrl, localUrl).catch(err => {
|
|
54
|
+
throw new Error(err.message);
|
|
55
|
+
});
|
|
56
|
+
});
|
|
57
|
+
|
|
58
|
+
after('List test cleanup hook', function() {
|
|
59
|
+
return lHooks.listCleanup(hookSftp, sftpUrl).catch(err => {
|
|
60
|
+
throw new Error(err.message);
|
|
61
|
+
});
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
// don't use arrow functions as it screws with the context, which
|
|
65
|
+
// causes issues with chai
|
|
66
|
+
it('list return should be a promise', function() {
|
|
67
|
+
return expect(sftp.list(join(sftpUrl, 'mocha-list'))).to.be.a('promise');
|
|
68
|
+
});
|
|
69
|
+
|
|
70
|
+
it('list return on empty directory should be empty', function() {
|
|
71
|
+
return expect(sftp.list(join(sftpUrl, 'mocha-list/empty'))).to.become([]);
|
|
72
|
+
});
|
|
73
|
+
|
|
74
|
+
it('list non-existent directory rejected', function() {
|
|
75
|
+
return expect(
|
|
76
|
+
sftp.list(join(sftpUrl, 'mocha-list/not-exist'))
|
|
77
|
+
).to.be.rejectedWith('No such file');
|
|
78
|
+
});
|
|
79
|
+
|
|
80
|
+
it('list existing dir returns details of each entry', async function() {
|
|
81
|
+
let list = await sftp.list(join(sftpUrl, 'mocha-list'));
|
|
82
|
+
return expect(list).to.containSubset([
|
|
83
|
+
{type: 'd', name: 'dir1'},
|
|
84
|
+
{type: 'd', name: 'dir2'},
|
|
85
|
+
{type: 'd', name: 'empty'},
|
|
86
|
+
{type: '-', name: 'file1.html', size: 11},
|
|
87
|
+
{type: '-', name: 'file2.md', size: 11},
|
|
88
|
+
{type: '-', name: 'test-file1.txt', size: 6973257},
|
|
89
|
+
{type: '-', name: 'test-file2.txt.gz', size: 570314}
|
|
90
|
+
]);
|
|
91
|
+
});
|
|
92
|
+
});
|
|
93
|
+
|
|
94
|
+
describe('Exist method tests', function() {
|
|
95
|
+
before('Exist test setup hook', function() {
|
|
96
|
+
return eHooks.existSetup(hookSftp, sftpUrl, localUrl).catch(err => {
|
|
97
|
+
throw new Error(err.message);
|
|
98
|
+
});
|
|
99
|
+
});
|
|
100
|
+
|
|
101
|
+
after('Exist test cleanup hook', function() {
|
|
102
|
+
return eHooks.existCleanup(hookSftp, sftpUrl).catch(err => {
|
|
103
|
+
throw new Error(err.message);
|
|
104
|
+
});
|
|
105
|
+
});
|
|
106
|
+
|
|
107
|
+
it('Exist return should be a promise', function() {
|
|
108
|
+
return expect(sftp.exists(sftpUrl)).to.be.a('promise');
|
|
109
|
+
});
|
|
110
|
+
|
|
111
|
+
it('Exist returns truthy for existing directory', function() {
|
|
112
|
+
return expect(sftp.exists(join(sftpUrl, 'exist-dir'))).to.eventually.equal(
|
|
113
|
+
'd'
|
|
114
|
+
);
|
|
115
|
+
});
|
|
116
|
+
|
|
117
|
+
it('Exist returns truthy for existing file', function() {
|
|
118
|
+
return expect(
|
|
119
|
+
sftp.exists(join(sftpUrl, 'exist-file.txt'))
|
|
120
|
+
).to.eventually.equal('-');
|
|
121
|
+
});
|
|
122
|
+
|
|
123
|
+
it('Exists return false value for non existent object', function() {
|
|
124
|
+
return expect(
|
|
125
|
+
sftp.exists(join(sftpUrl, 'no-such-dir/subdir'))
|
|
126
|
+
).to.eventually.equal(false);
|
|
127
|
+
});
|
|
128
|
+
|
|
129
|
+
it('Exists return false for bad path', function() {
|
|
130
|
+
return expect(sftp.exists('just/a/really/bad/path')).to.eventually.equal(
|
|
131
|
+
false
|
|
132
|
+
);
|
|
133
|
+
});
|
|
134
|
+
});
|
|
135
|
+
|
|
136
|
+
describe('Stat method tests', function() {
|
|
137
|
+
before(() => {
|
|
138
|
+
return sHooks.statSetup(hookSftp, sftpUrl).catch(err => {
|
|
139
|
+
throw new Error(err.message);
|
|
140
|
+
});
|
|
141
|
+
});
|
|
142
|
+
|
|
143
|
+
after(() => {
|
|
144
|
+
return sHooks.statCleanup(hookSftp, sftpUrl).catch(err => {
|
|
145
|
+
throw new Error(err.message);
|
|
146
|
+
});
|
|
147
|
+
});
|
|
148
|
+
|
|
149
|
+
it('Stat return should be a promise', function() {
|
|
150
|
+
return expect(sftp.stat(join(sftpUrl, 'mocha-stat.md'))).to.be.a('promise');
|
|
151
|
+
});
|
|
152
|
+
|
|
153
|
+
it('Stat on existing file returns stat data', async function() {
|
|
154
|
+
let stats = await sftp.stat(join(sftpUrl, 'mocha-stat.md'));
|
|
155
|
+
return expect(stats).to.containSubset({mode: 33279, size: 5});
|
|
156
|
+
});
|
|
157
|
+
|
|
158
|
+
it('Stat on non-existent file rejected', function() {
|
|
159
|
+
return expect(
|
|
160
|
+
sftp.stat(join(sftpUrl, 'mocha-stat1.md'))
|
|
161
|
+
).to.be.rejectedWith('No such file');
|
|
162
|
+
});
|
|
163
|
+
});
|
|
164
|
+
|
|
165
|
+
describe('Mkdir method tests', function() {
|
|
166
|
+
after('Mkdir test cleanup', function() {
|
|
167
|
+
return mHooks.mkdirCleanup(hookSftp, sftpUrl).catch(err => {
|
|
168
|
+
throw new Error(err.message);
|
|
169
|
+
});
|
|
170
|
+
});
|
|
171
|
+
|
|
172
|
+
it('Mkdir should return a promise', function() {
|
|
173
|
+
return expect(sftp.mkdir(join(sftpUrl, 'mocha'))).to.be.a('promise');
|
|
174
|
+
});
|
|
175
|
+
|
|
176
|
+
it('Mkdir without recursive option and bad path should be rejected', function() {
|
|
177
|
+
return expect(sftp.mkdir(join(sftpUrl, 'mocha3', 'mm'))).to.be.rejectedWith(
|
|
178
|
+
'Failed to create directory'
|
|
179
|
+
);
|
|
180
|
+
});
|
|
181
|
+
|
|
182
|
+
it('Mkdir with recursive option should create all directories', function() {
|
|
183
|
+
return sftp
|
|
184
|
+
.mkdir(join(sftpUrl, 'mocha', 'mocha-dir-force', 'subdir'), true)
|
|
185
|
+
.then(() => {
|
|
186
|
+
return sftp.list(join(sftpUrl, 'mocha', 'mocha-dir-force'));
|
|
187
|
+
})
|
|
188
|
+
.then(list => {
|
|
189
|
+
return expect(list).to.containSubset([{name: 'subdir'}]);
|
|
190
|
+
});
|
|
191
|
+
});
|
|
192
|
+
|
|
193
|
+
it('mkdir without recursive option creates dir', function() {
|
|
194
|
+
return sftp
|
|
195
|
+
.mkdir(join(sftpUrl, 'mocha', 'mocha-non-recursive'), false)
|
|
196
|
+
.then(() => {
|
|
197
|
+
return sftp.list(join(sftpUrl, 'mocha'));
|
|
198
|
+
})
|
|
199
|
+
.then(list => {
|
|
200
|
+
return expect(list).to.containSubset([{name: 'mocha-non-recursive'}]);
|
|
201
|
+
});
|
|
202
|
+
});
|
|
203
|
+
});
|
|
204
|
+
|
|
205
|
+
describe('Rmdir method tests', function() {
|
|
206
|
+
before('Rmdir method setup hook', function() {
|
|
207
|
+
return rHooks.rmdirSetup(hookSftp, sftpUrl).catch(err => {
|
|
208
|
+
throw new Error(err.message);
|
|
209
|
+
});
|
|
210
|
+
});
|
|
211
|
+
|
|
212
|
+
it('Rmdir should return a promise', function() {
|
|
213
|
+
return expect(sftp.rmdir(join(sftpUrl, 'mocha'))).to.be.a('promise');
|
|
214
|
+
});
|
|
215
|
+
|
|
216
|
+
it('Rmdir on non-existent directory should be rejected', function() {
|
|
217
|
+
return expect(
|
|
218
|
+
sftp.rmdir(join(sftpUrl, 'mocha-rmdir2'), true)
|
|
219
|
+
).to.be.rejectedWith('No such file');
|
|
220
|
+
});
|
|
221
|
+
|
|
222
|
+
it('Rmdir without recursion on empty directory', function() {
|
|
223
|
+
return expect(
|
|
224
|
+
sftp.rmdir(join(sftpUrl, 'mocha-rmdir', 'dir1'))
|
|
225
|
+
).to.eventually.equal('Successfully removed directory');
|
|
226
|
+
});
|
|
227
|
+
|
|
228
|
+
it('Rmdirrecursively remove all directories', function() {
|
|
229
|
+
return expect(
|
|
230
|
+
sftp.rmdir(join(sftpUrl, 'mocha-rmdir', 'dir3'), true)
|
|
231
|
+
).to.eventually.equal('Successfully removed directory');
|
|
232
|
+
});
|
|
233
|
+
|
|
234
|
+
it('Rmdir recursively remove dirs and files', function() {
|
|
235
|
+
return expect(
|
|
236
|
+
sftp.rmdir(join(sftpUrl, 'mocha-rmdir'), true)
|
|
237
|
+
).to.eventually.equal('Successfully removed directory');
|
|
238
|
+
});
|
|
239
|
+
});
|
|
240
|
+
|
|
241
|
+
describe('Delete method tests', function() {
|
|
242
|
+
before('Delete tests setup hook', function() {
|
|
243
|
+
return dHooks.deleteSetup(hookSftp, sftpUrl).catch(err => {
|
|
244
|
+
throw new Error(err.message);
|
|
245
|
+
});
|
|
246
|
+
});
|
|
247
|
+
|
|
248
|
+
it('Delete returns a promise', function() {
|
|
249
|
+
return expect(
|
|
250
|
+
sftp.delete(join(sftpUrl, 'mocha-delete-promise.md'))
|
|
251
|
+
).to.be.a('promise');
|
|
252
|
+
});
|
|
253
|
+
|
|
254
|
+
it('Delete a file', function() {
|
|
255
|
+
return expect(
|
|
256
|
+
sftp.delete(join(sftpUrl, 'mocha-delete.md'))
|
|
257
|
+
).to.eventually.equal('Successfully deleted file');
|
|
258
|
+
});
|
|
259
|
+
|
|
260
|
+
it('Delete non-existent file is rejected', function() {
|
|
261
|
+
return expect(
|
|
262
|
+
sftp.delete(join(sftpUrl, 'no-such-file.txt'))
|
|
263
|
+
).to.be.rejectedWith('Failed to delete file');
|
|
264
|
+
});
|
|
265
|
+
});
|
|
266
|
+
|
|
267
|
+
describe('Rename method tests', function() {
|
|
268
|
+
before('Rename setup hook', function() {
|
|
269
|
+
return rnHooks.renameSetup(hookSftp, sftpUrl).catch(err => {
|
|
270
|
+
throw new Error(err.message);
|
|
271
|
+
});
|
|
272
|
+
});
|
|
273
|
+
|
|
274
|
+
after('Rename cleanup hook', function() {
|
|
275
|
+
return rnHooks.renameCleanup(hookSftp, sftpUrl).catch(err => {
|
|
276
|
+
throw new Error(err.message);
|
|
277
|
+
});
|
|
278
|
+
});
|
|
279
|
+
|
|
280
|
+
it('Rename should return a promise', function() {
|
|
281
|
+
return expect(
|
|
282
|
+
sftp.rename(
|
|
283
|
+
join(sftpUrl, 'mocha-rename.md'),
|
|
284
|
+
join(sftpUrl, 'mocha-rename.txt')
|
|
285
|
+
)
|
|
286
|
+
).to.be.a('promise');
|
|
287
|
+
});
|
|
288
|
+
|
|
289
|
+
it('Rename file successfully', function() {
|
|
290
|
+
return sftp
|
|
291
|
+
.rename(
|
|
292
|
+
join(sftpUrl, 'mocha-rename.txt'),
|
|
293
|
+
join(sftpUrl, 'mocha-rename-new.md')
|
|
294
|
+
)
|
|
295
|
+
.then(() => {
|
|
296
|
+
return sftp.list(sftpUrl);
|
|
297
|
+
})
|
|
298
|
+
.then(list => {
|
|
299
|
+
return expect(list).to.containSubset([{name: 'mocha-rename-new.md'}]);
|
|
300
|
+
});
|
|
301
|
+
});
|
|
302
|
+
|
|
303
|
+
it('Rename non-existent file is rejected', function() {
|
|
304
|
+
return expect(
|
|
305
|
+
sftp.rename(join(sftpUrl, 'no-such-file.txt'), join(sftpUrl, 'dummy.md'))
|
|
306
|
+
).to.be.rejectedWith('No such file');
|
|
307
|
+
});
|
|
308
|
+
|
|
309
|
+
it('Rename to existing file name is rejected', function() {
|
|
310
|
+
return expect(
|
|
311
|
+
sftp.rename(
|
|
312
|
+
join(sftpUrl, 'mocha-rename-new.md'),
|
|
313
|
+
join(sftpUrl, 'mocha-conflict.md')
|
|
314
|
+
)
|
|
315
|
+
).to.be.rejectedWith('Failed to rename file');
|
|
316
|
+
});
|
|
317
|
+
});
|
|
318
|
+
|
|
319
|
+
describe('Chmod method tests', function() {
|
|
320
|
+
before('Chmod setup hook', function() {
|
|
321
|
+
return cHooks.chmodSetup(hookSftp, sftpUrl).catch(err => {
|
|
322
|
+
throw new Error(err.message);
|
|
323
|
+
});
|
|
324
|
+
});
|
|
325
|
+
|
|
326
|
+
after('Chmod cleanup hook', function() {
|
|
327
|
+
return cHooks.chmodCleanup(hookSftp, sftpUrl).catch(err => {
|
|
328
|
+
throw new Error(err.message);
|
|
329
|
+
});
|
|
330
|
+
});
|
|
331
|
+
|
|
332
|
+
it('Chmod should return a promise', function() {
|
|
333
|
+
return expect(sftp.chmod(join(sftpUrl, 'mocha-chmod.txt'), 0o444)).to.be.a(
|
|
334
|
+
'promise'
|
|
335
|
+
);
|
|
336
|
+
});
|
|
337
|
+
|
|
338
|
+
it('Chmod on a file reports correct mode', function() {
|
|
339
|
+
return sftp
|
|
340
|
+
.chmod(join(sftpUrl, 'mocha-chmod.txt'), 0o777)
|
|
341
|
+
.then(() => {
|
|
342
|
+
return sftp.list(sftpUrl);
|
|
343
|
+
})
|
|
344
|
+
.then(list => {
|
|
345
|
+
return expect(list).to.containSubset([
|
|
346
|
+
{
|
|
347
|
+
name: 'mocha-chmod.txt',
|
|
348
|
+
rights: {
|
|
349
|
+
user: 'rwx',
|
|
350
|
+
group: 'rwx',
|
|
351
|
+
other: 'rwx'
|
|
352
|
+
}
|
|
353
|
+
}
|
|
354
|
+
]);
|
|
355
|
+
});
|
|
356
|
+
});
|
|
357
|
+
|
|
358
|
+
it('Chmod on non-existent file is rejecterd', function() {
|
|
359
|
+
return expect(
|
|
360
|
+
sftp.chmod(join(sftpUrl, 'does-not-exist.txt'), 0o777)
|
|
361
|
+
).to.be.rejectedWith('No such file');
|
|
362
|
+
});
|
|
363
|
+
});
|