Fix bracket parsing for FETCH responses

fork
mscdex 11 years ago
parent 9e31da73c8
commit 97a2fb06a4

@ -31,7 +31,6 @@ var CRLF = '\r\n',
RE_CMD_FETCH = /^(?:UID )?FETCH/i,
RE_PARTID = /^(?:[\d]+[\.]{0,1})*[\d]+$/,
RE_ESCAPE = /\\\\/g,
//RE_ISPARTIAL = /<(\d+)>$/,
RE_DBLQ = /"/g,
RE_CMD = /^([^ ]+)(?: |$)/,
RE_ISHEADER = /HEADER/,
@ -260,7 +259,6 @@ ImapConnection.prototype.connect = function(loginCb) {
if (indata.expect > 0) {
r = read(b);
if (indata.streaming) {
//requests[0].fetchers[requests[0].key].msg.emit('data', r);
emitLitData(requests[0].key, r);
if (indata.expect === 0)
indata.streaming = false;
@ -290,8 +288,6 @@ ImapConnection.prototype.connect = function(loginCb) {
litType = m[1];
indata.expect = (m ? parseInt(m[2], 10) : -1);
if (indata.expect > -1) {
/*if (RE_ISPARTIAL.test(litType))
litType = litType.replace(RE_ISPARTIAL, '<$1.' + indata.expect + '>');*/
if ((m = /\* (\d+) FETCH/i.exec(indata.line))
&& /^BODY\[/i.test(litType)) {
msg = new ImapMessage();
@ -1187,18 +1183,7 @@ ImapConnection.prototype._fetch = function(which, uids, options, what, cb) {
key = pprefix;
if (wp.body === true)
key += 'TEXT]';
/*else if (typeof wp.body.start === 'number'
&& typeof wp.body.length === 'number') {
if (wp.body.start < 0)
throw new Error('Invalid `start` value: ' + wp.body.start);
else if (wp.body.length <= 0)
throw new Error('Invalid `length` value: ' + wp.body.length);
key += 'TEXT]<';
key += wp.body.start;
key += '.';
key += wp.body.length;
key += '>';
}*/ else
else
throw new Error('Invalid `body` value: ' + wp.body);
key = key.trim();

@ -82,28 +82,7 @@ exports.parseFetchBodies = function(str, literals) {
if (Array.isArray(result[i])) {
if (result[i].length === 0)
result[i].push('');
/*else if (result[i].length === 2 && typeof result[i][1] === 'number') {
// OK, so ordinarily this is where we'd transform a partial fetch
// key so that it matches up with a key in our request's fetchers object
// but since IMAP sucks, we have no way to match up a partial fetch
// response if less than the number of octets we requested were returned.
//
// Example: We request BODY[TEXT]<0.32>, but BODY[TEXT] is only 16 bytes,
// then we get back: BODY[TEXT]<0> {16}
// This leaves us with no way to find out what the original
// length request was. ARGH!!!^%&#^@#$%&$!
// Because of this and the fact that the server can return requested
// values in any order, I am disabling partial fetches entirely.
// BODY[TEXT]<0.32>
result[i][0] += '<';
result[i][0] += result[i][1]; // starting octet
result[i][0] += '.';
if (typeof result[i + 1] === 'number')
result[i][0] += result[i + 1];
else if (typeof
result[i][0] += '>';
}*/ else if (result[i].length > 1) {
else if (result[i].length > 1) {
// HEADER.FIELDS (foo) or HEADER.FIELDS (foo bar baz)
result[i][0] += ' (';
if (Array.isArray(result[i][1]))
@ -125,11 +104,11 @@ exports.parseFetchBodies = function(str, literals) {
exports.parseFetch = function(str, literals, fetchData) {
literals.lp = 0;
var result = exports.parseExpr(str, literals);
var result = exports.parseExpr(str, literals, false, 0, false);
for (var i = 0, len = result.length; i < len; i += 2) {
if (Array.isArray(result[i]))
continue;
result[i] = result[i].toUpperCase();
if (/^BODY\[/.test(result[i]))
continue;
if (result[i] === 'UID')
fetchData.uid = parseInt(result[i + 1], 10);
else if (result[i] === 'INTERNALDATE')
@ -325,10 +304,12 @@ exports.parseStructExtra = function(part, partLen, cur, next) {
}
};
exports.parseExpr = function(o, literals, result, start) {
exports.parseExpr = function(o, literals, result, start, useBrackets) {
start = start || 0;
var inQuote = false, lastPos = start - 1, isTop = false, inLitStart = false,
val;
if (useBrackets === undefined)
useBrackets = true;
if (!result)
result = [];
if (typeof o === 'string') {
@ -339,27 +320,21 @@ exports.parseExpr = function(o, literals, result, start) {
if (!inQuote) {
if (o.str[i] === '"')
inQuote = true;
else if (o.str[i] === ' ' || o.str[i] === ')' || o.str[i] === ']') {
else if (o.str[i] === ' ' || o.str[i] === ')'
|| (useBrackets && o.str[i] === ']')) {
if (i - (lastPos + 1) > 0) {
val = exports.convStr(o.str.substring(lastPos + 1, i), literals);
result.push(val);
}
if ((o.str[i] === ')' || o.str[i] === ']') && !isTop)
if ((o.str[i] === ')' || (useBrackets && o.str[i] === ']')) && !isTop)
return i;
lastPos = i;
} else if ((o.str[i] === '(' || o.str[i] === '[')) {
} else if ((o.str[i] === '(' || (useBrackets && o.str[i] === '['))) {
var innerResult = [];
i = exports.parseExpr(o, literals, innerResult, i + 1);
i = exports.parseExpr(o, literals, innerResult, i + 1, useBrackets);
lastPos = i;
result.push(innerResult);
}/* else if (i > 0 && o.str[i] === '<' && o.str[i - 1] === ']') {
lastPos = i;
inLitStart = true;
} else if (o.str[i] === '>' && inLitStart) {
val = exports.convStr(o.str.substring(lastPos + 1, i), literals);
result[result.length - 1].push(val);
inLitStart = false;
}*/
}
} else if (o.str[i] === '"' &&
(o.str[i - 1] &&
(o.str[i - 1] !== '\\'

Loading…
Cancel
Save