mirror of
https://github.com/nextcloud/richdocuments.git
synced 2025-12-18 05:20:43 +01:00
fix: Create new files on public pages for 31+
Signed-off-by: Julius Knorr <jus@bitgrid.net>
This commit is contained in:
parent
6e43e3b87a
commit
d82b195294
4 changed files with 143 additions and 170 deletions
|
|
@ -49,7 +49,10 @@ const getFileTypes = () => {
|
|||
}
|
||||
|
||||
const getFileType = (document) => {
|
||||
return getFileTypes()[document]
|
||||
return {
|
||||
...getFileTypes()[document],
|
||||
name: document,
|
||||
}
|
||||
}
|
||||
|
||||
export default {
|
||||
|
|
|
|||
|
|
@ -10,16 +10,14 @@ import {
|
|||
isDownloadHidden,
|
||||
} from './helpers/index.js'
|
||||
import { getCapabilities } from './services/capabilities.ts'
|
||||
import NewFileMenu from './view/NewFileMenu.js'
|
||||
import { registerNewFileMenuEntries } from './view/NewFileMenu.js'
|
||||
|
||||
document.addEventListener('DOMContentLoaded', () => {
|
||||
if (!isPublicShare() || !OCA.Viewer) {
|
||||
return
|
||||
}
|
||||
|
||||
if (OCA.Files && OCA.Files.fileActions) {
|
||||
OC.Plugins.register('OCA.Files.NewFileMenu', NewFileMenu)
|
||||
}
|
||||
registerNewFileMenuEntries()
|
||||
|
||||
const isEnabledFilesPdfViewer = getCapabilities().mimetypesNoDefaultOpen.includes('application/pdf')
|
||||
|
||||
|
|
|
|||
|
|
@ -6,16 +6,14 @@
|
|||
import axios from '@nextcloud/axios'
|
||||
import { generateOcsUrl, generateFilePath } from '@nextcloud/router'
|
||||
import { getSharingToken } from '@nextcloud/sharing/public'
|
||||
import { getCurrentDirectory } from '../helpers/filesApp.js'
|
||||
|
||||
export const createEmptyFile = async (mimeType, fileName, templateId = null) => {
|
||||
export const createEmptyFile = async (context, mimeType, fileName, templateId = null) => {
|
||||
const shareToken = getSharingToken()
|
||||
const directoryPath = getCurrentDirectory()
|
||||
|
||||
const response = await axios.post(generateOcsUrl('apps/richdocuments/api/v1/file', 2), {
|
||||
mimeType,
|
||||
fileName,
|
||||
directoryPath,
|
||||
directoryPath: context.dirname,
|
||||
shareToken,
|
||||
templateId,
|
||||
})
|
||||
|
|
|
|||
|
|
@ -4,174 +4,148 @@
|
|||
*/
|
||||
|
||||
import axios from '@nextcloud/axios'
|
||||
import { getCurrentDirectory } from '../helpers/filesApp.js'
|
||||
import { emit } from '@nextcloud/event-bus'
|
||||
import Types from '../helpers/types.js'
|
||||
import { createEmptyFile } from '../services/api.js'
|
||||
import { generateUrl, generateFilePath, generateOcsUrl } from '@nextcloud/router'
|
||||
import { showError } from '@nextcloud/dialogs'
|
||||
import { getCapabilities } from '../services/capabilities.ts'
|
||||
import { File, addNewFileMenuEntry, isFilenameValid, getUniqueName } from '@nextcloud/files'
|
||||
|
||||
/** @type OC.Plugin */
|
||||
const NewFileMenu = {
|
||||
attach(newFileMenu) {
|
||||
const self = this
|
||||
const document = Types.getFileType('document')
|
||||
const spreadsheet = Types.getFileType('spreadsheet')
|
||||
const presentation = Types.getFileType('presentation')
|
||||
const drawing = Types.getFileType('drawing')
|
||||
|
||||
newFileMenu.addMenuEntry({
|
||||
id: 'add-' + document.extension,
|
||||
displayName: t('richdocuments', 'New document'),
|
||||
templateName: t('richdocuments', 'New document') + '.' + document.extension,
|
||||
iconClass: 'icon-filetype-document',
|
||||
fileType: 'x-office-document',
|
||||
actionHandler(filename) {
|
||||
if (getCapabilities().templates) {
|
||||
self._openTemplatePicker('document', document.mime, filename)
|
||||
} else {
|
||||
self._createDocument(document.mime, filename)
|
||||
}
|
||||
},
|
||||
})
|
||||
|
||||
newFileMenu.addMenuEntry({
|
||||
id: 'add-' + spreadsheet.extension,
|
||||
displayName: t('richdocuments', 'New spreadsheet'),
|
||||
templateName: t('richdocuments', 'New spreadsheet') + '.' + spreadsheet.extension,
|
||||
iconClass: 'icon-filetype-spreadsheet',
|
||||
fileType: 'x-office-spreadsheet',
|
||||
actionHandler(filename) {
|
||||
if (getCapabilities().templates) {
|
||||
self._openTemplatePicker('spreadsheet', spreadsheet.mime, filename)
|
||||
} else {
|
||||
self._createDocument(spreadsheet.mime, filename)
|
||||
}
|
||||
},
|
||||
})
|
||||
|
||||
newFileMenu.addMenuEntry({
|
||||
id: 'add-' + presentation.extension,
|
||||
displayName: t('richdocuments', 'New presentation'),
|
||||
templateName: t('richdocuments', 'New presentation') + '.' + presentation.extension,
|
||||
iconClass: 'icon-filetype-presentation',
|
||||
fileType: 'x-office-presentation',
|
||||
actionHandler(filename) {
|
||||
if (getCapabilities().templates) {
|
||||
self._openTemplatePicker('presentation', presentation.mime, filename)
|
||||
} else {
|
||||
self._createDocument(presentation.mime, filename)
|
||||
}
|
||||
},
|
||||
})
|
||||
|
||||
newFileMenu.addMenuEntry({
|
||||
id: 'add-' + drawing.extension,
|
||||
displayName: t('richdocuments', 'New drawing'),
|
||||
templateName: t('richdocuments', 'New drawing') + '.' + drawing.extension,
|
||||
iconClass: 'icon-filetype-draw',
|
||||
fileType: 'x-office-drawing',
|
||||
actionHandler(filename) {
|
||||
if (getCapabilities().templates) {
|
||||
self._openTemplatePicker('drawing', drawing.mime, filename)
|
||||
} else {
|
||||
self._createDocument(drawing.mime, filename)
|
||||
}
|
||||
},
|
||||
})
|
||||
},
|
||||
|
||||
_createDocument(mimetype, filename, templateId = null) {
|
||||
OCA.Files.Files.isFileNameValid(filename)
|
||||
filename = FileList.getUniqueName(filename)
|
||||
|
||||
createEmptyFile(mimetype, filename, templateId).then((response) => {
|
||||
if (response && response.status === 'success') {
|
||||
FileList.add(response.data, { animate: true, scrollTo: true })
|
||||
const fileModel = FileList.getModelForFile(filename)
|
||||
const fileAction = OCA.Files.fileActions.getDefaultFileAction(fileModel.get('mimetype'), 'file', OC.PERMISSION_ALL)
|
||||
fileAction.action(filename, {
|
||||
$file: null,
|
||||
fileId: fileModel.id,
|
||||
dir: getCurrentDirectory(),
|
||||
fileList: FileList,
|
||||
fileActions: FileList.fileActions,
|
||||
})
|
||||
} else {
|
||||
showError(t('core', 'Could not create file') + ': ' + response.data.message)
|
||||
}
|
||||
})
|
||||
},
|
||||
|
||||
_openTemplatePicker(type, mimetype, filename) {
|
||||
axios.get(generateOcsUrl(`apps/richdocuments/api/v1/templates/${type}`, 2)).then(({ data: response }) => {
|
||||
if (response.ocs.data.length === 1) {
|
||||
const { id } = response.ocs.data[0]
|
||||
this._createDocument(mimetype, filename, id)
|
||||
return
|
||||
}
|
||||
this._buildTemplatePicker(response.ocs.data)
|
||||
.then(() => {
|
||||
const self = this
|
||||
const buttonlist = [{
|
||||
text: t('core', 'Cancel'),
|
||||
classes: 'cancel',
|
||||
click() {
|
||||
$(this).ocdialog('close')
|
||||
},
|
||||
}, {
|
||||
text: t('richdocuments', 'Create'),
|
||||
classes: 'primary',
|
||||
click() {
|
||||
const templateId = this.dataset.templateId
|
||||
self._createDocument(mimetype, filename, templateId)
|
||||
$(this).ocdialog('close')
|
||||
},
|
||||
}]
|
||||
|
||||
$('#template-picker').ocdialog({
|
||||
closeOnEscape: true,
|
||||
modal: true,
|
||||
buttons: buttonlist,
|
||||
})
|
||||
})
|
||||
})
|
||||
},
|
||||
|
||||
_buildTemplatePicker(data) {
|
||||
return axios.get(generateFilePath('richdocuments', 'templates', 'templatePicker.html')).then(({ data: tmpl }) => {
|
||||
const $tmpl = $(tmpl).eq(2)
|
||||
// init template picker
|
||||
const $dlg = $tmpl.octemplate({
|
||||
dialog_name: 'template-picker',
|
||||
dialog_title: t('richdocuments', 'Select template'),
|
||||
})
|
||||
|
||||
// create templates list
|
||||
const templates = Object.values(data)
|
||||
templates.forEach((template) => {
|
||||
this._appendTemplateFromData($dlg[0], template)
|
||||
})
|
||||
|
||||
$('body').append($dlg)
|
||||
})
|
||||
},
|
||||
|
||||
_appendTemplateFromData(dlg, data) {
|
||||
const template = dlg.querySelector('.template-model').cloneNode(true)
|
||||
template.className = ''
|
||||
template.querySelector('img').src = generateUrl('apps/richdocuments/template/preview/' + data.id)
|
||||
template.querySelector('h2').textContent = data.name
|
||||
template.onclick = function(e) {
|
||||
e.preventDefault()
|
||||
dlg.dataset.templateId = data.id
|
||||
const createFileTypeEntry = (type, displayName, iconClass, index) => ({
|
||||
id: 'add-' + type.extension,
|
||||
displayName: t('richdocuments', displayName),
|
||||
iconClass,
|
||||
order: 10 + index,
|
||||
async handler(context, content) {
|
||||
const filename = t('richdocuments', displayName) + '.' + type.extension
|
||||
if (getCapabilities().templates) {
|
||||
await openTemplatePicker(context, type.name, type.mime, filename, content)
|
||||
} else {
|
||||
await createDocument(context, type.mime, filename, null, content)
|
||||
}
|
||||
if (!dlg.dataset.templateId) {
|
||||
dlg.dataset.templateId = data.id
|
||||
}
|
||||
|
||||
dlg.querySelector('.template-container').appendChild(template)
|
||||
},
|
||||
})
|
||||
|
||||
export const registerNewFileMenuEntries = () => {
|
||||
const fileTypes = [
|
||||
{ type: Types.getFileType('document'), displayName: 'New document', iconClass: 'icon-filetype-document' },
|
||||
{ type: Types.getFileType('spreadsheet'), displayName: 'New spreadsheet', iconClass: 'icon-filetype-spreadsheet' },
|
||||
{ type: Types.getFileType('presentation'), displayName: 'New presentation', iconClass: 'icon-filetype-presentation' },
|
||||
{ type: Types.getFileType('drawing'), displayName: 'New drawing', iconClass: 'icon-filetype-draw' },
|
||||
]
|
||||
|
||||
fileTypes.forEach(({ type, displayName, iconClass }, index) => {
|
||||
addNewFileMenuEntry(createFileTypeEntry(type, displayName, iconClass, index))
|
||||
})
|
||||
}
|
||||
|
||||
export default NewFileMenu
|
||||
const createDocument = async (context, mimetype, filename, templateId = null, content = []) => {
|
||||
if (!isFilenameValid(filename)) {
|
||||
return
|
||||
}
|
||||
|
||||
filename = getUniqueName(
|
||||
filename,
|
||||
content.map((n) => n.basename),
|
||||
)
|
||||
|
||||
try {
|
||||
const response = await createEmptyFile(context, mimetype, filename, templateId)
|
||||
const { data } = response
|
||||
|
||||
const file = new File({
|
||||
source: context.source + '/' + filename,
|
||||
basename: filename,
|
||||
id: data.id,
|
||||
mtime: new Date(data.mtime),
|
||||
mime: data.mimetype,
|
||||
owner: null,
|
||||
permissions: data.permissions,
|
||||
root: context?.root,
|
||||
})
|
||||
emit('files:node:created', file)
|
||||
|
||||
if (response && response.status === 'success') {
|
||||
OCA.Viewer.open({ path: context.dirname + '/' + filename })
|
||||
} else {
|
||||
showError(t('core', 'Could not create file') + ': ' + response.data.message)
|
||||
}
|
||||
} catch (error) {
|
||||
console.error(error)
|
||||
showError(t('core', 'Could not create file'))
|
||||
}
|
||||
}
|
||||
|
||||
const openTemplatePicker = async (context, type, mimetype, filename, content = []) => {
|
||||
try {
|
||||
const { data: response } = await axios.get(generateOcsUrl(`apps/richdocuments/api/v1/templates/${type}`, 2))
|
||||
const templates = response.ocs.data
|
||||
|
||||
if (templates.length === 1) {
|
||||
await createDocument(context, mimetype, filename, templates[0].id, content)
|
||||
return
|
||||
}
|
||||
|
||||
await showTemplatePickerDialog(context, type, mimetype, filename, templates, content)
|
||||
} catch (error) {
|
||||
console.error(error)
|
||||
showError(t('core', 'Could not load templates'))
|
||||
}
|
||||
}
|
||||
|
||||
const showTemplatePickerDialog = async (context, type, mimetype, filename, templates, content) => {
|
||||
const { data: tmpl } = await axios.get(generateFilePath('richdocuments', 'templates', 'templatePicker.html'))
|
||||
const $tmpl = $(tmpl).eq(2)
|
||||
const $dlg = $tmpl.octemplate({
|
||||
dialog_name: 'template-picker',
|
||||
dialog_title: t('richdocuments', 'Select template'),
|
||||
})
|
||||
|
||||
templates.forEach((template) => {
|
||||
appendTemplateFromData($dlg[0], template)
|
||||
})
|
||||
|
||||
$('body').append($dlg)
|
||||
|
||||
const buttonlist = [
|
||||
{
|
||||
text: t('core', 'Cancel'),
|
||||
classes: 'cancel',
|
||||
click() {
|
||||
$(this).ocdialog('close')
|
||||
},
|
||||
},
|
||||
{
|
||||
text: t('richdocuments', 'Create'),
|
||||
classes: 'primary',
|
||||
click() {
|
||||
const templateId = this.dataset.templateId
|
||||
createDocument(context, mimetype, filename, templateId, content)
|
||||
$(this).ocdialog('close')
|
||||
},
|
||||
}
|
||||
]
|
||||
|
||||
$('#template-picker').ocdialog({
|
||||
closeOnEscape: true,
|
||||
modal: true,
|
||||
buttons: buttonlist,
|
||||
})
|
||||
}
|
||||
|
||||
const appendTemplateFromData = (dlg, data) => {
|
||||
const template = dlg.querySelector('.template-model').cloneNode(true)
|
||||
template.className = ''
|
||||
template.querySelector('img').src = generateUrl('apps/richdocuments/template/preview/' + data.id)
|
||||
template.querySelector('h2').textContent = data.name
|
||||
template.onclick = function(e) {
|
||||
e.preventDefault()
|
||||
dlg.dataset.templateId = data.id
|
||||
}
|
||||
if (!dlg.dataset.templateId) {
|
||||
dlg.dataset.templateId = data.id
|
||||
}
|
||||
|
||||
dlg.querySelector('.template-container').appendChild(template)
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue