diff --git a/komga-webui/src/components/readers/PagedReader.vue b/komga-webui/src/components/readers/PagedReader.vue index ca33adddf..1def81c77 100644 --- a/komga-webui/src/components/readers/PagedReader.vue +++ b/komga-webui/src/components/readers/PagedReader.vue @@ -84,8 +84,9 @@ import {buildSpreads} from '@/functions/book-spreads' export default Vue.extend({ name: 'PagedReader', - data: () => { + data: function () { return { + logger: 'PagedReader', carouselPage: 0, spreads: [] as PageDtoWithUrl[][], } @@ -122,19 +123,23 @@ export default Vue.extend({ }, watch: { pages: { - handler (val) { + handler(val) { this.spreads = buildSpreads(val, this.pageLayout) }, immediate: true, }, - currentPage (val) { + currentPage(val, old) { + this.$logDebug('[watch:currentPage]', `old:${old}`, `new:${val}`)() this.$emit('update:page', val) }, - page (val) { - this.carouselPage = this.toSpreadIndex(val) + page(val, old) { + this.$logDebug('[watch:page]', `old:${old}`, `new:${val}`)() + const spreadIndex = this.toSpreadIndex(val) + this.$logDebug('[watch:page]', `toSpreadIndex:${spreadIndex}`)() + this.carouselPage = spreadIndex }, pageLayout: { - handler (val) { + handler(val) { const current = this.page this.spreads = buildSpreads(this.pages, val) this.carouselPage = this.toSpreadIndex(current) @@ -142,14 +147,14 @@ export default Vue.extend({ immediate: true, }, }, - created () { + created() { window.addEventListener('keydown', this.keyPressed) }, - destroyed () { + destroyed() { window.removeEventListener('keydown', this.keyPressed) }, computed: { - shortcuts (): any { + shortcuts(): any { const shortcuts = [] switch (this.readingDirection) { case ReadingDirection.LEFT_TO_RIGHT: @@ -164,39 +169,40 @@ export default Vue.extend({ } return this.$_.keyBy(shortcuts, x => x.key) }, - flipDirection (): boolean { + flipDirection(): boolean { return this.readingDirection === ReadingDirection.RIGHT_TO_LEFT }, - vertical (): boolean { + vertical(): boolean { return this.readingDirection === ReadingDirection.VERTICAL }, - currentSlide (): number { + currentSlide(): number { return this.carouselPage + 1 }, - currentPage (): number { + currentPage(): number { + this.$logDebug('[currentPage]', `carouselPage:${this.carouselPage}`, `spreads.length:${this.spreads.length}`)() if (this.carouselPage >= 0 && this.carouselPage < this.spreads.length && this.spreads.length > 0) { return this.spreads[this.carouselPage][0].number } return 1 }, - slidesCount (): number { + slidesCount(): number { return this.spreads.length }, - canPrev (): boolean { + canPrev(): boolean { return this.currentSlide > 1 }, - canNext (): boolean { + canNext(): boolean { return this.currentSlide < this.slidesCount }, - isDoublePages (): boolean { + isDoublePages(): boolean { return this.pageLayout === PagedReaderLayout.DOUBLE_PAGES || this.pageLayout === PagedReaderLayout.DOUBLE_NO_COVER }, }, methods: { - keyPressed (e: KeyboardEvent) { + keyPressed(e: KeyboardEvent) { this.shortcuts[e.key]?.execute(this) }, - imgClass (spread: PageDtoWithUrl[]): string { + imgClass(spread: PageDtoWithUrl[]): string { const double = spread.length > 1 switch (this.scale) { case ScaleType.WIDTH: @@ -211,27 +217,27 @@ export default Vue.extend({ return 'img-fit-original' } }, - eagerLoad (spreadIndex: number): boolean { + eagerLoad(spreadIndex: number): boolean { return Math.abs(this.carouselPage - spreadIndex) <= 2 }, - centerClick () { + centerClick() { this.$emit('menu') }, - turnRight () { + turnRight() { if (!this.vertical) this.flipDirection ? this.prev() : this.next() }, - turnLeft () { + turnLeft() { if (!this.vertical) this.flipDirection ? this.next() : this.prev() }, - verticalPrev () { + verticalPrev() { if (this.vertical) this.prev() }, - verticalNext () { + verticalNext() { if (this.vertical) this.next() }, - prev () { + prev() { if (this.canPrev) { this.carouselPage-- window.scrollTo(0, 0) @@ -239,7 +245,7 @@ export default Vue.extend({ this.$emit('jump-previous') } }, - next () { + next() { if (this.canNext) { this.carouselPage++ window.scrollTo(0, 0) @@ -247,7 +253,8 @@ export default Vue.extend({ this.$emit('jump-next') } }, - toSpreadIndex (i: number): number { + toSpreadIndex(i: number): number { + this.$logDebug('[toSpreadIndex]', `i:${i}`, `isDoublePages:${this.isDoublePages}`)() if (this.spreads.length > 0) { if (this.isDoublePages) { for (let j = 0; j < this.spreads.length; j++) { diff --git a/komga-webui/src/main.ts b/komga-webui/src/main.ts index aa1a3f2c6..ccfeaf8c7 100644 --- a/komga-webui/src/main.ts +++ b/komga-webui/src/main.ts @@ -20,23 +20,20 @@ import komgaTransientBooks from './plugins/komga-transientbooks.plugin' import komgaSse from './plugins/komga-sse.plugin' import komgaTasks from './plugins/komga-tasks.plugin' import vuetify from './plugins/vuetify' +import logger from './plugins/logger.plugin' import './public-path' import router from './router' import store from './store' import i18n from './i18n' -import log from 'loglevel' Vue.prototype.$_ = _ Vue.prototype.$eventHub = new Vue() -Vue.prototype.$log = log -if (process.env.VUE_APP_LOG_LEVEL) - Vue.prototype.$log.setLevel(process.env.VUE_APP_LOG_LEVEL) - Vue.use(Vuelidate) Vue.use(lineClamp) Vue.use(httpPlugin) +Vue.use(logger) Vue.use(komgaFileSystem, {http: Vue.prototype.$http}) Vue.use(komgaSeries, {http: Vue.prototype.$http}) Vue.use(komgaCollections, {http: Vue.prototype.$http}) @@ -68,7 +65,6 @@ declare module 'vue/types/vue' { interface Vue { $_: LoDashStatic; $eventHub: Vue; - $log: log.RootLogger; } } diff --git a/komga-webui/src/plugins/logger.plugin.ts b/komga-webui/src/plugins/logger.plugin.ts new file mode 100644 index 000000000..814f72166 --- /dev/null +++ b/komga-webui/src/plugins/logger.plugin.ts @@ -0,0 +1,60 @@ +import _Vue from 'vue' +import log from 'loglevel' +import _, {isArray, isObject} from 'lodash' +import {format} from 'date-fns' + +export default { + install(Vue: typeof _Vue) { + if (process.env.VUE_APPlog_LEVEL) + log.setLevel(process.env.VUE_APPlog_LEVEL as any) + + Vue.prototype.$logTrace = function (...msg: any[]) { + const loggerName = _.get(this, 'logger') || _.get(this, '$options.name') + const logger = loggerName ? log.getLogger(loggerName) : log + return logger.trace.bind(logger, getPrefix('TRACE', loggerName), ...(stringArgs(msg))) + } + + Vue.prototype.$logDebug = function (...msg: any[]) { + const loggerName = _.get(this, 'logger') || _.get(this, '$options.name') + const logger = loggerName ? log.getLogger(loggerName) : log + return logger.debug.bind(logger, getPrefix('DEBUG', loggerName), ...(stringArgs(msg))) + } + + Vue.prototype.$logInfo = function (...msg: any[]) { + const loggerName = _.get(this, 'logger') || _.get(this, '$options.name') + const logger = loggerName ? log.getLogger(loggerName) : log + return logger.info.bind(logger, getPrefix('INFO', loggerName), ...(stringArgs(msg))) + } + + Vue.prototype.$logWarn = function (...msg: any[]) { + const loggerName = _.get(this, 'logger') || _.get(this, '$options.name') + const logger = loggerName ? log.getLogger(loggerName) : log + return logger.warn.bind(logger, getPrefix('WARN', loggerName), ...(stringArgs(msg))) + } + + Vue.prototype.$logError = function (...msg: any[]) { + const loggerName = _.get(this, 'logger') || _.get(this, '$options.name') + const logger = loggerName ? log.getLogger(loggerName) : log + return logger.error.bind(logger, getPrefix('ERROR', loggerName), ...(stringArgs(msg))) + } + }, +} + +function stringArgs(msg: any[]): any[] { + return msg.map(m => isObject(m) || isArray(m) ? JSON.stringify(m) : m) +} + +function getPrefix(level: string, loggerName: string): string { + const timestamp = format(new Date(), 'yyyy-MM-dd HH:mm:ss.SSS') + return `${timestamp} ${level} --- ${loggerName} :` +} + +declare module 'vue/types/vue' { + interface Vue { + $logTrace(...msg: any[]): (...msg: any[]) => void; + $logDebug(...msg: any[]): (...msg: any[]) => void; + $logInfo(...msg: any[]): (...msg: any[]) => void; + $logWarn(...msg: any[]): (...msg: any[]) => void; + $logError(...msg: any[]): (...msg: any[]) => void; + } +} diff --git a/komga-webui/src/views/BookReader.vue b/komga-webui/src/views/BookReader.vue index 0d28579cd..ecdf23c7d 100644 --- a/komga-webui/src/views/BookReader.vue +++ b/komga-webui/src/views/BookReader.vue @@ -420,8 +420,7 @@ export default Vue.extend({ if (screenfull.isEnabled) screenfull.on('change', this.fullscreenChanged) }, async mounted() { - this.$log.debug('mounted') - this.$log.debug(`route.query: ${JSON.stringify(this.$route.query)}`) + this.$logDebug('[mounted]', 'route.query:', this.$route.query)() this.readingDirection = this.$store.state.persistedState.webreader.readingDirection this.animations = this.$store.state.persistedState.webreader.animations @@ -454,7 +453,7 @@ export default Vue.extend({ // route update means either: // - going to previous/next book, in this case the query.page is not set, so it will default to first page // - pressing the back button of the browser and navigating to the previous book, in this case the query.page is set, so we honor it - this.$log.debug(`beforeRouteUpdate, to.query: ${JSON.stringify(to.query)}`) + this.$logDebug('[beforeRouteUpdate]', 'to.query:', to.query)() this.setup(to.params.bookId, Number(to.query.page)) } next() @@ -629,7 +628,7 @@ export default Vue.extend({ this.shortcuts[e.key]?.execute(this) }, async setup(bookId: string, page?: number) { - this.$log.debug(`setup bookId:${bookId}, page:${page}`) + this.$logDebug('[setup]', `bookId:${bookId}`, `page:${page}`)() this.book = await this.$komgaBooks.getBook(bookId) this.series = await this.$komgaSeries.getOneSeries(this.book.seriesId) @@ -654,8 +653,7 @@ export default Vue.extend({ pageDtos.forEach((p: any) => p['url'] = this.getPageUrl(p)) this.pages = pageDtos as PageDtoWithUrl[] - this.$log.debug(`pages count: ${this.pagesCount}`) - this.$log.debug(`read progress: ${JSON.stringify(this.book.readProgress)}`) + this.$logDebug('[setup]', `pages count:${this.pagesCount}`, 'read progress:', this.book.readProgress)() if (page && page >= 1 && page <= this.pagesCount) { this.goTo(page) } else if (this.book.readProgress?.completed === false) { @@ -736,7 +734,7 @@ export default Vue.extend({ } }, goTo(page: number) { - this.$log.debug(`goTo: ${page}`) + this.$logDebug('[goTo]', `page:${page}`)() this.page = page this.markProgress(page) },