Summary of the January 22nd Parse Service Disruption

We would like to share more details about the nature of the events during the January 22nd service disruption. We are working hard to improve reliability and would like to relay information about the nature of the service disruption, our efforts to restore functionality, and the steps we are taking to prevent this sort of issue from happening again.

The initial outage began at 8:16 A.M. PST and was related to a routine operation that involved rotating nodes to defragment and compact our database. This triggered a rare edge case in Cloud Code which caused all Cloud Code requests to simultaneously time out, which in turn caused a timeout feedback loop at the app server layer. In the process of restoring service, we also discovered that some indexes had been incorrectly built on one instance. This delayed our ability to recover quickly. Service was fully restored at 9:24 A.M.

In response to this incident, we have taken the following steps:

  • We are adding more sanity checks and safeguards around our routine database maintenance tasks and migrations.
  • We are adding significantly more monitoring around Cloud Code capacity and handling for unusual error states.
  • We are improving our ability to selectively target Parse functionality, so the impact of any performance degradation is localized and does not affect the majority of Parse apps.
  • We are adding post hoc analysis of smart indexing to catch any edge cases.

We apologize for the outage. We built this platform for engineers like ourselves and know that a platform outage can be terribly disruptive for our customers. Rest assured, the entire team here is committed to the long term stability of the platform and works hard to avoid such events. If you have any questions, please reach out to us through our Help & Community portal.

Charity Majors
January 23, 2013

Introducing the SendGrid Cloud Module

A few weeks ago, we unveiled Cloud Modules, a new way to integrate your Parse app with third-party services. With that release we promised several more modules would be on their way. Today, we’re happy to announce the first of these new modules, SendGrid. SendGrid provides an easy to use email service that allows you to send and receive emails using their API. Here’s a look at how the Cloud Module works:

var sendgrid = require("sendgrid");
sendgrid.initialize("sendgridAccountSid", "sendgridAuthToken");

Parse.Cloud.define("mySendGridFunction", function(request, response) {
  sendgrid.sendEmail({
    to: "community@parse.com",
    from: "sendgrid@parse.com",
    subject: "Hello from Cloud Code!",
    text: "Using Parse and SendGrid is great!"
  }, {
    success: function(httpResponse) { response.success("Email sent!"); },
    error: function(httpResponse) { response.error("Uh oh, something went wrong"); }
  });
});

To learn more about this new module check out our Cloud Modules guide. We’ll be releasing many more, so let us know what you’d like to see next using the form below.

Mattieu Gamache-Asselin
November 19, 2012

Lending a Hand

Parse Help

We can’t help but be amazed by some of the apps that have been built on Parse. There is truly an astonishing amount of skill and creativity in our developer community and we want to do all that we can to allow these talented individuals to innovate together and to share ideas.

We considered many prebuilt support forum and Q&A solutions, but we felt that none of them expressed our commitment to helping our customers and to fostering a Parse community spirit. So we brought this in house, and today we’re excited to announce the launch of Parse Help & Community. Modeled after popular programming forums, this new Q&A site will allow developers to interact directly with the Parse team and to help each other by sharing their Parse and mobile app experiences.

We’ll be actively participating in the discussions, so feel free to ask all of your Parse or mobile related questions there. If you have a more sensitive issue, you can still submit a private inquiry, and we’ll be more than happy to lend you a hand.

Mattieu Gamache-Asselin
August 9, 2012

New Tricks With Queries

We want data access via Parse to be fast and easy, no matter what sort of data you’re storing. Recently we’ve launched a few new features to help you access your data in different ways.

Often you want to run multiple queries that differ in only the value of one parameter. For example, you might want to download song information for any one of a list of artists. Rather than issue separate queries for each artist, you can now grab all of that information with one query, using whereKey:containedIn:

// We want to get information for any of these artists
NSArray *artists = [NSArray arrayWithObjects:@"The Beatles",
                                             @"Them Crooked Vultures",
                                             @"Freezepop',
                                             nil];

PFQuery *query = [PFQuery queryWithClassName:@"SongInfo"];
[query whereKey:@"artist" containedIn:artists];

[query findObjectsInBackgroundWithBlock:^(NSArray *songs, NSError *error) {
  // songs now contains SongInfo for any of the provided artists
}];

Another pattern we’ve noticed is that sometimes you want to run a query only because you’re interesting in counting the results. This introduces the overhead of sending the results when it isn’t really necessary. To make this faster, we’ve introduced countObjects methods, similar to the findObjects methods.

In our SongInfo example, if you’d like to count how many songs there are by The Beatles:

// Construct a query
PFQuery *query = [PFQuery queryWithClassName:@"SongInfo"];
[query whereKey:@"artist" equalTo:@"The Beatles"];

// Use countObjects instead of findObjects
[query countObjectsInBackgroundWithBlock:^(int count, NSError *error) {
  // count tells you how many objects matched the query
}];

Sometimes you want to page through data rather than access it all at once. For example, you might want to grab ten songs, and then another ten if the user swipes to see more. You can use query.skip and query.limit to control which results to retrieve. For example, to get the 51st through 100th most recent Beatles songs:

// Query for Beatles songs, most-recent-first
PFQuery *query = [PFQuery queryWithClassName:@"SongInfo"];
[query whereKey:@"artist" equalTo:@"The Beatles"];
[query orderByDescending:@"createdAt"];

// Skip the first 50, retrieve the next 50
query.skip = 50;
query.limit = 50;

[query findObjectsInBackgroundWithBlock:^(NSArray *songs, NSError *error) {
  // Now you have the 51st through 100th most recent Beatles songs
}];

Check out the iOS query documentation for more on what you can do with the PFQuery. If you’re working on Android, all of this functionality is available to you as well. Just check out the Android query documentation.

We’re always trying to make Parse easier and to make more things possible using Parse. Your feedback is the fuel that keeps this engine running. So please, don’t hesitate to send us feedback.

Thanks for reading!

Kevin Lacker
November 4, 2011