Parse SDK review

Parse is a new mobile app platform designed for creating iOS, Android, Windows Phone and Web applications. It is based on “Backend as a service” (Baas) model and it has available native SDK for every platform. But what Parse means in practice, when and how to use it?

One backend to rule them all is the slogan which Parse represents on its web. If we try to observe it from the  side of push notifications, integration with social networks, cloud storage and statistics, we would have exactly the same opinion. All this becomes very easy to integrate into any mobile platform using Parse and actually it is a job which will not last more than few hours.

Indeed, a Parse project set up is very well documented and therefore quite easy. SDKs for mobile platforms are supported by lot of examples which is why little more experienced developers will not have any problems in making simple apps. To make things even better, with Parse you will get quite large community. For almost every question that we were interested in, we found the answer on the Parse forums.

The real goal of Parse is to actually enable the backend without the need to build the backend. It gives us cloud space, scheduled jobs, system logging, SSL and database. Database is primarily designed to be manipulated from the client side, which means that app needs to query, save and delete data from the database. It is feeling like you are working on the local database, but it is on the cloud. However, with increasing complexity of the system, backend code (Parse Cloud Codewritten in the JavaScript) becomes unavoidable.

Work examples

Here we will not analyse simple code examples that are already available and very well explained in the official documentation, but we will try to present few specifics which we particularly liked. Parse is designed to work with classes and objects. If we look from the perspective of relational databases, table is representation of the class, the columns are attributes of the class, and the row in the table represents an object.

The basic class of Parse is PFObject (iOS) which can be subclassed to create custom object. Basic example is showed below. We created object of GameScore class with attributes: score, playerName and cheatMode.

12345 PFObject *gameScore = [PFObject objectWithClassName:@”GameScore”];gameScore[@”score”] = @1337;gameScore[@”playerName”] = @”Sean Plott”;gameScore[@”cheatMode”] = @NO;[gameScore saveInBackground];

Real power of the Parse comes when we create our own Objective-C subclass of the PFObject. Dynamic attributes automatically become columns of the table GameScore and Parse support all data types including arrays.

1234567891011 @interface GameScore : PFObject@property (nonatomic) NSInteger score;@property (nonatomic, strong) NSString *playerName;@property (nonatomic) BOOL cheatMode;@property (nonatomic) NSInteger tempScore; //some temp value that we do not want to store in the database@end @implementation GameScore@dynamic score, playerName, cheatMode;@synthesize tempScore = _tempScore;@end

As one of the drawbacks, we can state that there is impossible to make new subclass of the GameScore, except in the case that we simulate GameScore as abstract class whose object will never be stored in the cloud. Parse already has its own classes that inherit PFObject such as PFUser and PFFile (storage). PFUser is a class that provides an easy way to work with a user, sign-up, logging etc. and also can be subclassed.

It is actually  amazing how Parse SDK is integrated with mobile platforms, which unfortunately can not be said for the web.

Data retrieval can be done in two different ways. The first one is fetching the object for which we have a pointer, and the second one is using PFQuery:

12345 PFQuery *query = [GameScore querry];[query whereKey:@”playerName” equalTo:@”Sean Plott”];[query findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) { }];

Relationships

Parse cloud is based on the Mongo database, but making database architecture for Parse is not nearly equal to the Mongo and actually, it is more like a relational database. In order to make the architecture, we must understand the relations in the Parse, and there are four kinds of them:

  • pointer – This is the standard 1:N relationship where N objects contain a pointer to the one object.
  • array of pointers – Used for 1:N and N:N relationships. Because it saves data as a JSON, array of pointers is not recommended to use for relations with a large number of members.
  • Parse relation – Parse relation is something that Parse engineers recommends to use for N:N relationships. In implementation, it looks very similar to an array, but rarely meets the needs for this kind of relationship. For example, it is not possible to count objects or add additional attributes to the relationship.
  • Join tables – This is a standard N:N relationship for any relational database. The idea is to create an object that has two pointers (two foreign keys) on two different objects. Considering that on the background of the Parse is Mongo, it is quite logical that it is better to avoid this kind of relation.

Problems and drawbacks

Start working with Parse is excellent. There is special feeling  that whole system  is designed just for you, but going deeper first problems appears. One of the major limitations is fetching of a maximum of 1000 results in one query. In general, 1000 results is more than enough for one query (we usually create paging in such a situations), but the problem arises while using innerQuery:

1234567 PFQuery *innerQuery = [PFQuery queryWithClassName:@”Post”];[innerQuery whereKeyExists:@”image”];PFQuery *query = [PFQuery queryWithClassName:@”Comment”];[query whereKey:@”post” matchesQuery:innerQuery];[query findObjectsInBackgroundWithBlock:^(NSArray *comments, NSError *error) {// comments now contains the comments for posts with images}];

This is innerQuery example from Parse documentation, and also an example where the limit can be a problem. Specifically, the innerQuery also has a limit of 1000 results, which means that if there are more than 1000 posts with picture, it will not be possible to retrieve all the comments, nor an easy way to do paging. This problem can easily occur when you work on little more complex database with more than 10 connections.

We can mention even bigger problems with queries, such as lack of distinct queries (retrieve unique values) which is integral part of every relational database. For this reason we needed to make two, three or more queries with local filtering just to fetch one data. That does not sound so terrible until you realize that it’s two, three or more synchronous HTTP requests, which will cause a noticeable loading.

Also, there is a lack of incase sensitive string queries. This means that app needs to store additional lowercase column for every attribute we want to search in future. We noticed the problems with querying with multiple equalTo values ​​on parse relations as well as a large incompatibility with PFUser object. For example, there is includeKey method:

1 [query includeKey:@”user”];

It allows to fetch objects together with its attributes, but often return null if one of the attributes is subclass of PFUser. Similar thing happens when you try to refresh an object.

Although there are quite a few flaws, Parse is a still an excellent choice for apps with a simple backend. You can view list of all Parse limitations here.

That’s all about iOS SDK (and other mobile platforms) while SDK for Javascript left the impression of incompleteness, poor documentation and just few examples available. Parse also has beautiful dashboard and data browser, but it lacks of some important functionalities. Logging system is good, but it stores too short reports and there is no any option to debug cloud code or even test it locally.  Push notifications are done well, but sometimes they late in delivering up to an hour which can be serious problem. But worst of all is that Parse has to many limitations that does not allow to system operate normally (for example, only 160 API requests per mniute). You can view entire list of limitations in our new blog post.

Conclusion

If you intend to make an application that requires backend just for basic operations (push notifications, user registration and storage of basic data) we can safely recommend Parse. It is the fastest and easiest solution that avoids making the backend. However, as backend system becomes more complex, Parse becomes less desirable option. As a confirmation of this statement there is the Parse price plan.  The free version offers 1M requests, while the premium offers only 15M requests for $199 per month.

At the end, we can confirm that Parse is a good platform, stable, with good documentation and great community. It is owned by Facebook, which also gives it certain significance. But Parse is not necessarily the best solution for all applications and for all your needs. Our recommendation is to go on deep analyse of your requirements and what Parse actually gives to you before you decide to go with it.