Implement AutoFill Credential Provider Extension in iOS14 - swift

I'm trying to implement the AutoFill Credential Provider Extension, however I'm having some problems following the video of the WWDC where they presented this feature.
Is there someone that has already done it that could help me?
Right now, I added the AutoFill Credential Provider capability as well as the AutoFill Credential Provider extension, which right now looks like this:
import AuthenticationServices
class CredentialProviderViewController: ASCredentialProviderViewController {
override func prepareCredentialList(for serviceIdentifiers: [ASCredentialServiceIdentifier]) {
}
override func provideCredentialWithoutUserInteraction(for credentialIdentity: ASPasswordCredentialIdentity) {
let databaseIsUnlocked = true
if (databaseIsUnlocked) {
let passwordCredential = ASPasswordCredential(user: "j_appleseed", password: "apple1234")
self.extensionContext.completeRequest(withSelectedCredential: passwordCredential, completionHandler: nil)
} else {
self.extensionContext.cancelRequest(withError: NSError(domain: ASExtensionErrorDomain, code:ASExtensionError.userInteractionRequired.rawValue))
}
}
override func prepareInterfaceToProvideCredential(for credentialIdentity: ASPasswordCredentialIdentity) {
}
#IBAction func cancel(_ sender: AnyObject?) {
self.extensionContext.cancelRequest(withError: NSError(domain: ASExtensionErrorDomain, code: ASExtensionError.userCanceled.rawValue))
}
#IBAction func passwordSelected(_ sender: AnyObject?) {
let passwordCredential = ASPasswordCredential(user: "j_appleseed", password: "apple1234")
self.extensionContext.completeRequest(withSelectedCredential: passwordCredential, completionHandler: nil)
}
}
All of this was pre-written, but on the line
} else {
self.extensionContext.cancelRequest(withError: NSError(domain: ASExtensionErrorDomain, code:ASExtensionError.userInteractionRequired.rawValue))
}
I get the yellow warning "Will never be executed". Can someone help me understand how this extension works? Or is there a guide that I can follow? I can't find any nor on this website nor elsewhere on the internet.

There's not much in the way of documentation or sample code, and no tutorials that I can find. Essentially there is the video you already linked to, and the documentation for the ASCredentialProviderViewController class, which is here:
https://developer.apple.com/documentation/authenticationservices/ascredentialproviderviewcontroller?language=objc
But in your code, it should be quite clear why the line you quoted will never be executed. See my comments below:
let databaseIsUnlocked = true
if (databaseIsUnlocked) //this is always true, because you've just set it to be true
{
let passwordCredential = ASPasswordCredential(user: "j_appleseed", password: "apple1234")
self.extensionContext.completeRequest(withSelectedCredential: passwordCredential, completionHandler: nil)
} else { //so there is no "else"
self.extensionContext.cancelRequest(withError: NSError(domain: ASExtensionErrorDomain, code:ASExtensionError.userInteractionRequired.rawValue))
}
Presumably Apple thought people might want to replace "databaseIsUnlocked = true" with a check to see if their database is unlocked. If that doesn't apply to you, you can ignore that bit.

Related

Use of unresolved identifier 'FUIEmailAuth'FUIEmailAuth

I'm making a login screen using firebase auth UI and swift.
When I run the app, currently it only shows a welcome screen like this welcome screen.
But I want to display the page the firebase prebuilt UI with a text field that a user can type their email address, something like this. login-with email
Here is my current code.
import UIKit
import FirebaseUI
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
}
//MARK: - sign in / sign up
#IBAction func playPressed(_ sender: UIButton) {
let authUI = FUIAuth.defaultAuthUI()
guard authUI != nil else {
return
}
authUI?.delegate = self
authUI?.providers = [FUIEmailAuth()]
let authViewController = authUI!.authViewController()
present(authViewController, animated: true, completion: nil)
}
}
extension ViewController: FUIAuthDelegate{
func authUI(_ authUI: FUIAuth, didSignInWith authDataResult: AuthDataResult?, error: Error?) {
if error != nil {
return
}
performSegue(withIdentifier: K.loginSegue, sender: self)
}
}
and I get error on the code written as "authUI?.providers = [FUIEmailAuth()]". The error message is
Use of unresolved identifier 'FUIEmailAuth'FUIEmailAuth
I saw some other people run into the same problem, and I tried pod update, but I still get the error message.
Also, on the firebase document, they use 'FUIEmailAuth' in their sample code, so I wonder why I'm getting that error and how to fix it.
I just add pod 'FirebaseUI/Email' in my pod file and it solved the problem.

Failed dynamic config update

I'm trying to "send" an image to snapchat using the Snapchat Creative Kit SDK.
Here is the code I'm using:
import UIKit
import SCSDKCreativeKit
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
}
#IBAction func addToSnapBtn(_ sender: UIButton) {
let urltest = URL(string: "http://via.placeholder.com/750x1334");
if let urltest = urltest as? URL {
let picture = SCSDKSnapPhoto(imageUrl: urltest.absoluteURL);
let snapPicture = SCSDKPhotoSnapContent(snapPhoto: picture);
snapPicture.caption = "Test image";
snapPicture.attachmentUrl = "https://google.com/";
let api = SCSDKSnapAPI();
api.startSending(snapPicture) { (error) in
if let error = error {
print(error);
} else {
print("YES");
}
}
}
}
When the user clicks on the button that is linked to the "addToSnapBtn" method I get the following error:
2019-06-14 00:38:14.454846+0200 prosnap[1540:84256] [SnapKit] path=/v1/config trace_id=917679DA29A144CEB5AD8E4C9446FB45
2019-06-14 00:38:14.808965+0200 prosnap[1540:84256] [SnapKit] Dynamic config update status: failure
I've looked everywhere. Documentation, google, stackoverflow, you name it.
I'm relatively new to iOS app development and I have no experience with snapkit.
Can somebody point me in the right direction?
Thanks in advance.
Don't define let api = SCSDKSnapAPI() in function. Define it in UIViewController. Because when you define let api in function it will deinits before completion runs. I tried and it works.

How do you connect to AWS Cognito in Swift for user signing up and logging in?

I'm going to start this question by apologizing for such an open ended question, but I am really struggling and all the documentation is outdated.
Amazon's provided sample app hasn't been updated and I get nothing but errors when attempting to run it. I have a login page setup and ready to go with email and password, and I have tried this code:
#IBAction func signInButtonTouched(sender: UIButton) {
if (emailTextField.text != nil) && (passwordTextField.text != nil) {
let user = (UIApplication.sharedApplication().delegate as! AppDelegate).userPool!.getUser(emailTextField.text!)
user.getSession(emailTextField.text!, password: passwordTextField.text!, validationData: nil, scopes: nil).continueWithExecutor(AWSExecutor.mainThreadExecutor(), withBlock: {
(task:AWSTask!) -> AnyObject! in
if task.error == nil {
// user is logged in - show logged in UI
} else {
// error
}
return nil
})
} else {
// email or password not set
}
}
but unfortunately I'm getting App Delegate has no member "userPool" errors. It does though! I am very new at this, and I have searched github and read through all of Amazon's samples, but the documentation is either in Objective-C, or outdated and doesn't work properly.
Any help with this would be vastly appreciated.

Firebase swift ios login system error Assertion failed/Exec_BAD_INSTRUNCTION (code=EXC_i386_INVOP, subcode=0x0)

Im trying to use the built in authentication system in firebase and followed this TuT to do so
Firebase Login Tutorial
I am able to run my app but when i go to login and type in a valid (or invalid) login email and password it crashes with this error in the console:
Assertion failed: (request.URL), function -[FSRWebSocket initWithURLRequest:protocols:queue:andUserAgent:], file /Users/vikrum/dev/git/firebase-client-objc/Firebase/Firebase/Libraries/SocketRocket/FSRWebSocket.m, line 302.
(lldb)
When I don't type anything and hit login it crashes with this error (i have measures to prevent the app from crashing because of this, possiably side affect of the bigger issue):
<pre>fatal error: unexpectedly found nil while unwrapping an Optional value</pre>
The inline errors below are the same w/ both above console errors
Edit: I have noticed that in the pod directory in my app in the framework and then ios folders the contents are (My hierarchy with red error **LINKhttp://i.stack.imgur.com/IHCQw.png) highlighted in red. The directory for the 4 frameworks was iPhoneOS9.0.sdk for some reason i only have a iPhoneOS.sdk and iPhoneOS9.2.sdk also the firebase and the other framework below it have strange directory locations [(They all go to this location **LINKhttp://i.stack.imgur.com/Z6dX5.png) and i cant for the life of me figure out how to fix it (i'm not totally sure this is the error causing my app to crash after I try to log in but its the only error I have seen so it must be)
Edit 2: i've been looking around and every recent tut to make an app as of at least ios 9 has been confusing me because of this, i have seen 2 separate apps tuts where i downloaded the finale project and i wasn't able to run it because in the pod dir(all where for firebase and ios 9.2 when made and had all the frameworks for firebase) it said "/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS9.0.sdk/System/Library/Frameworks/CFNetwork.framework" and i cant change it because when i go to the little dir change button i have to get into the package contents of xcode and it wont let me do that
The inline error when I am redirected
Second files inline error (same)
Here is where i get directed when the app crashes and i get the error(2 places)
import Foundation
import Firebase
let BASE_URL = "https://baseball-pitcher-app.firebaseIO.comΩΩ"
let FIREBASE_REF = Firebase(url: BASE_URL)
var CURRENT_USER: Firebase
{
***let userID = NSUserDefaults.standardUserDefaults().valueForKey("uid") as! String*** ERROR IN THIS LINE
let currentUser = Firebase(url: "\(FIREBASE_REF)").childByAppendingPath("users").childByAppendingPath(userID)
return currentUser!
}
One thing I did find odd was that the error was in the logout button which is weird because i've never pressed it since the error occurred.
import UIKit
import Firebase
class LoginViewController: UIViewController, UITextFieldDelegate {
#IBOutlet weak var userUsernameTextField: UITextField!
#IBOutlet weak var userPasswordTextField: UITextField!
#IBOutlet weak var logoutButton: UIButton!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
self.userUsernameTextField.delegate = self;
self.userPasswordTextField.delegate = self;
}
override func viewDidAppear(animated: Bool)
{
super.viewDidAppear(animated)
if NSUserDefaults.standardUserDefaults().valueForKey("uid") != nil && CURRENT_USER.authData != nil
{
self.logoutButton.hidden = false
}
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func textFieldShouldReturn(textField: UITextField) -> Bool {
self.view.endEditing(true)
return false
}
#IBAction func loginButtonTapped(sender: AnyObject) {
let email = self.userUsernameTextField.text
let password = self.userPasswordTextField.text
if email != "" && password != ""
{
FIREBASE_REF.authUser(email, password: password, withCompletionBlock: { error, authData in
if error == nil
{
NSUserDefaults.standardUserDefaults().setValue(authData.uid, forKey: "uid")
print("Logged In :)")
self.logoutButton.hidden = false
}
else
{
print(error)
}
})
}
else
{
let alert = UIAlertController(title: "Error", message: "Enter Email and Password.", preferredStyle: UIAlertControllerStyle.Alert)
let action = UIAlertAction(title: "Ok", style: .Default, handler: nil)
alert.addAction(action)
self.presentViewController(alert, animated: true, completion: nil)
}
}
#IBAction func logoutButtonTapped(sender: AnyObject) {
CURRENT_USER.unauth()**** ERROR IN THIS LINE
NSUserDefaults.standardUserDefaults().setValue(nil, forKey: "uid")
self.logoutButton.hidden = true
}
The userId id is most likely nil, and in general it's better to catch the cases in which is it nil, like this
if let userID = NSUserDefaults.standardUserDefaults().valueForKey("uid") as? String {
print(userID) //do something with the user id here
} else {
print("The userID was nil.") //avoid the user id.
}
And the reason for the second error is that CURRENT_USER, since it never Auth'd to start with is now nil. Not sure why the button's IBAction is being called but check the actions and outlets in IB.
Also, the
var CURRENT_USER
is a little suspect.
Based on the name of the var, I would expect it to contain the Current User (as maybe a User Class?).
However when called, it returns a Firebase object which contains a path to the current users node (/appPath/users/users node) and no other user data. It doesn't appear to be populated when a user authenticates either.
Not sure if that was the intention or if it's used somewhere else, but doing this
CURRENT_USER.unauth()
may be an issue since it doesn't contain any auth data.

How can I do a Facebook login using Swift 2.0 and iOS 9.1?

I have added the latest Facebook SDK to my XCode 7.1 project written for iOS 9.1. Unfortunately all I know is Swift, not Objective C. Facebook's developer site documentation only has the documentation in Objective C. Every search on Google reveals documentation that is just too old because things have changed so much just in the past 6 months. So I'm kind of lost.
I did all the easy stuff with the plist file.
I was able to use:
import FBSDKCoreKit
import FBSDKLoginKit
I also added:
return FBSDKApplicationDelegate.sharedInstance().application(application, openURL: url, sourceApplication: sourceApplication, annotation: annotation)
and
return FBSDKApplicationDelegate.sharedInstance().application(application, didFinishLaunchingWithOptions: launchOptions)
To my AppDelegate.swift file. This all works and builds successfully. I have the correct frameworks added as well, obviously. Beyond this point I'm at a standstill because I don't know the syntax for adding a login button, for capturing what I assume would be returned json strings with tokens and other profile information I can use to store in the user's account, etc.
You're on the right track.
Have you set up your pList yet?
You're gonna have to add to your VC, add a login button, deal with delegate, and then deal with FB info. Something like (but not exactly) this:
class yourVC: UIViewController, FBSDKLoginButtonDelegate, UITextFieldDelegate
{
var loginView : FBSDKLoginButton = FBSDKLoginButton()
viewDidLoad() {
loginView.frame = CGRectMake(20, 20, theWidth-40, 40)
self.view.addSubview(loginView)
loginView.readPermissions = ["public_profile", "email", "user_friends","user_birthday"]
loginView.delegate = self
}
func loginButton(loginButton: FBSDKLoginButton!, didCompleteWithResult result: FBSDKLoginManagerLoginResult!, error: NSError!) {
if ((error) != nil)
{
//handle error
} else {
returnUserData()
}
}
func returnUserData()
{
let graphRequest : FBSDKGraphRequest = FBSDKGraphRequest(graphPath: "me", parameters: ["fields":"id,interested_in,gender,birthday,email,age_range,name,picture.width(480).height(480)"])
graphRequest.startWithCompletionHandler({ (connection, result, error) -> Void in
if ((error) != nil)
{
// Process error
print("Error: \(error)")
}
else
{
print("fetched user: \(result)")
let id : NSString = result.valueForKey("id") as! String
print("User ID is: \(id)")
//etc...
}
})
}
You're gonna have to play around with the returnData() part to get it right, but this code should get you 90% of the way there.
I've included a wide range of permissions (user age, interested in, etc), but you'll have to configure them yourself. Honestly this part (the hard part) is really similar with it's object C counterpart, which is much better documented. Just download some get projects where it's working, and try to parse them together into something that suits your fancy.
It can be hard to get it all working, but give it a go, and keep at it!
If you want to perform login from Facebook on click of your custom button, this will help:
#IBAction func onClickFacebookButton(sender: UIButton){
let login = FBSDKLoginManager()
login.loginBehavior = FBSDKLoginBehavior.SystemAccount
login.logInWithReadPermissions(["public_profile", "email"], fromViewController: self, handler: {(result, error) in
if error != nil {
print("Error : \(error.description)")
}
else if result.isCancelled {
}
else {
FBSDKGraphRequest(graphPath: "me", parameters: ["fields": "first_name, last_name, picture.type(large), email, name, id, gender"]).startWithCompletionHandler({(connection, result, error) -> Void in
if error != nil{
print("Error : \(error.description)")
}else{
print("userInfo is \(result))")
}
})
}
})
}