我如何保持用户登录应用程序?迅捷5

问题描述

您好,我制作了包含登录注册功能的应用程序,该功能运行良好,但是关闭应用程序时无法保持用户登录状态;它将用户返回到主视图控制器,在该视图控制器中,用户将不得不在注册登录之间进行选择。

任何人都可以帮忙吗?

这是我的代码:AppDelegate,登录注册

AppDelegate:

import UIKit
import Firebase

@UIApplicationMain
class AppDelegate: UIResponder,UIApplicationDelegate {

    func application(_ application: UIApplication,didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
        // Override point for customization after application launch.
        sleep(2);
        FirebaseApp.configure()
        return true
    }
}

登录

import UIKit
import Firebase
    
class LoginController: UIViewController {
    
    // MARK: - Properties
    @IBOutlet weak var passwordTextField: UITextField!
    @IBOutlet weak var login: UIButton!
    @IBOutlet weak var emailTextField: UILabel!
    
    var email = String()
    
    // MARK: - Init
    override func viewDidLoad() {
        super.viewDidLoad()
        emailTextField.text = email
    }
    
    // MARK: - Selectors
    
    @IBAction func loginButton(_ sender: UIButton) {
        
        guard let password = passwordTextField.text else {return}
        
        let finalPassword = password.trimmingCharacters(in: .whitespacesAndNewlines)
            
        //Password Validation and Alert
        if Utilities.isPasswordValid(finalPassword) == true {
            print("Password is Valid")
        } else {
            print("Password is not Valid")
            let myAlert = UIAlertController(title:"",message:"Please make sure your password is at least six characters,includes at least one number or special character,and is not a commonly used password.",preferredStyle:UIAlertController.Style.actionSheet)
            let okAction = UIAlertAction(title: "Cancel",style: UIAlertAction.Style.destructive,handler: nil)
            myAlert.addAction(okAction)
            self.present(myAlert,animated: true,completion: nil)
        
            return
        }
        
        loginUserIn(withEmail: email,password: password)
     }
    
    // MARK: - API
    
    func loginUserIn(withEmail email:String,password: String) {
        
        Auth.auth().signIn(withEmail: email,password: password) { (result,error) in
        
        if let error = error {
            print("Failed to sign in",error.localizedDescription)
            return
        }
        print("Success Log In")
        
            UserDefaults.standard.set(true,forKey: "nil")
            UserDefaults.standard.synchronize()
    }
  }
}

注册

import UIKit
import Firebase

class SignUpController: UIViewController {
    
    @IBOutlet weak var passwordTextField: UITextField!
    @IBOutlet weak var signUp: UIButton!
    @IBOutlet weak var emailText: UILabel!
    
    var email = String()
    
    // MARK: - Init
    
    override func viewDidLoad() {
        super.viewDidLoad()
        emailText.text = email
        signUp.addTarget(self,action: #selector(signUpButton),for: .touchUpInside)
    }

    // MARK: - Selectors
    
    @IBAction func signUpButton(_ sender: Any) {
    
    guard let password = passwordTextField.text,// use Swift's ability to infer the type here (and a couple other places)
                case let finalPassword = password.trimmingCharacters(in: .whitespacesAndNewlines),Utilities.isPasswordValid(finalPassword) else {
                // If we get here then either the password is null
                // or the password is not valid
                print("Password is not valid")

                // we need to display the alert,I'll move that into another function
                showPasswordInvaliDalert()

                return
            }

            // If we get here the password is valid
            print("Password is valid:",finalPassword)

        
        createuser(withEmail: email,password: password)
    }
        
    func showPasswordInvaliDalert() {
        // this is an alert not an action sheet
        let alert = UIAlertController(title: "",message: "Please make sure your password is at least six characters,preferredStyle: .actionSheet)
        // this is not a destructive action
        let okAction = UIAlertAction(title: "Cancel",style: .destructive,handler: nil)
        alert.addAction(okAction)
        self.present(alert,completion: nil)
    }
   
    // MARK: - API
    
    func createuser(withEmail email:String,password: String) {
        
        Auth.auth().createuser(withEmail: email,error) in
            
            if let error = error {
                print("Failed to sign up",error.localizedDescription)
                return
            }
            
            guard let uid = result?.user.uid else {return}
            
            let values = ["email": email]
            
            Database.database().reference().child("users").child(uid).updateChildValues(values,withCompletionBlock: { (error,ref) in
                
                if let error = error {
                    print("Falied to update",error.localizedDescription)
                    return
                }
                let mainStoryBoard = UIStoryboard(name: "Main",bundle: Bundle.main)
                
                guard let controller = mainStoryBoard.instantiateViewController(withIdentifier: "SubsViewController") as? SubsViewController else {
                    print("Error")
                    return
                }
                
                self.navigationController?.pushViewController(controller,animated: true)
                
               // self.present(controller,completion: nil)
            
            })
        }
    }
}

解决方法

遵循以下步骤:-

  • 一次用户成功登录集UserDefaults.standard.set(true,forKey: "islogin")
  • 将以下代码添加到appdelegate
private func application(_ application: UIApplication,didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
    // Override point for customization after application launch.
           
           let islogin = UserDefaults.standard.object(forKey: "token")
           if islogin {
               //set your login viewcontroller as root viewcontroller
           }else{
               //open the home screen 
           }
           return true
       }
  • 不要忘记在注销时将userdefault设置为false。
,
  • 设置布尔检查。

  • 在登录时将其设置为true。

  • 在注销时将其设置为false。

  • 在sceneDelegate上检查其状态

  • 根据当前值加载视图控制器。

    让isLoggedIn = userdefaults.standard.bool(forKey:“ loggedInValue”)

    if isLoggedIn == true{ 
     print("loggedIn")
    }else{
     print("loggedOut")
    }
    

在您的sceneDelegate集中设置

    func scene(_ scene: UIScene,willConnectTo session: UISceneSession,options connectionOptions: UIScene.ConnectionOptions) {
    // Use this method to optionally configure and attach the UIWindow `window` to the provided UIWindowScene `scene`.
    // If using a storyboard,the `window` property will automatically be initialized and attached to the scene.
    // This delegate does not imply the connecting scene or session are new (see `application:configurationForConnectingSceneSession` instead).
    let window = UIWindow(windowScene: scene as! UIWindowScene)
    // Assign window to SceneDelegate window property
    self.window = window
    
    if let loggedIn = UserDefaults.standard.bool(forKey: "IsUserLoggedIn") as? Bool{
        if loggedIn{
            let initialViewController = storyboard.instantiateViewController(withIdentifier: "LoggedInScreen")

            self.window?.rootViewController = initialViewController
        }else{
            let initialViewController = storyboard.instantiateViewController(withIdentifier: "SignUpScreen")
            self.window?.rootViewController = initialViewController
        }
    }else{
        let initialViewController = storyboard.instantiateViewController(withIdentifier: "SignUpScreen")
        self.window?.rootViewController = initialViewController
    }
    self.window?.makeKeyAndVisible()
    guard let _ = (scene as? UIWindowScene) else { return }
}