diff --git a/_includes/ios/files.md b/_includes/ios/files.md
index d70e5039a..c98b6d9c5 100644
--- a/_includes/ios/files.md
+++ b/_includes/ios/files.md
@@ -142,6 +142,8 @@ file?.saveInBackground({ (success: Bool, error: Error?) in
```
-You can delete files that are referenced by objects using the [REST API]({{ site.baseUrl }}/rest/guide/#deleting-files). You will need to provide the master key in order to be allowed to delete a file.
+##Deleting Files
-If your files are not referenced by any object in your app, it is not possible to delete them through the REST API. You may request a cleanup of unused files in your app's Settings page. Keep in mind that doing so may break functionality which depended on accessing unreferenced files through their URL property. Files that are currently associated with an object will not be affected.
+If you know the name of a file you can delete it using the [REST API]({{site.baseUrl}}/rest/guide/#deleting-files). Your master key is required for this operation.
+
+Note: Reguardless of the Parse Server storage configuration, deleting a `PFObject` with a `PFFileObject` does not delete the file itself meerly its reference. Additionally, Parse does **NOT** provide a way to find unreferenced file names in storage.
diff --git a/_includes/ios/getting-started.md b/_includes/ios/getting-started.md
index f0657de5d..1536bbd61 100644
--- a/_includes/ios/getting-started.md
+++ b/_includes/ios/getting-started.md
@@ -64,6 +64,7 @@ func application(application: UIApplication, didFinishLaunchingWithOptions launc
$0.server = "parseServerUrlString"
}
Parse.initialize(with: parseConfig)
+ return true
}
```
diff --git a/_includes/ios/local-datastore.md b/_includes/ios/local-datastore.md
index 530bf0e04..b69642b63 100644
--- a/_includes/ios/local-datastore.md
+++ b/_includes/ios/local-datastore.md
@@ -1,14 +1,19 @@
# Local Datastore
-The Parse iOS/OS X SDK provides a local datastore which can be used to store and retrieve `PFObject`s, even when the network is unavailable. To enable this functionality, add `libsqlite3.dylib` and add `isLocalDatastoreEnabled = true` to the `ParseClientConfiguration` block used in `Parse.initialize()`.
+The Parse iOS/OS X SDK provides a local datastore which can be used to store and retrieve `PFObject`s, even when the network is unavailable. To enable this functionality add `isLocalDatastoreEnabled = true` to the `ParseClientConfiguration` block used in `Parse.initialize()` or call `Parse.enableLocalDatastore()` prior to initializing Parse.
```objective_c
@implementation AppDelegate
- (void)application:(UIApplication *)application didFinishLaunchWithOptions:(NSDictionary *)options {
- [Parse enableLocalDatastore];
- [Parse setApplicationId:@"parseAppId" clientKey:@"parseClientKey"];
+ ParseClientConfiguration *configuration = [ParseClientConfiguration configurationWithBlock:^(id
configuration) {
+ configuration.applicationId = @"parseAppId";
+ configuration.clientKey = @"parseClientKey";
+ configuration.server = @"parseServerUrlString";
+ configuration.localDatastoreEnabled = YES;
+ }];
+ [Parse initializeWithConfiguration:configuration];
}
@end
@@ -74,28 +79,28 @@ Storing objects is great, but it's only useful if you can then get the objects b
```objective_c
PFQuery *query = [PFQuery queryWithClassName:@"GameScore"];
[query fromLocalDatastore];
-[[query getObjectInBackgroundWithId:@"xWMyZ4YE"] continueWithBlock:^id(BFTask *task) {
- if (task.error) {
- // Something went wrong.
- return task;
- }
+[query getObjectInBackgroundWithId:"" block:^(PFObject * _Nullable object, NSError * _Nullable error) {
+ if (!error) {
+ // Success
+ } else {
+ // Fail!
+ }
+}
// task.result will be your game score
return task;
}];
```
+
```swift
let query = PFQuery(className: "GameScore")
query.fromLocalDatastore()
-query.getObjectInBackgroundWithId("xWMyZ4YE").continueWithBlock {
- (task: BFTask!) -> AnyObject in
- if let error = task.error {
- // Something went wrong.
- return task;
+query.getObjectInBackground(withId: "string") { (object, error) in
+ if error == nil {
+ // Success!
+ } else {
+ // Failure!
}
-
- // task.result will be your game score
- return task;
}
```
diff --git a/_includes/ios/objects.md b/_includes/ios/objects.md
index 8be4805dd..41055d5cc 100644
--- a/_includes/ios/objects.md
+++ b/_includes/ios/objects.md
@@ -16,7 +16,7 @@ Each `PFObject` has a class name that you can use to distinguish different sorts
## Saving Objects
-Let's say you want to save the `GameScore` described above to the Parse Cloud. The interface is similar to a `NSMutableDictionary`, plus the `saveInBackground` method:
+Let's say you want to save the `GameScore` described above to a Parse Server. The interface is similar to a `NSMutableDictionary`. The `saveInBackgroundWithBlock` function:
```objective_c
@@ -24,7 +24,7 @@ PFObject *gameScore = [PFObject objectWithClassName:@"GameScore"];
gameScore[@"score"] = @1337;
gameScore[@"playerName"] = @"Sean Plott";
gameScore[@"cheatMode"] = @NO;
-[gameScore saveInBackgroundWithBlock:^(BOOL succeeded, NSError *error) {
+[gameScore saveInBackgroundWithBlock:^(BOOL succeeded, NSError * _Nullable error) {
if (succeeded) {
// The object has been saved.
} else {
@@ -37,18 +37,17 @@ let gameScore = PFObject(className:"GameScore")
gameScore["score"] = 1337
gameScore["playerName"] = "Sean Plott"
gameScore["cheatMode"] = false
-gameScore.saveInBackground {
- (success: Bool, error: Error?) in
- if (success) {
- // The object has been saved.
- } else {
- // There was a problem, check error.description
- }
+gameScore.saveInBackground { (succeeded, error) in
+ if (succeeded) {
+ // The object has been saved.
+ } else {
+ // There was a problem, check error.description
+ }
}
```
-After this code runs, you will probably be wondering if anything really happened. To make sure the data was saved, you can look at the Data Browser in your app on Parse. You should see something like this:
+After this code runs, you will probably be wondering if anything really happened. If [Parse Dashboard](https://github.com/parse-community/parse-dashboard) is implemented for your server, you can verify the data was saved in the data browser. You should see something like this:
```js
objectId: "xWMyZ4YEGZ", score: 1337, playerName: "Sean Plott", cheatMode: false,
@@ -57,9 +56,7 @@ createdAt:"2011-06-10T18:33:42Z", updatedAt:"2011-06-10T18:33:42Z"
There are two things to note here. You didn't have to configure or set up a new Class called `GameScore` before running this code. Your Parse app lazily creates this Class for you when it first encounters it.
-There are also a few fields you don't need to specify that are provided as a convenience. `objectId` is a unique identifier for each saved object. `createdAt` and `updatedAt` represent the time that each object was created and last modified in the Parse Cloud. Each of these fields is filled in by Parse, so they don't exist on a `PFObject` until a save operation has completed.
-
-Note: You can use the `saveInBackgroundWithBlock` method to provide additional logic to run after the save completes.
+There are also a few fields you don't need to specify that are provided and set by the system as a convenience. `objectId` is a unique identifier for each saved object. `createdAt` and `updatedAt` represent the time that each object was created or last modified and saved to the Parse Server. Each of these fields is filled in by Parse Server, so they don't exist on a `PFObject` until the first save operation has been completed.
## Retrieving Objects
@@ -69,22 +66,20 @@ Saving data to the cloud is fun, but it's even more fun to get that data out aga
```objective_c
PFQuery *query = [PFQuery queryWithClassName:@"GameScore"];
[query getObjectInBackgroundWithId:@"xWMyZ4YEGZ" block:^(PFObject *gameScore, NSError *error) {
- // Do something with the returned PFObject in the gameScore variable.
- NSLog(@"%@", gameScore);
+ if (!error) {
+ // Success!
+ } else {
+ // Failure!
+ }
}];
-// The InBackground methods are asynchronous, so any code after this will run
-// immediately. Any code that depends on the query result should be moved
-// inside the completion block above.
```
```swift
let query = PFQuery(className:"GameScore")
-query.getObjectInBackground(withId: "xWMyZEGZ") { (gameScore: PFObject?, error: Error?) in
- if let error = error {
- //The query returned an error
- print(error.localizedDescription)
+query.getObjectInBackground(withId: "xWMyZEGZ") { (gameScore, error) in
+ if error == nil {
+ // Success!
} else {
- //The object has been retrieved
- print(gameScore)
+ // Fail!
}
}
```
@@ -123,22 +118,35 @@ let acl = gameScore.acl
If you need to refresh an object you already have with the latest data that
- is in the Parse Cloud, you can call the `fetch` method like so:
+is in the database, you can use the `fetchInBackgroundWithBlock:` or `fetchInBackgroundWithTarget:selector:` methods.
+
```objective_c
-[myObject fetch];
+[myObject fetchInBackgroundWithBlock:^(PFObject * _Nullable object, NSError * _Nullable error) {
+ if (!error) {
+ // Success!
+ } else {
+ // Failure!
+ }
+}];
```
```swift
-myObject.fetch()
+myObject.fetchInBackground { (object, error) in
+ if error == nil {
+ // Success!
+ } else {
+ // Failure!
+ }
+}
```
-Note: In a similar way to the `save` methods, you can use the `fetchInBackgroundWithBlock` or `fetchInBackgroundWithTarget:selector:` methods to provide additional logic which will run after fetching the object.
+Note: In a similar way to the `save` methods, you can use the throwable `fetch` or `fetchIfNeeded` methods, or asyncronous task without completion. `fetchInBackground`
## The Local Datastore
-Parse also lets you store objects in a [local datastore](#local-datastore) on the device itself. You can use this for data that doesn't need to be saved to the cloud, but this is especially useful for temporarily storing data so that it can be synced later. To enable the datastore, add `libsqlite3.dylib` and add `isLocalDatastoreEnabled = true` to the `ParseClientConfiguration` block in your `AppDelegate` `application:didFinishLaunchWithOptions:` before calling `Parse.initialize()`. Once the local datastore is enabled, you can store an object by pinning it.
+Parse also lets you store objects in a [local datastore](#local-datastore) on the device itself. You can use this for data that doesn't need to be saved to the cloud, but this is especially useful for temporarily storing data so that it can be synced later. To enable the datastore, add `isLocalDatastoreEnabled = true` to the `ParseClientConfiguration` block in your `AppDelegate` `application:didFinishLaunchWithOptions:`, or call `Parse.enableLocalDatastore()` before calling `Parse.initialize()`. Once the local datastore is enabled, you can store an object by pinning it.
```objective_c
@@ -161,7 +169,7 @@ As with saving, this recursively stores every object and file that `gameScore` p
### Retrieving Objects from the Local Datastore
-Storing an object is only useful if you can get it back out. To get the data for a specific object, you can use a `PFQuery` just like you would while on the network, but using the `fromLocalDatastore` method to tell it where to get the data.
+Storing an object is only useful if you can get it back out. To get the data for a specific object, you can use a `PFQuery` just like you would while on the network, but using the `fromLocalDatastore:` method to tell it where to get the data.
```objective_c
@@ -192,7 +200,7 @@ query.getObjectInBackground(withId: "xWMyZEGZ").continueWith { (task: BFTask
-If you already have an instance of the object, you can instead use the `fetchFromLocalDatastoreInBackground` method.
+If you already have an instance of the object, you can instead use the `fetchFromLocalDatastoreInBackground:` method.
```objective_c
@@ -223,7 +231,7 @@ object.fetchFromLocalDatastoreInBackground().continueWith { (task: BFTask
```objective_c
@@ -236,7 +244,7 @@ gameScore.unpinInBackground()
## Saving Objects Offline
-Most save functions execute immediately, and inform your app when the save is complete. If you don't need to know when the save has finished, you can use `saveEventually` instead. The advantage is that if the user currently doesn't have a network connection, `saveEventually` will store the update on the device until a network connection is re-established. If your app is closed before the connection is back, Parse will try again the next time the app is opened. All calls to `saveEventually` (and `deleteEventually`) are executed in the order they are called, so it is safe to call `saveEventually` on an object multiple times.
+Most save functions execute immediately, and inform your app when the save is complete. For a network consious soltion on non-priority save requests use `saveEventually`. Not only does it retry saving upon regaining network connection, but If your app is closed prior to save completion Parse will try the next time the app is opened. Additionally, all calls to `saveEventually` (and `deleteEventually`) are executed in the order they are called, making it safe to call `saveEventually` on an object multiple times.
```objective_c
@@ -344,43 +352,39 @@ gameScore.saveInBackground()
```
-Note that it is not currently possible to atomically add and remove items from an array in the same save.
- You will have to call `save` in between every different kind of array operation.
+Note that it is not currently possible to atomically add and remove items from an array in the same save using. You will have to call `save` in between every different kind of array operation.
## Deleting Objects
-To delete an object from the cloud:
-
-```objective_c
-[gameScore deleteInBackground];
-```
-```swift
-gameScore.deleteInBackground()
-```
-
+There are a few ways to delete a `PFObject`. For basic asynchronous deletion of a single object call the objects `deleteInBackground` function. If you prefer to recieve a callback you can use the `deleteInBackgroundWithBlock:` or `deleteInBackgroundWithTarget:selector:` methods. If you want to block the calling thread, you can use the `delete` method. Lastly, `deleteEventually` is a network conscious option that deletes when possible but does not guarantee a timeframe for the tasks completion.
-If you want to run a callback when the delete is confirmed, you can use the `deleteInBackgroundWithBlock:` or `deleteInBackgroundWithTarget:selector:` methods. If you want to block the calling thread, you can use the `delete` method.
+For deleting multiple objects use the `PFObject` static function `deleteAllInBackground` to delete an array of objects asynchronously. The same can be done while blocking the calling thread using `deleteAll`. Lastly, to recieve a callback after deleting objects asyncronously use `deleteAllInBackground:block:` as demonstrated below.
-You can delete a single field from an object with the `removeObjectForKey` method:
```objective_c
-// After this, the playerName field will be empty
-[gameScore removeObjectForKey:@"playerName"];
-
-// Saves the field deletion to the Parse Cloud
-[gameScore saveInBackground];
+[PFObject deleteAllInBackground:objectArray block:^(BOOL succeeded, NSError * _Nullable error) {
+ if (succeeded) {
+ // The array of objects was successfully deleted.
+ } else {
+ // There was an error. Check the errors localizedDescription.
+ }
+}];
```
```swift
-// After this, the playerName field will be empty
-gameScore.remove(forKey: "playerName")
-
-// Saves the field deletion to the Parse Cloud
-gameScore.saveInBackground()
+PFObject.deleteAll(inBackground: objectArray) { (succeeded, error) in
+ if (succeeded) {
+ // The array of objects was successfully deleted.
+ } else {
+ // There was an error. Check the errors localizedDescription.
+ }
+}
```
+Note: Deleting an object from the server that contains a `PFFileObject` does **NOT** delete the file from storage. Instead, an objects deletion only deletes the data referencing the stored file. To delete the data from storage you must use the [REST API]({{site.baseUrl}}/rest/guide/#deleting-files). For more info about `PFFileObject`, please see the [Files](#files) section.
+
## Relational Data
Objects can have relationships with other objects. To model this behavior, any `PFObject` can be used as a value in other `PFObject`s. Internally, the Parse framework will store the referred-to object in just one place, to maintain consistency.
@@ -422,16 +426,19 @@ myComment.saveInBackground()
```
-You can also link objects using just their `objectId`s like so:
+Note: Saving an object with a relational pointer to another object will save both objects. However, two new objects with pointers to each other will cause a error for having a circular dependency.
+
+### Object Relationships With Minimal Data
+
+You can link objects without even fetching data by initializing `PFObjects` with only the class name and the objects `objectId` like so:
```objective_c
-// Add a relation between the Post with objectId "1zEcyElZ80" and the comment
-myComment[@"parent"] = [PFObject objectWithoutDataWithClassName:@"Post" objectId:@"1zEcyElZ80"];
+myComment[@"post"] = [PFObject objectWithoutDataWithClassName:@"Post" objectId:@"1zEcyElZ80"];
```
```swift
// Add a relation between the Post with objectId "1zEcyElZ80" and the comment
-myComment["parent"] = PFObject(withoutDataWithClassName:"Post", objectId:"1zEcyElZ80")
+myComment["post"] = PFObject(withoutDataWithClassName: "Post", objectId: "1zEcyElZ80")
```
@@ -439,17 +446,20 @@ By default, when fetching an object, related `PFObject`s are not fetched. These
```objective_c
-PFObject *post = fetchedComment[@"parent"];
-[post fetchIfNeededInBackgroundWithBlock:^(PFObject *post, NSError *error) {
- NSString *title = post[@"title"];
- // do something with your title variable
+PFObject *post = myComment[@"post"];
+[post fetchInBackgroundWithBlock:^(PFObject * _Nullable object, NSError * _Nullable error) {
+ NSString *title = post[@"title"];
+ if (title) { // do something with title }
}];
```
```swift
let post = myComment["parent"] as! PFObject
-post.fetchIfNeededInBackground { (post: PFObject?, error: Error?) in
- let title = post?["title"] as? String
- // do something with your title variable
+post.fetchIfNeededInBackground { (object, error) in
+ if let title = post["title"] as? String {
+ // do something with your title variable
+ } else if let errorString = error?.localizedDescription {
+ print(errorString)
+ }
}
```
@@ -461,78 +471,75 @@ You can also model a many-to-many relation using the `PFRelation` object. This
PFUser *user = [PFUser currentUser];
PFRelation *relation = [user relationForKey:@"likes"];
[relation addObject:post];
-[user saveInBackgroundWithBlock:^(BOOL succeeded, NSError *error) {
- if (succeeded) {
- // The post has been added to the user's likes relation.
- } else {
- // There was a problem, check error.description
- }
+[user saveInBackgroundWithBlock:^(BOOL succeeded, NSError * _Nullable error) {
+ if (succeeded) {
+ // The post has been added to the user's likes relation.
+ } else {
+ // There was a problem, check error.description
+ }
}];
```
```swift
-let user = PFUser.current()
-let relation = user?.relation(forKey: "likes")
-relation?.add(post)
-user?.saveInBackground(block: { (success: Bool, error: Error?) in
- if (success) {
+guard let user = PFUser.current() else { return }
+let relation = user.relation(forKey: "likes")
+relation.add(post)
+user.saveInBackground { (succeeded, error) in
+ if (succeeded) {
// The post has been added to the user's likes relation.
} else {
// There was a problem, check error.description
}
-})
-
+}
```
-You can remove a post from the `PFRelation` with something like:
-
-
-```objective_c
-[relation removeObject:post];
-```
-```swift
-relation?.remove(post)
-```
-
+You can remove a post from the `PFRelation` similarly using the `removeObject:` function followed by saving the parent object.
By default, the list of objects in this relation are not downloaded. You can get the list of `Post`s by using calling `findObjectsInBackgroundWithBlock:` on the `PFQuery` returned by `query`. The code would look like:
```objective_c
-[[relation query] findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
- if (error) {
- // There was an error
- } else {
- // objects has all the Posts the current user liked.
- }
+[[relation query] findObjectsInBackgroundWithBlock:^(NSArray * _Nullable objects, NSError * _Nullable error) {
+ if (error) {
+ // There was an error
+ } else {
+ // objects has all the Posts the current user liked.
+ }
}];
```
```swift
-relation?.query().findObjectsInBackground(block: { (objects: [PFObject]?, error: Error?) in
- if let error = error {
- // There was an error
- print(error.localizedDescription)
+relation.query().findObjectsInBackground { (object, error) in
+ if error == nil {
+ // Success
} else {
- // objects has all the Posts the current user liked.
+ // Failure!
}
})
```
-If you want only a subset of the `Post`s you can add extra constraints to the `PFQuery` returned by `query` like this:
+You can add constraints to a `PFRelation`'s query by adding constraints to the `PFQuery` returned by its `query` parameter as demonstrated below:
```objective_c
PFQuery *query = [relation query];
-// Add other query constraints.
+[query whereKey:"category" equalTo:@"development"];
+PFObject *object = [query getFirstObject]; // Query first object found
+if (object) {
+ // Do something with object
+}
```
```swift
-var query = relation?.query()
-// Add other query constraints.
-```
+var query = relation.query()
+query.whereKey("category", equalTo: "development")
+
+// Query first object found
+if let object = try? query.getFirstObject() {
+ // Do something with object
+} ```
-For more details on `PFQuery` please look at the query portion of this guide. A `PFRelation` behaves similar to an `NSArray` of `PFObject`, so any queries you can do on arrays of objects (other than `includeKey:`) you can do on `PFRelation`.
+You can learn more about queries by visiting the [PFQuery](#queries) section. A `PFRelation` behaves similarly to an array of `PFObject` yet has a built in query that's capable of everything a standard `PFQuery` is other than `includeKey:`.
## Data Types
@@ -596,7 +603,7 @@ bigObject.saveInBackground()
```
-We do not recommend storing large pieces of binary data like images or documents on `PFObject`. `PFObject`s should not exceed 128 kilobytes in size. We recommend you use `PFFileObject`s to store images, documents, and other types of files. You can do so by instantiating a `PFFileObject` object and setting it on a field. See [Files](#files) for more details.
+We do not recommend storing large pieces of binary data like images or documents on `PFObject`. We recommend you use `PFFileObject`s to store images, documents, and other types of files. You can do so by instantiating a `PFFileObject` object and setting it on a field. See [Files](#files) for more details.
For more information about how Parse handles data, check out our documentation on [Data](#data).
@@ -612,7 +619,7 @@ shield[@"fireProof"] = @NO;
shield[@"rupees"] = @50;
```
```swift
-var shield = PFObject(className:"Armor")
+var shield = PFObject(className: "Armor")
shield["displayName"] = "Wooden Shield"
shield["fireProof"] = false
shield["rupees"] = 50
@@ -638,20 +645,12 @@ shield.rupees = 50
### Subclassing PFObject
-To create a `PFObject` subclass:
+To create a subclass:
-1. Declare a subclass which conforms to the `PFSubclassing` protocol.
-2. Implement the class method `parseClassName`. This is the string you would pass to `initWithClassName:` and makes all future class name references unnecessary.
-3. Import `PFObject+Subclass` in your .m file. This implements all methods in `PFSubclassing` beyond `parseClassName`.
-4. Call `[YourClass registerSubclass]` before Parse `setApplicationId:clientKey:`.
+1. Declare a subclass of `PFObject` which conforms to the `PFSubclassing` protocol.
+2. Implement the static method `parseClassName` and return the string you would pass to `initWithClassName:`. This makes all future class name references unnecessary.
-An easy way to do this is with your class' [+load](https://developer.apple.com/reference/objectivec/nsobject/1418815-load?language=objc) (Obj-C only) or with [initialize](https://developer.apple.com/reference/objectivec/nsobject/1418639-initialize) (both Obj-C and Swift) methods.
-
-Please note that the `initialize` method is not called until the class receives its first message, meaning that you need to call any instance or class method on your subclass before it will be registered with Parse SDK.
-
-The following code successfully declares, implements, and registers the `Armor` subclass of `PFObject`:
-
-
+Note: Objective-C developers should Import `PFObject+Subclass` in your .m file. This implements all methods in `PFSubclassing` beyond `parseClassName`.
### Properties & Methods
@@ -659,8 +658,6 @@ Adding custom properties and methods to your `PFObject` subclass helps encapsula
`PFObject` supports dynamic synthesizers just like `NSManagedObject`. Declare a property as you normally would, but use `@dynamic` rather than `@synthesize` in your .m file. The following example creates a `displayName` property in the `Armor` class:
-
-
You can access the displayName property using `armor.displayName` or `[armor displayName]` and assign to it using `armor.displayName = @"Wooden Shield"` or `[armor setDisplayName:@"Wooden Sword"]`. Dynamic properties allow Xcode to provide autocomplete and catch typos.
`NSNumber` properties can be implemented either as `NSNumber`s or as their primitive counterparts. Consider the following example:
@@ -688,16 +685,19 @@ If you need more complicated logic than simple property access, you can declare
PFImageView *view = [[PFImageView alloc] initWithImage:kPlaceholderImage];
view.file = self.iconFile;
[view loadInBackground];
+
return view;
}
```
+
```swift
-@NSManaged var iconFile: PFFileObject
+@NSManaged var iconFile: PFFileObject!
func iconView() -> UIImageView {
let view = PFImageView(imageView: PlaceholderImage)
view.file = iconFile
view.loadInBackground()
+
return view
}
```
@@ -705,4 +705,4 @@ func iconView() -> UIImageView {
### Initializing Subclasses
-You should create new objects with the `object` class method. This constructs an autoreleased instance of your type and correctly handles further subclassing. To create a reference to an existing object, use `objectWithoutDataWithObjectId:`.
+You should initialize new instances of subclassses with standard initialization methods. To create a new instance of an existing Parse object, use the inherited `PFObject` class function `objectWithoutDataWithObjectId:`, or create a new object and set the objectId property manually.