Parse: Remove user when session ends? - objective-c

I was wondering if it were possible to remove a user completely from the database if their session ends? Maybe in sign up, I can check if there is a session for the username the person is using and if there isn't, it deletes the previous user and registers a new one?
How do I check if there is a current session for a certain username?
UPDATE:
PFQuery *query = [PFQuery queryWithClassName:#"Friends"];
[query whereKey:#"username" equalTo:[[PFUser currentUser] objectForKey:#"username"]];
[query findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
for (Friends *currentFriend in objects) {
[currentFriend deleteInBackground];
}
}];

You can either:
1. [Recommended] Use a anonymous user to begin with, Reference can be found here.
2. In AppDelegate.m - applicationWillTerminate: method, you can do
[user deleteInBackground];
[PFUser logOut];
This will delete your logged in user permanently, locally and from remotely.
To
check if a session has a certain username
, all you need to do is:
PFUser user = [PFUser currentUser];
if ([user.objectId isEqualToString:"myTargetUserId"]) {
NSLog("Target user exists");
}

Related

Why can not access to pointer object of _User in Parse?

I have a table called "Event" with public read and write access.
Inside this table I have one field called "user". This field is a pointer to _User table with public read and only user write access.
This is my code:
PFQuery *query = [PFQuery queryWithClassName:#"Event"];
[query whereKey:#"objectId" equalTo:self.objID];
[query getObjectInBackgroundWithId:self.objID block:^(PFObject *object, NSError *error) {
if (!error)
{
PFUser *host = [object objectForKey:#"user"];
NSLog(#"HOST == %#",host);
self.hostId = host.objectId;
}
]);
Now problem is, if userA create a row in Event table called eventA and userB create an Event called eventB. if UserA query eventB cannot access to userB information. However, if userA query eventA, it can access to itself information.
Answer is pretty much easy. It seems that I need to include key in my query:
[query includeKey:#"user"];

Parse.com combine nested query

I am new to using parse, and currently adding parse to an app that uses SOAP web services to replace them.
Now I come a little stuck, as due to having it done in MySQL and php I am trying to translate the logic from the tables and code to parse.
I have a function that I have written and it achieves exactly what I am after, however I just think its wrong and can be done better, for starters I am not calling findObjectsInBackground, which I know I need to.
I am trying to take this result and then reload a tableView.
NSMutableArray *activityfeed = [NSMutableArray new];
//get current user
PFUser *user = [PFUser currentUser];
if (user != nil) {
PFQuery *query = [PFQuery queryWithClassName:#"Event"];
//get event that user is involved in
[query whereKey:#"invited" equalTo:user];
//get the events
NSArray *events = [query findObjects];
//loop over the events
for (PFObject *event in events) {
//owner is a pointer to the users class
PFUser *owner = event[#"owner"];
if (![user.objectId isEqualToString:owner.objectId]) {
//ignore the info for the logged in user for now
//invited is a relation so one event has many users
PFRelation *relation = [event relationForKey:#"invited"];
PFQuery *query = [relation query];
[query orderByDescending:#"dateinvited"];
[query addDescendingOrder:#"dateaccepted"];
//get the friends that are involved with the event
NSArray *friends = [query findObjects];
for (PFUser *friend in friends) {//Perform logic checks here and then add to activityfeed}
}
}
}
return activityfeed;
So my logic above gets the current user, then get all the events that user is involved with, then get all the other people involved with that event and then work out what to display.
Is there a more efficient way of doing the above?
Usually we use whereKey:matchesQuery in cases like this. Take some research on this.
This question may help you find out some solution.

Correct way to user PFQuery to query relational data like Pointer

Ok so let's say I have a post of an event, and users can click a button to notify that they are attending this event. As of now I have a class called Activity in which I save the current user and the event to this class, so theres 2 columns. If I want to query all users who are attending an event, am I headed in the right direction to do this, or am I doing it complentely wrong?
So far I have:
-(PFQuery*)queryForTable {
PFQuery *activityQuery = [PFQuery queryWithClassName:#"Activity"];
[activityQuery whereKey:#"event" equalTo:self.event];
[activityQuery includeKey:#"going"];
return activityQuery;
}
cellForRowAtIndex:
UILabel *title = (UILabel*) [cell viewWithTag:1];
title.text = [object objectForKey:#"going.username"];
You can actually see what you have been done in the Parse dashboard. That's also their purpose to develop a data browser like this. It's way more convenient.
For your case, you just need to check whether the type is Pointer. Try to click on that if so in the dashboard. It will direct you to the target object.
Would suggest you to read this article first, it's about the relation:
https://parse.com/docs/relations_guide
Then, you should go check the iOS SDK tutorial:
includeKey is definitely what you need to use.
Here is the sample from Parse:
PFQuery *query = [PFQuery queryWithClassName:#"Comment"];
// Retrieve the most recent ones
[query orderByDescending:#"createdAt"];
// Only retrieve the last ten
query.limit = 10;
// Include the post data with each comment
[query includeKey:#"post"];
[query findObjectsInBackgroundWithBlock:^(NSArray *comments, NSError *error) {
// Comments now contains the last ten comments, and the "post" field
// has been populated. For example:
for (PFObject *comment in comments) {
// This does not require a network access.
PFObject *post = comment[#"post"];
NSLog(#"retrieved related post: %#", post);
}
}];
Your code looks right on so far. Then to retrieve your Activity class values, you can use:
PFQuery *activityQuery = [PFQuery queryWithClassName:#"Activity"];
// Set contraints here, example:
[activityQuery setLimit:100];
[query findObjectsInBackgroundWithBlock:^(NSArray *array, NSError *error) {
if (!error) {
// Success, do something with your objects.
}
}];

I want to create a ViewController where user can change there existing password. I m using Parse API

PFUser *user = [PFUser currentUser];
// I can see the details of the users when this is called including password
if (user) {
if ([_login_txtpassword.text isEqualToString:user[#"UserPasswrod"]]) {
user[#"userPassword"] = _login_txtnewpassword.text;
[user saveInBackground];
NSLog(#"done");
}
}
this code is not working.... i have put blocks to test my code ... it doesnt pass the if statement
A little conflict in my concepts related parse (so consider me as a noob)
P.S i have read the documentation and search internet but couldnt find a solution.
Many Many thanks in advcance
The right way to do this is to try to log the user in with the old password, then set the new password if successful. (notice this code uses the parse User password attribute, not #"userPassword" as in the OP code, which won't work under any circumstances)...
NSString *username = [PFUser currentUser].username;
NSString *oldPassword = self.oldPasswordTextField.text;
NSString *newPassword = self.newPasswordTextField.text;
[PFUser logInWithUsernameInBackground:username password:oldPassword
block:^(PFUser *user, NSError *error) {
if (user) {
user.password = newPassword;
[user saveInBackground];
} else {
// update UI to tell user that the old password is incorrect
}
}];
Actually you can't override the password of the current user directly from your ViewController. The user should request a new password, that will by sent to his/her email by Parse.
PFUser *currentUser = [PFUser currentUser];
NSString *userEmail = [NSString stringWithFormat: #"%#", currentUser.email];
[PFUser requestPasswordResetForEmailInBackground:userEmail];
or
[PFUser requestPasswordResetForEmailInBackground:self.userEmailTextfield.text];

Parse.com - Getting pointer data contained in [PFUser currentUser]

I am using the Parse.com iOS SDK, and I don't know what method I need to call to make sure that the PFUser currentUser contains the data for each pointer contained in it. It is probably very simple, but, as a beginner with this platform, I cannot find a solution.
Just to clarify, I am trying to get the username item in the following. It looks like it is always null, even though I am calling [[PFUser currentUser] fetchIfNeeded] before proceeding:
[[[PFUser currentUser] objectForKey:#"partner"] objectForKey:#"username"];
Thank you,
Andrea
You can do it in a single query by using includeKey:
PFQuery *query = [PFUser query];
[query includeKey:#"partner"];
[query includeKey:#"anotherPointerColumnName"];
[query getObjectInBackgroundWithId:[[PFUser currentUser] objectId]
block:^(PFObject *populatedUser, NSError *error) {
PFObject *partner = populatedUser[#"partner"];
PFObject *another = populatedUser[#"anotherPointerColumnName"];
}];
You can also use deeper levels, so if partner contained a pointer in it you needed called deeperPointerColumnName:
[query includeKey:#"partner.deeperPointerColumnName"];
Then in your completion block you can read it after you get the partner:
PFObject *partner = populatedUser[#"partner"];
PFObject *deeper = partner[#"deeperPointerColumnName"];
Well, I found a workaround by myself. It looks like the solution is to call the fetch method on the pointer before proceeding:
[[[PFUser currentUser] objectForKey:#"partner"] fetch];
If there is a cleaner and swifter way of doing it (automatically for instance) I would really appreciate any advice.