Commit 3724425d authored by zaver's avatar zaver
Browse files

Добавлено: pdf merge

Сломаны тесты, надо починить
parent fe0f077e
# DOCS
Для работы требуется nodejs 14
Для работы требуется nodejs 14 и pdftk
Для запуска
```bash
......
......@@ -15,7 +15,7 @@ export default class RouterFactory {
return this.getShortFilesPaths().map(path => this.getRoute(path))
}
public getRouteMap(): void {
public printRouteMap(): void {
console.log('Список всех доступных маршрутов:')
this.getShortFilesPaths().forEach(path => console.log(path))
}
......
......@@ -3,4 +3,8 @@ import { join } from 'path'
const documents = join(process.cwd(), 'documents')
const views = join(process.cwd(), 'src/views')
export { documents, views }
function getFilePathFromDocuments(file: string): string {
return join(documents, file)
}
export { documents, views, getFilePathFromDocuments }
import { ISendFiles } from '../root/api/sendFiles'
import { v4 } from 'uuid'
import { getFilePathFromDocuments } from '../globals'
import PDFMerge from 'pdf-merge'
export default function fileMerger(req: ISendFiles, res, next) {
if (filesUploaded(req)) {
mergeFiles(req)
res.send(req.mergedFile)
} else {
res.status(406)
res.send('Файлы не загружены')
next()
}
}
function filesUploaded(req: ISendFiles) {
return req.uploadedFiles != undefined
}
function mergeFiles(req: ISendFiles) {
req.mergedFile = {
fileName: req.body.filename,
serverName: v4() + req.body.doctype,
}
PDFMerge(
req.uploadedFiles.map(file => getFilePathFromDocuments(file.filename)),
{
output: getFilePathFromDocuments(req.mergedFile.serverName),
},
)
}
import { ISendFiles } from '../root/api/sendFiles'
import convert from '../shared/fileConverter'
export default function formatController(req: ISendFiles, res) {
initFilesToMerge(req)
uploadFiles(req)
res.send(req.filesToMerge)
}
function initFilesToMerge(req: ISendFiles): void {
if (req.filesToMerge == undefined) {
req.filesToMerge = {
extension: req.body.doctype,
filename: req.body.filename,
files: [],
}
}
}
function uploadFiles(req: ISendFiles): void {
req.uploadedFiles.forEach(file => {
if (file.extension == req.body.doctype) {
req.filesToMerge.files.push(file.filename)
} else {
req.filesToMerge.files.push(convert(file.filename, req.body.doctype))
}
})
}
......@@ -29,7 +29,6 @@ function saveFile(req: ISendFiles, file, cb) {
let uploadedFile = {
filename,
originalName: file.originalname,
extension: extname(filename),
}
req.uploadedFiles.push(uploadedFile)
cb(null, filename)
......
......@@ -9,10 +9,5 @@ export default class getFiles extends RouteHandler {
}
function getAllFilesFromDocuments() {
let files = []
readdirSync(documents).forEach(file => {
files.push(file)
console.log(file)
})
return files
return readdirSync(documents)
}
import RouteHandler from '../../RouteHandler'
import uploadDocuments from '../../middlewares/uploadDocuments'
import formatController from '../../middlewares/formatController'
import fileMerger from '../../middlewares/fileMerger'
import { Router } from 'express'
export interface ISendFiles extends Router {
req: any[]
body: {
readonly filename: string
readonly doctype: string
......@@ -11,16 +12,14 @@ export interface ISendFiles extends Router {
uploadedFiles: Array<{
filename: string
originalName: string
extension: string
}>
filesToMerge: {
filename: string
extension: string
files: Array<string>
mergedFile: {
fileName: string
serverName: string
}
}
export default class sendFiles extends RouteHandler {
middlewares = [uploadDocuments, formatController]
middlewares = [uploadDocuments, fileMerger]
post(req, res) {}
}
......@@ -11,7 +11,7 @@ const app = new App({
addons: [urlencoded({ extended: false }), json()],
})
routerFactory.getRouteMap()
routerFactory.printRouteMap()
app.listen()
export default app.app
import * as libre from 'libreoffice-convert'
import { readFileSync, writeFileSync } from 'fs'
import { documents } from '../globals'
import { join, basename, extname } from 'path'
export default function convert(filename, toExtension) {
let convertedFilename = join(documents, basename(filename, extname(filename))) + toExtension
const file = readFileSync(join(documents, basename(filename)))
libre.convert(file, toExtension, undefined, (err, done) => {
if (err) {
console.log(`Error converting file: ${err}`)
}
writeFileSync(convertedFilename, done)
})
return basename(convertedFilename)
}
......@@ -2,42 +2,42 @@ const request = require('supertest')
import { join } from 'path'
import * as fs from 'fs'
import app from '../server'
import { documents } from '../globals'
import { getFilePathFromDocuments } from '../globals'
describe('api/sendFiles', () => {
const sourceFolder = join(process.cwd(), 'src/tests/mocks')
const distFolder = documents
const sample1pdf = join(sourceFolder, 'sample1.pdf')
const sample2pdf = join(sourceFolder, 'sample2.pdf')
function checkAndRemoveFiles(files) {
console.log(files.body)
files.body.forEach(file => {
fs.accessSync(join(distFolder, file.filename))
fs.unlinkSync(join(distFolder, file.filename))
})
function checkAndRemoveFile(file) {
const { serverName } = file.body
console.log(file.body)
// fs.accessSync(getFilePathFromDocuments(serverName))
// fs.unlinkSync(getFilePathFromDocuments(serverName))
}
test('Отправка одного pdf файла ', async done => {
await request(app)
const res = await request(app)
.post('/api/sendFiles')
.field('doctype', '.pdf')
.field('filename', 'FOO')
.attach('documents', sample1pdf)
.then(res => {
checkAndRemoveFiles(res)
.attach('documents', sample2pdf)
.expect(200)
checkAndRemoveFile(res)
done()
})
})
test('Отправка двух pdf файлов', async done => {
await request(app)
const res = await request(app)
.post('/api/sendFiles')
.field('doctype', '.pdf')
.field('filename', 'FOO')
.attach('documents', sample1pdf)
.attach('documents', sample2pdf)
.expect(200)
.then(res => {
checkAndRemoveFiles(res)
checkAndRemoveFile(res)
done()
})
})
})
body {
padding: 20px;
#content {
display: flex;
}
\ No newline at end of file
......@@ -4,6 +4,7 @@
<meta charset="UTF-8">
<link rel="icon" href="document-icon.png">
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<link rel="stylesheet" href="css/styles.css">
</head>
<body>
<div id="root" @submit.prevent="sendFiles">
......@@ -13,16 +14,13 @@
type="file"
name="documents"
@change="getFiles"
multiple accept="application/pdf,application/msword,application/vnd.openxmlformats-officedocument.wordprocessingml.document"
multiple accept="application/pdf"
>
<br>
<input type="radio" id="pdf" value=".pdf" name="doctype" v-model="doctype" checked="checked">
<label for="pdf">pdf</label>
<input type="radio" id="docx" value=".docx" name="doctype" v-model="doctype">
<label for="docx">docx</label>
<br>
<input id="filename" type="text" v-model="filename" name="filename">
<label for="filename">Название файла</label>
......@@ -30,9 +28,9 @@
<br>
<button type="submit">Отправить документы</button>
</form>
<div v-for="files in response">
<div v-for="file in files">
<a :href="`${file.filename}`" :key="file.filename" target="_blank">{{file.originalName}}</a>
<div >
<div v-for="file in respondedFiles">
<a :href="`${file.serverName}`" :key="file.serverName" target="_blank">{{file.fileName}}</a>
<br>
</div>
</div>
......@@ -45,7 +43,8 @@
files: [],
doctype: '.pdf',
filename: 'FOO',
response: []
respondedFiles: [],
allFiles: []
},
methods:{
getFiles() {
......@@ -58,11 +57,28 @@
method: "POST",
body: form,
})
.then(response=>response.json().then(data=> {
.then(response=> {
if (response.ok) {
response.json().then(data => {
console.log(data)
console.log(this.response)
this.response.push(data)
}))
this.respondedFiles.push(data)
console.log(this.respondedFiles)
})
} else {
alert('Файлы не загружены')
}
})
},
getAllFiles() {
fetch('/api/getFiles')
.then(response=>{
if (response.ok) {
response.json()
.then(data=>{
this.allFiles = data
})
}
})
}
}
});
......
......@@ -470,6 +470,13 @@
"@types/yargs" "^15.0.0"
chalk "^4.0.0"
"@rkusa/linebreak@^1.0.0":
version "1.0.0"
resolved "https://registry.yarnpkg.com/@rkusa/linebreak/-/linebreak-1.0.0.tgz#987b6b1f8cc8f5901afbf45f4e9f7744518d0163"
integrity sha512-yCSm87XA1aYMgfcABSxcIkk3JtCw3AihNceHY+DnZGLvVP/g2z3UWZbi0xIoYpZWAJEVPr5Zt3QE37Q80wF1pA==
dependencies:
unicode-trie "^0.3.0"
"@sindresorhus/is@^0.14.0":
version "0.14.0"
resolved "https://registry.yarnpkg.com/@sindresorhus/is/-/is-0.14.0.tgz#9fb3a3cf3132328151f353de4632e01e52102bea"
......@@ -961,6 +968,11 @@ binary-extensions@^2.0.0:
resolved "https://registry.yarnpkg.com/binary-extensions/-/binary-extensions-2.1.0.tgz#30fa40c9e7fe07dbc895678cd287024dea241dd9"
integrity sha512-1Yj8h9Q+QDF5FzhMs/c9+6UntbD5MkRfRwac8DoEm9ZfUBZ7tZ55YcGVAzEe4bXsdQHEk+s9S5wsOKVdZrw0tQ==
bluebird@^3.5.1:
version "3.7.2"
resolved "https://registry.yarnpkg.com/bluebird/-/bluebird-3.7.2.tgz#9f229c15be272454ffa973ace0dbee79a1b0c36f"
integrity sha512-XpNj6GDQzdfW+r2Wnn7xiSAd7TM3jzkxGXBGTtWKuSXv1xUV+azxAm8jdWZN06QTQk+2N2XB9jRDkvbmQmcRtg==
body-parser@1.19.0, body-parser@^1.19.0:
version "1.19.0"
resolved "https://registry.yarnpkg.com/body-parser/-/body-parser-1.19.0.tgz#96b2709e57c9c4e09a6fd66a8fd979844f69f08a"
......@@ -3388,6 +3400,14 @@ onetime@^5.1.0:
dependencies:
mimic-fn "^2.1.0"
opentype.js@^1.3.3:
version "1.3.3"
resolved "https://registry.yarnpkg.com/opentype.js/-/opentype.js-1.3.3.tgz#65b8645b090a1ad444065b784d442fa19d1061f6"
integrity sha512-/qIY/+WnKGlPIIPhbeNjynfD2PO15G9lA/xqlX2bDH+4lc3Xz5GCQ68mqxj3DdUv6AJqCeaPvuAoH8mVL0zcuA==
dependencies:
string.prototype.codepointat "^0.2.1"
tiny-inflate "^1.0.3"
optionator@^0.8.1:
version "0.8.3"
resolved "https://registry.yarnpkg.com/optionator/-/optionator-0.8.3.tgz#84fa1d036fe9d3c7e21d99884b601167ec8fb495"
......@@ -3400,6 +3420,11 @@ optionator@^0.8.1:
type-check "~0.3.2"
word-wrap "~1.2.3"
os-tmpdir@~1.0.2:
version "1.0.2"
resolved "https://registry.yarnpkg.com/os-tmpdir/-/os-tmpdir-1.0.2.tgz#bbe67406c79aa85c5cfec766fe5734555dfa1274"
integrity sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=
p-cancelable@^1.0.0:
version "1.1.0"
resolved "https://registry.yarnpkg.com/p-cancelable/-/p-cancelable-1.1.0.tgz#d078d15a3af409220c886f1d9a0ca2e441ab26cc"
......@@ -3444,6 +3469,16 @@ package-json@^6.3.0:
registry-url "^5.0.0"
semver "^6.2.0"
pako@^0.2.5:
version "0.2.9"
resolved "https://registry.yarnpkg.com/pako/-/pako-0.2.9.tgz#f3f7522f4ef782348da8161bad9ecfd51bf83a75"
integrity sha1-8/dSL073gjSNqBYbrZ7P1Rv4OnU=
pako@^1.0.11:
version "1.0.11"
resolved "https://registry.yarnpkg.com/pako/-/pako-1.0.11.tgz#6c9599d340d54dfd3946380252a35705a6b992bf"
integrity sha512-4hLB8Py4zZce5s4yd9XzopqwVv/yGNhV1Bl8NTmCq1763HeK2+EwVTv+leGeL13Dnh2wfbqowVPXCIO0z4taYw==
parse-json@^5.0.0:
version "5.1.0"
resolved "https://registry.yarnpkg.com/parse-json/-/parse-json-5.1.0.tgz#f96088cdf24a8faa9aea9a009f2d9d942c999646"
......@@ -3499,6 +3534,34 @@ path-to-regexp@0.1.7:
resolved "https://registry.yarnpkg.com/path-to-regexp/-/path-to-regexp-0.1.7.tgz#df604178005f522f15eb4490e7247a1bfaa67f8c"
integrity sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=
pdf-merge@^1.2.0:
version "1.2.0"
resolved "https://registry.yarnpkg.com/pdf-merge/-/pdf-merge-1.2.0.tgz#a15d155e6e6fcff2e34148c6b8960119c5273593"
integrity sha512-/2QygIR3Q/p0SxUhj64LvUzYFVzFL8DQGV8GOpG3I44uXwSTiMS7tAd3dHvxLrnGYLzom2IPdlhnxqLyOC41VQ==
dependencies:
bluebird "^3.5.1"
shell-escape "^0.2.0"
tmp "0.0.33"
pdf-merger-js@^3.0.5:
version "3.0.5"
resolved "https://registry.yarnpkg.com/pdf-merger-js/-/pdf-merger-js-3.0.5.tgz#c70abd5f07cde9eb765e16f8e7f055a542079366"
integrity sha512-fu1DpmGUA4UCX6pdKG7kc5PXJlWrRRANijcH586UDNvsCpyReMZCtVU4B3rQRlqrH1EC8fsjwRK1WBAN/2NOlA==
dependencies:
pdfjs "^2.3.9"
pdfjs@^2.3.9:
version "2.4.1"
resolved "https://registry.yarnpkg.com/pdfjs/-/pdfjs-2.4.1.tgz#8e353fb4bbe536e133fb8ba019921e4b0787afdb"
integrity sha512-nsIaWECzhRfFwQkaKws4onoOq69Hkik9tk0UCv60rEEV/VGNXdlB7Fzp9kqyJJIAToO3ebekDfXbK0c4AVezuQ==
dependencies:
"@rkusa/linebreak" "^1.0.0"
opentype.js "^1.3.3"
pako "^1.0.11"
readable-stream "^3.6.0"
unorm "^1.6.0"
uuid "^8.3.0"
performance-now@^2.1.0:
version "2.1.0"
resolved "https://registry.yarnpkg.com/performance-now/-/performance-now-2.1.0.tgz#6309f4e0e5fa913ec1c69307ae364b4b377c9e7b"
......@@ -3993,6 +4056,11 @@ shebang-regex@^3.0.0:
resolved "https://registry.yarnpkg.com/shebang-regex/-/shebang-regex-3.0.0.tgz#ae16f1644d873ecad843b0307b143362d4c42172"
integrity sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==
shell-escape@^0.2.0:
version "0.2.0"
resolved "https://registry.yarnpkg.com/shell-escape/-/shell-escape-0.2.0.tgz#68fd025eb0490b4f567a027f0bf22480b5f84133"
integrity sha1-aP0CXrBJC09WegJ/C/IkgLX4QTM=
shellwords@^0.1.1:
version "0.1.1"
resolved "https://registry.yarnpkg.com/shellwords/-/shellwords-0.1.1.tgz#d6b9181c1a48d397324c84871efbcfc73fc0654b"
......@@ -4191,6 +4259,11 @@ string-width@^4.0.0, string-width@^4.1.0, string-width@^4.2.0:
is-fullwidth-code-point "^3.0.0"
strip-ansi "^6.0.0"
string.prototype.codepointat@^0.2.1:
version "0.2.1"
resolved "https://registry.yarnpkg.com/string.prototype.codepointat/-/string.prototype.codepointat-0.2.1.tgz#004ad44c8afc727527b108cd462b4d971cd469bc"
integrity sha512-2cBVCj6I4IOvEnjgO/hWqXjqBGsY+zwPmHl12Srk9IXSZ56Jwwmy+66XO5Iut/oQVR7t5ihYdLB0GMa4alEUcg==
string_decoder@^1.1.1:
version "1.3.0"
resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.3.0.tgz#42f114594a46cf1a8e30b0a84f56c78c3edac21e"
......@@ -4323,6 +4396,18 @@ throat@^5.0.0:
resolved "https://registry.yarnpkg.com/throat/-/throat-5.0.0.tgz#c5199235803aad18754a667d659b5e72ce16764b"
integrity sha512-fcwX4mndzpLQKBS1DVYhGAcYaYt7vsHNIvQV+WXMvnow5cgjPphq5CaayLaGsjRdSCKZFNGt7/GYAuXaNOiYCA==
tiny-inflate@^1.0.0, tiny-inflate@^1.0.3:
version "1.0.3"
resolved "https://registry.yarnpkg.com/tiny-inflate/-/tiny-inflate-1.0.3.tgz#122715494913a1805166aaf7c93467933eea26c4"
integrity sha512-pkY1fj1cKHb2seWDy0B16HeWyczlJA9/WW3u3c4z/NiWDsO3DOU5D7nhTLE9CF0yXv/QZFY7sEJmj24dK+Rrqw==
tmp@0.0.33:
version "0.0.33"
resolved "https://registry.yarnpkg.com/tmp/-/tmp-0.0.33.tgz#6d34335889768d21b2bcda0aa277ced3b1bfadf9"
integrity sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==
dependencies:
os-tmpdir "~1.0.2"
tmp@^0.2.1:
version "0.2.1"
resolved "https://registry.yarnpkg.com/tmp/-/tmp-0.2.1.tgz#8457fc3037dcf4719c251367a1af6500ee1ccf14"
......@@ -4512,6 +4597,14 @@ undefsafe@^2.0.3:
dependencies:
debug "^2.2.0"
unicode-trie@^0.3.0:
version "0.3.1"
resolved "https://registry.yarnpkg.com/unicode-trie/-/unicode-trie-0.3.1.tgz#d671dddd89101a08bac37b6a5161010602052085"
integrity sha1-1nHd3YkQGgi6w3tqUWEBBgIFIIU=
dependencies:
pako "^0.2.5"
tiny-inflate "^1.0.0"
union-value@^1.0.0:
version "1.0.1"
resolved "https://registry.yarnpkg.com/union-value/-/union-value-1.0.1.tgz#0b6fe7b835aecda61c6ea4d4f02c14221e109847"
......@@ -4534,6 +4627,11 @@ universalify@^1.0.0:
resolved "https://registry.yarnpkg.com/universalify/-/universalify-1.0.0.tgz#b61a1da173e8435b2fe3c67d29b9adf8594bd16d"
integrity sha512-rb6X1W158d7pRQBg5gkR8uPaSfiids68LTJQYOtEUhoJUWBdaQHsuT/EUduxXYxcrt4r5PJ4fuHW1MHT6p0qug==
unorm@^1.6.0:
version "1.6.0"
resolved "https://registry.yarnpkg.com/unorm/-/unorm-1.6.0.tgz#029b289661fba714f1a9af439eb51d9b16c205af"
integrity sha512-b2/KCUlYZUeA7JFUuRJZPUtr4gZvBh7tavtv4fvk4+KV9pfGiR6CQAQAWl49ZpR3ts2dk4FYkP7EIgDJoiOLDA==
unpipe@1.0.0, unpipe@~1.0.0:
version "1.0.0"
resolved "https://registry.yarnpkg.com/unpipe/-/unpipe-1.0.0.tgz#b2bf4ee8514aae6165b4817829d21b2ef49904ec"
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment