vinyl-ftp icon indicating copy to clipboard operation
vinyl-ftp copied to clipboard

clean() does not remove all the files

Open xenogenesi opened this issue 4 years ago • 2 comments

I'm doing some tests with an instance of ProFTPD executed locally in a docker container, I tried the upload with a project with several files and it seems to work correctly, since in the project eventually some files will be removed I tried to implement a task in gulp for clean().

After struggling a bit with the clean() syntax (IMHO would need more detailed documentation, there are some notable examples in the issues) what happens is that the task is executed sometime without errors, but of about 700+ files that I have deleted locally it only eliminates about ~20 each time I run it, and I have no errors even on the server side.

From what I see, the files (I'm not trying directories yet) to be deleted all arrive inside clean.js: check() and inside the condition if (method) (I replaced the call with a console.log), but in fact if I enable the call to the method it only deletes ~ 20 files.

I noticed by chance that leaving the call to the method, followed by cb(), deletes all the files (about ~770), but since cb is passed as an argument to the method call I guess that's not the way to solve

--- lib/clean.js.orig   2020-02-27 04:33:19.244345901 +0100
+++ lib/clean.js        2020-02-27 04:32:42.758586741 +0100
@@ -35,6 +35,7 @@
 
                if ( method ) {
                        self[ method ]( self.normalize(remote.path), cb );
+                       cb();
                } else {
                        cb();
                }

Below how I'm using clean(), not sure if it is correctly called in gulp (if I should wrap or terminate with something):

export function deployClean() {
    var conn = ftp.create({
        host:     'localhost',
        user:     'ftpuser',
        password: 'password',
        log:      gutil.log,
        secure: true,
        secureOtions: { rejectUnauthorized: false },
    });
    var cleanGlobs = [
        '**/*.php',
        '**/*.js',
    ];
    return new Promise((resolve, reject) => {
        conn.clean( cleanGlobs, './output', { base: '/' } )
            .on('error', reject)
            .on('finish', resolve)
    })
}

Every other time it works, but deleting only ~20 files, when it doesn't work there is this error:

[10:37:39] 'deployClean' errored after 876 ms
[10:37:39] Error: write after end
    at writeAfterEnd (/appjs/node_modules/readable-stream/lib/_stream_writable.js:288:12)
    at ParallelTransform.Writable.write (/appjs/node_modules/readable-stream/lib/_stream_writable.js:332:20)
    at PassThrough.ondata (_stream_readable.js:728:22)
    at PassThrough.emit (events.js:223:5)
    at PassThrough.EventEmitter.emit (domain.js:498:23)
    at PassThrough.Readable.read (_stream_readable.js:526:10)
    at flow (_stream_readable.js:1001:34)
    at ParallelTransform.pipeOnDrainFunctionResult (_stream_readable.js:804:7)
    at ParallelTransform.emit (events.js:223:5)
    at ParallelTransform.EventEmitter.emit (domain.js:498:23)

xenogenesi avatar Feb 27 '20 09:02 xenogenesi

Confirm same trouble...

c00lib1n avatar Mar 24 '20 10:03 c00lib1n

Personally, an invasive operation that removes files and directories, I would divide it into 2 steps:

  1. having a call that gives me the list of files/directories to be deleted in some easy-to-process format (json?)
  2. have method that takes the generated json and eliminates the paths contained

This would allow you to more easily check what is deleted without deleting, filter the files to be deleted (solving the problem that at the moment negative patterns do not work !), And would eventually allow you to easily use other programs/scripts to actually carry out the elimination.

xenogenesi avatar Mar 25 '20 01:03 xenogenesi