firebase uid always return nil - ios

Her is my database/rules:
{
"rules": {
".read": true,
".write": true
}
}
i am trying both way it is give me nil
FIRAuth.auth()?.createUser(withEmail: email, password: pass, completion: { (firuser, error) in
if error != nil {
print("error goes when try to user authenticated :) \(error)")
}
print("firuser : \(firuser)")
print("FIRAuth.auth()?.currentUser?.uid : \(FIRAuth.auth()?.currentUser?.uid)")
print("firuser?.uid : \(firuser?.uid)")
guard let userUID = firuser?.uid else{
print("user UID not found. should go stackoverflow ")
return
}
guard let userUID = firuser?.uid else{
print("user UID not found. should go stackoverflow ")
return
}
})
console log :
error :
Optional(Error Domain=FIRAuthErrorDomain Code=17995 "An error occurred when accessing the keychain. The #c NSLocalizedFailureReasonErrorKey field in the #c NSError.userInfo dictionary will contain more information about the error encountered" UserInfo={NSLocalizedDescription=An error occurred when accessing the keychain. The #c NSLocalizedFailureReasonErrorKey field in the #c NSError.userInfo dictionary will contain more information about the error encountered, error_name=ERROR_KEYCHAIN_ERROR, NSLocalizedFailureReason=SecItemAdd (-34018)})
firuser : nil
FIRAuth.auth()?.currentUser?.uid : nil
firuser?.uid : nil
server user added :

i was faced same problem ..but solve this way
Go to your *.xcodeproj
Go to the tab "Capabilities"
Activate "Keychain Sharing"

Related

Firebase Realtime Database doesn't save data from sign up page

I am working on sign up page of application in Swift. The part of authentication in Firebase works well, but the database doesn't save any information I request. Can anyone help?
My code:
Auth.auth().createUser(withEmail: userEmail,password: userPassword, completion: {(User, error) in
if error != nil {
print(error as Any)
return
}
guard let uid = User?.user.uid else {return}
let ref = Database.database().reference(fromURL:"Database-URL")
let userReference = ref.child("users").child(uid)
let values = ["Firstname": userFirstName,"email": userEmail]
userReference.updateChildValues(values, withCompletionBlock: { (error, reference) in
if error != nil {
print(error as Any)
return
}
})
})
The console prints an error
Optional(Error Domain=com.firebase Code=1 "Permission denied"
UserInfo={NSLocalizedDescription=Permission denied})
By default the database in a project in the new Firebase Console is only readable/writeable by authenticated users:
{
"rules": {
".read": "auth != null",
".write": "auth != null"
}
}
See the quickstart for the Firebase Database security rules.
Since you're not signing the user in from your code, the database denies you access to the data. To solve that you will either need to allow unauthenticated access to your database, or sign in the user before accessing the database.
Allow unauthenticated access to your database
The simplest workaround for the moment (until the tutorial gets updated) is to go into the Database panel in the console for you project, select the Rules tab and replace the contents with these rules:
{
"rules": {
".read": true,
".write": true
}
}
This makes your new database readable and writeable by everyone. Be certain to secure your database again before you go into production, otherwise somebody is likely to start abusing it.
I may not be sure but the completion for createUser doesnot give you User and error rather AuthResult and Error. So you have to get the user from result as below
Auth.auth().createUser(withEmail: email, password: password) { (authData, error) in
if let error = error {
debugPrint("FIREBASE ERROR : \(error.localizedDescription)")
} else {
if let authData = authData {
let user = authData.user //here get the user from result
self.saveToDB(user: user) . //save the user to database
}
}
}
This is the new code for firebase from may 2019. just change false to true like this:
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
match /{document=**} {
allow read, write: if true;
}
}
}

Firebase database Permission denied error facing using swift 4.2

guard let uid = user?.uid else {return}
let usernameValue = ["username":username]
let value = [uid: usernameValue]
Database.database().reference().child("user").updateChildValues(value, withCompletionBlock: { (err, ref) in
if let err = err{
print("failed to save user in db:", err)
}else{
print("successfully Work")
}
})
This is the error I am facing:
failed to save user in db: Error Domain=com.firebase Code=1 "Permission denied" UserInfo={NSLocalizedDescription=Permission denied}
You do not have the permission to manage the /user path in the database.
Check your Firebase security rules.
Allow unauthenticated access to your database.
Go into the Database panel in the console for you project, select the Rules tab and replace the contents with these rules:
{
"rules": {
".read": true,
".write": true
}
}
This makes your new database readable and writeable by everyone.
One more trick to avoid this problem call one of the signIn...methods of Firebase Authentication to ensure the user is signed in before accessing the database. 

Getting errors from Twitter.sharedInstance() Swift 3 iOS 10

I am writing app with Swift 3 on iOS 10. sharedInstance() method throws errors to console when user deny permissions to account from systems or account is not configured (e.g. "Unable to authenticate using the system account"). Errors are shows on console before enter to closure. I wont shows this errors to users in app e.g. on alert. This is my code:
Twitter.sharedInstance().logIn { (session, error) in
if error != nil {
// print(error?.localizedDescription ?? " ")
return
})
I get this error:
2016-11-29 14:49:09.023 CarReview[1254:31719] [TwitterKit] did encounter error with message "Unable to authenticate using the system account.": Error Domain=TWTRLogInErrorDomain Code=2 "User allowed permission to system accounts but there were none set up." UserInfo={NSLocalizedDescription=User allowed permission to system accounts but there were none set up.}
2016-11-29 14:49:09.024 CarReview[1254:31719] [TwitterKit] No matching scheme found.
2016-11-29 14:49:09.292 CarReview[1254:31719] [TwitterKit] did encounter error with message "Error obtaining user auth token.": Error Domain=TWTRLogInErrorDomain Code=-1 "<?xml version="1.0" encoding="UTF-8"?>
<hash>
<error>Desktop applications only support the oauth_callback value 'oob'</error>
<request>/oauth/request_token</request>
</hash>
" UserInfo={NSLocalizedDescription=<?xml version="1.0" encoding="UTF-8"?>
<hash>
<error>Desktop applications only support the oauth_callback value 'oob'</error>
<request>/oauth/request_token</request>
</hash>
}
I want show users this: "Unable to authenticate using the system account. User allowed permission to system accounts but there were none set up."
I am facing the same issue as in the question.
I have just set the callBack Url into the Twitter App and resolved the issues.
Go to https://apps.twitter.com/app -> Settings -> Callback URL and Update Settings to save.
I'm not sure I understand what you want to do but you probably want to print the result on the main thread:
Twitter.sharedInstance().logIn{(session, error) in
DispatchQueue.main.async{
if error != nil {
print("Failed to login with Twitter / error:", error!.localizedDescription)
}else{
print("succeeded")
}
}
}
OK, I use this code to notify user about some error:
if SLComposeViewController.isAvailable(forServiceType: SLServiceTypeTwitter) {
if ACAccountStore().accountType(withAccountTypeIdentifier: ACAccountTypeIdentifierTwitter).accessGranted {
Twitter.sharedInstance().logIn{
(session, error) in
if error != nil {
self.showAlert(title: "Twitter - Error", message: (error?.localizedDescription)!)
return
}
guard let token = session?.authToken else { return }
guard let secret = session?.authTokenSecret else { return }
let credential = FIRTwitterAuthProvider.credential(withToken: token, secret: secret)
FIRAuth.auth()?.signIn(with: credential, completion: { (user, error) in
if error != nil {
self.showAlert(title: "Firebase (Twitter)", message: (error?.localizedDescription)!)
return
}
self.showAlert(title: "Firebase (Twitter)", message: "Logged to Firebase via Twitter.")
})
}
} else {
showAlert(title: "Twitter - Error", message: "Give access to the system Twitter account.")
}
} else {
showAlert(title: "Twitter - Error", message: "No system accounts set up.")
}
But it isn't what I want:/
You need to use withMethods and specify using the systemAccounts, not webBased or all to use the iOS Twitter settings. The following code is in Swift 3:
twitSharedInstance.logIn(withMethods: .systemAccounts) { (session :TWTRSession?, error :Error?) in
if (error != nil) {
if (session != nil) {
//We have logged into Twitter.
}
}
}

Firebase unlink email/password auth from user on iOS

I'm trying to unlink email/password authentication from a user in Swift on iOS. I've read the documentation and managed to link and unlink Facebook authentication without a problem. However, after linking email/password credentials successfully, the providerData object is nil. The providerID is "Firebase" but when I pass that to the unlink code the following error is thrown:
Error Domain=FIRAuthErrorDomain Code=17016 "User was not linked to an account with the given provider." UserInfo={NSLocalizedDescription=User was not linked to an account with the given provider., error_name=ERROR_NO_SUCH_PROVIDER}
The unlink code I'm using is:
let providerId = (FIRAuth.auth()?.currentUser?.providerID)!
print("Trying to unlink:",providerId) // providerId = "Firebase"
FIRAuth.auth()?.currentUser?.unlinkFromProvider(providerId) { user, error in
if let error = error {
print("Unlink error:", error)
} else {
// Provider unlinked from account successfully
print("Unlinked...user.uid:", user!.uid, "Anonymous?:", user!.anonymous)
}
}
Reading the docs and having got it working for Facebook, I expected the providerData array to be populated with something after email authentication. So is my linking code wrong (it doesn't throw an error and appears to work fine)?
My linking code:
let credential = FIREmailPasswordAuthProvider.credentialWithEmail(email, password: password)
FIRAuth.auth()?.currentUser!.linkWithCredential(credential) { (user, error) in
if user != nil && error == nil {
// Success
self.success?(user: user!)
dispatch_async(dispatch_get_main_queue(), {
self.dismissViewControllerAnimated(true, completion: nil)
if type == "new" {
print("New user logged in...")
}
if type == "existing" {
print("Existing user logged in...")
}
})
} else {
print("Login error:",error)
self.showOKAlertWithTitle("Login Error", message: error!.localizedDescription)
}
}
Any pointers of how I can modify my approach would be great.
To get the profile information retrieved from the sign-in providers linked to a user, use the providerData property.
if let user = FIRAuth.auth()?.currentUser {
for profile in user.providerData {
// Id of the provider (ex: facebook.com)
let providerID = profile.providerID
}
} else {
// No user is signed in.
}
Calling FIRAuth.auth()?.currentUser?.providerID will result to "firebase".

Cannot convert value of type (PFUser!, NSError) void to expected argument type PFUserResultBlock

I am new to swift as well as programming but I am trying to retrieve check if a user can log in and I believe I did what Parse recommends to do to do so however I am receiving this error and am unsure as to why.
Here is my code
PFUser.logInWithUsernameInBackground(usernameTextField.text!, password: passwordTextField.text!){
(user: PFUser!, error: NSError) -> Void in
if user != nil {
//Yes User Exists
self.messageLabel.text = "User Exists"
}
else {
//no user doesnt exist
}
}
I updated the xcode for version 8.1 and Parse started giving the same error.
I changed the call to the method to return to work. Here's how I did here:
PFUser.logInWithUsername (inbackground: usernameTextField.text !, password: passwordTextField.text !, block: {(user, error) in
if user != nil {
//Yes User Exists
self.messageLabel.text = "User Exists"
}
else {
//no user doesnt exist
}
})

Resources