Comparing version 0.2.5 to 0.2.6
/* | ||
* @package jsFTP | ||
* @package jsftp | ||
* @copyright Copyright(c) 2011 Ajax.org B.V. <info AT ajax DOT org> | ||
@@ -20,6 +20,6 @@ * @author Sergi Mansilla <sergi DOT mansilla AT gmail DOT com> | ||
var FTPCredentials = { | ||
host: "sergimansilla.com", | ||
user: "fjakobs", | ||
host: "", | ||
user: "", | ||
port: 21, | ||
pass: "lecatoc" | ||
pass: "" | ||
}; | ||
@@ -148,3 +148,3 @@ | ||
} | ||
next(); | ||
@@ -151,0 +151,0 @@ }); |
204
jsftp.js
/* | ||
* @package jsFTP | ||
* @copyright Copyright(c) 2011 Ajax.org B.V. <info AT ajax DOT org> | ||
* @author Sergi Mansilla <sergi DOT mansilla AT gmail DOT com> | ||
* @package jsftp | ||
* @copyright Copyright(c) 2012 Ajax.org B.V. <info@c9.io> | ||
* @author Sergi Mansilla <sergi.mansilla@gmail.com> | ||
* @license https://github.com/sergi/jsFTP/blob/master/LICENSE MIT License | ||
@@ -9,3 +9,4 @@ */ | ||
var Net = require("net"); | ||
var ftpPasv = require("./lib/ftpPasv"); | ||
var Util = require("util"); | ||
var EventEmitter = require('events').EventEmitter; | ||
var Parser = require('./lib/ftpParser'); | ||
@@ -18,4 +19,4 @@ var S = require("streamer"); | ||
var RE_PASV = /[-\d]+,[-\d]+,[-\d]+,[-\d]+,([-\d]+),([-\d]+)/; | ||
var RE_RES = /^(\d\d\d)\s(.*)/; | ||
var RE_MULTI = /^(\d\d\d)-/; | ||
var RE_RES = /^(\d{3})\s(.*)/; | ||
var RE_MULTI = /^(\d{3})-/; | ||
var RE_NL_END = /\r\n$/; | ||
@@ -37,2 +38,31 @@ var RE_NL = /\r\n/; | ||
// From https://github.com/coolaj86/node-bufferjs | ||
function concat(bufs) { | ||
var buffer; | ||
var length = 0; | ||
var index = 0; | ||
if (!Array.isArray(bufs)) | ||
bufs = Array.prototype.slice.call(arguments); | ||
for (var i=0, l=bufs.length; i<l; i++) { | ||
buffer = bufs[i]; | ||
if (!Buffer.isBuffer(buffer)) | ||
buffer = bufs[i] = new Buffer(buffer); | ||
length += buffer.length; | ||
} | ||
buffer = new Buffer(length); | ||
bufs.forEach(function (buf, i) { | ||
buf = bufs[i]; | ||
buf.copy(buffer, index, 0, buf.length); | ||
index += buf.length; | ||
delete bufs[i]; | ||
}); | ||
return buffer; | ||
} | ||
// Queue function that maintains an ordered queue of streams. | ||
@@ -95,14 +125,10 @@ var queue = function queue() { | ||
var callback; | ||
var action = lcCmd; | ||
var action = lcCmd + " "; | ||
var args = slice.call(arguments); | ||
if (arguments.length) { | ||
var args = slice.call(arguments); | ||
if (typeof args[args.length - 1] === "function") | ||
callback = args.pop(); | ||
if (typeof args[args.length - 1] == "function") | ||
callback = args.pop(); | ||
action += args.join(" "); | ||
if (args.length) | ||
action += " " + args.join(" "); | ||
} | ||
if (lcCmd === "quit" && self._keepAliveInterval) | ||
@@ -124,7 +150,7 @@ clearInterval(self._keepAliveInterval); | ||
self.auth(self.options.user, self.options.pass, function() { | ||
enqueue(self.cmdQueue, [action, callback]); | ||
enqueue(self.cmdQueue, [action.trim(), callback]); | ||
}); | ||
} | ||
else { | ||
enqueue(self.cmdQueue, [action, callback]); | ||
enqueue(self.cmdQueue, [action.trim(), callback]); | ||
} | ||
@@ -134,7 +160,7 @@ }; | ||
this.cmdListeners = []; | ||
if (DEBUG_MODE) { | ||
this.on("command", this._log); | ||
this.on("response", this._log); | ||
} | ||
if (DEBUG_MODE) | ||
this.addCmdListener(this._log); | ||
this.host = cfg.host; | ||
@@ -144,3 +170,2 @@ this.port = cfg.port || FTP_PORT; | ||
var socket = this._createSocket(this.port, this.host); | ||
var cmd; | ||
@@ -151,3 +176,3 @@ // Writes a new command to the server, but before that it pushes the | ||
this.push = function(command, callback, onWriteCallback) { | ||
if (!command || typeof command != "string") | ||
if (!command || typeof command !== "string") | ||
return; | ||
@@ -158,9 +183,5 @@ | ||
socket.write(command + "\r\n"); | ||
self.cmdListeners.forEach(function(listener) { | ||
listener({ | ||
type: "command", | ||
code: "", | ||
text: self._sanitize(command) | ||
}); | ||
self.emit("command", { | ||
code: "", | ||
text: self._sanitize(command) | ||
}); | ||
@@ -181,11 +202,8 @@ | ||
this.connecting = true; | ||
var reConnect = function() { | ||
self.connecting = false; | ||
send(); | ||
}; | ||
try { | ||
socket = this._createSocket(this.port, this.host, reConnect); | ||
createStreams(); | ||
socket = this._createSocket(this.port, this.host, function() { | ||
self.connecting = false; | ||
send(); | ||
}); | ||
this.createStreams(); | ||
} | ||
@@ -208,4 +226,4 @@ catch (e) { | ||
var cmds, tasks; | ||
var createStreams = this.createStreams = function() { | ||
var cmd, cmds, tasks; | ||
this.createStreams = function() { | ||
self.cmdQueue = queue(); | ||
@@ -220,5 +238,3 @@ (self.nextCmd = function nextCmd() { | ||
// Stream of FTP commands from the client. | ||
cmds = function(next, stop) { | ||
cmd = next; | ||
}; | ||
cmds = function(next, stop) { cmd = next; }; | ||
@@ -234,11 +250,3 @@ /** | ||
// future. | ||
var mark = isMark(x.code); | ||
/* | ||
if (mark) { | ||
self.cmdListeners.forEach(function(listener) { | ||
listener(null, x); | ||
}); | ||
} | ||
*/ | ||
return !mark; | ||
return !isMark(x.code); | ||
}, self.serverResponse(input)), S.append(S.list(null), cmds)); | ||
@@ -253,12 +261,10 @@ | ||
createStreams(); | ||
this.createStreams(); | ||
this.cmd = cmd; | ||
}; | ||
Util.inherits(Ftp, EventEmitter); | ||
(function() { | ||
"use strict"; | ||
this.addCmdListener = function(listener) { | ||
if (this.cmdListeners.indexOf(listener) === -1) | ||
this.cmdListeners.push(listener); | ||
}; | ||
@@ -279,3 +285,3 @@ this._createSocket = function(port, host, firstTask) { | ||
socket.on("connect", function() { | ||
if (DEBUG_MODE) console.log("FTP socket connected"); | ||
this.emit("connected"); | ||
firstTask && firstTask(); | ||
@@ -295,3 +301,2 @@ self.connecting = false; | ||
this.serverResponse = function(source) { | ||
var self = this; | ||
var NL = "\n"; | ||
@@ -304,13 +309,13 @@ var buffer = []; | ||
var lines = data.replace(RE_NL_END, "").replace(RE_NL, NL).split(NL); | ||
lines.forEach(function(line) { | ||
var simpleRes = RE_RES.exec(line); | ||
var multiRes; | ||
var multiRes = RE_MULTI.exec(line); | ||
if (simpleRes) { | ||
var code = parseInt(simpleRes[1], 10); | ||
if (buffer.length) { | ||
buffer.push(line); | ||
// Multiline responses from FTP signal last line by | ||
// starting the last line with the code that they started with. | ||
if (currentCode === code) { | ||
@@ -323,13 +328,11 @@ line = buffer.join(NL); | ||
self.cmdListeners.forEach(function(listener) { | ||
listener({ | ||
type: "response", | ||
code: code, | ||
text: line | ||
}); | ||
}); | ||
next({ code: code, text: line }); | ||
var data = { | ||
code: code, | ||
text: line | ||
}; | ||
this.emit("response", data); | ||
next(data); | ||
} | ||
else { | ||
if (!buffer.length && (multiRes = RE_MULTI.exec(line))) | ||
if (!buffer.length && multiRes) | ||
currentCode = parseInt(multiRes[1], 10); | ||
@@ -339,3 +342,2 @@ | ||
} | ||
}, this); | ||
@@ -367,10 +369,11 @@ }, stop); | ||
// In FTP every response code above 399 means error in some way. | ||
// Since the RFC is not respected by many servers, we are goiong to | ||
// Since the RFC is not respected by many servers, we are going to | ||
// overgeneralize and consider every value above 399 as an error. | ||
if (ftpResponse && ftpResponse.code > 399) { | ||
err = new Error(ftpResponse.text || "Unknown FTP error.") | ||
err.code = ftpResponse.code; | ||
callback(err); | ||
} else { | ||
callback(null, ftpResponse); | ||
err = new Error(ftpResponse.text || "Unknown FTP error.") | ||
err.code = ftpResponse.code; | ||
callback(err); | ||
} | ||
else { | ||
callback(null, ftpResponse); | ||
} | ||
@@ -405,5 +408,2 @@ } | ||
this._sanitize = function(cmd) { | ||
if (!cmd) | ||
return; | ||
var _cmd = cmd.slice(0, 5); | ||
@@ -432,3 +432,3 @@ if (_cmd === "pass ") | ||
features = features.slice(1, -1).map(function(feature) { | ||
return /^\s*(\w*)\s*/.exec(feature)[1].trim().toLowerCase(); | ||
return (/^\s*(\w*)\s*/).exec(feature)[1].trim().toLowerCase(); | ||
}); | ||
@@ -481,3 +481,3 @@ } | ||
this.authenticating = true; | ||
//this._initialize(function() { | ||
this._initialize(function() { | ||
self.raw.user(user, function(err, res) { | ||
@@ -511,3 +511,3 @@ if (!err && [230, 331, 332].indexOf(res.code) > -1) { | ||
}); | ||
//}); | ||
}); | ||
}; | ||
@@ -522,3 +522,3 @@ | ||
* | ||
* mode {String}, optional: "I" or "A", referring to binary or text format, respectively. Default is binary., | ||
* mode {String}, optional: "I" or "A", referring to binary or text format, respectively. Default is binary. | ||
* cmd {String}: String of the command to execute, | ||
@@ -541,9 +541,22 @@ * onCmdWrite {function}, optional: Function to execute just after writing the command to the socket. | ||
var port = (parseInt(match[1], 10) & 255) * 256 + (parseInt(match[2], 10) & 255); | ||
self.dataConn = new ftpPasv({ | ||
host: self.host, | ||
port: port, | ||
mode: data.mode, | ||
callback: callback, | ||
ftp: self | ||
}); | ||
var contents; | ||
var onData = function(result) { | ||
if (data.mode === "I") | ||
contents = concat([contents || [], result]); | ||
else | ||
contents = [contents, result].join("\n"); | ||
}; | ||
var onEnd = function(error) { | ||
callback(error, contents); | ||
}; | ||
var psvSocket = Net.createConnection(port, self.host); | ||
psvSocket.setEncoding("utf8"); | ||
psvSocket.on("data", onData); | ||
psvSocket.on("end", onEnd); | ||
psvSocket.on("error", onEnd); | ||
self.dataConn = { | ||
socket: psvSocket | ||
}; | ||
}; | ||
@@ -581,4 +594,3 @@ | ||
this.get = function(filePath, callback) { | ||
var self = this; | ||
self.setPassive({ | ||
this.setPassive({ | ||
mode: "I", | ||
@@ -661,3 +673,3 @@ cmd: "retr " + filePath, | ||
if ((err && (data.code === 502 || data.code === 500)) || | ||
// Not sure if the "hummingbird" system check ^^^ his still | ||
// Not sure if the "hummingbird" system check ^^^ is still | ||
// necessary. If they support any standards, the 500 error | ||
@@ -674,4 +686,2 @@ // should have us covered. Let's leave it for now. | ||
} | ||
}; | ||
@@ -678,0 +688,0 @@ |
/** | ||
* @package jsFTP | ||
* @package jsftp | ||
* @copyright Copyright(c) 2011 Ajax.org B.V. <info AT ajax DOT org> | ||
* @author Sergi Mansilla <sergi DOT mansilla AT gmail DOT com> | ||
* @author Sergi Mansilla <sergi.mansilla@gmail.com> | ||
* @license https://github.com/sergi/jsFTP/blob/master/LICENSE MIT License | ||
* | ||
* See RFC at http://www.w3.org/Protocols/rfc959 | ||
* | ||
*/ | ||
// See RFC at http://www.w3.org/Protocols/rfc959 | ||
@@ -9,0 +11,0 @@ "use strict"; |
{ | ||
"name": "jsftp", | ||
"id": "jsftp", | ||
"version": "0.2.5", | ||
"version": "0.2.6", | ||
"description": "A sane FTP client implementation for NodeJS", | ||
@@ -6,0 +6,0 @@ "keywords": [ "ftp", "streams", "files", "server", "client", "async" ], |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Native code
Supply chain riskContains native code (e.g., compiled binaries or shared libraries). Including native code can obscure malicious behavior.
Found 3 instances in 1 package
2
181792
21
1654