NAME
Module::Generic::File::Magic - File type and MIME detection with 3-level backend cascade
SYNOPSIS
use Module::Generic::File::Magic qw( :flags );
my $magic = Module::Generic::File::Magic->new( flags => MAGIC_MIME_TYPE ) ||
die( Module::Generic::File::Magic->error );
# Which backend is active?
printf "Backend: %s\n", $magic->backend; # xs, json, or file
# Detect from a file path
my $mime = $magic->from_file( '/path/to/archive.tar.gz' ) ||
die( $magic->error );
# -> "application/gzip"
# Detect from an in-memory buffer
open( my $fh, '<:raw', '/path/to/file' ) or die( $! );
read( $fh, my $buf, 4096 );
close( $fh );
my $mime = $magic->from_buffer( $buf ) || die( $magic->error );
# Detect from an open filehandle
open( my $fh, '<:raw', '/path/to/file' ) or die( $! );
my $mime = $magic->from_filehandle( $fh ) || die( $magic->error );
# Convenience wrappers
my $type = $magic->mime_type_from_file( '/path/to/file' );
my $enc = $magic->mime_encoding_from_file( '/path/to/file' );
my $full = $magic->mime_from_file( '/path/to/file' );
# -> "application/gzip; charset=binary"
# Control the read size for pure-Perl backends (default: 512 bytes)
my $magic2 = Module::Generic::File::Magic->new(
flags => MAGIC_MIME_TYPE,
max_read => 1024,
) || die( Module::Generic::File::Magic->error );
# Change max_read at any time
$magic->max_read(1024);
# Procedural interface
use Module::Generic::File::Magic qw( :functions );
my $mime = magic_mime_type( '/path/to/file' );
VERSION
v0.1.0
DESCRIPTION
Module::Generic::File::Magic detects file types and MIME types using a three-level cascade, automatically selecting the best available backend:
- Level 1 — xs (preferred)
-
libmagic.so.1is loaded at runtime viadlopen(3)— nomagic.h, nolibmagic-devpackage required at build time. Full libmagic accuracy and performance. TheMAGIC_COMPRESS,MAGIC_SYMLINK, and all other flags are fully supported.compile(),check(), andlist()are only available at this level. - Level 2 — json
-
libmagicis absent. The module loadslib/Module/Generic/File/magic.json(generated from the freedesktop.org shared-mime-info database, bundled with the distribution) and runs pure-Perl byte-pattern matching. Covers ~500 MIME types with magic signatures. - Level 3 — file
-
No pattern matched at level 2. Invokes
file(1)in a subprocess as a last resort.from_bufferwrites a temporary file via File::Temp.
The active backend is available via $magic->backend and the package variable $Module::Generic::File::Magic::BACKEND.
Note that within the json backend, a text-content heuristic is applied before falling through to file(1).
CONSTRUCTOR
new
my $magic = Module::Generic::File::Magic->new( %opts ) ||
die( Module::Generic::File::Magic->error );
flags— integer bitmask (default:MAGIC_NONE)magic_db— path to a custom.mgcdatabase (xs backend only)max_read— maximum bytes read from a file for pure-Perl backends (default:512)
METHODS
backend
Returns the name of the active backend: "xs", "json", or "file". Note that the reported value is the top-level configured backend; the actual detection at runtime may cascade through multiple levels.
check( [ $filename ] )
Validates a magic database. xs backend only.
close
Releases the magic_t cookie. No-op on non-xs backends.
compile( $filename )
Compiles a magic source file into a .mgc database. xs backend only.
flags
Getter/setter for the libmagic flags bitmask.
from_buffer( $scalar )
Detects type from a raw byte scalar.
from_file( $path )
Detects type from a file path.
from_filehandle( $fh )
Detects type from an open filehandle.
list( [ $filename ] )
Prints magic database entries to stdout. xs backend only.
magic_db
Getter/setter for the custom magic database path (xs backend only).
max_read( [ $bytes ] )
Getter/setter for the maximum number of bytes read from a file when using pure-Perl backends. The default is 512 bytes, which covers all signatures in the bundled JSON database. Increase this value for formats whose signatures appear at large offsets (e.g. application/x-tar at offset 257).
mime_encoding_from_buffer / _from_file / _from_filehandle
Returns the charset (e.g. binary).
mime_from_buffer / _from_file / _from_filehandle
Returns e.g. application/gzip; charset=binary.
mime_type_from_buffer / _from_file / _from_filehandle
Returns e.g. application/gzip.
version
Returns the libmagic version string (e.g. "5.45"), or undef when not using the xs backend.
EXPORTED FUNCTIONS
use Module::Generic::File::Magic qw( :functions );
magic_from_buffer( $scalar [, $flags] )
magic_from_file( $path [, $flags] )
magic_mime_type( $path )
magic_mime_encoding( $path )
EXPORT TAGS
:flags, :functions, :all
FLAG CONSTANTS
MAGIC_NONE No flags (default)
MAGIC_DEBUG Print debug messages to stderr [xs only]
MAGIC_SYMLINK Follow symlinks
MAGIC_COMPRESS Examine inside compressed files
MAGIC_DEVICES Look at block/char device content [xs only]
MAGIC_MIME_TYPE Return MIME type
MAGIC_MIME_ENCODING Return MIME charset
MAGIC_MIME MAGIC_MIME_TYPE | MAGIC_MIME_ENCODING
MAGIC_CONTINUE Return all matches [xs only]
MAGIC_CHECK Print warnings [xs only]
MAGIC_PRESERVE_ATIME Restore access time [xs only]
MAGIC_RAW Do not convert unprintable chars [xs only]
MAGIC_ERROR Treat ENOENT as real error [xs only]
MAGIC_APPLE Return Apple creator/type [xs only]
MAGIC_EXTENSION Return file extensions [xs only]
MAGIC_NO_CHECK_* Disable specific checks [xs only]
Flags marked [xs only] are silently ignored on non-xs backends.
INSTALLATION
The only requirement for the xs backend is the libmagic1 runtime package:
# Debian / Ubuntu
sudo apt-get install libmagic1
# RPM-based
sudo yum install file-libs
# macOS (Homebrew)
brew install libmagic
No libmagic-dev or file-devel required. The module compiles and works on any system with a C compiler (the same one that built Perl).
FILES
lib/Module/Generic/File/magic.jsonBundled magic signature database generated from the freedesktop.org shared-mime-info XML. Used by the json backend. To regenerate:
perl scripts/gen_magic_json.pl [xml_path] [out_json_path]
AUTHOR
Jacques Deguest <jack@deguest.jp>
SEE ALSO
Module::Generic::Finfo, File::LibMagic, File::MimeInfo
The libmagic(3) man page.
COPYRIGHT & LICENSE
Copyright (c) 2026 DEGUEST Pte. Ltd.
You can use, copy, modify and redistribute this package and associated files under the same terms as Perl itself.