I want to set up email/password authentication with firebase, and have this written which is similar to the documentation. I have only one registered email that I'm testing with, and when I attempt to sign in with that everything works well. But when I enter another email/password, the completion block does not execute.
Auth.auth().signIn(withEmail: email, password: password) { [weak self] (user, error) in
guard let strongSelf = self else {
return
}
if let error = error {
let errorAlert = UIAlertController(title: "Error", message: error.localizedDescription, preferredStyle: .alert)
errorAlert.addAction(UIAlertAction(title: "OK", style: .default, handler: nil))
strongSelf.present(errorAlert, animated: true, completion: nil)
return
}
}
Nevermind I fixed it. I had a performSegue line right outside of the completion, when it should have been inside, after the guard and if let statement.
Related
I know the downloadURL function has been deprecated, but I can't seem to get the new completion function to work:
#IBAction func postButtonClicked(_ sender: Any) {
let mediaFolder = Storage.storage().reference().child("media")
if let data = UIImageJPEGRepresentation(postImage.image!, 0.5) {
mediaFolder.child("\(uuid).jpg").putData(data, metadata: nil, completion: { (metadata, error) in
if error != nil {
let alert = UIAlertController(title: "Error", message: error?.localizedDescription, preferredStyle: UIAlertControllerStyle.alert)
let okButton = UIAlertAction(title: "OK", style: UIAlertActionStyle.cancel, handler: nil)
alert.addAction(okButton)
self.present(alert, animated: true, completion: nil)
} else {
let imageURL = mediaFolder.downloadURL(completion: { (url, error) in
if error != nil {
print("error!!!!")
} else {
return url?.absoluteString
}
})
print(imageURL)
}
})
}
}
I just can't get this to work. I always get the error!!!!! message in the log and I'm not sure why. I've been struggling with this code for the past 3 hours and for some reason I just can't get the imageURL to print.
All I want is to get imageURL to equal url?.absoluteString
Any help would greatly be appreciated
You're not getting the URL to print out because you're not querying the right storage references.
First, check if the image is actually uploaded in the storage and then add the child Id to your mediaFolder in the else statement:
mediaFolder.child("\(uuid).jpg").downloadURL(completion: { (url, error) in
})
I'm trying to create an authentication security code for admin to login/ register. What I wish to do is login to perform segue if the user pass through the code which exists in firebase database. So now it doesn't works as Error alert box keep popping out event I have enter the correct security code.
let alertController = UIAlertController(title: "Security Code?", message: "Please enter your dedicated security code", preferredStyle: .alert)
let confirmAction = UIAlertAction(title: "Next", style: .default) { (_) in
let code = alertController.textFields?[0].text
let scref=Database.database().reference();
scref.queryOrdered(byChild: "securitycode").queryEqual(toValue: code).observe(.value, with: { (snapshot) in
if (snapshot.exists())
{
Auth.auth().signIn(withEmail: self.emailText.text!, password: self.passwordText.text!, completion: { (user, error) in
if user != nil
{
//if sign in sucessful
self.performSegue(withIdentifier: "segueadmin", sender: self)
} else
{
if let myError = error?.localizedDescription{
print(myError)
let alertController = UIAlertController(title: "Error!", message: myError, preferredStyle: UIAlertControllerStyle.alert)
alertController.addAction(UIAlertAction(title: "Ok", style: UIAlertActionStyle.default) {
UIAlertAction in
// Insert code to run on button click below
self.printYes()
})
self.present(alertController, animated: true, completion: nil)
}else{
print("ERROR")
}
}
})}
let cancelAction = UIAlertAction(title: "Cancel", style: .cancel) { (_) in }
alertController.addTextField { (textField) in
textField.placeholder = "Enter Code:"
}
//adding the action to dialogbox
alertController.addAction(confirmAction)
alertController.addAction(cancelAction)
//finally presenting the dialog box
self.present(alertController, animated: true, completion: nil)
}
}
I think it might be an issue when you query your database.
Try this code :
scref.child("securitycode").child(code).observe(.value, with: { (snapshot) in
if (snapshot.exists()) {
...//Do your thing
}
With this your aim the reference /securitycode/{code} and if it exists it seems that there is a correct value stored in your database so you can proceed. If not the user can't proceed.
Oops! Very careless of me! It because of I didn't structure the data well and forgot to put " " for the data in Firebase.
So the firebase database should be:
And the code shall be:
ref=Database.database().reference().child("securitycode")
ref.queryOrdered(byChild: "code")
.queryEqual(toValue: self.textf.text)
.observe(DataEventType.value, with: { (snapshot) in
I am trying log users as simply as possible using the signup and getSession function.
I have not encountered difficulties in using the signup function to create new users in my cognate user pool.
When I try to create a function for logging, I try this code :
func signin(){
let pool = AWSCognitoIdentityUserPool(forKey: AWSCognitoUserPoolSignInProviderKey)
let user = pool.getUser("toto")
user.getSession("toto", password: "BabaBobo1&", validationData: nil).continueWith(block: {[weak self] (task) -> Any? in
DispatchQueue.main.async {
if let error = task.error as? NSError {
let alertController = UIAlertController(title: error.userInfo["__type"] as? String,
message: error.userInfo["message"] as? String,
preferredStyle: .alert)
let retryAction = UIAlertAction(title: "Retry", style: .default, handler: nil)
alertController.addAction(retryAction)
self?.present(alertController, animated: true, completion: nil)
}else if let session = task.result {
let alertController = UIAlertController(title: "token",
message: session.accessToken?.tokenString,
preferredStyle: .alert)
let OKAction = UIAlertAction(title: "OK", style: .default, handler: nil)
alertController.addAction(OKAction)
self?.present(alertController, animated: true, completion: nil)
}
}
return nil
})
}
It appears that the trailing block is never executed. Does anyone knows what I am doing wrong ?
My aim is to reduce the AWS linked code to the minimum. I want to avoid as much as possible to use the different delegate protocols provided in the SDK
I am having difficulty in capturing a Cognito Sign Up Error. I am trying to alert the user when Cognito returns a "UsernameExistsException","message":"User already exists" Error.
Below is my code:
self.pool!.signUp(usernameTextField.text!, password: passwordTextField.text!, userAttributes: attributes, validationData: nil).continue(successBlock: { (task:AWSTask!) in
// needs to be async so we can ALWAYS return nil for AWSTask
DispatchQueue.main.async {
if task.error != nil { // some sort of error
let myerror = task.error
print("\(myerror)")
let alert = UIAlertController(title: "Sign Up Error", message: (task.error?.localizedDescription)! as String, preferredStyle: UIAlertControllerStyle.alert)
alert.addAction(UIAlertAction(title: "Ok", style: UIAlertActionStyle.default, handler: nil))
self.present(alert, animated: true, completion: nil)
}
else {
let response: AWSCognitoIdentityUserPoolSignUpResponse = task.result! as AWSCognitoIdentityUserPoolSignUpResponse
// NSLog("AWSCognitoIdentityUserPoolSignUpResponse: \(response)")
self.user = response.user
let alert = UIAlertController(title: "Sign Up Successful", message: "", preferredStyle: UIAlertControllerStyle.alert)
alert.addAction(UIAlertAction(title: "OK", style: UIAlertActionStyle.default, handler: { action in self.performSegue(withIdentifier: "confrimationSegue", sender: self) }))
self.present(alert, animated: true, completion: nil)
}
}
return nil
})
For some reason am unable to break into the task.error != nil conditional statement. When I force an error the error does not print and alert action does not present to the view. Am I attempting to alert the user in the wrong function? How else can I check for the Username Already Exists error presented by cognito. Thanks in advance.
You are using a successBlock, which means that the block that you set is only going to be called when the sign up was performed succesfully. That's why the error is always nil.
In order to have the error, you should set the callback simply by something like the following:
userPool
.signUp(user.email, password: user.password, userAttributes: attributes, validationData: nil)
.continue({ response in
if let error = response.error {
// Error ocurred
} else {
// No error ocurred
})
This continue method only recieves the callback and will be called when a error happens.
I'm trying to have it so when a user creates an account... if their email hasn't been used before an Alert box appears saying "Account created" and if the email is already in created (on Parse) then an alert should appear notifying the user.
I can't seem to get my code to do both..only display one message. What am I doing wrong here?
Thanks!
func createNewUser() {
let newUser = PFUser()
newUser.email = emailSignUp.text
newUser.username = emailSignUp.text
newUser.password = passwordSignUp.text
newUser.signUpInBackgroundWithBlock { ( success: Bool, error: NSError?) -> Void in
if newUser.username != nil {
let alert: UIAlertController = UIAlertController(title: "Account created", message: "Please confirm your email", preferredStyle: .Alert)
let okButton = UIAlertAction(title: "OK", style: .Default) { action -> Void in
}
alert.addAction(okButton)
self.presentViewController(alert, animated: true, completion: nil)
}
else {
let alert: UIAlertController = UIAlertController(title: "Email already registered", message: "Please enter a different email", preferredStyle: .Alert)
let okButton = UIAlertAction(title: "OK", style: .Default, handler: nil)
alert.addAction(okButton)
self.presentViewController(alert, animated: true, completion: nil)
}
}
}
If memory serves the error that's returned if a user already exists is a different string than a generic error. You can try to match the error string and then display an alert if it matches or a different one if it's just an error (like the error string itself).
newUser.signUpInBackgroundWithBlock { ( success: Bool, error: NSError?) -> Void in
if error != nil {
if let errorString = error.userInfo?[“error”] as? String {
if errorString == “username \(emailSignUp.text) already taken” {
// Create alert that address is taken
} else {
// Create other case alert, though it may make sense to just display the error string in an alert box
}
}
} else {
// Do your usual stuff
}