Socket
Socket
Sign inDemoInstall

jsftp

Package Overview
Dependencies
Maintainers
1
Versions
84
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

jsftp - npm Package Compare versions

Comparing version 1.5.3 to 1.5.4

73

.vscode/launch.json
{
"version": "0.1.0",
// List of configurations. Add new configurations or edit existing ones.
// ONLY "node" and "mono" are supported, change "type" to switch.
"configurations": [
{
// Name of configuration; appears in the launch configuration drop down menu.
"name": "Launch app.js",
// Type of configuration. Possible values: "node", "mono".
"type": "node",
// Workspace relative or absolute path to the program.
"program": "app.js",
// Automatically stop program after launch.
"stopOnEntry": true,
// Command line arguments passed to the program.
"args": [],
// Workspace relative or absolute path to the working directory of the program being debugged. Default is the current workspace.
"cwd": ".",
// Workspace relative or absolute path to the runtime executable to be used. Default is the runtime executable on the PATH.
"runtimeExecutable": null,
// Optional arguments passed to the runtime executable.
"runtimeArguments": [],
// Environment variables passed to the program.
"env": { },
// Use JavaScript source maps (if they exist).
"sourceMaps": false
},
{
"name": "Attach",
"type": "node",
// TCP/IP address. Default is "localhost".
"address": "localhost",
// Port to attach to.
"port": 5858,
"sourceMaps": false
}
]
}
"version": "0.2.0",
"configurations": [
{
"name": "Launch",
"type": "node",
"request": "launch",
"program": "${workspaceRoot}/jsftp.js",
"stopOnEntry": false,
"args": [],
"cwd": "${workspaceRoot}",
"preLaunchTask": null,
"runtimeExecutable": null,
"runtimeArgs": [
"--nolazy"
],
"env": {
"NODE_ENV": "development"
},
"externalConsole": false,
"sourceMaps": false,
"outDir": null
},
{
"name": "Attach",
"type": "node",
"request": "attach",
"port": 5858,
"address": "localhost",
"restart": false,
"sourceMaps": false,
"outDir": null,
"localRoot": "${workspaceRoot}",
"remoteRoot": null
}
]
}

@@ -29,3 +29,3 @@ /* vim:set ts=2 sw=2 sts=2 expandtab */

var IDLE_TIME = 30000;
var NOOP = function() {};
var NOOP = function() { };
var COMMANDS = [

@@ -35,6 +35,6 @@ // Commands without parameters

// Commands with one or more parameters
'cwd', 'dele', 'list', 'mdtm', 'mkd', 'mode', 'nlst', 'pass', 'retr', 'rmd',
'rnfr', 'rnto', 'site', 'stat', 'stor', 'type', 'user', 'xrmd', 'opts',
'appe', 'cwd', 'dele', 'list', 'mdtm', 'mkd', 'mode', 'nlst', 'pass', 'retr', 'rmd',
'rnfr', 'rnto', 'site', 'stat', 'stor', 'type', 'user', 'xrmd', 'opts', 'rest',
// Extended features
'chmod', 'size'
'chmod', 'size', 'mlst', 'mlsdt',
];

@@ -44,22 +44,21 @@

marks: [125, 150],
ignore: 226
ignore: 226,
};
// Regular Expressions
var RE_PASV = /([-\d]+,[-\d]+,[-\d]+,[-\d]+),([-\d]+),([-\d]+)/;
var FTP_NEWLINE = /\r\n|\n/;
function getPasvPort(text, callback) {
function getPasvPort(text) {
var match = RE_PASV.exec(text);
if (!match) {
return callback(new Error('Bad passive host/port combination'));
return null;
}
callback(null, {
return {
host: match[1].replace(/,/g, '.'),
port: (parseInt(match[2], 10) & 255) * 256 + (parseInt(match[3], 10) & 255)
});
port: (parseInt(match[2], 10) & 255) * 256 + (parseInt(match[3], 10) & 255),
};
}
function runCmd(cmd) {
function runCmd() {
var callback = NOOP;

@@ -78,29 +77,28 @@ var args = [].slice.call(arguments);

var Ftp = module.exports = function(cfg) {
var self = this;
Object.keys(cfg).forEach(function(option) {
self[option] = self[option] || cfg[option];
});
EventEmitter.call(this);
this.host = cfg.host || 'localhost';
this.port = cfg.port || FTP_PORT;
this.user = cfg.user || 'anonymous';
this.pass = cfg.pass || '@anonymous';
// True if the server doesn't support the `stat` command. Since listing a
// directory or retrieving file properties is quite a common operation, it is
// more efficient to avoid the round-trip to the server.
this.useList = false;
this.port = this.port || FTP_PORT;
this.useList = cfg.useList || false;
this.commandQueue = [];
EventEmitter.call(this);
var self = this;
// Generate generic methods from parameter names. they can easily be
// overriden if we need special behavior. they accept any parameters given,
// it is the responsability of the user to validate the parameters.
this.raw = function() { return runCmd.apply(self, arguments); };
// it is the responsibility of the user to validate the parameters.
this.raw = function() {
return runCmd.apply(self, arguments);
};
COMMANDS.forEach(function(cmd) {
self.raw[cmd] = runCmd.bind(self, cmd);
});
COMMANDS.forEach(function(cmd) { self.raw[cmd] = runCmd.bind(self, cmd); });
this.on('data', dbgResponse);
this.on('data', function(data) {
if (self.debugMode)
self.emit('jsftp_debug', 'response', data || {});
});
this._createSocket(this.port, this.host);

@@ -111,8 +109,2 @@ };

Ftp.prototype.setDebugMode = function(debugOn) {
console.warn('`setDebugMode` is deprecated and will be removed in the ' +
'future. For debugging, set the DEBUG env variable to 1.');
this.debugMode = (debugOn !== false);
};
Ftp.prototype.reemit = function(event) {

@@ -123,5 +115,2 @@ var self = this;

debug('event:' + event, data || {});
if (self.debugMode) {
self.emit('jsftp_debug', 'event:' + event, data || {});
}
};

@@ -152,3 +141,3 @@ };

dbgResponse(data.text);
self.parseResponse.call(self, data);
self.parseResponse(data);
});

@@ -159,4 +148,8 @@ this.pipeline.on('error', this.reemit('error'));

Ftp.prototype.parseResponse = function(response) {
if (this.commandQueue.length === 0) return;
if ([220].indexOf(response.code) > -1) return;
if (this.commandQueue.length === 0) {
return;
}
if ([220].indexOf(response.code) > -1) {
return;
}

@@ -167,3 +160,3 @@ var next = this.commandQueue[0].callback;

if (!next.expectsMark ||
next.expectsMark.marks.indexOf(response.code) === -1) {
next.expectsMark.marks.indexOf(response.code) === -1) {
return;

@@ -192,3 +185,5 @@ }

Ftp.prototype.send = function(command) {
if (!command) return;
if (!command) {
return;
}

@@ -198,5 +193,3 @@ dbgCommand(command);

if (this.debugMode) {
this.emit('jsftp_debug', 'user_command', command);
}
dbgCommand(command);
};

@@ -239,6 +232,6 @@

action: action,
callback: callback
callback: callback,
};
if (this.authenticated || /feat|syst|user|pass/.test(action)) {
if (this.authenticated || /^(feat|syst|user|pass)/.test(action)) {
this.commandQueue.push(cmd);

@@ -298,4 +291,8 @@ this.nextCmd();

return featureLines
.map(function(feat) { return feat.trim().toLowerCase(); })
.filter(function(feat) { return !!feat; });
.map(function(feat) {
return feat.trim().toLowerCase();
})
.filter(function(feat) {
return !!feat;
});
};

@@ -337,4 +334,8 @@

if (!user) user = 'anonymous';
if (!pass) pass = '@anonymous';
if (!user) {
user = 'anonymous';
}
if (!pass) {
pass = '@anonymous';
}

@@ -348,3 +349,2 @@ this.authenticating = true;

}
self.raw.pass(pass, function(err, res) {

@@ -377,3 +377,5 @@ self.authenticating = false;

this.raw.type(type, function(err, data) {
if (!err) self.type = type;
if (!err) {
self.type = type;
}

@@ -400,33 +402,39 @@ callback(err, data);

self.getPasvSocket(function(err, socket) {
if (err) return callback(err);
self.getPasvSocket(function(err, socket) {
if (err) {
return callback(err);
}
socket.setEncoding('utf8');
socket.on('data', function(data) {
listing += data;
});
socket.setEncoding('utf8');
socket.on('data', function(data) {
listing += data;
});
self.pasvTimeout.call(self, socket, callback);
self.pasvTimeout(socket, callback);
socket.once('close', function(err) { callback(err, listing); });
socket.once('error', callback);
socket.once('close', function(err) {
callback(err, listing);
});
socket.once('error', callback);
function cmdCallback(err, res) {
if (err) return callback(err);
function cmdCallback(err, res) {
if (err) {
return callback(err);
}
var isExpectedMark = expectedMarks.marks.some(function(mark) {
return mark === res.code;
});
var isExpectedMark = expectedMarks.marks.some(function(mark) {
return mark === res.code;
});
if (!isExpectedMark) {
callback(new Error(
'Expected marks ' + expectedMarks.toString() + ' instead of: ' +
res.text));
}
if (!isExpectedMark) {
callback(new Error(
'Expected marks ' + expectedMarks.toString() + ' instead of: ' +
res.text));
}
}
cmdCallback.expectsMark = expectedMarks;
cmdCallback.expectsMark = expectedMarks;
self.execute('list ' + (path || ''), cmdCallback);
});
self.execute('list ' + (path || ''), cmdCallback);
});
};

@@ -439,4 +447,3 @@

total: data.totalSize || 0,
transferred: data.socket[
data.action === 'get' ? 'bytesRead' : 'bytesWritten']
transferred: data.socket[data.action === 'get' ? 'bytesRead' : 'bytesWritten']
});

@@ -487,3 +494,2 @@ };

socket.pipe(writeStream);
socket.resume();
};

@@ -508,3 +514,5 @@ }

this.getPasvSocket(function(err, socket) {
if (err) return cmdCallback(err);
if (err) {
return cmdCallback(err);
}

@@ -518,3 +526,3 @@ socket.on('error', function(err) {

self.pasvTimeout.call(self, socket, cmdCallback);
self.pasvTimeout(socket, cmdCallback);
socket.pause();

@@ -565,4 +573,5 @@

self.getPutSocket(to, function(err, socket) {
if (err) return;
from.pipe(socket);
if (!err) {
from.pipe(socket);
}
}, callback);

@@ -573,3 +582,5 @@ }

this.getPutSocket(to, function(err, socket) {
if (!err) socket.end(from);
if (!err) {
socket.end(from);
}
}, callback);

@@ -579,3 +590,3 @@ } else if (typeof from === 'string') {

if (err && err.code === 'ENOENT') {
return callback(new Error('Local file doesn\'t exist.'));
return callback(new Error("Local file doesn't exist."));
}

@@ -614,3 +625,5 @@

this.getPasvSocket(function(err, socket) {
if (err) return _callback(err);
if (err) {
return _callback(err);
}
socket.on('close', doneCallback);

@@ -620,3 +633,5 @@ socket.on('error', doneCallback);

var putCallback = once(function putCallback(err, res) {
if (err) return _callback(err);
if (err) {
return _callback(err);
}

@@ -626,3 +641,3 @@ // Mark 150 indicates that the 'STOR' socket is ready to receive data.

if (res.code === 125 || res.code === 150) {
self.pasvTimeout.call(self, socket, doneCallback);
self.pasvTimeout(socket, doneCallback);
return _callback(null, socket);

@@ -640,3 +655,3 @@ }

Ftp.prototype.pasvTimeout = function(socket, cb) {
Ftp.prototype.pasvTimeout = function(socket, callback) {
var self = this;

@@ -647,3 +662,3 @@ socket.once('timeout', function() {

socket.end();
cb(new Error('Passive socket timeout'));
callback(new Error('Passive socket timeout'));
});

@@ -657,18 +672,18 @@ };

this.execute('pasv', function(err, res) {
if (err) return callback(err);
if (err) {
return callback(err);
}
getPasvPort(res.text, function(err, options) {
if (err) return callback(err);
var options = getPasvPort(res.text);
if (!options) {
return callback(new Error('Bad passive host/port combination'));
}
var socket = self._pasvSocket = Net.createConnection(options);
socket.setTimeout(self.timeout || TIMEOUT);
socket.once('connect', function() {
self._pasvSocket = socket;
});
socket.once('close', function() {
self._pasvSocket = undefined;
});
var socket = self._pasvSocket = Net.createConnection(options);
socket.setTimeout(self.timeout || TIMEOUT);
socket.once('close', function() {
self._pasvSocket = undefined;
});
callback(null, socket);
});
callback(null, socket);
});

@@ -706,14 +721,18 @@ };

function entriesToList(err, entries) {
if (err) return callback(err);
if (err) {
return callback(err);
}
ListingParser.parseFtpEntries(entries.text || entries, function(err, files) {
if (err) return callback(err);
if (err) {
return callback(err);
}
files.forEach(function(file) {
// Normalize UTF8 doing canonical decomposition, followed by
// canonical Composition
file.name = unorm.nfc(file.name);
});
callback(null, files);
files.forEach(function(file) {
// Normalize UTF8 doing canonical decomposition, followed by
// canonical Composition
file.name = unorm.nfc(file.name);
});
callback(null, files);
});
}

@@ -730,8 +749,8 @@

// trips to the server to check.
if ((err && (err.code === 502 || err.code === 500)) ||
(self.system && self.system.indexOf('hummingbird') > -1))
// Not sure if the 'hummingbird' system check ^^^ is still
// necessary. If they support any standards, the 500 error
// should have us covered. Let's leave it for now.
{
var errored = (err && (err.code === 502 || err.code === 500));
var isHummingbird = self.system && self.system.indexOf('hummingbird') > -1;
if (errored || isHummingbird) {
// Not sure if the 'hummingbird' system check ^^^ is still
// necessary. If they support any standards, the 500 error
// should have us covered. Let's leave it for now.
self.useList = true;

@@ -749,7 +768,6 @@ self.list(filePath, entriesToList);

this.raw.rnfr(from, function(err) {
if (err) return callback(err);
self.raw.rnto(to, function(err, res) {
callback(err, res);
});
if (err) {
return callback(err);
}
self.raw.rnto(to, callback);
});

@@ -756,0 +774,0 @@ };

{
"name": "jsftp",
"id": "jsftp",
"version": "1.5.3",
"version": "1.5.4",
"description": "A sane FTP client implementation for NodeJS",

@@ -24,19 +24,20 @@ "keywords": [

"dependencies": {
"debug": "2.2.0",
"event-stream": "3.1.7",
"ftp-response-parser": "1.0.0",
"once": "1.3.0",
"parse-listing": "1.1.3",
"unorm": "1.4.1"
"debug": "^2.2.0",
"event-stream": "^3.1.7",
"ftp-response-parser": "^1.0.1",
"once": "^1.3.3",
"parse-listing": "^1.1.3",
"unorm": "^1.4.1"
},
"devDependencies": {
"concat-stream": "1.5.0",
"concat-stream": "^1.5.0",
"ftp-test-server": "0.0.2",
"istanbul": "0.3.22",
"mocha": "1.21.4",
"ftpd": "^0.2.15",
"istanbul": "^0.3.22",
"mocha": "^1.21.4",
"mocha-istanbul": "0.2.0",
"rimraf": "2.2.8",
"sinon": "1.17.1"
"rimraf": "^2.2.8",
"sinon": "^1.17.1"
},
"main": "./jsftp.js",
"main": "lib/jsftp.js",
"engines": {

@@ -49,8 +50,3 @@ "node": ">=0.10"

},
"licenses": [
{
"type": "MIT",
"url": "https://github.com/sergi/jsftp/blob/master/LICENSE"
}
]
"license": "MIT"
}

@@ -1,9 +0,15 @@

jsftp [![Build Status](https://secure.travis-ci.org/sergi/jsftp.png)](http://travis-ci.org/sergi/jsftp) <a href="http://flattr.com/thing/1452098/" target="_blank"><img src="http://api.flattr.com/button/flattr-badge-large.png" alt="Flattr this" title="Flattr this" border="0" /></a>
=====
# jsftp [![travis][travis-image]][travis-url] [![npm][npm-image]][npm-url] [![downloads][downloads-image]][downloads-url] [![js-semistandard-style][semistandard-image]][semistandard-url]
[travis-image]: https://img.shields.io/travis/sergi/jsftp.svg?style=flat
[travis-url]: https://travis-ci.org/sergi/jsftp
[npm-image]: https://img.shields.io/npm/v/jsftp.svg?style=flat
[npm-url]: https://npmjs.org/package/jsftp
[downloads-image]: https://img.shields.io/npm/dm/jsftp.svg?style=flat
[downloads-url]: https://npmjs.org/package/jsftp
[semistandard-image]: https://img.shields.io/badge/code%20style-semistandard-brightgreen.svg?style=flat-square
[semistandard-url]: https://github.com/Flet/semistandard
A client FTP library for NodeJS that focuses on correctness, clarity
and conciseness. It doesn't get in the way and plays nice with streaming APIs.
[![NPM](https://nodei.co/npm/jsftp.png)](https://nodei.co/npm/jsftp/)
Starting it up

@@ -219,3 +225,3 @@ --------------

Ftp.setDebugMode(true); // Debug Mode on
Ftp.setDebugMode(false; // Debug mode off
Ftp.setDebugMode(false); // Debug mode off
```

@@ -222,0 +228,0 @@

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc