feat: restore page version
This commit is contained in:
parent
e50dc89519
commit
e85de92715
@ -55,7 +55,7 @@
|
|||||||
v-list-item(@click='download(ph.versionId)')
|
v-list-item(@click='download(ph.versionId)')
|
||||||
v-list-item-avatar(size='24'): v-icon mdi-cloud-download-outline
|
v-list-item-avatar(size='24'): v-icon mdi-cloud-download-outline
|
||||||
v-list-item-title Download Version
|
v-list-item-title Download Version
|
||||||
v-list-item(@click='restore(ph.versionId)', :disabled='ph.versionId === 0')
|
v-list-item(@click='restore(ph.versionId, ph.versionDate)', :disabled='ph.versionId === 0')
|
||||||
v-list-item-avatar(size='24'): v-icon(:disabled='ph.versionId === 0') mdi-history
|
v-list-item-avatar(size='24'): v-icon(:disabled='ph.versionId === 0') mdi-history
|
||||||
v-list-item-title Restore
|
v-list-item-title Restore
|
||||||
v-list-item(@click='branchOff(ph.versionId)')
|
v-list-item(@click='branchOff(ph.versionId)')
|
||||||
@ -111,6 +111,17 @@
|
|||||||
.overline View Mode
|
.overline View Mode
|
||||||
v-card.mt-3(light, v-html='diffHTML', flat)
|
v-card.mt-3(light, v-html='diffHTML', flat)
|
||||||
|
|
||||||
|
v-dialog(v-model='isRestoreConfirmDialogShown', max-width='650', persistent)
|
||||||
|
v-card
|
||||||
|
.dialog-header.is-orange {{$t('history:restore.confirmTitle')}}
|
||||||
|
v-card-text.pa-4
|
||||||
|
i18next(tag='span', path='history:restore.confirmText')
|
||||||
|
strong(place='date') {{ restoreTarget.versionDate | moment('LLL') }}
|
||||||
|
v-card-actions
|
||||||
|
v-spacer
|
||||||
|
v-btn(text, @click='isRestoreConfirmDialogShown = false', :disabled='restoreLoading') {{$t('common:actions.cancel')}}
|
||||||
|
v-btn(color='orange darken-2', dark, @click='restoreConfirm', :loading='restoreLoading') {{$t('history:restore.confirmButton')}}
|
||||||
|
|
||||||
nav-footer
|
nav-footer
|
||||||
notify
|
notify
|
||||||
search-results
|
search-results
|
||||||
@ -124,6 +135,7 @@ import _ from 'lodash'
|
|||||||
import gql from 'graphql-tag'
|
import gql from 'graphql-tag'
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
|
i18nOptions: { namespaces: 'history' },
|
||||||
props: {
|
props: {
|
||||||
pageId: {
|
pageId: {
|
||||||
type: Number,
|
type: Number,
|
||||||
@ -194,7 +206,13 @@ export default {
|
|||||||
offsetPage: 0,
|
offsetPage: 0,
|
||||||
total: 0,
|
total: 0,
|
||||||
viewMode: 'line-by-line',
|
viewMode: 'line-by-line',
|
||||||
cache: []
|
cache: [],
|
||||||
|
restoreTarget: {
|
||||||
|
versionId: 0,
|
||||||
|
versionDate: ''
|
||||||
|
},
|
||||||
|
isRestoreConfirmDialogShown: false,
|
||||||
|
restoreLoading: false
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
@ -335,8 +353,59 @@ export default {
|
|||||||
download (versionId) {
|
download (versionId) {
|
||||||
window.location.assign(`/d/${this.locale}/${this.path}?v=${versionId}`)
|
window.location.assign(`/d/${this.locale}/${this.path}?v=${versionId}`)
|
||||||
},
|
},
|
||||||
restore (versionId) {
|
restore (versionId, versionDate) {
|
||||||
|
this.restoreTarget = {
|
||||||
|
versionId,
|
||||||
|
versionDate
|
||||||
|
}
|
||||||
|
this.isRestoreConfirmDialogShown = true
|
||||||
|
},
|
||||||
|
async restoreConfirm () {
|
||||||
|
this.restoreLoading = true
|
||||||
|
this.$store.commit(`loadingStart`, 'history-restore')
|
||||||
|
try {
|
||||||
|
const resp = await this.$apollo.mutate({
|
||||||
|
mutation: gql`
|
||||||
|
mutation ($pageId: Int!, $versionId: Int!) {
|
||||||
|
pages {
|
||||||
|
restore (pageId: $pageId, versionId: $versionId) {
|
||||||
|
responseResult {
|
||||||
|
succeeded
|
||||||
|
errorCode
|
||||||
|
slug
|
||||||
|
message
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`,
|
||||||
|
variables: {
|
||||||
|
versionId: this.restoreTarget.versionId,
|
||||||
|
pageId: this.pageId
|
||||||
|
}
|
||||||
|
})
|
||||||
|
if (_.get(resp, 'data.pages.restore.responseResult.succeeded', false) === true) {
|
||||||
|
this.$store.commit('showNotification', {
|
||||||
|
style: 'success',
|
||||||
|
message: this.$t('history:restore.success'),
|
||||||
|
icon: 'check'
|
||||||
|
})
|
||||||
|
this.isRestoreConfirmDialogShown = false
|
||||||
|
setTimeout(() => {
|
||||||
|
window.location.assign(`/${this.locale}/${this.path}`)
|
||||||
|
}, 1000)
|
||||||
|
} else {
|
||||||
|
throw new Error(_.get(resp, 'data.pages.restore.responseResult.message', 'An unexpected error occured'))
|
||||||
|
}
|
||||||
|
} catch (err) {
|
||||||
|
this.$store.commit('showNotification', {
|
||||||
|
style: 'red',
|
||||||
|
message: err.message,
|
||||||
|
icon: 'alert'
|
||||||
|
})
|
||||||
|
}
|
||||||
|
this.$store.commit(`loadingStop`, 'history-restore')
|
||||||
|
this.restoreLoading = false
|
||||||
},
|
},
|
||||||
branchOff (versionId) {
|
branchOff (versionId) {
|
||||||
|
|
||||||
|
@ -385,7 +385,7 @@ module.exports = {
|
|||||||
try {
|
try {
|
||||||
const page = await WIKI.models.pages.query().findById(args.id)
|
const page = await WIKI.models.pages.query().findById(args.id)
|
||||||
if (!page) {
|
if (!page) {
|
||||||
throw new Error('Invalid Page Id')
|
throw new WIKI.Error.PageNotFound()
|
||||||
}
|
}
|
||||||
await WIKI.models.pages.renderPage(page)
|
await WIKI.models.pages.renderPage(page)
|
||||||
return {
|
return {
|
||||||
@ -394,6 +394,42 @@ module.exports = {
|
|||||||
} catch (err) {
|
} catch (err) {
|
||||||
return graphHelper.generateError(err)
|
return graphHelper.generateError(err)
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
/**
|
||||||
|
* RESTORE PAGE VERSION
|
||||||
|
*/
|
||||||
|
async restore (obj, args, context) {
|
||||||
|
try {
|
||||||
|
const page = await WIKI.models.pages.query().select('path', 'localeCode').findById(args.pageId)
|
||||||
|
if (!page) {
|
||||||
|
throw new WIKI.Error.PageNotFound()
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!WIKI.auth.checkAccess(context.req.user, ['write:pages'], {
|
||||||
|
path: page.path,
|
||||||
|
locale: page.localeCode
|
||||||
|
})) {
|
||||||
|
throw new WIKI.Error.PageRestoreForbidden()
|
||||||
|
}
|
||||||
|
|
||||||
|
const targetVersion = await WIKI.models.pageHistory.getVersion({ pageId: args.pageId, versionId: args.versionId })
|
||||||
|
if (!targetVersion) {
|
||||||
|
throw new WIKI.Error.PageNotFound()
|
||||||
|
}
|
||||||
|
|
||||||
|
await WIKI.models.pages.updatePage({
|
||||||
|
...targetVersion,
|
||||||
|
id: targetVersion.pageId,
|
||||||
|
user: context.req.user,
|
||||||
|
action: 'restored'
|
||||||
|
})
|
||||||
|
|
||||||
|
return {
|
||||||
|
responseResult: graphHelper.generateSuccess('Page version restored successfully.')
|
||||||
|
}
|
||||||
|
} catch (err) {
|
||||||
|
return graphHelper.generateError(err)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
Page: {
|
Page: {
|
||||||
|
@ -129,6 +129,11 @@ type PageMutation {
|
|||||||
render(
|
render(
|
||||||
id: Int!
|
id: Int!
|
||||||
): DefaultResponse @auth(requires: ["manage:system"])
|
): DefaultResponse @auth(requires: ["manage:system"])
|
||||||
|
|
||||||
|
restore(
|
||||||
|
pageId: Int!
|
||||||
|
versionId: Int!
|
||||||
|
): DefaultResponse @auth(requires: ["write:pages", "manage:pages", "manage:system"])
|
||||||
}
|
}
|
||||||
|
|
||||||
# -----------------------------------------------
|
# -----------------------------------------------
|
||||||
|
@ -153,6 +153,10 @@ module.exports = {
|
|||||||
message: 'Destination page path already exists.',
|
message: 'Destination page path already exists.',
|
||||||
code: 6006
|
code: 6006
|
||||||
}),
|
}),
|
||||||
|
PageRestoreForbidden: CustomError('PageRestoreForbidden', {
|
||||||
|
message: 'You are not authorized to restore this page version.',
|
||||||
|
code: 6011
|
||||||
|
}),
|
||||||
PageUpdateForbidden: CustomError('PageUpdateForbidden', {
|
PageUpdateForbidden: CustomError('PageUpdateForbidden', {
|
||||||
message: 'You are not authorized to update this page.',
|
message: 'You are not authorized to update this page.',
|
||||||
code: 6009
|
code: 6009
|
||||||
|
@ -326,7 +326,8 @@ module.exports = class Page extends Model {
|
|||||||
await WIKI.models.pageHistory.addVersion({
|
await WIKI.models.pageHistory.addVersion({
|
||||||
...ogPage,
|
...ogPage,
|
||||||
isPublished: ogPage.isPublished === true || ogPage.isPublished === 1,
|
isPublished: ogPage.isPublished === true || ogPage.isPublished === 1,
|
||||||
action: 'updated'
|
action: opts.action ? opts.action : 'updated',
|
||||||
|
versionDate: ogPage.updatedAt
|
||||||
})
|
})
|
||||||
|
|
||||||
// -> Update page
|
// -> Update page
|
||||||
@ -422,7 +423,8 @@ module.exports = class Page extends Model {
|
|||||||
// -> Create version snapshot
|
// -> Create version snapshot
|
||||||
await WIKI.models.pageHistory.addVersion({
|
await WIKI.models.pageHistory.addVersion({
|
||||||
...page,
|
...page,
|
||||||
action: 'moved'
|
action: 'moved',
|
||||||
|
versionDate: page.updatedAt
|
||||||
})
|
})
|
||||||
|
|
||||||
const destinationHash = pageHelper.generateHash({ path: opts.destinationPath, locale: opts.destinationLocale, privateNS: opts.isPrivate ? 'TODO' : '' })
|
const destinationHash = pageHelper.generateHash({ path: opts.destinationPath, locale: opts.destinationLocale, privateNS: opts.isPrivate ? 'TODO' : '' })
|
||||||
@ -503,7 +505,8 @@ module.exports = class Page extends Model {
|
|||||||
// -> Create version snapshot
|
// -> Create version snapshot
|
||||||
await WIKI.models.pageHistory.addVersion({
|
await WIKI.models.pageHistory.addVersion({
|
||||||
...page,
|
...page,
|
||||||
action: 'deleted'
|
action: 'deleted',
|
||||||
|
versionDate: page.updatedAt
|
||||||
})
|
})
|
||||||
|
|
||||||
// -> Delete page
|
// -> Delete page
|
||||||
|
Loading…
Reference in New Issue
Block a user