问题是如何将JavaScript Date格式化为一个字符串,声明时间经过,类似于您在Stack Overflow上看到的时间显示方式。

e.g.

1分钟前 1小时前 1天前 1个月前 一年前


当前回答

简单易读版本:

const relativeTimePeriods = [
    [31536000, 'year'],
    [2419200, 'month'],
    [604800, 'week'],
    [86400, 'day'],
    [3600, 'hour'],
    [60, 'minute'],
    [1, 'second']
];

function relativeTime(date, isUtc=true) {
    if (!(date instanceof Date)) date = new Date(date * 1000);
    const seconds = (new Date() - date) / 1000;
    for (let [secondsPer, name] of relativeTimePeriods) {
        if (seconds >= secondsPer) {
            const amount = Math.floor(seconds / secondsPer);
            return `${amount} ${name}${amount ? 's' : ''}s ago`;
        }
    }
    return 'Just now';
}

其他回答

function dateToHowManyAgo(stringDate){
    var currDate = new Date();
    var diffMs=currDate.getTime() - new Date(stringDate).getTime();
    var sec=diffMs/1000;
    if(sec<60)
        return parseInt(sec)+' second'+(parseInt(sec)>1?'s':'')+' ago';
    var min=sec/60;
    if(min<60)
        return parseInt(min)+' minute'+(parseInt(min)>1?'s':'')+' ago';
    var h=min/60;
    if(h<24)
        return parseInt(h)+' hour'+(parseInt(h)>1?'s':'')+' ago';
    var d=h/24;
    if(d<30)
        return parseInt(d)+' day'+(parseInt(d)>1?'s':'')+' ago';
    var m=d/30;
    if(m<12)
        return parseInt(m)+' month'+(parseInt(m)>1?'s':'')+' ago';
    var y=m/12;
    return parseInt(y)+' year'+(parseInt(y)>1?'s':'')+' ago';
}
console.log(dateToHowManyAgo('2019-11-07 19:17:06'));

我修改了Sky Sanders的版本。Math.floor(…)操作在if块中计算

       var timeSince = function(date) {
            var seconds = Math.floor((new Date() - date) / 1000);
            var months = ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"];
            if (seconds < 5){
                return "just now";
            }else if (seconds < 60){
                return seconds + " seconds ago";
            }
            else if (seconds < 3600) {
                minutes = Math.floor(seconds/60)
                if(minutes > 1)
                    return minutes + " minutes ago";
                else
                    return "1 minute ago";
            }
            else if (seconds < 86400) {
                hours = Math.floor(seconds/3600)
                if(hours > 1)
                    return hours + " hours ago";
                else
                    return "1 hour ago";
            }
            //2 days and no more
            else if (seconds < 172800) {
                days = Math.floor(seconds/86400)
                if(days > 1)
                    return days + " days ago";
                else
                    return "1 day ago";
            }
            else{

                //return new Date(time).toLocaleDateString();
                return date.getDate().toString() + " " + months[date.getMonth()] + ", " + date.getFullYear();
            }
        }
function mdiv(dividend, divisor) {
    return [ Math.floor(dividend/divisor), dividend % divisor ];
}
// pass in milliseconds, gained by Date1.getTime() - Date2.getTime()
// if max_units is two, the result will be, for example
// 2years 12months ago, or 2hours 38minutes ago
// return formated period

function readable_period(ms, max_units=2){
    let [yy, yr] = mdiv(ms, 3.154e10);
    let [mm, mr] = mdiv(yr, 2.628e9);
    let [dd, dr] = mdiv(mr, 8.64e7);
    let [hh, hr] = mdiv(dr, 3.6e6);
    let [tt, ss] = mdiv(hr, 6e4);

    var ymdht = ['year', 'month', 'day', 'hour', 'minute'];
    let res = [];
    [yy, mm, dd, hh, tt].forEach((tis, ii)=>{
        if(res.length === max_units){return};
        if(tis !== 0){
            res.push(tis === 1 ? `${tis}${ymdht[ii]}` : `${tis}${ymdht[ii]}s`);
        }
    });
    return res.length === 0 ? '' : res.join(' ') + ' ago';
}
 I achieve this by following method

   timeAgo = (date) => {
            var ms = (new Date()).getTime() - date.getTime();
            var seconds = Math.floor(ms / 1000);
            var minutes = Math.floor(seconds / 60);
        var hours = Math.floor(minutes / 60);
        var days = Math.floor(hours / 24);
        var months = Math.floor(days / 30);
        var years = Math.floor(months / 12);
    
        if (ms === 0) {
            return 'Just now';
        } if (seconds < 60) {
            return seconds + ' seconds Ago';
        } if (minutes < 60) {
            return minutes + ' minutes Ago';
        } if (hours < 24) {
            return hours + ' hours Ago';
        } if (days < 30) {
            return days + ' days Ago';
        } if (months < 12) {
            return months + ' months Ago';
        } else {
            return years + ' years Ago';
        }
    
    }
    
        console.log(timeAgo(new Date()));
        console.log(timeAgo(new Date('Jun 27 2020 10:12:19')));
        console.log(timeAgo(new Date('Jun 27 2020 00:12:19')));
        console.log(timeAgo(new Date('May 28 2020 13:12:19')));
        console.log(timeAgo(new Date('May 28 2017 13:12:19')));

我使用这个包:javascript-time-ago

设置TimeAgo 导入TimeAgo 从javascript-time-ago/locale/en.json导入en TimeAgo.addDefaultLocale (en) 写一个函数 // twitter-now是twitter风格。查看文档以获得更多选项 const clockToDateString = (timestamp) => timeAgo。format(new Date(timestamp.toNumber() * 1000), 'twitter-now') 在dom中使用它 < div > {clockToDateString (post.postTime)} < / div >