Интеграция Date-fns с Vue.js строится вокруг принципа минимальной связности: библиотека не требует глобальной конфигурации и легко встраивается как в отдельные компоненты, так и в слой бизнес-логики.
Установка зависимости выполняется стандартным способом:
npm install date-fns
или
yarn add date-fns
Date-fns представляет собой набор чистых функций, что делает его удобным для использования в реактивной системе Vue без дополнительных обёрток.
В Vue-проектах использование Date-fns обычно распределяется по трём уровням:
Основная идея — отделение форматирования и вычислений от шаблонов компонентов.
Базовая функция форматирования импортируется напрямую:
import { format } from 'date-fns'
const formatted = format(new Date(), 'dd.MM.yyyy')
Использование в компоненте Vue:
<script setup>
import { format } from 'date-fns'
const now = new Date()
const formattedDate = format(now, 'dd.MM.yyyy HH:mm')
</script>
<template>
<div>
{{ formattedDate }}
</div>
</template>
Подход подходит для статических значений, когда пересчёт не требуется при изменении реактивного состояния.
При работе с динамическими датами применяется реактивная модель:
<script setup>
import { computed, ref } from 'vue'
import { format } from 'date-fns'
const timestamp = ref(Date.now())
const formatted = computed(() => {
return format(new Date(timestamp.value), 'yyyy-MM-dd HH:mm:ss')
})
</script>
<template>
<div>
{{ formatted }}
</div>
</template>
computed обеспечивает автоматическое обновление при
изменении исходного значения.
Для масштабируемых приложений логика Date-fns выносится в composables.
// useDateFormat.js
import { computed } from 'vue'
import { format } from 'date-fns'
export function useDateFormat(dateRef, pattern = 'dd.MM.yyyy') {
const formatted = computed(() => {
if (!dateRef.value) return ''
return format(new Date(dateRef.value), pattern)
})
return {
formatted
}
}
Использование:
<script setup>
import { ref } from 'vue'
import { useDateFormat } from './useDateFormat'
const date = ref(Date.now())
const { formatted } = useDateFormat(date, 'dd.MM.yyyy HH:mm')
</script>
Такой слой позволяет централизовать работу с форматами и упростить поддержку.
Date-fns поддерживает локализацию через отдельные модули:
import { format } from 'date-fns'
import { ru } from 'date-fns/locale'
Пример форматирования с локалью:
const formatted = format(new Date(), 'PPPP', { locale: ru })
В Vue-компоненте локаль часто передаётся как зависимость:
<script setup>
import { computed } from 'vue'
import { format } from 'date-fns'
import { ru } from 'date-fns/locale'
const date = new Date()
const formatted = computed(() => {
return format(date, 'd MMMM yyyy', { locale: ru })
})
</script>
Подход позволяет централизовать поддержку мультиязычности.
Date-fns предоставляет функции сравнения, которые удобно применять в вычисляемых свойствах.
import { isAfter, isBefore } from 'date-fns'
Пример использования:
<script setup>
import { ref, computed } from 'vue'
import { isAfter } from 'date-fns'
const deadline = ref(new Date('2026-12-31'))
const now = ref(new Date())
const isExpired = computed(() => {
return isAfter(now.value, deadline.value)
})
</script>
Такая модель часто используется для статусов событий, дедлайнов и уведомлений.
Date-fns предоставляет функции для вычисления разницы:
import { differenceInDays, differenceInHours } from 'date-fns'
Пример:
<script setup>
import { computed, ref } from 'vue'
import { differenceInDays } from 'date-fns'
const start = ref(new Date('2026-01-01'))
const end = ref(new Date())
const days = computed(() => {
return differenceInDays(end.value, start.value)
})
</script>
Такой подход применяется в аналитике, трекинге активности и отображении прогресса.
При работе с input-элементами часто требуется преобразование строки в дату и обратно.
import { parse, format } from 'date-fns'
Пример:
<script setup>
import { ref } from 'vue'
import { parse, format } from 'date-fns'
const input = ref('01.05.2026')
const date = computed(() => {
return parse(input.value, 'dd.MM.yyyy', new Date())
})
const formatted = computed(() => {
return format(date.value, 'yyyy-MM-dd')
})
</script>
Такая схема используется в кастомных datepicker-компонентах.
При интенсивных вычислениях с датами в реактивной системе важно минимизировать повторные вызовы форматирования.
Типичный подход — предварительное вычисление:
import { format } from 'date-fns'
function formatList(dates) {
return dates.map(d => format(d, 'dd.MM.yyyy'))
}
В Vue это часто комбинируется с watch:
import { watch, ref } from 'vue'
import { format } from 'date-fns'
const rawDates = ref([])
const formatted = ref([])
watch(rawDates, (newVal) => {
formatted.value = newVal.map(d => format(d, 'dd.MM.yyyy'))
})
В крупных проектах создаётся единый слой работы с датами:
// dateService.js
import { format, isValid } from 'date-fns'
export function safeFormat(date, pattern) {
if (!isValid(date)) return ''
return format(date, pattern)
}
Далее сервис подключается в компонентах без прямого импорта Date-fns.
Особенность Vue 3 заключается в глубокой реактивности объектов. При работе с Date-fns важно учитывать, что Date не является реактивным типом сам по себе.
Решение — хранение timestamp:
const date = ref(Date.now())
и преобразование только в вычисляемых свойствах:
const formatted = computed(() => format(new Date(date.value), 'dd.MM.yyyy'))
Такой подход исключает проблемы синхронизации состояния.
В серверном рендеринге форматирование дат выполняется на стороне сервера и должно быть детерминированным.
Особое внимание уделяется локали:
import { format } from 'date-fns'
import { ru } from 'date-fns/locale'
export function renderDate(date) {
return format(date, 'dd MMMM yyyy', { locale: ru })
}
Результат сериализуется и передаётся клиенту без повторного вычисления.
Для унификации отображения дат в интерфейсе создаются константы:
export const DATE_FORMATS = {
short: 'dd.MM.yyyy',
long: 'dd MMMM yyyy',
time: 'HH:mm',
full: 'dd.MM.yyyy HH:mm'
}
Использование:
format(new Date(), DATE_FORMATS.full)
Такой подход снижает дублирование и повышает согласованность UI.
Date-fns по умолчанию работает с локальным временем среды выполнения.
Для управления временными зонами применяется дополнительный слой,
например date-fns-tz.
import { format } from 'date-fns'
import { utcToZonedTime } from 'date-fns-tz'
const timeZone = 'Europe/Moscow'
const zonedDate = utcToZonedTime(new Date(), timeZone)
const formatted = format(zonedDate, 'dd.MM.yyyy HH:mm')
В Vue это часто инкапсулируется в composable:
export function useZonedDate(dateRef, zone) {
const formatted = computed(() => {
const zoned = utcToZonedTime(dateRef.value, zone)
return format(zoned, 'dd.MM.yyyy HH:mm')
})
return { formatted }
}