Comparing version 2.0.3 to 2.0.5
@@ -0,3 +1,42 @@ | ||
# Change Log | ||
All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines. | ||
<a name="2.0.5"></a> | ||
## [2.0.5](https://github.com/broofa/node-mime/compare/v2.0.1...v2.0.5) (2017-12-22) | ||
### Bug Fixes | ||
* ES5 support (back to node v0.4) ([f14ccb6](https://github.com/broofa/node-mime/commit/f14ccb6)) | ||
# Changelog | ||
## v2.0.4 (24/11/2017) | ||
- [**closed**] Switch to mime-score module for resolving extension contention issues. [#182](https://github.com/broofa/node-mime/issues/182) | ||
- [**closed**] Update mime-db to 1.31.0 in v1.x branch [#181](https://github.com/broofa/node-mime/issues/181) | ||
--- | ||
## v1.5.0 (22/11/2017) | ||
- [**closed**] need ES5 version ready in npm package [#179](https://github.com/broofa/node-mime/issues/179) | ||
- [**closed**] mime-db no trace of iWork - pages / numbers / etc. [#178](https://github.com/broofa/node-mime/issues/178) | ||
- [**closed**] How it works in brownser ? [#176](https://github.com/broofa/node-mime/issues/176) | ||
- [**closed**] Missing `./Mime` [#175](https://github.com/broofa/node-mime/issues/175) | ||
- [**closed**] Vulnerable Regular Expression [#167](https://github.com/broofa/node-mime/issues/167) | ||
--- | ||
## v2.0.3 (25/09/2017) | ||
*No changelog for this release.* | ||
--- | ||
## v1.4.1 (25/09/2017) | ||
- [**closed**] Issue when bundling with webpack [#172](https://github.com/broofa/node-mime/issues/172) | ||
--- | ||
## v2.0.2 (15/09/2017) | ||
@@ -4,0 +43,0 @@ - [**V2**] fs.readFileSync is not a function [#165](https://github.com/broofa/node-mime/issues/165) |
'use strict'; | ||
const Mime = require('./Mime'); | ||
var Mime = require('./Mime'); | ||
module.exports = new Mime(require('./types/standard'), require('./types/other')); |
'use strict'; | ||
const Mime = require('./Mime'); | ||
var Mime = require('./Mime'); | ||
module.exports = new Mime(require('./types/standard')); |
101
Mime.js
@@ -7,63 +7,66 @@ 'use strict'; | ||
*/ | ||
class Mime { | ||
constructor() { | ||
this._types = Object.create(null); | ||
this._extensions = Object.create(null); | ||
function Mime() { | ||
this._types = Object.create(null); | ||
this._extensions = Object.create(null); | ||
for (var i = 0; i < arguments.length; i++) { | ||
this.define(arguments[i]); | ||
} | ||
for (var i = 0; i < arguments.length; i++) { | ||
this.define(arguments[i]); | ||
} | ||
} | ||
/** | ||
* Define mimetype -> xtension mappings. Each key is a mime-type that maps | ||
* to an array of extensions associated with the type. The first extension is | ||
* used as the default extension for the type. | ||
* | ||
* e.g. mime.define({'audio/ogg', ['oga', 'ogg', 'spx']}); | ||
* | ||
* @param map (Object) type definitions | ||
*/ | ||
define(typeMap, force) { | ||
for (let type in typeMap) { | ||
var extensions = typeMap[type]; | ||
for (let i = 0; i < extensions.length; i++) { | ||
var ext = extensions[i]; | ||
if (!force && (ext in this._types)) { | ||
throw new Error(`Attempt to change mapping for "${ext}" extension from "${this._types[ext]}" to "${type}". Pass \`force=true\` to allow this, otherwise remove "${ext}" from the list of extensions for "${type}".`); | ||
} | ||
this._types[ext] = type; | ||
/** | ||
* Define mimetype -> xtension mappings. Each key is a mime-type that maps | ||
* to an array of extensions associated with the type. The first extension is | ||
* used as the default extension for the type. | ||
* | ||
* e.g. mime.define({'audio/ogg', ['oga', 'ogg', 'spx']}); | ||
* | ||
* @param map (Object) type definitions | ||
*/ | ||
Mime.prototype.define = function(typeMap, force) { | ||
for (var type in typeMap) { | ||
var extensions = typeMap[type]; | ||
for (var i = 0; i < extensions.length; i++) { | ||
var ext = extensions[i]; | ||
if (!force && (ext in this._types)) { | ||
throw new Error( | ||
'Attempt to change mapping for "' + ext + | ||
'" extension from "' + this._types[ext] + '" to "' + type + | ||
'". Pass `force=true` to allow this, otherwise remove "' + ext + | ||
'" from the list of extensions for "' + type + '".' | ||
); | ||
} | ||
// Use first extension as default | ||
if (force || !this._extensions[type]) { | ||
this._extensions[type] = extensions[0]; | ||
} | ||
this._types[ext] = type; | ||
} | ||
// Use first extension as default | ||
if (force || !this._extensions[type]) { | ||
this._extensions[type] = extensions[0]; | ||
} | ||
} | ||
}; | ||
/** | ||
* Lookup a mime type based on extension | ||
*/ | ||
getType(path) { | ||
path = String(path); | ||
var last = path.replace(/^.*[/\\]/, '').toLowerCase(); | ||
var ext = last.replace(/^.*\./, '').toLowerCase(); | ||
/** | ||
* Lookup a mime type based on extension | ||
*/ | ||
Mime.prototype.getType = function(path) { | ||
path = String(path); | ||
var last = path.replace(/^.*[/\\]/, '').toLowerCase(); | ||
var ext = last.replace(/^.*\./, '').toLowerCase(); | ||
var hasPath = last.length < path.length; | ||
var hasDot = ext.length < last.length - 1; | ||
var hasPath = last.length < path.length; | ||
var hasDot = ext.length < last.length - 1; | ||
return (hasDot || !hasPath) && this._types[ext] || null; | ||
} | ||
return (hasDot || !hasPath) && this._types[ext] || null; | ||
}; | ||
/** | ||
* Return file extension associated with a mime type | ||
*/ | ||
getExtension(type) { | ||
type = /^\s*([^;\s]*)/.test(type) && RegExp.$1; | ||
return type && this._extensions[type.toLowerCase()] || null; | ||
} | ||
} | ||
/** | ||
* Return file extension associated with a mime type | ||
*/ | ||
Mime.prototype.getExtension = function(type) { | ||
type = /^\s*([^;\s]*)/.test(type) && RegExp.$1; | ||
return type && this._extensions[type.toLowerCase()] || null; | ||
}; | ||
module.exports = Mime; |
@@ -13,9 +13,3 @@ { | ||
}, | ||
"contributors": [ | ||
{ | ||
"name": "Benjamin Thomas", | ||
"url": "http://github.com/bentomas", | ||
"email": "benjamin@benjaminthomas.org" | ||
} | ||
], | ||
"contributors": [], | ||
"description": "A comprehensive library for mime-type mapping", | ||
@@ -29,5 +23,6 @@ "license": "MIT", | ||
"mime-db": "1.30.0", | ||
"mime-score": "1.0.1", | ||
"mime-types": "2.1.15", | ||
"mocha": "3.5.3", | ||
"runmd": "0.1.8" | ||
"runmd": "1.0.1" | ||
}, | ||
@@ -49,3 +44,3 @@ "scripts": { | ||
}, | ||
"version": "2.0.3" | ||
"version": "2.0.5" | ||
} |
@@ -0,1 +1,4 @@ | ||
<!-- | ||
-- This file is auto-generated from src/README_js.md. Changes should be made there. | ||
--> | ||
# Mime | ||
@@ -7,5 +10,4 @@ | ||
Version 2 is a breaking change from 1.x, as the semver implies. Specifically: | ||
Version 2 is a breaking change from 1.x as the semver implies. Specifically: | ||
* **ES6 support required (node@>=6)** | ||
* `lookup()` renamed to `getType()` | ||
@@ -17,3 +19,5 @@ * `extension()` renamed to `getExtension()` | ||
## Install - NPM | ||
## Install | ||
### NPM | ||
``` | ||
@@ -23,2 +27,21 @@ npm install mime | ||
### Browser | ||
It is recommended that you use a bundler such as | ||
[webpack](https://webpack.github.io/) or [browserify](http://browserify.org/) to | ||
package your code. However, browser-ready versions are available via wzrd.in. | ||
E.g. For the full version: | ||
<script src="https://wzrd.in/standalone/mime@latest"></script> | ||
<script> | ||
mime.getType(...); // etc. | ||
<script> | ||
Or, for the `mime/lite` version: | ||
<script src="https://wzrd.in/standalone/mime%2flite@latest"></script> | ||
<script> | ||
mimelite.getType(...); // (Note `mimelite` here) | ||
<script> | ||
## Quick Start | ||
@@ -48,23 +71,2 @@ | ||
## Browser-ready Versions | ||
To use this module in the browser, you would typlically use | ||
[webpack](https://webpack.github.io/) or [browserify](http://browserify.org/) to | ||
package your code. However, browser-ready versions are available via wzrd.in. | ||
E.g. For the full version: | ||
<script src="http://wzrd.in/standalone/mime@latest"></script> | ||
Or, for the "lite" version: | ||
<script src="http://wzrd.in/standalone/mime%2flite@latest"></script> | ||
Then: | ||
```html | ||
<script> | ||
mime.getType(...); // etc. | ||
</script> | ||
``` | ||
## Mime .vs. mime-types .vs. mime-db modules | ||
@@ -71,0 +73,0 @@ |
@@ -5,59 +5,16 @@ #!/usr/bin/env node | ||
const fs = require('fs'); | ||
const path = require('path'); | ||
var fs = require('fs'); | ||
var path = require('path'); | ||
var mimeScore = require('mime-score'); | ||
let db = require('mime-db'); | ||
let chalk = require('chalk'); | ||
var db = require('mime-db'); | ||
var chalk = require('chalk'); | ||
const STANDARD_FACET_SCORE = 900; | ||
var STANDARD_FACET_SCORE = 900; | ||
// Get a mimetype "score" that can be used to resolve conflicts over extensions | ||
// in a deterministic way. | ||
// | ||
// In case of conflict over an extension, the highest score wins | ||
function getScore(entry) { | ||
let pri = 0; | ||
const [type, subtype] = entry.type.split('/'); | ||
const facet = /^([a-z]+\.|x-)/.test(subtype) && RegExp.$1 || undefined; | ||
var byExtension = {}; | ||
// https://tools.ietf.org/html/rfc6838#section-3 defines "facets" that can be | ||
// used to distinguish standard .vs. vendor .vs. experimental .vs. personal | ||
// mime types. | ||
switch (facet) { | ||
case 'vnd.': pri += 400; break; | ||
case 'x.': pri += 300; break; | ||
case 'x-': pri += 200; break; | ||
case 'prs.': pri += 100; break; | ||
default: pri += STANDARD_FACET_SCORE; | ||
} | ||
// Use mime-db's logic for ranking by source | ||
switch (entry.source) { | ||
// Prioritize by source (same as mime-types module) | ||
case 'iana': pri += 40; break; | ||
case 'apache': pri += 20; break; | ||
case 'nginx': pri += 10; break; | ||
default: pri += 30; break; | ||
} | ||
// Prefer application over other types (e.g. text/xml and application/xml, and | ||
// text/rtf and application/rtf all appear to be respectable mime thingz. Lovely, | ||
// right?) | ||
switch (type) { | ||
case 'application': pri += 1; break; | ||
default: break; | ||
} | ||
// All other things being equal, use length | ||
pri += 1 - entry.type.length/100; | ||
return pri; | ||
} | ||
const byExtension = {}; | ||
// Clear out any conflict extensions in mime-db | ||
for (let type in db) { | ||
let entry = db[type]; | ||
for (var type in db) { | ||
var entry = db[type]; | ||
entry.type = type; | ||
@@ -67,19 +24,20 @@ | ||
entry.extensions.forEach(ext => { | ||
entry.extensions.forEach(function(ext) { | ||
if (ext in byExtension) { | ||
const e0 = entry; | ||
const e1 = byExtension[ext]; | ||
e0.pri = getScore(e0); | ||
e1.pri = getScore(e1); | ||
var e0 = entry; | ||
var e1 = byExtension[ext]; | ||
e0.pri = mimeScore(e0.type, e0.source); | ||
e1.pri = mimeScore(e1.type, e1.source); | ||
let drop = e0.pri < e1.pri ? e0 : e1; | ||
let keep = e0.pri >= e1.pri ? e0 : e1; | ||
drop.extensions = drop.extensions.filter(e => e !== ext); | ||
var drop = e0.pri < e1.pri ? e0 : e1; | ||
var keep = e0.pri >= e1.pri ? e0 : e1; | ||
drop.extensions = drop.extensions.filter(function(e) {return e !== ext;}); | ||
console.log(`${ext}: Keeping ${chalk.green(keep.type)} (${keep.pri}), dropping ${chalk.red(drop.type)} (${drop.pri})`); | ||
console.log( | ||
ext + ': Keeping ' + chalk.green(keep.type) + ' (' + keep.pri + | ||
'), dropping ' + chalk.red(drop.type) + ' (' + drop.pri + ')' | ||
); | ||
} | ||
byExtension[ext] = entry; | ||
}); | ||
//maps[map][key] = extensions; | ||
} | ||
@@ -93,10 +51,10 @@ | ||
// https://tools.ietf.org/html/rfc6838#section-3.1 | ||
const standard = {}; | ||
const other = {}; | ||
var standard = {}; | ||
var other = {}; | ||
Object.keys(db).sort().forEach(k => { | ||
const entry = db[k]; | ||
Object.keys(db).sort().forEach(function(k) { | ||
var entry = db[k]; | ||
if (entry.extensions) { | ||
if (getScore(entry) >= STANDARD_FACET_SCORE) { | ||
if (mimeScore(entry.type, entry.source) >= STANDARD_FACET_SCORE) { | ||
standard[entry.type] = entry.extensions; | ||
@@ -111,3 +69,1 @@ } else { | ||
writeTypesFile(other, path.join(__dirname, '../types', 'other.json')); | ||
//console.log(JSON.stringify(maps, null, 2)); |
@@ -10,5 +10,4 @@ ```javascript --hide | ||
Version 2 is a breaking change from 1.x, as the semver implies. Specifically: | ||
Version 2 is a breaking change from 1.x as the semver implies. Specifically: | ||
* **ES6 support required (node@>=6)** | ||
* `lookup()` renamed to `getType()` | ||
@@ -20,3 +19,5 @@ * `extension()` renamed to `getExtension()` | ||
## Install - NPM | ||
## Install | ||
### NPM | ||
``` | ||
@@ -26,2 +27,21 @@ npm install mime | ||
### Browser | ||
It is recommended that you use a bundler such as | ||
[webpack](https://webpack.github.io/) or [browserify](http://browserify.org/) to | ||
package your code. However, browser-ready versions are available via wzrd.in. | ||
E.g. For the full version: | ||
<script src="https://wzrd.in/standalone/mime@latest"></script> | ||
<script> | ||
mime.getType(...); // etc. | ||
<script> | ||
Or, for the `mime/lite` version: | ||
<script src="https://wzrd.in/standalone/mime%2flite@latest"></script> | ||
<script> | ||
mimelite.getType(...); // (Note `mimelite` here) | ||
<script> | ||
## Quick Start | ||
@@ -31,3 +51,3 @@ | ||
```javascript --context | ||
```javascript --run default | ||
const mime = require('mime'); | ||
@@ -51,23 +71,2 @@ | ||
## Browser-ready Versions | ||
To use this module in the browser, you would typlically use | ||
[webpack](https://webpack.github.io/) or [browserify](http://browserify.org/) to | ||
package your code. However, browser-ready versions are available via wzrd.in. | ||
E.g. For the full version: | ||
<script src="http://wzrd.in/standalone/mime@latest"></script> | ||
Or, for the "lite" version: | ||
<script src="http://wzrd.in/standalone/mime%2flite@latest"></script> | ||
Then: | ||
```html | ||
<script> | ||
mime.getType(...); // etc. | ||
</script> | ||
``` | ||
## Mime .vs. mime-types .vs. mime-db modules | ||
@@ -112,3 +111,3 @@ | ||
```javascript --context | ||
```javascript --run default | ||
// Require Mime class | ||
@@ -135,3 +134,3 @@ const Mime = require('mime/Mime'); | ||
```javascript --context | ||
```javascript --run default | ||
mime.getType('js'); // RESULT | ||
@@ -149,3 +148,3 @@ mime.getType('json'); // RESULT | ||
```javascript --context | ||
```javascript --run default | ||
mime.getType('foo/txt'); // RESULT | ||
@@ -159,3 +158,3 @@ mime.getType('bogus_type'); // RESULT | ||
```javascript --context | ||
```javascript --run default | ||
mime.getExtension('text/plain'); // RESULT | ||
@@ -176,3 +175,3 @@ mime.getExtension('application/json'); // RESULT | ||
```javascript --context | ||
```javascript --run default | ||
mime.define({'text/x-abc': ['abc', 'abcd']}); | ||
@@ -179,0 +178,0 @@ |
@@ -10,5 +10,5 @@ 'use strict'; | ||
it('new constructor()', function() { | ||
const Mime = require('../Mime'); | ||
var Mime = require('../Mime'); | ||
const mime = new Mime( | ||
var mime = new Mime( | ||
{'text/a': ['a', 'a1']}, | ||
@@ -32,5 +32,5 @@ {'text/b': ['b', 'b1']} | ||
it('define()', function() { | ||
const Mime = require('../Mime'); | ||
var Mime = require('../Mime'); | ||
const mime = new Mime({'text/a': ['a']}, {'text/b': ['b']}); | ||
var mime = new Mime({'text/a': ['a']}, {'text/b': ['b']}); | ||
@@ -115,3 +115,6 @@ assert.throws(function() { | ||
diffs.forEach(function(d) { | ||
console.warn(` ${d[0]}[${chalk.blue(d[1])}] = ${chalk.red(d[2])}, mime[${d[1]}] = ${chalk.green(d[3])}`); | ||
console.warn( | ||
' ' + d[0]+ '[' + chalk.blue(d[1]) + '] = ' + chalk.red(d[2]) + | ||
', mime[' + d[1] + '] = ' + chalk.green(d[3]) | ||
); | ||
}); | ||
@@ -129,3 +132,3 @@ } | ||
// MDN types listed at https://goo.gl/lHrFU6 | ||
const MDN = { | ||
var MDN = { | ||
'aac': 'audio/aac', | ||
@@ -189,11 +192,11 @@ 'abw': 'application/x-abiword', | ||
for (let ext in MDN) { | ||
const expected = MDN[ext]; | ||
const actual = mime.getType(ext); | ||
for (var ext in MDN) { | ||
var expected = MDN[ext]; | ||
var actual = mime.getType(ext); | ||
if (actual !== expected) diffs.push(['MDN', ext, expected, actual]); | ||
} | ||
for (let ext in mimeTypes.types) { | ||
const expected = mimeTypes.types[ext]; | ||
const actual = mime.getType(ext); | ||
for (var ext in mimeTypes.types) { | ||
var expected = mimeTypes.types[ext]; | ||
var actual = mime.getType(ext); | ||
if (actual !== expected) diffs.push(['mime-types', ext, expected, actual]); | ||
@@ -200,0 +203,0 @@ } |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
67667
189
8
379