在 UIWebView 中保存 username/password 以供将来自动登录

Saving username/password in UIWebView for future auto login

我正在努力为学校网站制作一个简单的 iOS 应用程序。该应用程序具有内置的 UIWebView 来加载网站的登录页面。用户第一次加载页面时,he/she 需要像以前一样登录。我希望应用程序可以为用户保存 username/password。因此,下一个用户使用该应用程序时,它会自动填写并提交表单以自动登录。

我发现堆栈 overflow.com 中的几个链接非常有用。例如,

[1] Is it possible for a UIWebView to save and autofill previously entered form values (e.g., username & password)?

[2]

我试图为我的程序做同样的事情。自动填充部分适用于硬编码测试 username/password。但是,我在保存来自 UIWebView 的凭据时遇到了问题。 "stringByEvaluatingJavaScriptFromString: @" 方法不从 HTML.

中检索元素

我的代码如下。我使用 viewDidLoad 加载网站并希望使用 webView 保存凭据。

- (void)viewDidLoad {
  [super viewDidLoad];
  NSURL *url = [NSURL URLWithString:urlString];
  NSString *urlString = @"https://learn.packagingschool.com/users/sign_in";
  NSURL *url = [NSURL URLWithString:urlString];
  NSURLRequest *urlRequest = [NSURLRequest requestWithURL:url];
  [self.webView loadRequest:urlRequest];
  [self.webView setDelegate:self];
}

- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType; {

    //save form data
    if(navigationType == UIWebViewNavigationTypeFormSubmitted) {

    //grab the data from the page
    NSString *inputEmail = [webView stringByEvaluatingJavaScriptFromString: @"document.getElementByID('user_email').value"];
    NSString *inputPassword = [webView stringByEvaluatingJavaScriptFromString: @"document.getElenebtByName('user[password]')[0].value"];

    NSLog(@"email is %@\npassword is %@", inputEmail, inputPassword);

    //store values locally
    [[NSUserDefaults standardUserDefaults] setObject:inputEmail forKey:@"email"];
    [[NSUserDefaults standardUserDefaults] setObject:inputPassword forKey:@"password"];

    NSLog(@"email is %@\npassword is %@", inputEmail, inputPassword);

    //[SFHFKeychainUtils storeUsername:username andPassword:password forServiceName:@"MyService" updateExisting:YES error:nil];

  }    
  return YES;
}

当我点击 webView 中的提交按钮时,没有从网站检索到任何字符串。

2017-02-23 11:19:46.732 Packaging School[441:5425] email is 
password is 
2017-02-23 11:19:46.755 Packaging School[441:5425] email is 
password is 

请帮我解决问题。非常感谢!

改变

NSString *inputEmail = [webView stringByEvaluatingJavaScriptFromString: @"document.getElementByID('user_email').value"];
NSString *inputPassword = [webView stringByEvaluatingJavaScriptFromString: @"document.getElenebtByName('user[password]')[0].value"];

NSString *inputEmail = [webView stringByEvaluatingJavaScriptFromString: @"document.getElementById('user_email').value"];
NSString *inputPassword = [webView stringByEvaluatingJavaScriptFromString: @"document.getElementsByName('user[password]')[0].value"];
import UIKit
import WebKit
import WKCookieWebView
import CoreLocation
import SwiftKeychainWrapper

class MoviesViewController: UIViewController, WKUIDelegate, WKNavigationDelegate, CLLocationManagerDelegate {
let locationManager = CLLocationManager()
var currentLocaton: CLLocation!

lazy var webView: WKCookieWebView = {
    let webView: WKCookieWebView = WKCookieWebView(frame: self.view.bounds)
    webView.translatesAutoresizingMaskIntoConstraints = false
    webView.navigationDelegate = self
    webView.wkNavigationDelegate = self
    return webView

}()

@IBOutlet weak var Activity: UIActivityIndicatorView!
@IBOutlet weak var SAMBACK: UIBarButtonItem!

@IBAction func SAMBACK(_ sender: Any) {
    if webView.canGoBack{
        webView.goBack()
    }
}

func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
    Activity.stopAnimating()
    SAMBACK.isEnabled = webView.canGoBack
}

func webView(_ webView: WKWebView, didFail navigation: WKNavigation!, withError error: Error) {
    Activity.stopAnimating()
}


override func viewDidLoad() {
    super.viewDidLoad()

    ArgAppUpdater.getSingleton().showUpdateWithForce()

    // SAM - Load Background webView to Black Color
    webView.backgroundColor = UIColor(red: 51/255, green: 51/255, blue: 51/255, alpha: 1)
    webView.isOpaque = false

    webView.allowsBackForwardNavigationGestures = true

    let webConfiguration = WKWebViewConfiguration()

    locationManager.delegate = self
    locationManager.desiredAccuracy = kCLLocationAccuracyBest
    locationManager.requestWhenInUseAuthorization()
    locationManager.stopMonitoringSignificantLocationChanges()

    // Do any additional setup after loading the view, typically from a nib.

    if CheckInternet.Connection(){

        setupWebView()
        webView.onDecidePolicyForNavigationAction = { (webView, navigationAction, decisionHandler) in
            decisionHandler(.allow)
        }

        webView.onDecidePolicyForNavigationResponse = { (webView, navigationResponse, decisionHandler) in
            decisionHandler(.allow)
        }

        webView.onUpdateCookieStorage = { [weak self] (webView) in
            self?.printCookie()
        }

        // add activity
        self.webView.addSubview(self.Activity)
        self.Activity.startAnimating()
        self.webView.navigationDelegate = self
        self.Activity.hidesWhenStopped = true
        webView.load(URLRequest(url: URL(string: "http://www.gmail.com")!))

    }
    else{
        self.Alert(Message: "Your Device is not connect to internet, Please check your connection")
    }

    func locationAuthStatus(){
        if CLLocationManager.authorizationStatus() == .authorizedWhenInUse{

            currentLocaton = locationManager.location
            print(currentLocaton.coordinate.latitude)
            print(currentLocaton.coordinate.longitude)
        } else {

            locationManager.requestWhenInUseAuthorization()
            locationAuthStatus()
        }
    }
}

func Alert (Message: String){
    let alert = UIAlertController (title: "Prime Cineplex", message: "Your Device is not connect to internet, Please check your connection", preferredStyle: .alert)

    let settingsAction = UIAlertAction(title: "Settings", style: .default) { (_) -> Void in
        guard let settingsUrl = URL(string: UIApplication.openSettingsURLString) else {
            return
        }

        if UIApplication.shared.canOpenURL(settingsUrl) {
            UIApplication.shared.open(settingsUrl, completionHandler: { (success) in
                print("Settings opened: \(success)") // Prints true
            })
        }
    }
    alert.addAction(settingsAction)
    //let cancelAction = UIAlertAction(title: "Exit", style: .cancel, handler: nil)
    //alert.addAction(cancelAction)
    present(alert, animated: true, completion: nil)
}

// MARK: - Private
private func setupWebView() {
    view.addSubview(webView)

    let views: [String: Any] = ["webView": webView]

    view.addConstraints(NSLayoutConstraint.constraints(
        withVisualFormat: "H:|-0-[webView]-0-|",
        options: [],
        metrics: nil,
        views: views))
    view.addConstraints(NSLayoutConstraint.constraints(
        withVisualFormat: "V:|-0-[webView]-0-|",
        options: [],
        metrics: nil,
        views: views))
}

private func printCookie() {
    print("=====================Cookies=====================")
    HTTPCookieStorage.shared.cookies?.forEach {
        print([=10=])
    }
    print("=================================================")
}

}