chunk-date-range
Advanced tools
Comparing version 0.0.1 to 0.1.0
@@ -7,3 +7,5 @@ { | ||
"keywords": [], | ||
"dependencies": {}, | ||
"dependencies": { | ||
"component/map": "0.0.1" | ||
}, | ||
"development": {}, | ||
@@ -10,0 +12,0 @@ "license": "MIT", |
0.1.0 / 2014-06-15 | ||
================== | ||
* adding duration, removing map component | ||
0.0.1 / 2010-01-03 | ||
@@ -3,0 +8,0 @@ ================== |
101
index.js
@@ -1,46 +0,43 @@ | ||
var map; | ||
try { | ||
map = require('map-component'); | ||
} catch (err) { | ||
map = require('map'); | ||
} | ||
var Dates = require('date-math'); | ||
module.exports = chunk; | ||
/** | ||
* Return an array of new start and end dates split into the number of chunks | ||
* Module exports | ||
* | ||
* @param {Date} start | ||
* @param {Date} end | ||
* @param {Number} chunks number of chunks to split into | ||
* @param {Date} start | ||
* @param {Date} end | ||
* @param {Number|String} chunks amount of chunks to split into, or duration | ||
* @return {Array} array | ||
* | ||
* @return {Array} | ||
* | ||
* [ | ||
* { | ||
* start: Date, | ||
* end: Date | ||
* } | ||
* ] | ||
* } ... | ||
*/ | ||
function chunk (start, end, chunks) { | ||
module.exports = function(start, end, chunks){ | ||
start = new Date(start); | ||
end = new Date(end); | ||
return typeof chunks === 'number' | ||
? number(start, end, chunks) | ||
: duration(start, end, chunks); | ||
} | ||
var diff = end - start | ||
, interval = diff / chunks; | ||
/** | ||
* Return an array of new start and end dates split into the number of chunks | ||
* | ||
* @param {Date} start | ||
* @param {Date} end | ||
* @param {Number} chunks number of chunks to split into | ||
*/ | ||
var dates = map(range(chunks), function (i) { | ||
var base = start.getTime() + (i * interval); | ||
return { | ||
start: new Date(Math.floor(base)), | ||
end: new Date(Math.floor(base + interval)) | ||
}; | ||
function number(start, end, size){ | ||
var diff = end - start; | ||
var interval = diff / size; | ||
var dates = range(size).map(function(i){ | ||
var base = +start + (i * interval); | ||
var floor = new Date(Math.floor(base)); | ||
var ceil = new Date(Math.floor(base + interval)); | ||
return entry(floor, ceil); | ||
}); | ||
// make sure we still end at the right time with rounding errors | ||
@@ -51,8 +48,50 @@ dates[dates.length - 1].end = end; | ||
/** | ||
* Chunk the dates based upon `duration` | ||
* | ||
* @param {Date} start | ||
* @param {Date} end | ||
* @param {String} duration 'day', 'week', 'year', etc. | ||
*/ | ||
function duration(start, end, duration){ | ||
var math = Dates[duration]; | ||
if (!math) throw new Error('unsupported duration ' + duration); | ||
var roundStart = math.ceil(start); | ||
var roundEnd = math.floor(end); | ||
var diff = roundEnd < roundStart | ||
? 0 | ||
: math.diff(roundStart, roundEnd); | ||
if (!diff) return [entry(start, end)]; // they are on the same interval | ||
var arr = []; | ||
if (+start !== +roundStart) arr.push(entry(start, roundStart)); | ||
for (var i = roundStart; i < roundEnd; i = math.shift(i, 1)) { | ||
arr.push(entry(i, math.shift(i, 1))); | ||
} | ||
if (+roundEnd !== +end) arr.push(entry(roundEnd, end)); | ||
return arr; | ||
} | ||
/** | ||
* Create a new entry in our array | ||
* | ||
* @param {Date} start | ||
* @param {Date} end | ||
* @return {Object} | ||
*/ | ||
function entry(start, end){ | ||
return { start: start, end: end }; | ||
} | ||
/** | ||
* Return an array of size len from 0-len | ||
* | ||
* @param {Number} len | ||
* @return {Array} arr | ||
*/ | ||
function range (len) { | ||
function range(len){ | ||
var arr = []; | ||
@@ -59,0 +98,0 @@ for (var i = 0; i < len; i++) arr.push(i); |
{ | ||
"name": "chunk-date-range", | ||
"version": "0.0.1", | ||
"version": "0.1.0", | ||
"description": "Split a date range into chunks of equal size", | ||
@@ -12,9 +12,8 @@ "keywords": [], | ||
"dependencies": { | ||
"map-component": "0.0.1" | ||
"date-math": "0.0.1" | ||
}, | ||
"devDependencies": { | ||
"mocha": "*", | ||
"should": "*" | ||
"mocha": "*" | ||
}, | ||
"main": "index" | ||
} | ||
} |
# chunk-date-range | ||
Split a date range into a certain amount of equal sized chunks. | ||
Split a date range into a certain amount of equal sized chunks, or into boundaries by 'day', 'week', 'year', etc. | ||
@@ -11,5 +11,5 @@ ## Quickstart | ||
var start = new Date('5/11/2013') | ||
, end = new Date('5/20/2013') | ||
, chunks = 2; | ||
var start = new Date('5/11/2013'); | ||
var end = new Date('5/20/2013'); | ||
var chunks = 2; | ||
@@ -24,2 +24,13 @@ chunk(start, end, chunks); | ||
*/ | ||
chunk(start, end, 'day'); | ||
/** | ||
* [ { start: Sat May 11 2013 00:00:00 GMT-0700 (PDT), | ||
* end: Sat May 11 2013 17:00:00 GMT-0700 (PDT) }, | ||
* [...] | ||
* { start: Sun May 19 2013 17:00:00 GMT-0700 (PDT), | ||
* end: Mon May 20 2013 00:00:00 GMT-0700 (PDT) } | ||
*/ | ||
``` | ||
@@ -33,3 +44,3 @@ | ||
* end - Date to end with | ||
* chunks - number of chunks to split into | ||
* chunks - number of chunks to split into, or the duration | ||
@@ -36,0 +47,0 @@ returns `chunks` evenly spaced intervals beginning with `start` and ending with `end` in the form |
55
test.js
var assert = require('assert') | ||
, chunk = require('./'); | ||
var chunk = require('./'); | ||
var Dates = require('date-math'); | ||
describe('chunk-date-range', function () { | ||
it('should split the dates into equal size chunks', function () { | ||
var start = new Date('5/1/2013') | ||
, end = new Date('5/11/2013') | ||
, splits = 10; | ||
describe('by number', function(){ | ||
it('should split the dates into equal size chunks', function (){ | ||
var start = new Date('5/1/2013') | ||
var end = new Date('5/11/2013') | ||
var splits = 10; | ||
var chunks = chunk(start, end, splits); | ||
assert.equal(chunks.length, splits); | ||
verify(chunks, start, end); | ||
}); | ||
}); | ||
var chunks = chunk(start, end, splits); | ||
assert(chunks.length === splits); | ||
assert(chunks[0].start.getTime() === start.getTime()); | ||
assert(chunks[splits-1].end.getTime() === end.getTime()); | ||
describe('by duration', function(){ | ||
it('should split the dates into the specified time range', function(){ | ||
var start = new Date('2013-05-01T05:00:00Z'); | ||
var end = new Date('2013-05-11T21:00:00Z'); | ||
var chunks = chunk(start, end, 'day'); | ||
verify(chunks, start, end); | ||
assert.equal(chunks.length, 11); | ||
assert.equal(+chunks[0].end, +Dates.day.ceil(start)); | ||
assert.equal(+chunks[10].start, +Dates.day.floor(end)); | ||
}); | ||
it('should not add extra entries for round start and end dates', function(){ | ||
var start = new Date('2013-05-01T00:00:00Z'); | ||
var end = new Date('2013-05-11T00:00:00Z'); | ||
var chunks = chunk(start, end, 'day'); | ||
verify(chunks, start, end); | ||
assert.equal(chunks.length, 10); | ||
}); | ||
it('should split the dates which overlap on the same day', function(){ | ||
var start = new Date('2013-05-01T03:00:00Z'); | ||
var end = new Date('2013-05-01T21:00:00Z'); | ||
var chunks = chunk(start, end, 'day'); | ||
verify(chunks, start, end); | ||
assert.equal(chunks.length, 1); | ||
}); | ||
}); | ||
function verify(chunks, start, end){ | ||
assert.equal(+chunks[0].start, +start); | ||
assert.equal(+chunks[chunks.length-1].end, +end); | ||
chunks.forEach(function (chunk, i) { | ||
var next = chunks[i+1]; | ||
if (!next) return; | ||
assert(chunk.end.getTime() === next.start.getTime()); | ||
assert.equal(+chunk.end, +next.start); | ||
}); | ||
}); | ||
} | ||
}); |
Sorry, the diff of this file is not supported yet
7337
1
148
78
+ Addeddate-math@0.0.1
+ Addeddate-math@0.0.1(transitive)
- Removedmap-component@0.0.1
- Removedcomponent-props@1.1.1(transitive)
- Removedmap-component@0.0.1(transitive)
- Removedto-function@2.0.6(transitive)