MIME Type Reference — TypeScript source
A searchable map of common file extensions to their MIME types - text, image, audio, video, application, font, and multipart. Look up by extension or by type, filter by category, and copy the exact Content-Type string for any format.
This is the TypeScript implementation — the same logic the interactive tool runs, in a shareable, citable form.
// MIME / Content-Type reference - pure, deterministic data + lookups. No DOM,
// no React. A curated set of common file extensions mapped to their standard
// MIME types, grouped by the seven top-level media types (RFC 2046): text,
// image, audio, video, application, font, and multipart. `type` always equals
// the top-level segment of the entry's own `mime`, so the category filter and
// the Content-Type never disagree.
/** The seven top-level media types a curated entry can belong to. */
export type MimeCategory =
| 'text'
| 'image'
| 'audio'
| 'video'
| 'application'
| 'font'
| 'multipart';
export interface MimeEntry {
/** File extension, lowercase, no leading dot (e.g. `json`). */
ext: string;
/** Full MIME / Content-Type string (e.g. `application/json`). */
mime: string;
/** Top-level media type - matches the `mime` string's first segment. */
type: MimeCategory;
/** Human-readable format name (e.g. `JSON`). */
name: string;
}
/** Display order of the categories (used by the UI filter). */
export const MIME_CATEGORIES: MimeCategory[] = [
'text',
'image',
'audio',
'video',
'application',
'font',
'multipart',
];
/**
* The curated extension ↔ MIME table. One entry is one (extension, type) pair,
* so a single extension with several MIME types (e.g. `.js`) appears more than
* once, and a single MIME with several extensions (e.g. `image/jpeg`) appears
* once per extension. MIME values follow IANA / MDN conventions.
*/
export const MIME: MimeEntry[] = [
// ── text ──────────────────────────────────────────────────────────────────
{ ext: 'txt', mime: 'text/plain', type: 'text', name: 'Plain text' },
{ ext: 'html', mime: 'text/html', type: 'text', name: 'HTML document' },
{ ext: 'htm', mime: 'text/html', type: 'text', name: 'HTML document' },
{ ext: 'xhtml', mime: 'application/xhtml+xml', type: 'application', name: 'XHTML' },
{ ext: 'css', mime: 'text/css', type: 'text', name: 'CSS stylesheet' },
{ ext: 'csv', mime: 'text/csv', type: 'text', name: 'Comma-separated values' },
{ ext: 'xml', mime: 'application/xml', type: 'application', name: 'XML document' },
{ ext: 'js', mime: 'text/javascript', type: 'text', name: 'JavaScript' },
{ ext: 'js', mime: 'application/javascript', type: 'application', name: 'JavaScript (legacy)' },
{ ext: 'mjs', mime: 'text/javascript', type: 'text', name: 'JavaScript module' },
{ ext: 'json', mime: 'application/json', type: 'application', name: 'JSON' },
{ ext: 'md', mime: 'text/markdown', type: 'text', name: 'Markdown' },
{ ext: 'yaml', mime: 'text/yaml', type: 'text', name: 'YAML' },
{ ext: 'yml', mime: 'text/yaml', type: 'text', name: 'YAML' },
{ ext: 'ics', mime: 'text/calendar', type: 'text', name: 'iCalendar' },
{ ext: 'rtf', mime: 'application/rtf', type: 'application', name: 'Rich text' },
{ ext: 'tsv', mime: 'text/tab-separated-values', type: 'text', name: 'Tab-separated values' },
// ── image ─────────────────────────────────────────────────────────────────
{ ext: 'jpg', mime: 'image/jpeg', type: 'image', name: 'JPEG image' },
{ ext: 'jpeg', mime: 'image/jpeg', type: 'image', name: 'JPEG image' },
{ ext: 'png', mime: 'image/png', type: 'image', name: 'PNG image' },
{ ext: 'gif', mime: 'image/gif', type: 'image', name: 'GIF image' },
{ ext: 'webp', mime: 'image/webp', type: 'image', name: 'WebP image' },
{ ext: 'avif', mime: 'image/avif', type: 'image', name: 'AVIF image' },
{ ext: 'svg', mime: 'image/svg+xml', type: 'image', name: 'SVG image' },
{ ext: 'bmp', mime: 'image/bmp', type: 'image', name: 'Bitmap image' },
{ ext: 'ico', mime: 'image/x-icon', type: 'image', name: 'Icon' },
{ ext: 'tif', mime: 'image/tiff', type: 'image', name: 'TIFF image' },
{ ext: 'tiff', mime: 'image/tiff', type: 'image', name: 'TIFF image' },
{ ext: 'heic', mime: 'image/heic', type: 'image', name: 'HEIC image' },
// ── audio ─────────────────────────────────────────────────────────────────
{ ext: 'mp3', mime: 'audio/mpeg', type: 'audio', name: 'MP3 audio' },
{ ext: 'wav', mime: 'audio/wav', type: 'audio', name: 'WAV audio' },
{ ext: 'ogg', mime: 'audio/ogg', type: 'audio', name: 'Ogg audio' },
{ ext: 'oga', mime: 'audio/ogg', type: 'audio', name: 'Ogg audio' },
{ ext: 'flac', mime: 'audio/flac', type: 'audio', name: 'FLAC audio' },
{ ext: 'aac', mime: 'audio/aac', type: 'audio', name: 'AAC audio' },
{ ext: 'm4a', mime: 'audio/mp4', type: 'audio', name: 'M4A audio' },
{ ext: 'weba', mime: 'audio/webm', type: 'audio', name: 'WebM audio' },
{ ext: 'mid', mime: 'audio/midi', type: 'audio', name: 'MIDI' },
{ ext: 'midi', mime: 'audio/midi', type: 'audio', name: 'MIDI' },
// ── video ─────────────────────────────────────────────────────────────────
{ ext: 'mp4', mime: 'video/mp4', type: 'video', name: 'MP4 video' },
{ ext: 'webm', mime: 'video/webm', type: 'video', name: 'WebM video' },
{ ext: 'avi', mime: 'video/x-msvideo', type: 'video', name: 'AVI video' },
{ ext: 'mov', mime: 'video/quicktime', type: 'video', name: 'QuickTime video' },
{ ext: 'mkv', mime: 'video/x-matroska', type: 'video', name: 'Matroska video' },
{ ext: 'mpeg', mime: 'video/mpeg', type: 'video', name: 'MPEG video' },
{ ext: 'mpg', mime: 'video/mpeg', type: 'video', name: 'MPEG video' },
{ ext: 'ogv', mime: 'video/ogg', type: 'video', name: 'Ogg video' },
{ ext: 'm4v', mime: 'video/mp4', type: 'video', name: 'M4V video' },
// ── application ───────────────────────────────────────────────────────────
{ ext: 'pdf', mime: 'application/pdf', type: 'application', name: 'PDF document' },
{ ext: 'zip', mime: 'application/zip', type: 'application', name: 'ZIP archive' },
{ ext: 'gz', mime: 'application/gzip', type: 'application', name: 'Gzip archive' },
{ ext: 'tar', mime: 'application/x-tar', type: 'application', name: 'Tar archive' },
{ ext: 'rar', mime: 'application/vnd.rar', type: 'application', name: 'RAR archive' },
{ ext: '7z', mime: 'application/x-7z-compressed', type: 'application', name: '7-Zip archive' },
{ ext: 'bin', mime: 'application/octet-stream', type: 'application', name: 'Binary data' },
{ ext: 'exe', mime: 'application/x-msdownload', type: 'application', name: 'Windows executable' },
{ ext: 'jar', mime: 'application/java-archive', type: 'application', name: 'Java archive' },
{ ext: 'wasm', mime: 'application/wasm', type: 'application', name: 'WebAssembly' },
{ ext: 'doc', mime: 'application/msword', type: 'application', name: 'Word document' },
{ ext: 'docx', mime: 'application/vnd.openxmlformats-officedocument.wordprocessingml.document', type: 'application', name: 'Word document (OOXML)' },
{ ext: 'xls', mime: 'application/vnd.ms-excel', type: 'application', name: 'Excel spreadsheet' },
{ ext: 'xlsx', mime: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet', type: 'application', name: 'Excel spreadsheet (OOXML)' },
{ ext: 'ppt', mime: 'application/vnd.ms-powerpoint', type: 'application', name: 'PowerPoint' },
{ ext: 'pptx', mime: 'application/vnd.openxmlformats-officedocument.presentationml.presentation', type: 'application', name: 'PowerPoint (OOXML)' },
// ── font ──────────────────────────────────────────────────────────────────
{ ext: 'woff', mime: 'font/woff', type: 'font', name: 'WOFF font' },
{ ext: 'woff2', mime: 'font/woff2', type: 'font', name: 'WOFF2 font' },
{ ext: 'ttf', mime: 'font/ttf', type: 'font', name: 'TrueType font' },
{ ext: 'otf', mime: 'font/otf', type: 'font', name: 'OpenType font' },
{ ext: 'eot', mime: 'application/vnd.ms-fontobject', type: 'application', name: 'Embedded OpenType' },
// ── multipart ─────────────────────────────────────────────────────────────
{ ext: 'mht', mime: 'multipart/related', type: 'multipart', name: 'MHTML web archive' },
{ ext: 'mhtml', mime: 'multipart/related', type: 'multipart', name: 'MHTML web archive' },
];
/** Lowercase an extension and drop a leading dot so `.JSON` and `json` match. */
export function normalizeExt(ext: string): string {
return ext.trim().toLowerCase().replace(/^\.+/, '');
}
/**
* Find every entry whose extension matches. The dot is optional and matching is
* case-insensitive, so `lookupByExt('.js')`, `lookupByExt('JS')`, and
* `lookupByExt('js')` are equivalent. Returns `[]` for an unknown/empty ext.
*/
export function lookupByExt(ext: string): MimeEntry[] {
const e = normalizeExt(ext);
if (!e) return [];
return MIME.filter((m) => m.ext === e);
}
/**
* Find every entry whose MIME type matches, case-insensitively (also tolerating
* surrounding whitespace). One MIME commonly maps to several extensions - e.g.
* `image/jpeg` → `jpg`, `jpeg` - so all are returned. `[]` for unknown/empty.
*/
export function lookupByMime(mime: string): MimeEntry[] {
const m = mime.trim().toLowerCase();
if (!m) return [];
return MIME.filter((e) => e.mime.toLowerCase() === m);
}
export interface MimeFilter {
/** Constrain to a single top-level category. Omitted = any category. */
type?: MimeCategory;
/** Free text matched (case-insensitively) against ext, mime, and name. */
query?: string;
}
/**
* Filter the full table by category and/or a free-text query. Omitted options
* are ignored; an empty query returns the category-filtered set unchanged. An
* unknown category value yields nothing (it is not silently coerced).
*/
export function filter(opts: MimeFilter = {}): MimeEntry[] {
const q = (opts.query ?? '').trim().toLowerCase();
return MIME.filter((e) => {
if (opts.type !== undefined && e.type !== opts.type) return false;
if (q) {
return (
e.ext.toLowerCase().includes(q) ||
e.mime.toLowerCase().includes(q) ||
e.name.toLowerCase().includes(q)
);
}
return true;
});
}
Also available in 13 other languages
Every CosmoDev tool ships its pure logic in TypeScript (web) and Go (CLI), with authored implementations in a dozen-plus languages — the same contract, ported. Compare all languages side by side →