-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
... for computing statistics about a single npm-package
- Loading branch information
Showing
8 changed files
with
307 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,82 @@ | ||
const path = require('path') | ||
const deep = require('deep-aplus')(Promise) | ||
const pify = require('pify') | ||
const fs = require('fs') | ||
const stat = pify(fs.stat) | ||
const glob = pify(require('glob')) | ||
|
||
/** | ||
* Computes and aggregates a number of statistics from a package directory | ||
* in the node_modules folder | ||
* | ||
*/ | ||
class PackageStats { | ||
/** | ||
* Create a new PackageStats object | ||
* @param {string} directory path to the package-json files | ||
* @param {{file: string, stat: fs.Stats}} files files and stats in this package | ||
*/ | ||
constructor (directory, files) { | ||
/** | ||
* @type {string} | ||
*/ | ||
this.directory = directory | ||
/** | ||
* @type {{file: string, stat: fs.Stats}} | ||
*/ | ||
this.files = files | ||
} | ||
|
||
totalByteSize () { | ||
if (!this._totalByteSize) { | ||
this._totalByteSize = this.files.reduce((result, file) => result + file.stat.size, 0) | ||
} | ||
return this._totalByteSize | ||
} | ||
|
||
totalBlockSize () { | ||
if (!this._totalBlocksize) { | ||
this._totalBlockSize = this.files.reduce((result, file) => { | ||
return result + Math.ceil(file.stat.size / file.stat.blksize) * file.stat.blksize | ||
}, 0) | ||
} | ||
return this._totalBlockSize | ||
} | ||
|
||
/** | ||
* Returns a new PackageStats-object with the same directory | ||
* and the union of all files in this package and the other packages | ||
* @param {PackageStats[]} packages | ||
*/ | ||
merge (packages) { | ||
var uniq = {} | ||
// Merge files | ||
this.files.forEach(file => { uniq[file.file] = file }) | ||
packages.forEach(pkg => { | ||
pkg.files.forEach(file => { uniq[file.file] = file }) | ||
}) | ||
// Recreate file array | ||
var files = Object.keys(uniq).map((key) => uniq[key]) | ||
return new PackageStats(this.directory, files) | ||
} | ||
|
||
/** | ||
* | ||
* @param packageJsonPath | ||
* @return {Promise<PackageStats>} | ||
*/ | ||
static loadFrom (packageJsonPath) { | ||
var directory = path.dirname(packageJsonPath) | ||
return glob('**', {dot: true, cwd: directory, mark: true, ignore: 'node_modules/**'}) | ||
// Add the directory itself | ||
.then(files => ['./'].concat(files)) | ||
// Gather stats | ||
.then(files => files.map(file => ({file: path.join(directory, file), stat: stat(path.join(directory, file))}))) | ||
// Wait for promises | ||
.then(deep) | ||
// creaate PackageStats-object | ||
.then((files) => new PackageStats(directory, files)) | ||
} | ||
} | ||
|
||
module.exports = {PackageStats} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,65 @@ | ||
/* eslint-env mocha */ | ||
|
||
const chai = require('chai') | ||
chai.use(require('dirty-chai')) | ||
const expect = chai.expect | ||
const {PackageStats} = require('../src/PackageStats') | ||
|
||
describe('The PackageStats-class', function () { | ||
it('should load the package-stats from a directory', function () { | ||
return PackageStats.loadFrom('test/fixtures/project1/package.json') | ||
.then((packageStats) => { | ||
expect(packageStats.directory).to.equal('test/fixtures/project1') | ||
expect(sortedNameAndSize(packageStats.files)).to.deep.equal([ | ||
'test/fixtures/project1/ - 4096', | ||
'test/fixtures/project1/dir/ - 4096', | ||
'test/fixtures/project1/dir/file2.txt - 2', | ||
'test/fixtures/project1/file3.txt - 3', | ||
'test/fixtures/project1/file5000.txt - 5000', | ||
'test/fixtures/project1/file6.txt - 6' | ||
]) | ||
}) | ||
}) | ||
|
||
it('should compute the byte-size of all the files in a directory', function () { | ||
return PackageStats.loadFrom('test/fixtures/project1/package.json') | ||
.then((packageStats) => { | ||
expect(packageStats.totalByteSize()).to.equal(4096 + 4096 + 2 + 3 + 5000 + 6) | ||
}) | ||
}) | ||
|
||
it('should compute the disk usage (by whole blocks) of the directory', function () { | ||
return PackageStats.loadFrom('test/fixtures/project1/package.json') | ||
.then((packageStats) => { | ||
expect(packageStats.totalBlockSize()).to.equal(7 * 4096) | ||
}) | ||
}) | ||
|
||
it('should merge two stats-object by unioning the files', function () { | ||
return Promise.all([ | ||
PackageStats.loadFrom('test/fixtures/project1/package.json'), | ||
PackageStats.loadFrom('test/fixtures/project2/package.json'), | ||
PackageStats.loadFrom('test/fixtures/project1/package.json') | ||
]) | ||
.then((packages) => { | ||
// Merge package with the first package being the main package | ||
const merged = packages[0].merge(packages.slice(1)) | ||
expect(merged, 'Must return a copy').not.to.equal(packages[0]) | ||
expect(merged.directory).to.equal('test/fixtures/project1') | ||
expect(sortedNameAndSize(merged.files)).to.deep.equal([ | ||
'test/fixtures/project1/ - 4096', | ||
'test/fixtures/project1/dir/ - 4096', | ||
'test/fixtures/project1/dir/file2.txt - 2', | ||
'test/fixtures/project1/file3.txt - 3', | ||
'test/fixtures/project1/file5000.txt - 5000', | ||
'test/fixtures/project1/file6.txt - 6', | ||
'test/fixtures/project2/ - 4096', | ||
'test/fixtures/project2/file10.txt - 10' | ||
]) | ||
}) | ||
}) | ||
}) | ||
|
||
function sortedNameAndSize (files) { | ||
return files.map((file) => file.file + ' - ' + file.stat.size).sort() | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
ab |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,100 @@ | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 | ||
0123456789012345678901234567890123456789012345678 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
abcef |
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
012345678 |