WSL/SLF GitLab Repository

Commit cfa5544f authored by Dominik Haas's avatar Dominik Haas
Browse files

refactoring of methods for the uppy uplaod

parent 49a3628c
......@@ -13,14 +13,13 @@
*/
import Uppy from '@uppy/core';
import AwsS3Multipart from '@uppy/aws-s3-multipart';
import GoldenRetriever from '@uppy/golden-retriever';
import axios from 'axios';
const domain = process.env.VUE_APP_ENVIDAT_PROXY;
let uppyInstance = null;
let apiKey = null;
let currentResourceId = undefined;
const uppyId = 'resource-upload';
const defaultRestrictions = {
......@@ -46,7 +45,7 @@ function createUppyInstance(autoProceed = true, debug = false, restrictions = de
return uppy;
}
async function initiateMultipart(file) {
export async function initiateMultipart(file) {
// this.$store.dispatch(
// `${USER_NAMESPACE}/METADATA_EDITING_MULTIPART_UPLOAD_INIT`,
// payload,
......@@ -65,7 +64,7 @@ const files = {
const payload = {
// id: await this.createCKANResource(file),
id: '',
id: currentResourceId,
name: file.name,
size: file.size,
};
......@@ -82,7 +81,107 @@ const files = {
key: res.data.result.name,
};
} catch (error) {
console.log(`Multipart initiation failed: ${error}`);
console.error(`Multipart initiation failed: ${error}`);
return error;
}
}
export async function requestPresignedUrls(file, { uploadId, partNumbers }) {
const url = `${domain}/api/action/cloudstorage_get_presigned_url_list_multipart`;
const payload = {
id: currentResourceId,
uploadId,
partNumbersList: partNumbers,
filename: file.name,
};
try {
const res = await axios.post(url, payload, {
headers: {
Authorization: apiKey,
},
});
return {
presignedUrls: res.data.result.presignedUrls,
// headers: {
// 'Content-Type': 'application/octet-stream',
// },
};
} catch (error) {
console.error(`Presigning urls failed: ${error}`);
return error;
}
}
export async function completeMultipart(file, uploadData) {
const url = `${domain}/api/action/cloudstorage_finish_multipart`;
const payload = {
id: currentResourceId,
uploadId: uploadData.uploadId,
partInfo: JSON.stringify(uploadData.parts),
};
try {
const res = await axios.post(url, payload, {
headers: {
Authorization: apiKey,
},
});
return { location: await res.data.result.url };
} catch (error) {
console.error(`Multipart completion failed: ${error}`);
return error;
}
}
export async function abortMultipart(file, uploadData) {
const url = `${domain}/api/action/cloudstorage_abort_multipart`;
const payload = {
id: currentResourceId,
deletedInCKAN: await this.deleteCKANResource(),
};
try {
// const res =
await axios.post(url, payload, {
headers: {
Authorization: apiKey,
},
});
// console.log(
// `Multipart upload aborted. Resource ID ${this.resourceId} | S3 Upload ID ${uploadData.uploadId}`,
// );
return {};
} catch (error) {
// console.log(
// `Multipart abort failed for Resource ID ${this.resourceId}: ${error}`,
// );
return error;
}
}
export async function listUploadedParts(file, { uploadId, key }) {
const url = `${domain}/api/action/cloudstorage_multipart_list_parts`;
const payload = {
uploadId,
uploadKey: key,
};
try {
const res = await axios.post(url, payload, {
headers: {
Authorization: apiKey,
},
});
console.log(`Multipart parts: ${res.data.result}`);
return res.data.result;
} catch (error) {
console.log(`Listing multipart parts failed: ${error}`);
return error;
}
}
......@@ -100,26 +199,56 @@ export function getUppyInstance(userApiKey) {
uppyInstance = createUppyInstance();
uppyInstance
.use(GoldenRetriever, { serviceWorker: true })
.use(AwsS3Multipart, {
limit: 4,
getChunkSize(file) {
// at least 25MB per request, at most 500 requests
return Math.max(1024 * 1024 * 25, Math.ceil(file.size / 500));
},
createMultipartUpload: initiateMultipart,
prepareUploadParts: this.requestPresignedUrls,
listParts: this.listUploadedParts,
abortMultipartUpload: this.abortMultipart,
completeMultipartUpload: this.completeMultipart,
})
.on('upload-complete', this.$emit('uploadComplete', 'Done'));
/*
const testing = process.env.NODE_ENV === 'test';
if (!testing) {
uppyInstance
.use(GoldenRetriever, { serviceWorker: true })
.use(AwsS3Multipart, {
limit: 4,
getChunkSize(file) {
// at least 25MB per request, at most 500 requests
return Math.max(1024 * 1024 * 25, Math.ceil(file.size / 500));
},
createMultipartUpload: initiateMultipart,
prepareUploadParts: requestPresignedUrls,
listParts: listUploadedParts,
abortMultipartUpload: abortMultipart,
completeMultipartUpload: completeMultipart,
})
}
*/
// uppyInstance.on('upload-complete', this.$emit('uploadComplete', 'Done'));
return uppyInstance;
}
export function setCurrentResourceId(id) {
currentResourceId = id;
}
export function addFile(fileName, filepath, filedata) {
if (hasUppyInstance()) {
uppyInstance.addFile({
name: fileName,
type: 'image/png', // file type
data: filedata, // file blob
meta: {
// optional, store the directory path of a file so Uppy can tell identical files in different directories apart.
relativePath: filepath,
},
source: 'Local', // optional, determines the source of the file, for example, Instagram.
isRemote: false, // optional, set to true if actual file is not in the browser, but on some remote server, for example,
// when using companion in combination with Instagram.
});
}
}
export function subscribeOnUppyEvent(event, callback) {
if (hasUppyInstance()) {
uppyInstance.on(event, callback);
......@@ -132,3 +261,11 @@ export function unSubscribeOnUppyEvent(event, callback) {
}
}
export function destoryUppyInstance() {
apiKey = null;
// this will cancel all pending uploads
uppyInstance.close();
uppyInstance = null;
}
......@@ -9,8 +9,12 @@
<v-row>
<v-col cols="12">
<drag-drop :uppy="uppy" />
<status-bar :uppy="uppy" />
<DragDrop :uppy="uppy"
v-on:ondragover="logEvent"
v-on:ondragleave="logEvent"
v-on:ondrop="logEvent" />
<StatusBar :uppy="uppy" />
</v-col>
</v-row>
</v-container>
......@@ -36,7 +40,6 @@ import '@uppy/core/dist/style.css';
import '@uppy/drag-drop/dist/style.css';
import '@uppy/status-bar/dist/style.css';
import Uppy from '@uppy/core';
import AwsS3Multipart from '@uppy/aws-s3-multipart';
import GoldenRetriever from '@uppy/golden-retriever';
......@@ -45,6 +48,16 @@ import {
USER_SIGNIN_NAMESPACE,
} from '@/modules/user/store/userMutationsConsts';
import {
destoryUppyInstance,
getUppyInstance,
initiateMultipart,
listUploadedParts,
requestPresignedUrls,
abortMultipart,
completeMultipart,
} from '@/factories/uploadFactory';
const domain = process.env.VUE_APP_ENVIDAT_PROXY;
export default {
......@@ -52,54 +65,47 @@ export default {
props: {
metadataId: String,
},
beforeMount() {},
mounted() {
this.setupUppy();
},
beforeDestroy() {
this.uppy.close();
destoryUppyInstance();
this.uppy = null;
},
computed: {
uppy() {
return new Uppy({
autoProceed: true,
debug: false,
// logger: Uppy.debugLogger,
restrictions: {
maxFileSize: 1024 * 1024 * 1024 * 20, // 20 GB
maxNumberOfFiles: 1,
minNumberOfFiles: 1,
},
})
.use(GoldenRetriever, { serviceWorker: true })
.use(AwsS3Multipart, {
limit: 4,
getChunkSize(file) {
// at least 25MB per request, at most 500 requests
return Math.max(1024 * 1024 * 25, Math.ceil(file.size / 500));
},
createMultipartUpload: this.initiateMultipart,
prepareUploadParts: this.requestPresignedUrls,
listParts: this.listUploadedParts,
abortMultipartUpload: this.abortMultipart,
completeMultipartUpload: this.completeMultipart,
})
.on('upload-complete', this.$emit('uploadComplete', 'Done'));
},
files() {
return [
{
name: this.fileName,
size: this.fileSize,
type: this.fileType,
},
];
},
userApiKey() {
if (this.$store) {
return this.$store.getters[`${USER_SIGNIN_NAMESPACE}/getUserApiKey`];
}
return null;
},
},
methods: {
setupUppy() {
if (this.uppy === null) {
this.uppy = getUppyInstance(this.userApiKey);
}
this.uppy
.use(GoldenRetriever, { serviceWorker: true })
.use(AwsS3Multipart, {
limit: 4,
getChunkSize(file) {
// at least 25MB per request, at most 500 requests
return Math.max(1024 * 1024 * 25, Math.ceil(file.size / 500));
},
createMultipartUpload: initiateMultipart,
prepareUploadParts: requestPresignedUrls,
listParts: listUploadedParts,
abortMultipartUpload: abortMultipart,
completeMultipartUpload: completeMultipart,
});
// this.$options.components.DragDrop.o
},
async createCKANResource(file) {
// this.$store.dispatch(
// `${USER_NAMESPACE}/METADATA_EDITING_POST_RESOURCE`,
......@@ -171,137 +177,13 @@ export default {
return error;
}
},
async initiateMultipart(file) {
// this.$store.dispatch(
// `${USER_NAMESPACE}/METADATA_EDITING_MULTIPART_UPLOAD_INIT`,
// payload,
// );
this.fileName = file.name;
this.fileSize = file.size;
this.fileType = file.type;
this.$emit('createResources', this.files);
const url = `${domain}/api/action/cloudstorage_initiate_multipart`;
const payload = {
// id: await this.createCKANResource(file),
id: '',
name: file.name,
size: file.size,
};
try {
const res = await axios.post(url, payload, {
headers: {
Authorization: this.userApiKey,
},
});
return {
uploadId: res.data.result.id,
key: res.data.result.name,
};
} catch (error) {
// console.log(`Multipart initiation failed: ${error}`);
return error;
}
},
async requestPresignedUrls(file, partData) {
const url = `${domain}/api/action/cloudstorage_get_presigned_url_list_multipart`;
const payload = {
id: this.resourceId,
uploadId: partData.uploadId,
partNumbersList: partData.partNumbers,
filename: file.name,
};
try {
const res = await axios.post(url, payload, {
headers: {
Authorization: this.userApiKey,
},
});
return {
presignedUrls: res.data.result.presignedUrls,
// headers: {
// 'Content-Type': 'application/octet-stream',
// },
};
} catch (error) {
// console.log(`Presigning urls failed: ${error}`);
return error;
}
},
async completeMultipart(file, uploadData) {
const url = `${domain}/api/action/cloudstorage_finish_multipart`;
const payload = {
id: this.resourceId,
uploadId: uploadData.uploadId,
partInfo: JSON.stringify(uploadData.parts),
};
try {
const res = await axios.post(url, payload, {
headers: {
Authorization: this.userApiKey,
},
});
return { location: await res.data.result.url };
} catch (error) {
// console.log(`Multipart completion failed: ${error}`);
return error;
}
},
async abortMultipart(__, uploadData) {
const url = `${domain}/api/action/cloudstorage_abort_multipart`;
const payload = {
id: this.resourceId,
deletedInCKAN: await this.deleteCKANResource(),
};
try {
const res = await axios.post(url, payload, {
headers: {
Authorization: this.userApiKey,
},
});
// console.log(
// `Multipart upload aborted. Resource ID ${this.resourceId} | S3 Upload ID ${uploadData.uploadId}`,
// );
return {};
} catch (error) {
// console.log(
// `Multipart abort failed for Resource ID ${this.resourceId}: ${error}`,
// );
return error;
}
},
async listUploadedParts(__, uploadData) {
const url = `${domain}/api/action/cloudstorage_multipart_list_parts`;
const payload = {
uploadId: uploadData.uploadId,
uploadKey: uploadData.key,
};
try {
const res = await axios.post(url, payload, {
headers: {
Authorization: this.userApiKey,
},
});
console.log(`Multipart parts: ${res.data.result}`);
return res.data.result;
} catch (error) {
console.log(`Listing multipart parts failed: ${error}`);
return error;
}
logEvent(event) {
console.log(`Got event ${event}`);
console.log(event);
},
},
data: () => ({
uppy: null,
labels: {
title: 'Create Resource from Files',
},
......
......@@ -14,7 +14,7 @@
import { enhanceMetadatas, enhanceTags } from '@/factories/metaDataFactory';
import { VALIDATION_ERROR, } from './userMutationsConsts';
import { VALIDATION_ERROR } from './userMutationsConsts';
export function extractError(store, reason, errorProperty = 'error') {
......
import {
addFile,
getUppyInstance, subscribeOnUppyEvent,
} from '@/factories/uploadFactory';
const fs = require('fs');
describe('uploadFactory - renderMarkdown', () => {
it('renderMarkdown - getUppyInstance() no apiKey', () => {
const uppy = getUppyInstance();
const uppy2 = getUppyInstance();
expect(uppy).toBeDefined();
expect(uppy2).toBeDefined();
expect(uppy.id).toEqual(uppy2.id);
});
it('renderMarkdown - subscribe on events', () => {
const filePath = `${__dirname}/../../src/assets/`;
const pngFile = 'noisy_pattern.png';
const dataString = fs.readFileSync(`${filePath}${pngFile}`);
const uppy = getUppyInstance();
subscribeOnUppyEvent('file-added', (file) => {
console.log(`added file: ${file.name}`);
expect(file).toBeDefined();
})
// addFile(pngFile, filePath, dataString);
});
});
/*
describe('stringFactory - stripMarkdown', () => {
it('stripMarkdown - empty', () => {
const emptyOutput = stripMarkdown();
expect(emptyOutput).toBe('');
});
});
*/
Supports Markdown
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