Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

probe-image-size

Package Overview
Dependencies
Maintainers
1
Versions
32
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

probe-image-size - npm Package Compare versions

Comparing version 2.2.0 to 3.0.0

15

CHANGELOG.md

@@ -0,1 +1,16 @@

3.0.0 / 2016-12-02
------------------
- Rewrite internals to `Promise`.
- Separate options from url for http probe (old signature still supported
for compatibility).
- `err.status` -> `err.statusCode`
- remove `{ rejectUnauthorized: false }` from defaults.
- User-Agent string update.
- Replaced `request` dependency with `got` (read options description in doc).
- Retry requests on network fail.
- Switched from `readable-stream` to native `stream` (node 4+ has normal Stream3).
- Proper class for errors.
2.2.0 / 2016-10-26

@@ -2,0 +17,0 @@ ------------------

89

http.js
'use strict';
var once = require('./lib/common').once;
var error = require('./lib/common').error;
var request = require('request').defaults({
var ProbeError = require('./lib/common').ProbeError;
var got = require('got');
var merge = require('deepmerge');
var pkg = require('./package.json');
var probeStream = require('./stream');
var defaultAgent = pkg.name + '/' + pkg.version + '(+https://github.com/nodeca/probe-image-size)';
var defaults = {
timeout: 30000,
maxRedirects: 2,
rejectUnauthorized: false,
retries: 1,
headers: {
'User-Agent': 'Image size prober https://github.com/nodeca/probe-image-size'
'User-Agent': defaultAgent
}
});
};
var probeStream = require('./stream');
var P;
module.exports = function probeHttp(options, _callback) {
var callback = once(_callback);
var req;
module.exports = function probeHttp(src, options) {
// lazy Promise init
P = P || require('any-promise');
try {
req = request(options);
} catch (err) {
callback(err);
return;
}
return new P(function (resolve, reject) {
var request, length, finalUrl;
req.on('response', function (res) {
if (res.statusCode === 200) {
probeStream(res, function (err, result) {
req.abort();
var stream = got.stream(src, merge.all([ {}, defaults, options ], { clone: true }));
if (result) {
var length = res.headers['content-length'];
stream.on('request', function (req) {
request = req;
});
stream.on('response', function (res) {
if (res.statusCode === 200) {
var len = res.headers['content-length'];
if (length && length.match(/^\d+$/)) {
result.length = +length;
}
if (len && len.match(/^\d+$/)) length = +len;
finalUrl = res.url;
result.url = res.request.uri.href;
}
return;
}
callback(err, result);
reject(new ProbeError('bad status code: ' + res.statusCode, null, res.statusCode));
});
stream.on('error', function (err) {
if (err.statusCode) {
reject(new ProbeError('bad status code: ' + err.statusCode, null, err.statusCode));
return;
}
reject(err);
});
probeStream(stream)
.then(function (result) {
if (length) result.length = length;
result.url = finalUrl;
resolve(result);
})
.catch(reject)
.then(function () {
/* istanbul ignore else */
if (request) request.abort();
});
} else {
var err = error('bad status code: ' + res.statusCode, null, res.statusCode);
req.abort();
callback(err);
}
});
req.on('error', function (err) { callback(err); });
};

@@ -56,0 +71,0 @@

@@ -6,35 +6,48 @@ 'use strict';

var probeHttp = require('./http');
var nextTick = require('next-tick');
var merge = require('deepmerge');
// Cache for promise implementation
var P;
/* eslint-disable consistent-return */
module.exports = function get_image_size(src, callback) {
var prober;
module.exports = function get_image_size(src, options, callback) {
if (typeof src.on === 'function' && typeof src.emit === 'function') {
// looks like an EventEmitter, treating it as a stream
prober = probeStream;
} else {
prober = probeHttp;
callback = options;
if (!callback) return probeStream(src);
probeStream(src)
.then(function (size) { nextTick(callback.bind(null, null, size)); })
.catch(function (err) { nextTick(callback.bind(null, err)); });
return;
}
if (!callback) {
P = P || require('any-promise');
// HTTP (not stream)
if (typeof src === 'string') {
// `probe(string [, options, callback])`
if (typeof options === 'function') {
callback = options;
options = {};
}
options = options || {};
return new P(function (resolve, reject) {
prober(src, function (err, data) {
if (err) reject(err);
else resolve(data);
});
});
} else {
// Legacy style, `probe(object [, callback])`
callback = options;
options = merge({}, src, { clone: true });
src = options.url;
delete options.url;
}
prober(src, callback);
if (!callback) return probeHttp(src, options);
probeHttp(src, options)
.then(function (size) { nextTick(callback.bind(null, null, size)); })
.catch(function (err) { nextTick(callback.bind(null, err)); });
};
module.exports.parsers = require('./lib/parsers_stream');
module.exports.sync = require('./sync');
module.exports.Error = require('./lib/common').ProbeError;
'use strict';
var Transform = require('readable-stream').Transform;
var Transform = require('stream').Transform;
var streamParser = require('stream-parser');

@@ -19,13 +19,3 @@ var inherits = require('util').inherits;

exports.once = function (fn) {
var called = false;
return function () {
if (!called) {
called = true;
fn.apply(this, arguments);
}
};
};
exports.sliceEq = function (src, start, dest) {

@@ -78,9 +68,18 @@ for (var i = start, j = 0; j < dest.length;) {

exports.error = function (message, code, status) {
var err = new Error(message);
if (code) err.code = code;
if (status) err.status = status;
function ProbeError(message, code, statusCode) {
Error.call(this);
Error.captureStackTrace(this, this.constructor);
return err;
};
this.name = this.constructor.name;
this.message = message;
if (code) this.code = code;
if (statusCode) this.statusCode = statusCode;
}
// Inherit from Error
require('inherits')(ProbeError, Error);
exports.ProbeError = ProbeError;

@@ -35,5 +35,3 @@ 'use strict';

parser.on('finish', function () { parser.push(null); });
return parser;
};

@@ -36,5 +36,3 @@ 'use strict';

parser.on('finish', function () { parser.push(null); });
return parser;
};

@@ -102,5 +102,3 @@ 'use strict';

parser.on('finish', function () { parser.push(null); });
return parser;
};

@@ -43,5 +43,3 @@ 'use strict';

parser.on('finish', function () { parser.push(null); });
return parser;
};

@@ -39,5 +39,3 @@ 'use strict';

parser.on('finish', function () { parser.push(null); });
return parser;
};

@@ -5,3 +5,3 @@ 'use strict';

var Transform = require('readable-stream').Transform;
var Transform = require('stream').Transform;

@@ -18,3 +18,3 @@ var STATE_IDENTIFY = 0; // look for '<'

var SVG_HEIGHT_RE = /\bheight="([^%]+?)"|\bheight='([^%]+?)'/;
var SVG_VIEWBOX_RE = /\bviewbox="(.+?)"|\bviewbox='(.+?)'/;
var SVG_VIEWBOX_RE = /\bview[bB]ox="(.+?)"|\bview[bB]ox='(.+?)'/;
var SVG_UNITS_RE = /in$|mm$|cm$|pt$|pc$|px$|em$|ex$/;

@@ -189,5 +189,3 @@

parser.on('finish', function () { parser.push(null); });
return parser;
};

@@ -113,5 +113,3 @@ 'use strict';

parser.on('finish', function () { parser.push(null); });
return parser;
};

@@ -20,2 +20,3 @@ 'use strict';

// bad code block signature
parser.push(null);
return;

@@ -44,2 +45,3 @@ }

// bad code block signature
parser.push(null);
return;

@@ -103,5 +105,3 @@ }

parser.on('finish', function () { parser.push(null); });
return parser;
};

@@ -27,3 +27,3 @@ 'use strict';

var SVG_HEIGHT_RE = /\bheight="([^%]+?)"|\bheight='([^%]+?)'/;
var SVG_VIEWBOX_RE = /\bviewbox="(.+?)"|\bviewbox='(.+?)'/;
var SVG_VIEWBOX_RE = /\bview[bB]ox="(.+?)"|\bview[bB]ox='(.+?)'/;
var SVG_UNITS_RE = /in$|mm$|cm$|pt$|pc$|px$|em$|ex$/;

@@ -30,0 +30,0 @@

{
"name": "probe-image-size",
"version": "2.2.0",
"version": "3.0.0",
"description": "Get image size without full download (JPG, GIF, PNG, WebP, BMP, TIFF, PSD)",

@@ -35,4 +35,6 @@ "keywords": [

"any-promise": "^1.3.0",
"readable-stream": "^2.1.4",
"request": "^2.60.0",
"deepmerge": "^1.3.0",
"got": "^6.6.3",
"inherits": "^2.0.3",
"next-tick": "^1.0.0",
"stream-parser": "~0.3.1"

@@ -42,7 +44,7 @@ },

"coveralls": "^2.11.9",
"eslint": "~3.0.1",
"eslint": "^3.11.1",
"from2": "^2.1",
"istanbul": "^0.4.1",
"mocha": "^2.2.5"
"mocha": "^3.2.0"
}
}

@@ -34,3 +34,3 @@ probe-image-size

//
probe('http://example.com/image.jpg', function (err, result) {
probe('http://example.com/image.jpg').then(result => {
console.log(result); // =>

@@ -52,9 +52,9 @@ /*

//
probe({ url: 'http://example.com/image.jpg', timeout: 5000 }, function (err, result) {
probe('http://example.com/image.jpg', { timeout: 5000 }).then(function (result) {
console.log(result);
});
// With Promise
// With callback
//
probe('http://example.com/image.jpg').then(function (result) {
probe('http://example.com/image.jpg', function (err, result) {
console.log(result);

@@ -67,3 +67,3 @@ });

probe(input, function (err, result) {
probe(input).then(result => {
console.log(result);

@@ -87,3 +87,3 @@

### probe(src [, callback(err, result)])
### probe(src [, options, callback]) -> Promise

@@ -93,8 +93,9 @@ `src` can be of this types:

- __String__ - URL to fetch
- __Object__ - options for [request](https://github.com/request/request),
defaults are `{ timeout: 5000, maxRedirects: 2 }`
- __Stream__ - readable stream
`result` contains:
`options` - HTTP only. See [`got` documentation](https://github.com/sindresorhus/got).
Defaults changed to `{ retries: 1, timeout: 30000 }`
`result` (Promise) contains:
```js

@@ -113,10 +114,10 @@ {

`err` is an error, which is extended with:
Returned errors can be extended with 2 fields:
- `code` - equals to `ECONTENT` if the library failed to parse the file;
- `status` - equals to a HTTP status code if it receives a non-200 response.
- `code` - equals to `ECONTENT` if the library failed to parse the file;
- `status` - equals to a HTTP status code if it receives a non-200 response.
If callback not provided, `Promise` will be returned.
If callback (legacy node style) provided, `Promise` will not be returned.
__Note.__ If you use `Stream` as source, it's your responsibility to close that
__Note 1.__ If you use `Stream` as source, it's your responsibility to close that
stream in callback. In other case you can get memory leak, because stream will

@@ -126,3 +127,7 @@ be left in paused state. With http requests that's not a problem - everything

__Note 2.__ We still support legacy v2.x signature for http probe (`src` is
Object as described in [request](https://github.com/request/request)). But it
will be deprecated in next versions.
### sync.probe(src) -> result|null

@@ -129,0 +134,0 @@

'use strict';
var once = require('./lib/common').once;
var error = require('./lib/common').error;
var parsers = require('./lib/parsers_stream');
var ProbeError = require('./lib/common').ProbeError;
var parsers = require('./lib/parsers_stream');
var PassThrough = require('stream').PassThrough;
var P;
function unrecognizedFormat() {
return error('unrecognized file format', 'ECONTENT');
}
module.exports = function probeStream(stream) {
// lazy Promise init
P = P || require('any-promise');
module.exports = function probeStream(stream, _callback) {
var callback = once(function () {
// We should postpone callback to allow all piped parsers accept .write().
// In other case, if stream is closed from callback that can cause
// exceptions like "write after end".
var args = Array.prototype.slice.call(arguments);
var proxy = new PassThrough();
var cnt = 0; // count of working parsers
process.nextTick(function () {
_callback.apply(null, args);
});
});
var result = new P(function (resolve, reject) {
stream.on('error', reject);
proxy.on('error', reject);
var pStreams = [];
function nope() {}
// prevent "possible EventEmitter memory leak" warnings
stream.setMaxListeners(0);
function cleanup(strm) {
var i;
if (strm) {
stream.unpipe(strm);
strm.end();
i = pStreams.indexOf(strm);
if (i >= 0) pStreams.splice(i, 1);
return;
function parserEnd() {
proxy.unpipe(this);
this.removeAllListeners();
cnt--;
// if all parsers finished without success -> fail.
if (!cnt) reject(new ProbeError('unrecognized file format', 'ECONTENT'));
}
for (i = 0; i < pStreams.length; i++) {
stream.unpipe(pStreams[i]);
pStreams[i].end();
}
pStreams.length = 0;
}
Object.keys(parsers).forEach(function (type) {
var pStream = parsers[type]();
stream.on('error', function (err) { cleanup(); callback(err); });
cnt++;
Object.keys(parsers).forEach(function (type) {
var pStream = parsers[type]();
pStream.on('data', function (result) {
callback(null, result);
cleanup();
});
pStream.on('error', function () {
pStream.once('data', resolve);
pStream.once('end', parserEnd);
// silently ignore errors because user does not need to know
// that something wrong is happening here
pStream.on('error', nope);
proxy.pipe(pStream);
});
});
pStream.on('end', function () {
cleanup(pStream);
function cleanup() {
stream.unpipe(proxy);
proxy.end();
}
if (pStreams.length === 0) {
cleanup();
callback(unrecognizedFormat());
}
});
result.then(cleanup).catch(cleanup);
stream.pipe(pStream);
stream.pipe(proxy);
pStreams.push(pStream);
});
return result;
};

@@ -78,0 +58,0 @@

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