2 unstable releases
Uses new Rust 2024
| 0.2.0 | Oct 22, 2025 |
|---|---|
| 0.1.0 | Oct 21, 2025 |
#401 in Audio
50 downloads per month
Used in 2 crates
39KB
660 lines
mime-type
A Rust library for working with MIME types and file extensions. This crate provides a simple, ergonomic API for converting between file extensions and their corresponding MIME type strings.
Features
- Type-safe MIME type handling with enums for different categories
- Bidirectional conversion between file extensions and MIME type strings
- Multiple categories including images, videos, audio, documents, archives, fonts, books, and applications
- Zero dependencies and lightweight
- Display trait implementation for easy MIME type string output
Usage
Getting MIME type from file extension
use mime_type::{MimeType, MimeFormat};
// Get MIME type from extension
let mime = MimeType::from_ext("png");
assert_eq!(mime.unwrap().to_string(), "image/png");
// Works with multiple extensions for the same format
let jpeg1 = MimeType::from_ext("jpg");
let jpeg2 = MimeType::from_ext("jpeg");
assert_eq!(jpeg1.unwrap().to_string(), jpeg2.unwrap().to_string());
// Returns None for unknown extensions
let unknown = MimeType::from_ext("unknown");
assert!(unknown.is_none());
Getting MIME type from MIME string
use mime_type::{MimeType, MimeFormat};
let mime = MimeType::from_mime("video/mp4");
match mime {
Some(MimeType::Video(video)) => println!("It's a video: {}", video),
_ => println!("Not a video"),
}
Working with specific categories
use mime_type::{Image, Video, Audio, Document, MimeFormat};
// Directly use category enums
let png = Image::Png;
println!("{}", png); // Outputs: image/png
// Check extensions for specific categories
if let Some(mime) = Image::from_ext("webp") {
println!("Found image: {}", mime);
}
Pattern matching on MIME types
use mime_type::{MimeType, MimeFormat};
let mime = MimeType::from_ext("mp3").unwrap();
match mime {
MimeType::Audio(audio) => println!("Audio file: {}", audio),
MimeType::Video(video) => println!("Video file: {}", video),
MimeType::Image(image) => println!("Image file: {}", image),
_ => println!("Other file type"),
}
Supported Categories
Image Formats
JPEG, PNG, GIF, WebP, CR2, TIFF, BMP, HEIF, AVIF, JXR, PSD, ICO, ORA, DjVu
Video Formats
MP4, M4V, MKV, WebM, MOV, AVI, WMV, MPG, FLV
Audio Formats
MIDI, MP3, M4A, OGG, FLAC, WAV, AMR, AAC, AIFF, DSF, APE
Document Formats
DOC, DOCX, XLS, XLSX, PPT, PPTX, ODT, ODS, ODP
Archive Formats
ZIP, TAR, RAR, GZ, BZ2, 7Z, XZ, PDF, and many more
Font Formats
TTF, OTF, WOFF, WOFF2
Book Formats
EPUB, MOBI
Application Formats
WASM, EXE, DLL, ELF, and various executable formats
Edge Cases and Known Limitations
Duplicate MIME Types
Some file formats share the same MIME type but have different extensions:
EXE and DLL: Both map to application/vnd.microsoft.portable-executable
- When converting from MIME type to extension, only
EXEvariant is returned - This is by design as they share the same PE (Portable Executable) format
ELF and OBJ: Both map to application/x-executable
- When converting from MIME type, only
ELFvariant is returned - These represent different executable object formats but share a MIME type
EPUB Duplication
EPUB files appear in both Archive and Book categories:
Archive::Epubmaps toapplication/epub+zipBook::Epubalso maps toapplication/epub+zip
Behavior:
MimeType::from_ext("epub")returnsMimeType::Archive(Archive::Epub)(Archive is checked first)MimeType::from_mime("application/epub+zip")returnsMimeType::Archive(Archive::Epub)- The
Book::Epubvariant is effectively unreachable through the standard API
Recommendation: Use Archive::Epub for EPUB files, or access Book::Epub directly if you need the Book variant specifically.
Font MIME Type Ambiguity
Font formats have some MIME type overlap:
TTF and OTF: Both return application/font-sfnt
- When converting from this MIME type, only
TTFis returned - Both use the SFNT (Spline Font) container format
WOFF and WOFF2: Both currently return application/font-woff
- This is likely a bug; WOFF2 should use
font/woff2 - When converting from MIME type, only
WOFFis returned
One-Way Mappings
Some conversions are not perfectly reversible:
// Extension -> MIME -> Extension may not round-trip
let mime = MimeType::from_ext("dll").unwrap();
// mime.to_string() == "application/vnd.microsoft.portable-executable"
// But from_mime() would return Application::Exe, not Dll
Case Sensitivity
- File extensions are case-sensitive in the current implementation
.JPG(uppercase) will not match, only.jpg(lowercase) will- Always normalize extensions to lowercase before using this library
Publishing
To publish a new version of the crate to crates.io, use the publish.sh script:
./publish.sh <version>
For example:
./publish.sh 0.2.0
The script will:
- Validate the version format (must be X.Y.Z)
- Check that you're on the
mainbranch - Verify the version isn't already in
Cargo.toml - Update the version in
Cargo.toml - Commit the changes with message "Release version to X.Y.Z"
- Create a git tag with the version number
- Push the tag and changes to the remote repository
Note: The actual publishing to crates.io is done by the GitHub Actions workflow.