[javascript] Moment JS start and end of given month

I need to calculate a JS date given year=2014 and month=9 (September 2014).

I tried this:

var moment = require('moment');
var startDate = moment( year+'-'+month+'-'+01 + ' 00:00:00' );
            var endDate = startDate.endOf('month');
            console.log(startDate.toDate());
            console.log(endDate.toDate());

Both of logs show:

Tue Sep 30 2014 23:59:59 GMT+0200 (CEST)
Tue Sep 30 2014 23:59:59 GMT+0200 (CEST)

End date is correct but... why the start date is not?

This question is related to javascript momentjs

The answer is


you can use this directly for the end or start date of the month

new moment().startOf('month').format("YYYY-DD-MM");
new moment().endOf("month").format("YYYY-DD-MM");

you can change the format by defining a new format


var d = new moment();
var startMonth = d.clone().startOf('month');
var endMonth = d.clone().endOf('month');
console.log(startMonth, endMonth);

doc


Don't really think there is some direct method to get the last day but you could do something like this:

var dateInst = new moment();
/**
 * adding 1 month from the present month and then subtracting 1 day, 
 * So you would get the last day of this month 
 */
dateInst.add(1, 'months').date(1).subtract(1, 'days');
/* printing the last day of this month's date */
console.log(dateInst.format('YYYY MM DD'));

const dates = getDatesFromDateRange("2014-05-02", "2018-05-12", "YYYY/MM/DD", 1);           
console.log(dates);
// you get the whole from-to date ranges as per parameters
var onlyStartDates = dates.map(dateObj => dateObj["to"]);
console.log(onlyStartDates);
// moreover, if you want only from dates then you can grab by "map" function

function getDatesFromDateRange( startDate, endDate, format, counter ) {
    startDate = moment(startDate, format);
    endDate = moment(endDate, format);

    let dates = [];
    let fromDate = startDate.clone();
    let toDate = fromDate.clone().add(counter, "month").startOf("month").add(-1, "day");
    do {
        dates.push({
            "from": fromDate.format(format),
            "to": ( toDate < endDate ) ? toDate.format(format) : endDate.format(format)
        });
        fromDate = moment(toDate, format).add(1, "day").clone();
        toDate = fromDate.clone().add(counter, "month").startOf("month").add(-1, "day");
    } while ( fromDate < endDate );
    return dates;
}

Please note, .clone() is essential in momentjs else it'll override the value. It seems in your case.

It's more generic, to get bunch of dates that fall between dates.


The following code should work:

$('#reportrange').daterangepicker({
                startDate: start,
                endDate: end,
                ranges: {
                    'Hoy': [moment(), moment()],
                    'Ayer': [moment().subtract(1, 'days'), moment().subtract(1, 'days')],
                    'Ultimos 7 dias': [moment().subtract(6, 'days'), moment()],
                    'Ultimos 30 dias': [moment().subtract(29, 'days'), moment()],
                    'Mes actual': [moment().startOf('month'), moment().endOf('month')],
                    'Ultimo mes': [moment().subtract(1, 'month').startOf('month'), moment().subtract(1, 'month').endOf('month')],
                    'Enero': [moment().month(0).startOf('month') , moment().month(0).endOf('month')],
                    'Febrero': [moment().month(1).startOf('month') , moment().month(1).endOf('month')],
                    'Marzo': [moment().month(2).startOf('month') , moment().month(2).endOf('month')],
                    'Abril': [moment().month(3).startOf('month') , moment().month(3).endOf('month')],
                    'Mayo': [moment().month(4).startOf('month') , moment().month(4).endOf('month')],
                    'Junio': [moment().month(5).startOf('month') , moment().month(5).endOf('month')],
                    'Julio': [moment().month(6).startOf('month') , moment().month(6).endOf('month')],
                    'Agosto': [moment().month(7).startOf('month') , moment().month(7).endOf('month')],
                    'Septiembre': [moment().month(8).startOf('month') , moment().month(8).endOf('month')],
                    'Octubre': [moment().month(9).startOf('month') , moment().month(9).endOf('month')],
                    'Noviembre': [moment().month(10).startOf('month') , moment().month(10).endOf('month')],
                    'Diciembre': [moment().month(11).startOf('month') , moment().month(11).endOf('month')]
                }
            }, cb);

Try the following code:

const moment=require('moment');
console.log("startDate=>",moment().startOf('month').format("YYYY-DD-MM"));
console.log("endDate=>",moment().endOf('month').format("YYYY-DD-MM"));

_x000D_
_x000D_
const year = 2014;_x000D_
const month = 09;_x000D_
_x000D_
// months start at index 0 in momentjs, so we subtract 1_x000D_
const startDate = moment([year, month - 1, 01]).format("YYYY-MM-DD");_x000D_
_x000D_
// get the number of days for this month_x000D_
const daysInMonth = moment(startDate).daysInMonth();_x000D_
_x000D_
// we are adding the days in this month to the start date (minus the first day)_x000D_
const endDate = moment(startDate).add(daysInMonth - 1, 'days').format("YYYY-MM-DD");_x000D_
_x000D_
console.log(`start date: ${startDate}`);_x000D_
console.log(`end date:   ${endDate}`);
_x000D_
<script_x000D_
src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.20.1/moment.min.js">_x000D_
</script>
_x000D_
_x000D_
_x000D_


Try the following code:

moment(startDate).startOf('months')
moment(startDate).endOf('months')

your startDate is first-day-of-month, In this case we can use

var endDate = moment(startDate).add(1, 'months').subtract(1, 'days');

Hope this helps!!


When you use .endOf() you are mutating the object it's called on, so startDate becomes Sep 30

You should use .clone() to make a copy of it instead of changing it

var startDate = moment(year + '-' + month + '-' + 01 + ' 00:00:00');
            var endDate = startDate.clone().endOf('month');
            console.log(startDate.toDate());
            console.log(endDate.toDate());

Mon Sep 01 2014 00:00:00 GMT+0700 (ICT) 
Tue Sep 30 2014 23:59:59 GMT+0700 (ICT)