How can I upload images/pdf’s to the app, without using the upload component available? In my use case I want to be able to upload from a HTML bridge component documents that I have generated.
This can be done in 3-4 parts, depending on your use case.
- You will need to define the format that you want to use to save the document. This can be a Uint8Array or base64. When saving as a Uint8Array, you will need to convert this to a base64 string.
Example Conversion between Uint8Array and Base64
function converArrayBufferToBase64(buffer) {
var binary = '';
var bytes = new Uint8Array(buffer);
var len = bytes.byteLength;
for (var i = 0; i < len; i++) {
binary += String.fromCharCode(bytes[i]);
}
return window.btoa(binary);
}
- You then need to be able to post this
base64
string to your app container. More information can be found here: https://github.com/journeyapps/journey-iframe-client
let _base64String = '<myData>';
const JourneyClient = new JourneyIFrameClient();
JourneyClient.post("saveBase64", _base64String);
- Once the application receives the base64 string, you will need to save this into a text field to enable a Cloud Code Task to convert this for you.
App Code:
component.html().on('saveBase64', function(base64String) {
console.log("Base64 Received");
view.site_file.base64_string = base64Pdf;
view.site_file.save();
});
Database Model:
<model name="site_file" label="Site File">
<field name="archived" label="Archived?" type="boolean" />
<field name="created_at" label="Created At" type="datetime" />
<field name="attachment" label="Original Attachment" type="attachment" />
<field name="base64_string" label="Base64 String" type="text" /> <!-- Helper For Upload -->
<belongs-to model="user" name="created_by" />
<webhook type="update" receiver="cloudcode" action="convert_base64" />
<display>{caption}</display>
</model>
Note the webhook being used here to call the Cloud Code task for conversion
- You will now need to create a CloudCode task to handle the upload of the document for you
export async function run(event) {
let _site_file = await DB.site_file.first(event.object.id);
// Convert the annotated pdf to attachment
if(_site_file.base64_string) {
let _attachment = {
content: data,
filename: "Document.pdf"
}
await uploadAttachment(_site_file.annotated_base64_string, _site_file, 'attachment');
// Clear the base64 string
_site_file.annotated_base64_string = null;
await _site_file.save();
}
}
/**
* Uploads an Attachment to the backend.
*/
async uploadAttachment(attachment, object, field) {
try {
let _model = {
id: object.id,
}
_model[field] = { "base64": attachment.content, "filename": attachment.filename };
let patch_body = {};
patch_body[object.type.name] = _model;
console.log(`Uploading Data to [url=${url}/objects/${object.type.name}/${object.id}.json]`);
let _response = await fetch(`${this.backend.url}/objects/${object.type.name}/${object.id}.json`, {
headers: {
'Authorization': this.config.authorization,
'Content-Type': 'application/json'
},
method: 'PATCH',
body: JSON.stringify(patch_body)
});
//Check the response, and throw the appropriate error if required.
if(_response.status === 401 || _response.status == 403) {
throw new Error("User not authenticated");
} else if(!_response.ok) {
throw _response;
}
let _data = await _response.json();
return _data;
} catch (error) {
console.error(error);
throw error;
}
}
This should allow you the capability to upload files to the backend with the added bonus of using the offline capabilities of the Journey Apps ecosystem.
4 Likes