image-size vs imageinfo
Determining Image Dimensions in Node.js Applications
image-sizeimageinfoSimilar Packages:

Determining Image Dimensions in Node.js Applications

image-size and imageinfo are both Node.js utilities designed to read image file headers and extract metadata, specifically width and height, without loading the entire image into memory. image-size is a widely adopted library that supports a broad range of modern and legacy image formats (including WebP, SVG, and HEIC) and offers both synchronous and asynchronous APIs. imageinfo is a lighter-weight alternative that focuses on speed and simplicity, primarily targeting common web formats like JPEG, PNG, and GIF, often providing a streamlined interface for quick metadata extraction. Both tools solve the problem of validating asset dimensions during build times or server-side processing without the overhead of full image decoding.

Npm Package Weekly Downloads Trend

3 Years

Github Stars Ranking

Stat Detail

Package
Downloads
Stars
Size
Issues
Publish
License
image-size02,220378 kB44a year agoMIT
imageinfo059-415 years ago-

image-size vs imageinfo: Extracting Image Dimensions in Node.js

When building backend services, build tools, or asset pipelines in Node.js, you often need to know an image's width and height without decoding the entire file. Loading a 10MB image just to read its header is wasteful. image-size and imageinfo both solve this by reading specific bytes from the file stream. However, they differ in format support, API design, and maintenance momentum. Let's compare how they handle real-world engineering tasks.

📂 Supported Formats: Broad Coverage vs Core Web Standards

image-size supports a wide array of formats, including modern web standards and some proprietary types.

  • It handles JPEG, PNG, GIF, BMP, PSD, SVG, WebP, and even HEIC.
  • This makes it robust for user-generated content platforms where file types vary wildly.
// image-size: Supports many formats out of the box
const sizeOf = require('image-size');

try {
  const dimensions = sizeOf('path/to/image.webp');
  console.log(dimensions.width, dimensions.height);
} catch (e) {
  console.error('Unsupported format or corrupt file');
}

imageinfo focuses on the most common web formats to keep the logic lean.

  • It primarily targets JPEG, PNG, GIF, and BMP.
  • If you encounter newer formats like WebP or HEIC, it may fail or return incomplete data.
// imageinfo: Focused on core formats
const imageinfo = require('imageinfo');

const info = imageinfo.checkBuffer(buffer);
if (info) {
  console.log(info.width, info.height, info.format);
} else {
  console.log('Unknown format');
}

⚡ API Style: Sync/Async Flexibility vs Buffer Focus

image-size offers both synchronous and asynchronous methods.

  • You can pass a file path directly for sync operations.
  • For non-blocking I/O, it provides a callback-based async API or Promise support.
// image-size: Async usage with Promises
const sizeOf = require('image-size');

sizeOf('path/to/image.png', (err, dimensions) => {
  if (err) throw err;
  console.log(`${dimensions.width}x${dimensions.height}`);
});

// Or with promises in newer versions
const dimensions = await sizeOf('path/to/image.png');

imageinfo is designed to work directly with buffers or strings.

  • It does not inherently handle file paths; you must read the file yourself.
  • This gives you control over I/O but adds boilerplate code for file reading.
// imageinfo: Requires manual buffer loading
const fs = require('fs');
const imageinfo = require('imageinfo');

const buffer = fs.readFileSync('path/to/image.png');
const info = imageinfo.checkBuffer(buffer);

if (info) {
  console.log(`${info.width}x${info.height}`);
}

🛡️ Error Handling: Typed Errors vs Null Returns

image-size throws exceptions when it encounters invalid files or unsupported types.

  • This forces you to use try/catch blocks, ensuring errors aren't silently ignored.
  • It provides specific error messages that help debug corrupt assets.
// image-size: Throws on error
try {
  const dimensions = sizeOf('corrupt.jpg');
} catch (err) {
  // Handle specific error types
  console.error('Failed to read dimensions:', err.message);
}

imageinfo typically returns null or undefined if detection fails.

  • You must explicitly check the return value before accessing properties.
  • This can lead to runtime errors if you forget to validate the result.
// imageinfo: Returns null on failure
const info = imageinfo.checkBuffer(buffer);

if (!info) {
  // Must manually handle failure case
  console.warn('Could not determine image info');
  return;
}

console.log(info.width);

📦 Installation and Dependencies

image-size has a few dependencies to handle different format parsers.

  • This keeps the core logic modular but increases the node_modules footprint slightly.
  • It is actively maintained, which means security patches are applied regularly.
# image-size: Standard install
npm install image-size

imageinfo is often a single-file module with zero dependencies.

  • This makes it extremely fast to install and ideal for serverless functions where size matters.
  • However, fewer dependencies mean fewer eyes on the code for security audits.
# imageinfo: Lightweight install
npm install imageinfo

🌐 Real-World Scenarios

Scenario 1: User Avatar Upload Validation

You need to ensure uploaded avatars are square and under a certain resolution.

  • Best choice: image-size
  • Why? Users might upload WebP or HEIC from mobile devices. image-size handles these gracefully.
// image-size: Handle diverse uploads
const dimensions = sizeOf(req.file.buffer);
if (dimensions.width !== dimensions.height) {
  return res.status(400).send('Image must be square');
}

Scenario 2: Static Site Build Optimization

You are generating srcset attributes for a blog during build time.

  • Best choice: imageinfo
  • Why? You control the asset pipeline, so formats are known (PNG/JPG). Speed and simplicity win.
// imageinfo: Fast build script
const buffer = fs.readFileSync(`./assets/${file}`);
const info = imageinfo.checkBuffer(buffer);
if (info) {
  generateSrcSet(info.width);
}

Scenario 3: Async Stream Processing

You are processing images from a remote URL stream without saving to disk.

  • Best choice: image-size
  • Why? Its async API integrates better with stream pipelines without manual buffer management.
// image-size: Stream friendly
const request = require('request');
const sizeOf = require('image-size');

request(url).on('response', function (response) {
  sizeOf(response, function (err, dimensions) {
    console.log(dimensions);
  });
});

📌 Summary Table

Featureimage-sizeimageinfo
Format Support🌐 Broad (WebP, SVG, HEIC, etc.)📄 Core (JPEG, PNG, GIF)
API Input📂 Path, Buffer, or Stream📦 Buffer or String
Execution⚡ Sync & Async🔄 Sync (Buffer check)
Error Style🛑 Throws Exceptions⚠️ Returns Null
Dependencies📦 Moderate🍃 Zero/Minimal
Maintenance✅ Active⚠️ Check Status

💡 Final Recommendation

Think in terms of format risk and integration complexity:

  • Need to trust user uploads? → Use image-size. The broad format support prevents crashes when users upload unexpected file types.
  • Building a controlled pipeline? → Use imageinfo. If you control the input (e.g., internal assets), the lighter weight is advantageous.
  • Need async flow?image-size has better native support for non-blocking operations.

Both libraries solve the same fundamental problem efficiently. image-size is the robust, general-purpose tool for production apps facing the open web. imageinfo is the scalpel for specific, controlled tasks where every kilobyte counts.

How to Choose: image-size vs imageinfo

  • image-size:

    Choose image-size if your project requires support for a wide variety of image formats beyond the basics, such as WebP, SVG, or HEIC, or if you need both synchronous and asynchronous API options. It is the safer bet for long-term maintenance given its larger community footprint and frequent updates, making it ideal for build tools, CMS backends, or asset pipelines where format diversity is common. The trade-off is a slightly larger dependency footprint compared to minimalistic alternatives, but the reliability and format coverage usually justify this in production environments.

  • imageinfo:

    Choose imageinfo if you need a minimal, fast solution for standard web formats (JPEG, PNG, GIF) and prefer a straightforward, callback-style or promise-based interface without extra configuration. It is well-suited for lightweight microservices, simple upload validators, or scripts where minimizing dependencies is a priority and exotic image formats are not expected. However, verify its current maintenance status before adoption, as smaller utilities in this space sometimes receive less frequent updates than broader ecosystem tools.

README for image-size

image-size

Build Status Package Version Downloads

Fast, lightweight NodeJS package to get dimensions of any image file or buffer.

Key Features

  • Zero dependencies
  • Supports all major image formats
  • Works with both files and buffers
  • Minimal memory footprint - reads only image headers
  • ESM and CommonJS support
  • TypeScript types included

Supported formats

  • BMP
  • CUR
  • DDS
  • GIF
  • HEIC (HEIF, AVCI, AVIF)
  • ICNS
  • ICO
  • J2C
  • JPEG-2000 (JP2)
  • JPEG
  • JPEG-XL
  • KTX (1 and 2)
  • PNG
  • PNM (PAM, PBM, PFM, PGM, PPM)
  • PSD
  • SVG
  • TGA
  • TIFF
  • WebP

Installation

npm install image-size
# or
yarn add image-size
# or
pnpm add image-size

Usage

Passing in a Buffer/Uint8Array

Best for streams, network requests, or when you already have the image data in memory.

import { imageSize } from 'image-size'
// or
const { imageSize } = require('image-size')

const dimensions = imageSize(buffer)
console.log(dimensions.width, dimensions.height)

Reading from a file

Best for local files. Returns a promise.

import { imageSizeFromFile } from 'image-size/fromFile'
// or
const { imageSizeFromFile } = require('image-size/fromFile')

const dimensions = await imageSizeFromFile('photos/image.jpg')
console.log(dimensions.width, dimensions.height)

Note: Reading from files has a default concurrency limit of 100 To change this limit, you can call the setConcurrency function like this:

import { setConcurrency } from 'image-size/fromFile'
// or
const { setConcurrency } = require('image-size/fromFile')
setConcurrency(123456)

Reading from a file Syncronously (not recommended) ⚠️

v1.x of this library had a sync API, that internally used sync file reads.

This isn't recommended because this blocks the node.js main thread, which reduces the performance, and prevents this library from being used concurrently.

However if you still need to use this package syncronously, you can read the file syncronously into a buffer, and then pass the buffer to this library.

import { readFileSync } from 'node:fs'
import { imageSize } from 'image-size'

const buffer = readFileSync('photos/image.jpg')
const dimensions = imageSize(buffer)
console.log(dimensions.width, dimensions.height)

3. Command Line

Useful for quick checks.

npx image-size image1.jpg image2.png

Multi-size

If the target file/buffer is an HEIF, an ICO, or a CUR file, the width and height will be the ones of the largest image in the set.

An additional images array is available and returns the dimensions of all the available images

import { imageSizeFromFile } from 'image-size/fromFile'
// or
const { imageSizeFromFile } = require('image-size/fromFile')

const { images } = await imageSizeFromFile('images/multi-size.ico')
for (const dimensions of images) {
  console.log(dimensions.width, dimensions.height)
}

Using a URL

import url from 'node:url'
import http from 'node:http'
import { imageSize } from 'image-size'

const imgUrl = 'http://my-amazing-website.com/image.jpeg'
const options = url.parse(imgUrl)

http.get(options, function (response) {
  const chunks = []
  response
    .on('data', function (chunk) {
      chunks.push(chunk)
    })
    .on('end', function () {
      const buffer = Buffer.concat(chunks)
      console.log(imageSize(buffer))
    })
})

Disabling certain image types

import { disableTypes } from 'image-size'
// or
const { disableTypes } = require('image-size')

disableTypes(['tiff', 'ico'])

JPEG image orientation

If the orientation is present in the JPEG EXIF metadata, it will be returned by the function. The orientation value is a number between 1 and 8 representing a type of orientation.

import { imageSizeFromFile } from 'image-size/fromFile'
// or
const { imageSizeFromFile } = require('image-size/fromFile')

const { width, height, orientation } = await imageSizeFromFile('images/photo.jpeg')
console.log(width, height, orientation)

Limitations

  1. Partial File Reading

    • Only reads image headers, not full files
    • Some corrupted images might still report dimensions
  2. SVG Limitations

    • Only supports pixel dimensions and viewBox
    • Percentage values not supported
  3. File Access

    • Reading from files has a default concurrency limit of 100
    • Can be adjusted using setConcurrency()
  4. Buffer Requirements

    • Some formats (like TIFF) require the full header in buffer
    • Streaming partial buffers may not work for all formats

License

MIT

Credits

not a direct port, but an attempt to have something like dabble's imagesize as a node module.

Contributors