mirror of
https://framagit.org/les/gancio.git
synced 2025-01-31 16:42:22 +01:00
use local instance timezone everywhere #151
This commit is contained in:
parent
6776b1b1b1
commit
35e44a8a80
7 changed files with 72 additions and 65 deletions
|
@ -9,6 +9,7 @@
|
|||
@update:from-page='updatePage'
|
||||
:locale='$i18n.locale'
|
||||
:attributes='attributes'
|
||||
:timezone='settings.instance_timezone'
|
||||
transition='fade'
|
||||
aria-label='Calendar'
|
||||
is-expanded
|
||||
|
@ -26,8 +27,8 @@ export default {
|
|||
events: { type: Array, default: () => [] }
|
||||
},
|
||||
data () {
|
||||
const month = dayjs().month() + 1
|
||||
const year = dayjs().year()
|
||||
const month = dayjs.tz().month() + 1
|
||||
const year = dayjs.tz().year()
|
||||
return {
|
||||
selectedDate: null,
|
||||
page: { month, year }
|
||||
|
@ -42,9 +43,7 @@ export default {
|
|||
methods: {
|
||||
...mapActions(['updateEvents', 'showPastEvents']),
|
||||
updatePage (page) {
|
||||
return new Promise((resolve, reject) => {
|
||||
this.$emit('monthchange', page)
|
||||
})
|
||||
},
|
||||
click (day) {
|
||||
this.$emit('dayclick', day)
|
||||
|
|
|
@ -78,8 +78,7 @@ export default {
|
|||
todayEvents () {
|
||||
const start = dayjs(this.value.from).startOf('day').unix()
|
||||
const end = dayjs(this.value.from).endOf('day').unix()
|
||||
const events = this.events.filter(e => e.start_datetime >= start && e.start_datetime <= end)
|
||||
return events
|
||||
return this.events.filter(e => e.start_datetime >= start && e.start_datetime <= end)
|
||||
},
|
||||
attributes () {
|
||||
return attributesFromEvents(this.events, this.tags)
|
||||
|
@ -92,10 +91,10 @@ export default {
|
|||
},
|
||||
|
||||
fromHour () {
|
||||
return this.value.from && this.value.fromHour ? dayjs(this.value.from).format('HH:mm') : null
|
||||
return this.value.from && this.value.fromHour ? dayjs.tz(this.value.from).format('HH:mm') : null
|
||||
},
|
||||
dueHour () {
|
||||
return this.value.due && this.value.dueHour ? dayjs(this.value.due).format('HH:mm') : null
|
||||
return this.value.due && this.value.dueHour ? dayjs.tz(this.value.due).format('HH:mm') : null
|
||||
},
|
||||
hourList () {
|
||||
const hourList = []
|
||||
|
@ -196,7 +195,7 @@ export default {
|
|||
} else if (what === 'fromHour') {
|
||||
if (value) {
|
||||
const [hour, minute] = value.split(':')
|
||||
const from = dayjs(this.value.from).hour(hour).minute(minute).second(0)
|
||||
const from = dayjs.tz(this.value.from).hour(hour).minute(minute).second(0)
|
||||
this.$emit('input', { ...this.value, from, fromHour: true })
|
||||
} else {
|
||||
this.$emit('input', { ...this.value, fromHour: false })
|
||||
|
@ -204,7 +203,7 @@ export default {
|
|||
} else if (what === 'dueHour') {
|
||||
if (value) {
|
||||
const [hour, minute] = value.split(':')
|
||||
const fromHour = dayjs(this.value.from).hour()
|
||||
const fromHour = dayjs.tz(this.value.from).hour()
|
||||
|
||||
// add a day
|
||||
let due = dayjs(this.value.from)
|
||||
|
@ -226,20 +225,20 @@ export default {
|
|||
let from = value.start
|
||||
let due = value.end
|
||||
if (this.value.fromHour) {
|
||||
from = dayjs(value.start).hour(dayjs(this.value.from).hour())
|
||||
from = dayjs.tz(value.start).hour(dayjs.tz(this.value.from).hour())
|
||||
}
|
||||
if (this.value.dueHour) {
|
||||
due = dayjs(value.end).hour(dayjs(this.value.due).hour())
|
||||
due = dayjs.tz(value.end).hour(dayjs.tz(this.value.due).hour())
|
||||
}
|
||||
this.$emit('input', { ...this.value, from, due })
|
||||
} else {
|
||||
let from = value
|
||||
let due = this.value.due
|
||||
if (this.value.fromHour) {
|
||||
from = dayjs(value).hour(dayjs(this.value.from).hour())
|
||||
from = dayjs.tz(value).hour(dayjs.tz(this.value.from).hour())
|
||||
}
|
||||
if (this.value.dueHour && this.value.due) {
|
||||
due = dayjs(value).hour(dayjs(this.value.due).hour())
|
||||
due = dayjs.tz(value).hour(dayjs.tz(this.value.due).hour())
|
||||
}
|
||||
this.$emit('input', { ...this.value, from, due })
|
||||
}
|
||||
|
|
|
@ -84,7 +84,7 @@ export default {
|
|||
validate ({ store }) {
|
||||
return (store.state.auth.loggedIn || store.state.settings.allow_anon_event)
|
||||
},
|
||||
async asyncData ({ params, $axios, error, store }) {
|
||||
async asyncData ({ params, $axios, error }) {
|
||||
if (params.edit) {
|
||||
const data = { event: { place: {}, media: [] } }
|
||||
data.id = params.edit
|
||||
|
@ -101,8 +101,8 @@ export default {
|
|||
data.event.place.address = event.place.address || ''
|
||||
data.date = {
|
||||
recurrent: event.recurrent,
|
||||
from: new Date(dayjs.unix(event.start_datetime)),
|
||||
due: new Date(dayjs.unix(event.end_datetime)),
|
||||
from: dayjs.unix(event.start_datetime).toDate(),
|
||||
due: dayjs.unix(event.end_datetime).toDate(),
|
||||
multidate: event.multidate,
|
||||
fromHour: true,
|
||||
dueHour: true
|
||||
|
@ -118,8 +118,8 @@ export default {
|
|||
return {}
|
||||
},
|
||||
data () {
|
||||
const month = dayjs().month() + 1
|
||||
const year = dayjs().year()
|
||||
const month = dayjs.tz().month() + 1
|
||||
const year = dayjs.tz().year()
|
||||
return {
|
||||
mdiFileImport, mdiFormatTitle, mdiTagMultiple, mdiCloseCircle,
|
||||
valid: false,
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
<template lang="pug">
|
||||
v-container#home(fluid)
|
||||
v-container#home(fluid)
|
||||
|
||||
//- Announcements
|
||||
#announcements.mx-1.mt-1(v-if='announcements.length')
|
||||
|
@ -20,7 +20,6 @@
|
|||
//- Events
|
||||
#events.mb-2.mt-1.pl-1.pl-sm-2
|
||||
Event(:event='event' @destroy='destroy' v-for='(event, idx) in visibleEvents' :lazy='idx>2' :key='event.id' @tagclick='tagClick' @placeclick='placeClick')
|
||||
|
||||
</template>
|
||||
|
||||
<script>
|
||||
|
@ -37,7 +36,7 @@ export default {
|
|||
name: 'Index',
|
||||
components: { Event, Search, Announcement, Calendar },
|
||||
middleware: 'setup',
|
||||
async asyncData ({ params, $api, store }) {
|
||||
async asyncData ({ $api }) {
|
||||
const events = await $api.getEvents({
|
||||
start: dayjs().startOf('month').unix(),
|
||||
end: null,
|
||||
|
@ -45,13 +44,13 @@ export default {
|
|||
})
|
||||
return { events }
|
||||
},
|
||||
data ({ $store }) {
|
||||
data () {
|
||||
return {
|
||||
mdiCloseCircle,
|
||||
first: true,
|
||||
isCurrentMonth: true,
|
||||
now: dayjs().unix(),
|
||||
date: dayjs().format('YYYY-MM-DD'),
|
||||
date: dayjs.tz().format('YYYY-MM-DD'),
|
||||
events: [],
|
||||
start: dayjs().startOf('month').unix(),
|
||||
end: null,
|
||||
|
@ -113,10 +112,8 @@ export default {
|
|||
}
|
||||
},
|
||||
methods: {
|
||||
// onIntersect (isIntersecting, eventId) {
|
||||
// this.intersecting[eventId] = isIntersecting
|
||||
// },
|
||||
...mapActions(['setFilters']),
|
||||
|
||||
destroy (id) {
|
||||
this.events = this.events.filter(e => e.id !== id)
|
||||
},
|
||||
|
@ -158,16 +155,15 @@ export default {
|
|||
this.selectedDay = null
|
||||
|
||||
// check if current month is selected
|
||||
if (month - 1 === dayjs().month() && year === dayjs().year()) {
|
||||
if (month - 1 === dayjs.tz().month() && year === dayjs.tz().year()) {
|
||||
this.isCurrentMonth = true
|
||||
this.start = dayjs().startOf('month').unix()
|
||||
this.date = dayjs().format('YYYY-MM-DD')
|
||||
this.date = dayjs.tz().format('YYYY-MM-DD')
|
||||
} else {
|
||||
this.isCurrentMonth = false
|
||||
this.date = ''
|
||||
this.start = dayjs().year(year).month(month - 1).startOf('month').unix() // .startOf('week').unix()
|
||||
}
|
||||
// TODO: check if calendar view is double
|
||||
this.end = dayjs().year(year).month(month).endOf('month').unix() // .endOf('week').unix()
|
||||
this.updateEvents()
|
||||
},
|
||||
|
@ -175,7 +171,7 @@ export default {
|
|||
this.setFilters(filters)
|
||||
},
|
||||
dayChange (day) {
|
||||
this.selectedDay = day ? dayjs(day).format('YYYY-MM-DD') : null
|
||||
this.selectedDay = day ? dayjs.tz(day).format('YYYY-MM-DD') : null
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -7,12 +7,15 @@ import localizedFormat from 'dayjs/plugin/localizedFormat'
|
|||
|
||||
|
||||
import 'dayjs/locale/it'
|
||||
import 'dayjs/locale/en'
|
||||
import 'dayjs/locale/es'
|
||||
import 'dayjs/locale/ca'
|
||||
import 'dayjs/locale/pl'
|
||||
import 'dayjs/locale/eu'
|
||||
import 'dayjs/locale/nb'
|
||||
import 'dayjs/locale/fr'
|
||||
import 'dayjs/locale/de'
|
||||
import 'dayjs/locale/gl'
|
||||
|
||||
dayjs.extend(relativeTime)
|
||||
dayjs.extend(utc)
|
||||
|
@ -23,25 +26,27 @@ export default ({ app, store }) => {
|
|||
// set timezone to instance_timezone!!
|
||||
// to show local time relative to event's place
|
||||
// not where in the world I'm looking at the page from
|
||||
dayjs.tz.setDefault(store.state.settings.instance_timezone)
|
||||
dayjs.locale(store.state.locale)
|
||||
const instance_timezone = store.state.settings.instance_timezone
|
||||
const locale = store.state.locale
|
||||
dayjs.tz.setDefault(instance_timezone)
|
||||
dayjs.locale(locale)
|
||||
|
||||
// replace links with anchors
|
||||
// TODO: remove fb tracking id?
|
||||
Vue.filter('linkify', value => value.replace(/(https?:\/\/([^\s]+))/g, '<a href="$1">$2</a>'))
|
||||
Vue.filter('url2host', url => url.match(/^https?:\/\/(.[^/:]+)/i)[1])
|
||||
Vue.filter('datetime', value => dayjs(value).locale(store.state.locale).format('ddd, D MMMM HH:mm'))
|
||||
Vue.filter('dateFormat', (value, format) => dayjs(value).format(format))
|
||||
Vue.filter('unixFormat', (timestamp, format) => dayjs.unix(timestamp).format(format))
|
||||
Vue.filter('datetime', value => dayjs.tz(value).locale(locale).format('ddd, D MMMM HH:mm'))
|
||||
Vue.filter('dateFormat', (value, format) => dayjs.tz(value).format(format))
|
||||
Vue.filter('unixFormat', (timestamp, format) => dayjs.unix(timestamp).tz(instance_timezone).format(format))
|
||||
|
||||
// shown in mobile homepage
|
||||
Vue.filter('day', value => dayjs.unix(value).locale(store.state.locale).format('dddd, D MMM'))
|
||||
Vue.filter('mediaURL', (event, type) => {
|
||||
Vue.filter('day', value => dayjs.unix(value).tz(instance_timezone).locale(store.state.locale).format('dddd, D MMM'))
|
||||
Vue.filter('mediaURL', (event, type, format = '.jpg') => {
|
||||
if (event.media && event.media.length) {
|
||||
if (type === 'alt') {
|
||||
return event.media[0].name
|
||||
} else {
|
||||
return store.state.settings.baseurl + '/media/' + (type === 'thumb' ? 'thumb/' : '') + event.media[0].url
|
||||
return store.state.settings.baseurl + '/media/' + (type === 'thumb' ? 'thumb/' : '') + event.media[0].url.replace(/.jpg$/, format)
|
||||
}
|
||||
} else if (type !== 'alt') {
|
||||
return store.state.settings.baseurl + '/media/' + (type === 'thumb' ? 'thumb/' : '') + 'logo.svg'
|
||||
|
@ -49,16 +54,16 @@ export default ({ app, store }) => {
|
|||
return ''
|
||||
})
|
||||
|
||||
Vue.filter('from', timestamp => dayjs.unix(timestamp).fromNow())
|
||||
Vue.filter('from', timestamp => dayjs.unix(timestamp).tz(instance_timezone).fromNow())
|
||||
|
||||
Vue.filter('recurrentDetail', event => {
|
||||
const parent = event.parent
|
||||
const { frequency, type } = parent.recurrent
|
||||
let recurrent
|
||||
if (frequency === '1w' || frequency === '2w') {
|
||||
recurrent = app.i18n.t(`event.recurrent_${frequency}_days`, { days: dayjs.unix(parent.start_datetime).format('dddd') })
|
||||
recurrent = app.i18n.t(`event.recurrent_${frequency}_days`, { days: dayjs.unix(parent.start_datetime).tz(instance_timezone).format('dddd') })
|
||||
} else if (frequency === '1m' || frequency === '2m') {
|
||||
const d = type === 'ordinal' ? dayjs.unix(parent.start_datetime).date() : dayjs.unix(parent.start_datetime).format('dddd')
|
||||
const d = type === 'ordinal' ? dayjs.unix(parent.start_datetime).date() : dayjs.unix(parent.start_datetime).tz(instance_timezone).format('dddd')
|
||||
if (type === 'ordinal') {
|
||||
recurrent = app.i18n.t(`event.recurrent_${frequency}_days`, { days: d })
|
||||
} else {
|
||||
|
@ -70,8 +75,8 @@ export default ({ app, store }) => {
|
|||
})
|
||||
|
||||
Vue.filter('when', (event) => {
|
||||
const start = dayjs.unix(event.start_datetime)
|
||||
const end = dayjs.unix(event.end_datetime)
|
||||
const start = dayjs.unix(event.start_datetime).tz(instance_timezone)
|
||||
const end = dayjs.unix(event.end_datetime).tz(instance_timezone)
|
||||
|
||||
// const normal = `${start.format('dddd, D MMMM (HH:mm-')}${end.format('HH:mm) ')}`
|
||||
// // recurrent event
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
const config = require('../../config')
|
||||
const moment = require('dayjs')
|
||||
const { htmlToText } = require('html-to-text')
|
||||
|
||||
const { Model, DataTypes } = require('sequelize')
|
||||
|
@ -14,9 +13,12 @@ const Place = require('./place')
|
|||
const User = require('./user')
|
||||
const Tag = require('./tag')
|
||||
|
||||
const utc = require('dayjs/plugin/utc')
|
||||
const dayjs = require('dayjs')
|
||||
const timezone = require('dayjs/plugin/timezone')
|
||||
const utc = require('dayjs/plugin/utc')
|
||||
|
||||
dayjs.extend(utc)
|
||||
dayjs.extend(timezone)
|
||||
|
||||
class Event extends Model {}
|
||||
|
||||
|
@ -76,7 +78,7 @@ Event.prototype.toAP = function (username, locale, to = []) {
|
|||
const plainDescription = htmlToText(this.description && this.description.replace('\n', '').slice(0, 1000))
|
||||
const content = `
|
||||
📍 ${this.place && this.place.name}
|
||||
📅 ${moment.unix(this.start_datetime).locale(locale).format('dddd, D MMMM (HH:mm)')}
|
||||
📅 ${dayjs.unix(this.start_datetime).tz().locale(locale).format('dddd, D MMMM (HH:mm)')}
|
||||
|
||||
${plainDescription}
|
||||
`
|
||||
|
@ -99,8 +101,8 @@ Event.prototype.toAP = function (username, locale, to = []) {
|
|||
name: this.title,
|
||||
url: `${config.baseurl}/event/${this.slug || this.id}`,
|
||||
type: 'Event',
|
||||
startTime: moment.unix(this.start_datetime).locale(locale).format(),
|
||||
endTime: this.end_datetime ? moment.unix(this.end_datetime).locale(locale).format() : null,
|
||||
startTime: dayjs.unix(this.start_datetime).tz().locale(locale).format(),
|
||||
endTime: this.end_datetime ? dayjs.unix(this.end_datetime).tz().locale(locale).format() : null,
|
||||
location: {
|
||||
name: this.place.name,
|
||||
address: this.place.address
|
||||
|
|
|
@ -5,6 +5,10 @@ module.exports = function () {
|
|||
const log = require('../server/log')
|
||||
const settingsController = require('./api/controller/settings')
|
||||
const db = require('./api/models/index')
|
||||
const dayjs = require('dayjs')
|
||||
const timezone = require('dayjs/plugin/timezone')
|
||||
dayjs.extend(timezone)
|
||||
|
||||
async function start (nuxt) {
|
||||
|
||||
if (config.status == 'READY') {
|
||||
|
@ -27,6 +31,8 @@ module.exports = function () {
|
|||
await settingsController.load()
|
||||
}
|
||||
|
||||
dayjs.tz.setDefault(settingsController.settings.instance_timezone)
|
||||
|
||||
let TaskManager
|
||||
if (config.status === 'READY' && process.env.NODE_ENV == 'production') {
|
||||
TaskManager = require('../server/taskManager').TaskManager
|
||||
|
|
Loading…
Reference in a new issue