Я работаю над способом загрузки в ведро AWS S3 с метеорного сервера и реагирования на внешний интерфейс.
Я определил следующие файлы
server/methods.js
import { Meteor } from 'meteor/meteor';
import { check } from 'meteor/check';
const AWS = require('aws-sdk')
const s3_bucket = "bucket-name"
import { mediaFiles } from '../imports/api/files.collection';
const s3 = new AWS.S3({
accessKeyId: '<key>',
secretAccessKey: '<secret>',
endpoint: 's3.eu-west-2.amazonaws.com',
region: 'eu-west-2',
signatureVersion: 'v4'
});
Meteor.methods({
'aws.getUploadId' (filename, filetype) {
let params = {
Bucket: s3_bucket,
Key: filename,
ContentType: filetype
}
return new Promise((resolve, reject) => {
s3.createMultipartUpload(params, (err, data) => {
if (err) reject(err)
if (data) resolve(data.UploadId)
})
})
},
'aws.uploadPart' (filename, blob, upload_id, index) {
let params = {
Bucket: s3_bucket,
Key: filename,
PartNumber: index,
UploadId: upload_id,
}
return new Promise((resolve, reject) => {
s3.uploadPart(params, (err, data) => {
if (err) reject(err)
if (data) resolve(data)
})
})
},
'aws.completeUpload' (filename, upload_id, upload_parts) {
console.log("aws.completeUpload called")
console.log(`filename: ${filename}\nID: ${upload_id}\nUpload_parts****${upload_parts}****`)
let params = {
Bucket: s3_bucket,
Key: filename,
UploadId: upload_id,
MultipartUpload: {Parts: upload_parts}
}
return new Promise((resolve, reject) => {
s3.completeMultipartUpload(params, (err, data) => {
if (err) reject(err)
if (data) resolve(data)
})
})
},
});
upload.js # client side
import { Meteor } from 'meteor/meteor';
import React, { Component } from 'react';
import { Page, Icon, ProgressBar, Input, Select } from 'react-onsenui';
import _ from 'underscore';
import Navbar from './Navbar';
class Upload extends Component {
state = {
uploadId : '',
media_file : null,
filename : ''
}
setUploadFileParameters = (e) => {
e.preventDefault();
e.stopPropagation();
console.log('setUploadFileParameters called')
const media_file = e.target.files[0]
const filename = media_file.name
const filetype = media_file.type
Meteor.call('aws.getUploadId', filename, filetype, (err, res) => {
if (err) console.log("Error getting id: ", err)
if (res) {
this.setState({ media_file: media_file, filename: filename, uploadId: res })
}
})
}
uploadIt = (e) => {
e.preventDefault();
const t = e.target
const upload_id = this.state.uploadId
const media_file = t.media_file.files[0]
console.log(`mediafile: ${media_file}`)
try {
const FILE_CHUNK_SIZE = 10000000 // 10MB
const fileSize = media_file.size
const filename = media_file.name
const NUM_CHUNKS = Math.round(fileSize / FILE_CHUNK_SIZE) + 1
let start, end, blob
let upload_parts = []
for (let index = 1; index < NUM_CHUNKS + 1; index++) {
start = (index - 1)*FILE_CHUNK_SIZE
end = (index)*FILE_CHUNK_SIZE
blob = (index < NUM_CHUNKS) ? media_file.slice(start, end) : media_file.slice(start)
// Puts each file part into the storage server
Meteor.call('aws.uploadPart', filename, blob, upload_id, index, (err, res) => {
if (err) console.log("uploading part error ", err)
if (res) {
// console.log("RES: ", typeof res, res)
upload_parts.push({Etag: res.ETag, PartNumber: index})
}
})
}
// Generate the parts list to complete the upload
// Calls the CompleteMultipartUpload endpoint in the backend server
console.log("upload_parts: ", upload_parts)
Meteor.call('aws.completeUpload', filename, upload_id, upload_parts, (err, res) => {
console.log("Complete upload called *****")
if (err) console.log("Complete upload err: ", err)
if (res) console.log("Complete upload res: ", res)
})
}
catch(err) {
console.log(err)
}
}
render() {
const { showMenu } = this.props
console.log("State: ", JSON.stringify(this.state))
return (
<Page renderToolbar={Navbar('Upload', showMenu)}>
<div className="form-container">
{Meteor.user() &&
<form onSubmit={(e) => this.uploadIt(e)}>
<p>File</p>
<Input
type="file"
id="fileinput"
ref="fileinput"
name="media_file"
onChange={e => this.setUploadFileParameters(e)}
/>
<br/>
<button
type="submit"
value="Upload"
className="btn upload-work-button"
>
Upload
</button>
</form>
}
</div>
</Page>
)
}
}
export default Upload;
У меня проблема в том, что содержимое upload_parts
не передается на внутренний сервер метеора.Журнал консоли на внутреннем сервере ничего не возвращает.Он даже не возвращает undefined
.Мне нужна помощь с этим.