The Cosync Storage solution for asset management within a MongoDB Application has three components:
- A MongoDB Realm Application configured with the Amazon S3 credentials along with a set of triggers and functions for computing asset URLs
- A set of data models and functions for modeling assets, asset uploads, and expiring asset URLs
- Client side code for handling asset initialization, image asset cuts, video previews, upload progress, and HTTPS uploading
The data models used to model assets are the following
- CosyncAssetUpload
- CosyncAsset
Schemas for these data models are discussed in the next section below. The Cosync Storage sample application code provides version of these data models for Swift, Kotlin, and React-Native. All of these data models assume a partition key called _partition. As a recommended best practice, we suggest that CosyncAssetUpload(s) exist within the user’s private partition, to maximize scalability.
The CosyncAssetUpload object is used by a client application to initiate the upload of an asset to the Amazon S3 Storage service. The CosyncAsset object is used to record an uploaded asset in MongoDB Realm. This object is automatically created by the backend code running on the MongoDB Realm Application server.
Expiring Assets
For security purposes, the Cosync Storage module allows a developer to control whether an asset’s URLs expires or not. Expiring URLs are used to protect sensitive assets from being shared over the Internet. Asset URLs can expire in a few hours (the default is 24) or in a few minutes depending on how sensitive the information is.
Asset expiration is controlled through the expirationHours property in the CosyncAssetUpload object at the time of the upload process. If an asset expires, the expirationHours property on the CosyncAsset object will set to a value greater than zero, and the expiration property will specify a date in UTC when the asset URLs expire. If an asset has expired, the client side code can call the function CosyncRefreshAsset(assetId) to force the backend to refresh the URLs for the asset. The new URLs that are computed will expire in so many expirationHours from the time the function was called.
The Cosync Engine Storage module also supports non expiring assets. However, the developer should remember that URLs to non-expiring assets present a security risk should they be leaked to the wider Internet. On the other hand, there is one less management step for dealing with non-expiring assets.
Asset upload process
A client application initiates an asset upload by first creating a CosyncAssetUpload object within a Realm partition. Our recommendation is to set the _partition key value to the private user realm for optimal security purposes - that way no one else can ease drop on what is being uploaded.
To proceed with an asset upload, the client application code must fill in the uid field with the user id that is uploading the asset, it must set a unique sessionId that identifies the device from which the asset is being uploaded, and it must set a filePath in the Amazon S3 bucket where the asset will be placed. The API also provides two properties: extra and assetPartition that are used to store extra information about the asset and optionally which partition the final CosyncAsset object should be created in. The expirationHours property specifies how many hours (a floating point value) the asset will expire in. If this property is set to zero, the asset never expires. When a CosyncAssetUpload object is created, its status property is set to pending.
Once the client application has created the CosyncAssetUpload object in Realm, the backend trigger CosyncAssetUploadTrigger that is attached to the MongoDB Realm Application on the server will fire. This trigger will compute the read and write URLs in the Amazon S3 Storage service that the client can use to upload the asset with. Once this computation has taken place, the trigger function will set status property of the CosyncAssetUpload object to initialized. The application client code will in turn be listening for any changes to the CosyncAssetUpload object. Upon receiving an initialized upload object, the client will proceed to upload the asset to the write URLs that were set by the backend in the CosyncAssetUpload object. When the upload process is complete, the application client will set the status property to uploaded. Note, the client will only listen for CosyncAssetUpload objects whose sessionId corresponds to the device in question upon which the client application is running. The write URLs that are returned by the Cosync Storage service must always be used in conjunction with an HTTPS PUT command. The service does not presently implement URLs that support a multipart HTTPS POST command.
The following diagram presents a visual of the asset uploading process:
Note: The Cosync Engine Storage services uses the MongoDB Realm third-party AWS Service to implement this functionality. It simply uses this service to compute the pre-signed URLs needed to upload and read asset information. The third-party service simply acts as a broker between MongoDB Realm and Amazon S3, while the Cosync Engine Storage packages all of this into an easy to understand bundle that can be seamlessly integrated into a working client application.