GithubHelp home page GithubHelp logo

rotaready / moment-range Goto Github PK

View Code? Open in Web Editor NEW
1.7K 36.0 203.0 518 KB

Fancy date ranges for Moment.js

License: The Unlicense

JavaScript 92.97% TypeScript 7.03%
javascript moment-range moment date time date-time node

moment-range's People

Contributors

andresteenveld avatar aristide-n avatar aroller avatar beaumontjonathan avatar bradleyayers avatar carlholloway avatar cooperised avatar deavial avatar fidothe avatar gf3 avatar jdforsythe avatar jkimbo avatar jochendiekenbrock avatar krvajal avatar mathiasduc avatar mewwts avatar nd0ut avatar nick-dijkshoorn avatar pablodgonzalez avatar pronebel avatar rkushnir avatar rosshadden avatar rosskevin avatar scotthovestadt avatar stuartleigh avatar tb avatar thomasvanlankveld avatar tristanjm avatar wilgert avatar wmertens avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

moment-range's Issues

Allow to display frendly date range string

It would be nice if it was like this:

var range = moment().range(moment("03/15/2015 10:15 AM"), moment("03/26/2015 2:35 PM"));
return range.humanize("LL");

Code return: "March 15-26, 2015"

var range = moment().range(moment("03/15/2015 10:15 AM"), moment("03/15/2015 02:35 PM"));
return range.humanize("LLL");

Code return: "March 15 2015 10:15 a.m. - 2:35 p.m."

var range = moment().range(moment("03/15/2015 10:15 AM"), moment("03/15/2018 02:35 PM"));
return range.humanize("YYYY");

Code return: "2015 - 2018"

var range = moment().range(moment("03/15/2015 10:15 AM"), moment("04/26/2015 2:35 PM"));
return range.humanize("MMMM D");

Code return: "March 15 - April 26"

subtract doesn't exclude boundary date

var range1 = moment.range("2014-03-31", "2014-04-30");
var range2 = moment.range("2013-12-31", "2014-04-30");
range2.subtract(range1); // 2013-12-31 to 2014-03-31

Wouldn't you expect the resulting range to end with 2013-03-30, since subtract implies that you don't want any days that are part of what you are subtracting? It's a bit like saying 5-3 = 3.

Request: Simple iteration

Is there no method to iterate over the range in a unit of time, e.g. days?

I wish to simply go from one date to another in days. The multiple range iteration is a bit confusing.

tests use local time zone

tests fails on my pc:

  1) DateRange #diff() should use momentjs' diff method:
     AssertionError: expected 7948800000 to equal 7945200000
    at Object.Assertion.equal (/home/anton0xf/dev/js/external/moment-range/node_modules/should/lib/should.js:303:10)
    at Context.<anonymous> (/home/anton0xf/dev/js/external/moment-range/test/moment-range.coffee:322:24)
    at Test.Runnable.run (/home/anton0xf/dev/js/external/moment-range/node_modules/grunt-mocha-test/node_modules/mocha/lib/runnable.js:211:32)
    at Runner.runTest (/home/anton0xf/dev/js/external/moment-range/node_modules/grunt-mocha-test/node_modules/mocha/lib/runner.js:358:10)
    at /home/anton0xf/dev/js/external/moment-range/node_modules/grunt-mocha-test/node_modules/mocha/lib/runner.js:404:12
    at next (/home/anton0xf/dev/js/external/moment-range/node_modules/grunt-mocha-test/node_modules/mocha/lib/runner.js:284:14)
    at /home/anton0xf/dev/js/external/moment-range/node_modules/grunt-mocha-test/node_modules/mocha/lib/runner.js:293:7
    at next (/home/anton0xf/dev/js/external/moment-range/node_modules/grunt-mocha-test/node_modules/mocha/lib/runner.js:237:23)
    at Object._onImmediate (/home/anton0xf/dev/js/external/moment-range/node_modules/grunt-mocha-test/node_modules/mocha/lib/runner.js:261:5)
    at processImmediate [as _immediateCallback] (timers.js:330:15)

It happens because my timezone is Asia/Yekaterinburg. And between d_1 and d_2 (27 March 2011) we adjust our clock (one hour forward). You should use UTC for tests to avoid such issues.

Bug with Overlap on a one day range

Hi,
I found that when you run an overlap with one range and another range that has one day range and matches the end of the other range, overlap returns false, when it should return the overlap section:

var rangeA = moment.range("15-5-2015","20-5-2015");
var rangeB = moment.range("20-5-2015", "20-5"2015);
rangeA.overlap(rangeB) --> returns false.

The fix is simple:
change line 134:
from
} else if (((this.start <= (_ref7 = other.start) && _ref7 < (_ref6 = other.end)) && _ref6 <= this.end)) {

to

} else if (((this.start <= (_ref7 = other.start) && _ref7 <= (_ref6 = other.end)) && _ref6 <= this.end)) {
^^^
the range end date can be exactly like the start date.

moment.range constructor should accept an array

Given that you can export a moment.range to an array, the moment.range constructor should accept an array.

Example:

var start = new Date(2011, 2, 5);
var end   = new Date(2011, 5, 5);
var dr    = moment.range(start, end);

var dateRange = dr.toDate(); // [new Date(2011, 2, 5), new Date(2011, 5, 5)];

/* later on in applicationsville */

var myRange = moment.range(dateRange); // I should be able to do this.

I would create a pull request myself, it's just a small an easy addition. Unfortunately, I don't speak Coffeescript.

moment-range uses different moment than owner on node.js

Because moment-range requires moment itself the moment object it augments is different than the one you get simply by using require('moment').

Firstly, this means you can't use multiple moment plugins as moment because they will be part of different moment objects.

Secondly, this means potential versioning troubles. When you require moment yourself you have a version with a range you define and control. But the >= 1 means that any version of moment can show up, and if the latest is suddenly incompatible with code you've written, then everything is broken and you can't fix it, because you cannot control moment-range's version.

The simple thing to do is just move moment to devDependencies.

Add moment-range to cdnjs

Have you considered adding your lib to cdnjs.com? I have been using your lib for a while now and it would make an excellent addition to cdnjs as I pull all my stuff from there now. For your consideration. Cheers.

Enhancements?

Thank you for this great library!!! I have forked the library and added a few more features. So, if you would like to merge these changes please let me know and I can clean it up and add test cases. If there any issues, please me know. The features added are as follows:

Querying

Support for multiple subsequent add/subtract calls.

 RangeA.subtract(RangeB).subtract(RangeC).add(RangeD).by(...)

Query String

Additionally, moment.range has been modified to also support with a range query string inputs which will be converted to a DateRange. Examples of this are as follows:

  1. (2009>>2012)
  2. (2009>>2012)(^2008-2010)
  3. (January 1, 2012>>2015)

Subtraction Boundary

You can say whether you want to include/exclude the boundary dates during subtraction.

// 1 second offset from left/right of range
RangeA.subtract(RangeB).subtract(RangeC, 1, 's') 

Note: This can be done by the user quite easily, but I figured it would be awesome if the library supported it.

Can't iterate a range in reverse order

I want to iterate over a date range from latest to earliest date, but this doesn't seem to work:

var start = moment("2011-11-27", "YYYY-MM-DD");
var end   = moment("2011-04-15", "YYYY-MM-DD");
var range = moment().range(start, end);
range.by('days', function (day) {
    // Never get's called. :(
    console.log(day)
});

"moment.locale is not a function" error and "Cannot read property 'length' of undefined"

Using 1.1.0.

For some reason moment-range is not able to perform many of the basic functions that moment can.

Before 1.1.0:

  • One could call moment() to get the current time and date in a moment instance, but now that produces: "Cannot read property 'length' of undefined" because it does not have any arguments.
  • One could define the locale by calling moment.locale(...) but now that produces the error: "moment.locale is not a function"

Do moment and moment-range need to be declared separately and moment-range called exclusively for ranges and moment called for everything else?

ReadMe Typo

"Find out if your moment falls within a date range:

var start = new Date(2012, 4, 1);
var end   = new Date(2012, 4, 23);
var when  = moment("2012-05-10", "YYYY-MM-DD");
var range = moment().range(start, end);

when.within(range); // true"

Should evaluate to false, no?

indexof on Array not working in IE8

Hi,

Getting following error in IE8 :

SCRIPT438: Object doesn't support property or method 'indexOf'
moment-range.js, line 214 character 3

One way to fix this is using jquery inArray() but that would mean adding jquery dependency. Following is the suggested code:

moment.fn.range = function(start, end) {
var arr = ['year', 'month', 'week', 'day', 'hour', 'minute', 'second'];
if ($.inArray(start, arr) > -1) {
return new DateRange(moment(this).startOf(start), moment(this).endOf(start));
} else {
return new DateRange(start, end);
}
};

Subtract is not working

So I have tested this for about an hour now and its not working.
I have two ranges:
range1: from 01/01/2015 to 10/01/2015
range2: from 02/01/2015 to 04/01/2015

when I do: range1.substract(range2) I get the full range1 inside an array
when I do: range2.substract(range1) I get the full range2 inside an array

Sub-range test

It would be nice to have a simple contains_range function. I'd be happy to contribute this.

range start and end appear immutable

Say I want to mutate myRange to date boundaries. Per momentjs' mutability of moment objects, I would do this:

myRange.start.startOf('day');
myRange.end.endOf('day');

That however doesn't seem to work, i.e., range start and end components appear immutable.

Bug?

Module methods missing in node.js

When requiring 'moment-range' in node.js, I actually get the standard moment object without the moment-range methods.

require('moment-range').range; // - undefined

Or to put it more simply, the following will evaluate to true!

require('moment') === require('moment-range'); // - true

Steps to replicate:

  1. npm install moment-range
  2. open node console
  3. execute: require('moment-range') === require('moment');

Expected false, actual true.

Please help. Thanks.

Wrong week number for months range

Hi

I am having a strange problem when trying to get the week numbers of a range of months.
screen shot 2015-04-17 at 10 55 39

This is not happening always, and it depends on how many months apart is the range. For example if the past is 1, 2 or 4 months, I am having the correct isoWeek for today. If the past is 3, 5 or 6 (the max I have tested it), the range seems to return the wrong isoWeek.

Any ideas?

Thanks

Ranges of times?

Hi. Does this work for checking the range between two different times on the same day?

Iterating over months or years when leap years are involved doesn't work as expected

The current implementation uses a naive 365-days-per-year calculation, which means that if you iterate over years like so:

var years = [];
var range = moment().range(moment("2011", "YYYY"), moment("2013", "YYYY"));
range.by("years", function(year) { years.push(year.year()) });

Then years end up being [2011, 2012, 2012] and not [2011, 2012, 2013] because on the final iteration year ends up being 2012-12-31 because 2012 was a leap year.

The same applies for months in 2012 - February has 29 days but moment-range still thinks it has 28.

Allow initializing with string

It would be nice if it wasn't mandatory to wrap the date strings in moment() objects.

I have code that looks like this:
var range = moment().range(moment(startDate), moment(endDate));

I would rather:
var range = moment().range(startDate, endDate);

The value comes from a date picker textfield.

Exit iteration early

I think it'd be nice to have the ability to exit a Moment range iteration early.
Is this possible as of 1.0.5?

AMD define should not include a name parameter

Using a name parameter breaks the portability of the AMD module. In my situation, I use the following name format for libraries: <library>.<plugin>.

Because moment-range provides moment-range as the first parameter to the define function, I'm forced to edit the source and remove the parameter, to let the define call get the module name based on the path.

Other libraries, such as Backbone, do not specify the name parameter.

This same issue goes for moment itself, but since it's the base library, its path will usually stay like that anyway.

identical edge cases not 'contained'

*** EDIT: ***
please close this ticket, i did not see the latest commit that added the edge case My bad. :/


Hi there. I love your extension and i use it pretty regularly within an application i am developing.

I ran across this issue:

var userChoice =  new moment(1353312000000);

var start = new moment(1353312000000);

var stop = new moment(1353484800000);

var range = new moment().range(start,stop);


/*
*THIS* does *not* work
*/

if(range.contains(userChoice)){
     alert("Yes, the value 1353312000000 is in the range of 1353312000000 and 1353484800000";
}


/*
*THIS* does  work
*/

if(range.contains(userChoice) || range.start.valueOf() === userChoice.valueOf() ||  range.end.valueOf() === userChoice.valueOf() {
     alert("Yes, the value 1353312000000 is in the range of 1353312000000 and 1353484800000";
}


Is this expected behavior? I thought the contains function was inclusive.

Stagger ranges?

I see no obvious way to stagger a range.

For example, rather than have an entire range in incremental fashion, it would be preferable to leave specific dates out in the iteration. For example:

Exclude fridays and sundays

A range should be considered overlapping even if start and end dates are the same

If a range with the same start and end date is within a second range, the overlaps method should return true.

Example:

        var start = new Date(2012, 4, 1)
            , end   = new Date(2012, 4, 23)
            , range = moment().range(start, end);

        var start2 = new Date(2012, 4, 23)
            , end2   = new Date(2012, 4, 26)
            , range2 = moment().range(start2, end2);

        var start3 = new Date(2012, 4, 2)
            , end3   = new Date(2012, 4, 3)
            , range3 = moment().range(start3, end3);

        var start4 = new Date(2012, 4, 2)
            , end4   = new Date(2012, 4, 2)
            , range4 = moment().range(start4, end4);

        console.log(range.overlaps(range2)); // false
        console.log(range.overlaps(range3)); // true
        console.log(range.overlaps(range4)); // should be true
        console.log(range4.overlaps(range)); // should true

Possible bug

I am not sure if it's bug. Maybe I am wrong.

     moment().range(curStartWeek, newStartWeek  ).by('weeks', function(moment) {
                            if(moment.isBefore(newStartWeek)) {
                                console.log(moment.format('GGGG-[W]WW'));
                                w2ui['forecastGrid'].remove( moment.format('GGGG-[W]WW'));
                            }

                        });

In console:

2014-W15
2014-W16
2014-W17
2014-W22
2014-W19

Thank you!

To-value in ranges are inclusive, how to make them exclusive?

Hey guys. Thanks for a cool lib. Simple question. Suppose we have:

var dateA = moment('2015-01-04T00:00:00+00:00');
var dateB = moment('2015-01-06T00:00:00+00:00');

And we're trying to find the weekdays in the range that starts on dateA and ends on dateB.

var weekdays = [];
moment()
  .range(dateA, dateB)
  .by('d', function (mom) {
      weekdays.push(mom.isoWeekday());
  });

This output will be [7, 1, 2], while what I'd expected/want is [7, 1]. Currently, my dirty little hack is doing

//...
  moment()
    .range(dateA, dateB.subtract(1, 'ms'))
//...

and it provides the desired result. Is there a way to do this without the hack? Would you accept a pull request with functionality along the lines of

DateRange.prototype.by = function(range, hollaback, inclusive) {
   ...
}

with usage,

  // ...
  .by('d', function (mom) {
      weekdays.pus(mom.isoWeekday());
  }, false);

This should be backwards compatible, if I'm not mistaken.

Thanks again. 👍

Range diffs for months are incorrect.

coffee> moment(+new Date('Mon Sep 01 2014 00:00:00')).add(2, 'months').format('ddd MMM D YYYY HH:mm:ss')
'Sat Nov 1 2014 00:00:00'

coffee> moment.range(+new Date('Mon Sep 01 2014 00:00:00'), +new Date('Sat Oct 31 2014 00:00:00')).diff('months')
1
coffee> moment.range(+new Date('Mon Sep 01 2014 00:00:00'), +new Date('Sat Oct 31 2014 23:59:59')).diff('months')
2
coffee> moment.range(+new Date('Mon Sep 01 2014 00:00:00'), +new Date('Sat Oct 31 2014 12:00:00')).diff('months')
2
coffee> moment.range(+new Date('Mon Sep 01 2014 00:00:00'), +new Date('Sat Oct 31 2014 11:59:59')).diff('months')
1

Diffs seem to be calculated through the middle instead of the end of the last day.

Consider "duration()" as an alias of "diff()"

I want to find the intersection of two ranges, and get its duration.
The Readme didn't offer any clues until I read the entire thing carefully to find diff(). At first glance I assumed "difference" would be the opposite of "intersection".

Just something small that tripped me up and almost turned me away, hope the feedback is helpful.

Having trouble using this with npm/node

Hi again. I'm having trouble using this with npm and node.

I ran these commands in my project:

npm install -d moment
npm install -d moment-range

And this is my code in CoffeeScript:

moment        = require "moment"
moment_range  = require "moment-range"

testDate = "17/07/2012"
testTime = "4:00 PM"
testDateTime = testDate + " " + testTime
datetime = moment(testDateTime, 'DD/MM/YYYY h:ss A')
oneHourFromNow = moment().add 'hours', 1
sevenDaysFromNow = moment().add 'days', 7
range = moment_range().range(oneHourFromNow, sevenDaysFromNow)
datetime.within range

In my node.js log, I get this error about the second last line:

Error while executing ~/sandbox/file.js
TypeError: Object Mon Jul 16 2012 17:20:37 GMT+0800 (MYT) has no method 'range'
at ~/sandbox/file.js:XX:18

Time ranges

Would be nice to have functionality to check if a date is in a given time range, ignoring date. It does not seem that is possible at the moment.

Something like

var time1 = moment('2014-03-02T12:01:00');
var timerange = moment.range.time('12:00', '13:00');
timerange.contains(time1); //=> true

or maybe something more generic like this:

var time1 = moment('2014-03-02T12:01:00');
var timerange = moment.range('2014-01-01T12:00', '2014-01-02T13:00').ignore('year', 'month', 'day');
timerange.contains(time1); //=> true

Or even supply a function to the ignore function and implement some custom range logic.

Could be I'm not considering potential problems here, but wanted to throw it out there as a suggestion.

Getting errors after update?

After updating to 1.1.0, we are getting this error when we are running our tests.

ReferenceError: Can't find variable: require
at /myApp/bower_components/moment-range/lib/moment-range.js:5

Any suggestions?

Iterating over date range?

Very nice plugin. Would love to get something like this in:

var start = moment("2011-04-15", "YYYY-MM-DD")
  , end   = moment("2011-11-27", "YYYY-MM-DD")
  , range = moment().range(start, end);

range.years(); // [2011]
range.months(); // [04, 05, 06, 07, 08, 09, 10, 11]
range.daysOfYear(); // [105, 106, ... , 331]
//etc…

So that it would be easy to do something like:

range.days(function(m) {
  console.log(m.format()); // might be a moment object 
})

Node: Use moment-range with moment-timezone?

Can you clarify in the documents how these things can be used together, or if they must not be used together?

If I:

moment = require('moment-timezone'),            // Time / Timezone handling
moment_range = require('moment-range'),                // Time range handling

I get two separate libraries, both extending moment. It is workable, but complicates my code a bit.

Thanks!

range.by() going behind end value by length of one interval

example code, expected to iterate over the days of the last two and current month:

var start = moment().startOf('month').add('month', -2);
var end = moment().endOf('month');
var range = moment().range(start, end);
var interval = moment().range(start, start.clone().add('day', 1));
range.by(interval, function (moment) {
    console.log(moment.format("YYYY-MM-DD"));
});

but it also shows the first day of the next month, which is not in the defined range, but end+interval.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.