Skip to content

Instantly share code, notes, and snippets.

@pszabop
Last active March 17, 2017 21:02
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save pszabop/f2fc9fad4bd87ede757c05dd30741a1d to your computer and use it in GitHub Desktop.
Save pszabop/f2fc9fad4bd87ede757c05dd30741a1d to your computer and use it in GitHub Desktop.
snippet of upload code for a signed POST URL with minio
--------------SUMMARY -----------------
// Uploading a multimedia resource file is a 3-step process:
//
// 1. Acquire an "upload ticket"
// 2. Use the upload ticket to upload the file
// 3. Acquire a "perma link" to the uploaded file
//
-------------- SERVER SIDE ----------------------
picture.initiate = function(current, original) {
var policy = minio.newPostPolicy();
const filename = random.uuid4() + '.' + current.type;
policy.setBucket(config.s3.tmpBucket);
policy.setKey(filename);
const expires = new Date;
expires.setSeconds(config.s3.tmpTTL);
policy.setExpires(expires);
policy.setContentType('application/octet-stream'); // binary data
policy.setContentLengthRange(config.s3.uploadSizeMin, config.s3.uploadSizeMax);
return minio.presignedPostPolicyAsync(policy)
.spread((url, formData) => {
current.uploadLink = url;
current.uploadForm = JSON.stringify(formData);
current.filename = filename;
current.state = picture.StateEnum.uploading;
return current;
});
};
---------------- CLIENT SIDE ------------------------
function uploadMultimediaResource(file, uploadTicket, onSuccess, onFailure)
{
console.info(`${objectName}.uploadMultimediaResource(uploadTicket = ${JSON.stringify(uploadTicket)})`);
// Create the object that will upload the multimedia resource.
const xhr = new XMLHttpRequest();
// Specify the HTTP transfer type, URL, and whether the transfer is asynchronous.
xhr.open('POST', uploadTicket.uploadLink, true);
// Define the request header.
const uploadForm = JSON.parse(uploadTicket.uploadForm);
_.each(uploadForm, (value, key) => {
console.info(`Setting request header "${key}" to "${value}"`);
xhr.setRequestHeader(key, value);
});
// Define the "onload" event handler.
xhr.onload = () => {
if (xhr.status == 200) {
const responseHeader = xhr.getRequestHeader();
const resourceId = uploadTicket.id;
const resourceChecksum = 'junk';
console.info(`${objectName}.uploadMultimediaResource: responseHeader = ${responseHeader}`)
getMultimediaResourcePermaLink(resourceId, resourceChecksum, onSuccess, onFailure)
} else {
const errorMessage = `${objectName}.uploadMultimediaResource(): xhr status code = ${xhr.status}`;
onFailure(errorMessage);
}
};
// Send the multimedia resource.
xhr.send(file);
[.....]
and the graphQL in the browser code that interacts with the server that has functional unit tests
function setMultimediaResource(file, onSuccess, onFailure)
{
console.info(`${objectName}.setMultimediaResource()`);
// Uploading a multimedia resource file is a 3-step process:
//
// 1. Acquire an "upload ticket"
// 2. Use the upload ticket to upload the file
// 3. Acquire a "perma link" to the uploaded file
//
// Each of these steps is handled by a separate function in this file.
const mutation = `
mutation {
pictureSet (
picture: {
description: "",
type: "${file.type}",
}
)
{
id,
description,
type,
checksum,
uploadLink,
uploadForm,
state
}
}`;
console.info(`mutation = ${mutation}`);
httpAgent
.post(config.persistence.appServerQueryUrl)
.withCredentials()
.set('Content-Type', 'application/graphql')
.set('Accept', 'application/json')
.send(mutation)
.then(function(res) {
console.info(`res = ${JSON.stringify(res)}`);
if (res.ok && !res.body.errors)
{
uploadMultimediaResource(file, res.body.data.pictureSet, onSuccess, onFailure);
}
else
{
const errorMessage = res.body.errors ? JSON.stringify(res.body.errors) : 'Unknown error';
console.error(`${objectName}.setMultimediaResource() GraphQL error: ${errorMessage}`)
onFailure(new Error(errorMessage));
}
})
.catch(function(error) {
console.error(`Exception in ${objectName}.setMultimediaResource(): ${error} ${error.stack}`);
onFailure(error);
});
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment