3
votes

Context

My application enables users to upload an .mp4 file to Google Cloud Storage through Google App Engine using the createUploadUrl() pattern. The upload works fine and I'm able to obtain the corresponding FileInfo object in the handler. I'm using the App Engine SDK 1.8.2 for Java.

The Challenge

I need to grab the "duration" property off of the .mp4 file and store it in my database but the FileInfo object doesn't provide access to this metadata. I have a few ideas on how I might go about doing this (which I've listed below) but none of them are very straightforward given that the project I'm working on has several legacy dependencies.

I'd love to hear any ideas or suggestions you have on how to tackle this (and ideally any success stories if you have!)

Ideas

  1. I know that there are scripts and utilities like ffmpeg and mdls (for mac) that can read metadata off of the file but my understanding is that these wouldn't be able to run in Google App Engine and I would need to kick off separate processes using something like Google Compute Engine.
  2. I could create a custom flash upload control that reads the duration logic when the user selects the file for upload and passes it in through standard form submission.
  3. I'm also aware that there's a Google Cloud Storage JSON API that's been in Beta stage now. I don't see any functionality that would allow me to read the "duration" property off of the .mp4 file but I may be missing something...

Code

HTML Form

<form name="myForm" id="myForm" action="<%=createUploadUrl("/upload, uploadOptions)%>" method="POST" enctype="multipart/form-data">
    <input type="file" name="uploadFileControl" id="uploadFileControl" value="Select...">
    <input type="submit" value="Submit">
</form>

Server Side Handler

DAO dao = new DAO();
BlobstoreService blobstoreService = BlobstoreServiceFactory.getBlobstoreService();
Map<String, List<FileInfo>> fileInfos = blobstoreService.getFileInfos(req);
List<FileInfo> uploadedFile = fileInfos.get("uploadFileControl");

if(uploadedFile != null) {
    FileInfo file = uploadedFile.get(0);
    String fileName = file.getFilename();
}
3

3 Answers

2
votes

Google Cloud Storage is content-type agnostic, i.e., it treats any kind of content in the same way (videos, music, zip files, documents, you name it). It also doesn't parse or "read" uploaded content (which is encrypted at REST anyway). Because of that Google Cloud Storage can't possibly know about the specifics of a given file format like mp4, hence you won't find any such functionality in the APIs. I am assuming the same holds for AppEngine and its FileInfo object.

0
votes

You could google "python mp4 parser" and see if anything comes up...

0
votes

Posting back with the solution I ended up going with.

I used a video player plug-in called mediaelement.js (http://mediaelementjs.com/) to load in the uploaded file from GCS. The video player has a "duration" property that gets updated every time a new video file is loaded which makes the whole thing quite straightforward.

Two other options I was investigating involved 1) using a java utility called mp4parser (https://code.google.com/p/mp4parser/) to load in the uploaded file from Google Cloud Storage into GAE and manually extracting out the duration metadata and 2) updating an open source upload utility called Plupload (http://plupload.com/) to extract out the duration metadata as the file was being uploaded.

Hope this helps anyone else who runs into a similar issue!