const formatNumber = n => { n = n.toString() return n[1] ? n : `0${n}` } const formatDate = date => { const d = date instanceof Date ? date : new Date(date) const year = d.getFullYear() const month = d.getMonth() + 1 const day = d.getDate() return `${[year, month, day].map(formatNumber).join('-')}` } const formatTime = date => { const d = date instanceof Date ? date : new Date(date) if (Number.isNaN(d.getTime())) { return '' } const year = d.getFullYear() const month = d.getMonth() + 1 const day = d.getDate() const hour = d.getHours() const minute = d.getMinutes() const second = d.getSeconds() return `${[year, month, day].map(formatNumber).join('-')} ${[hour, minute, second].map(formatNumber).join(':')}` } const today = () => formatDate(new Date()) const parseDate = value => { if (value instanceof Date) { return new Date(value.getFullYear(), value.getMonth(), value.getDate()) } const text = String(value || '').trim() const matched = text.match(/^(\d{4})-(\d{2})-(\d{2})$/) if (matched) { return new Date(Number(matched[1]), Number(matched[2]) - 1, Number(matched[3])) } return new Date() } const addDays = (value, days) => { const date = parseDate(value) date.setDate(date.getDate() + toNumber(days)) return formatDate(date) } const uid = prefix => `${prefix}_${Date.now()}_${Math.random().toString(16).slice(2, 8)}` const toNumber = value => { const number = Number(value) return Number.isFinite(number) ? number : 0 } const minutesBetween = (start, end) => { const startTime = new Date(start).getTime() const endTime = new Date(end).getTime() if (!Number.isFinite(startTime) || !Number.isFinite(endTime) || endTime <= startTime) { return 0 } return Math.round((endTime - startTime) / 60000) } const round = (value, digits = 1) => { const base = Math.pow(10, digits) return Math.round(toNumber(value) * base) / base } const percent = (value, digits = 0) => `${round(value, digits)}%` const paginate = (rows, page = 1, pageSize = 10) => { const safePage = Math.max(1, toNumber(page) || 1) const safePageSize = Math.max(1, toNumber(pageSize) || 10) const total = rows.length const totalPages = Math.max(1, Math.ceil(total / safePageSize)) const current = Math.min(safePage, totalPages) const start = (current - 1) * safePageSize return { rows: rows.slice(start, start + safePageSize), page: current, pageSize: safePageSize, total, totalPages, } } module.exports = { addDays, formatDate, formatTime, formatNumber, minutesBetween, paginate, percent, round, today, toNumber, uid, }