├── .gitignore ├── AppDelegate.cs ├── Entitlements.plist ├── Helpers └── KeychainHelper.cs ├── Info.plist ├── LICENSE.txt ├── Main.cs ├── Main.storyboard ├── README.md ├── Resources ├── Images.xcassets │ └── AppIcons.appiconset │ │ └── Contents.json ├── LaunchScreen.xib └── Touch_ID-512.png ├── SecureMyApp.csproj ├── SecureMyApp.sln ├── SecureMyApp.userprefs ├── ViewController.cs ├── ViewController.designer.cs └── packages ├── NUnit.2.6.3 └── license.txt ├── Xamarin.UITest.0.7.1 ├── Xamarin.UITest-License.rtf └── tools │ └── test-cloud.exe └── repositories.config /.gitignore: -------------------------------------------------------------------------------- 1 | 2 | *.nupkg 3 | 4 | *.xml 5 | 6 | *.md 7 | 8 | *.dll 9 | -------------------------------------------------------------------------------- /AppDelegate.cs: -------------------------------------------------------------------------------- 1 | using Foundation; 2 | using UIKit; 3 | 4 | namespace SecureMyApp 5 | { 6 | // The UIApplicationDelegate for the application. This class is responsible for launching the 7 | // User Interface of the application, as well as listening (and optionally responding) to application events from iOS. 8 | [Register("AppDelegate")] 9 | public class AppDelegate : UIApplicationDelegate 10 | { 11 | // class-level declarations 12 | 13 | public override UIWindow Window 14 | { 15 | get; 16 | set; 17 | } 18 | 19 | public override bool FinishedLaunching(UIApplication application, NSDictionary launchOptions) 20 | { 21 | // Override point for customization after application launch. 22 | // If not required for your application you can safely delete this method 23 | 24 | return true; 25 | } 26 | 27 | public override void OnResignActivation(UIApplication application) 28 | { 29 | // Invoked when the application is about to move from active to inactive state. 30 | // This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) 31 | // or when the user quits the application and it begins the transition to the background state. 32 | // Games should use this method to pause the game. 33 | } 34 | 35 | public override void DidEnterBackground(UIApplication application) 36 | { 37 | // Use this method to release shared resources, save user data, invalidate timers and store the application state. 38 | // If your application supports background exection this method is called instead of WillTerminate when the user quits. 39 | } 40 | 41 | public override void WillEnterForeground(UIApplication application) 42 | { 43 | // Called as part of the transiton from background to active state. 44 | // Here you can undo many of the changes made on entering the background. 45 | } 46 | 47 | public override void OnActivated(UIApplication application) 48 | { 49 | // Restart any tasks that were paused (or not yet started) while the application was inactive. 50 | // If the application was previously in the background, optionally refresh the user interface. 51 | } 52 | 53 | public override void WillTerminate(UIApplication application) 54 | { 55 | // Called when the application is about to terminate. Save data, if needed. See also DidEnterBackground. 56 | } 57 | } 58 | } 59 | 60 | 61 | -------------------------------------------------------------------------------- /Entitlements.plist: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /Helpers/KeychainHelper.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using Security; 3 | 4 | //Code taken from: https://github.com/Krumelur/iOSPasswordStorage/blob/master/KeychainHelpers.cs 5 | using Foundation; 6 | 7 | 8 | namespace SecureMyApp.Helpers 9 | { 10 | public static class KeychainHelpers 11 | { 12 | /// 13 | /// Deletes a username/password record. 14 | /// 15 | /// the username to query. Not case sensitive. May not be NULL. 16 | /// the service description to query. Not case sensitive. May not be NULL. 17 | /// 18 | /// Defines if the record you want to delete is syncable via iCloud keychain or not. Note that using the same username and service ID 19 | /// but different synchronization settings will result in two keychain entries. 20 | /// 21 | /// Status code 22 | public static SecStatusCode DeletePasswordForUsername(string username, string serviceId, bool synchronizable) 23 | { 24 | if (username == null) 25 | { 26 | throw new ArgumentNullException("userName"); 27 | } 28 | 29 | if (serviceId == null) 30 | { 31 | throw new ArgumentNullException("serviceId"); 32 | } 33 | 34 | // Querying is case sesitive - we don't want that. 35 | username = username.ToLower(); 36 | serviceId = serviceId.ToLower(); 37 | 38 | // Query and remove. 39 | SecRecord queryRec = new SecRecord(SecKind.GenericPassword) { Service = serviceId, Label = serviceId, Account = username, Synchronizable = synchronizable }; 40 | SecStatusCode code = SecKeyChain.Remove(queryRec); 41 | return code; 42 | } 43 | 44 | /// 45 | /// Sets a password for a specific username. 46 | /// 47 | /// the username to add the password for. Not case sensitive. May not be NULL. 48 | /// the password to associate with the record. May not be NULL. 49 | /// the service description to use. Not case sensitive. May not be NULL. 50 | /// defines how the keychain record is protected 51 | /// 52 | /// Defines if keychain record can by synced via iCloud keychain. 53 | /// Note that using the same username and service ID but different synchronization settings will result in two keychain entries. 54 | /// 55 | /// SecStatusCode.Success if everything went fine, otherwise some other status 56 | public static SecStatusCode SetPasswordForUsername(string username, string password, string serviceId, SecAccessible secAccessible, bool synchronizable) 57 | { 58 | if (username == null) 59 | { 60 | throw new ArgumentNullException("userName"); 61 | } 62 | 63 | if (serviceId == null) 64 | { 65 | throw new ArgumentNullException("serviceId"); 66 | } 67 | 68 | if (password == null) 69 | { 70 | throw new ArgumentNullException("password"); 71 | } 72 | 73 | // Querying is case sesitive - we don't want that. 74 | username = username.ToLower(); 75 | serviceId = serviceId.ToLower(); 76 | 77 | // Don't bother updating. Delete existing record and create a new one. 78 | DeletePasswordForUsername(username, serviceId, synchronizable); 79 | 80 | // Create a new record. 81 | // Store password UTF8 encoded. 82 | SecStatusCode code = SecKeyChain.Add(new SecRecord(SecKind.GenericPassword) 83 | { 84 | Service = serviceId, 85 | Label = serviceId, 86 | Account = username, 87 | Generic = NSData.FromString(password, NSStringEncoding.UTF8), 88 | Accessible = secAccessible, 89 | Synchronizable = synchronizable 90 | }); 91 | 92 | return code; 93 | } 94 | 95 | /// 96 | /// Gets a password for a specific username. 97 | /// 98 | /// the username to query. Not case sensitive. May not be NULL. 99 | /// the service description to use. Not case sensitive. May not be NULL. 100 | /// 101 | /// Defines if the record you want to get is syncable via iCloud keychain or not. Note that using the same username and service ID 102 | /// but different synchronization settings will result in two keychain entries. 103 | /// 104 | /// 105 | /// The password or NULL if no matching record was found. 106 | /// 107 | public static string GetPasswordForUsername(string username, string serviceId, bool synchronizable) 108 | { 109 | if (username == null) 110 | { 111 | throw new ArgumentNullException("userName"); 112 | } 113 | 114 | if (serviceId == null) 115 | { 116 | throw new ArgumentNullException("serviceId"); 117 | } 118 | 119 | // Querying is case sesitive - we don't want that. 120 | username = username.ToLower(); 121 | serviceId = serviceId.ToLower(); 122 | 123 | SecStatusCode code; 124 | // Query the record. 125 | SecRecord queryRec = new SecRecord(SecKind.GenericPassword) { Service = serviceId, Label = serviceId, Account = username, Synchronizable = synchronizable }; 126 | queryRec = SecKeyChain.QueryAsRecord(queryRec, out code); 127 | 128 | // If found, try to get password. 129 | if (code == SecStatusCode.Success && queryRec != null && queryRec.Generic != null) 130 | { 131 | // Decode from UTF8. 132 | return NSString.FromData(queryRec.Generic, NSStringEncoding.UTF8); 133 | } 134 | 135 | // Something went wrong. 136 | return null; 137 | } 138 | } 139 | } 140 | 141 | -------------------------------------------------------------------------------- /Info.plist: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | CFBundleDisplayName 6 | SecureMyApp 7 | CFBundleIdentifier 8 | com.xamarin.securemyapp 9 | CFBundleShortVersionString 10 | 1.0 11 | CFBundleVersion 12 | 1.0 13 | LSRequiresIPhoneOS 14 | 15 | MinimumOSVersion 16 | 8.4 17 | UIDeviceFamily 18 | 19 | 1 20 | 21 | UILaunchStoryboardName 22 | LaunchScreen 23 | UIMainStoryboardFile 24 | Main 25 | UIRequiredDeviceCapabilities 26 | 27 | armv7 28 | 29 | UISupportedInterfaceOrientations 30 | 31 | UIInterfaceOrientationPortrait 32 | UIInterfaceOrientationLandscapeLeft 33 | UIInterfaceOrientationLandscapeRight 34 | 35 | XSAppIconAssets 36 | Resources/Images.xcassets/AppIcons.appiconset 37 | 38 | 39 | -------------------------------------------------------------------------------- /LICENSE.txt: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2015 Mike James 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /Main.cs: -------------------------------------------------------------------------------- 1 | using UIKit; 2 | 3 | namespace SecureMyApp 4 | { 5 | public class Application 6 | { 7 | // This is the main entry point of the application. 8 | static void Main(string[] args) 9 | { 10 | // if you want to use a different Application Delegate class from "AppDelegate" 11 | // you can specify it here. 12 | UIApplication.Main(args, null, "AppDelegate"); 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /Main.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 47 | 60 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # SecureMyApp 2 | Xamarin.iOS local authentication using Keychain & Touch ID 3 | 4 | ![screenshot](http://micjames.co.uk/wp-content/uploads/2015/08/Screen-Shot-2015-08-17-at-16.55.22.png) 5 | 6 | ## Why? 7 | 8 | Securing your app doesn't always require a backend service and iOS gives you a number of options to authenticate users locally. 9 | 10 | ## Features 11 | 12 | * Keychain 13 | * Touch ID 14 | 15 | ### Coming later 16 | 17 | * 1Password extension support 18 | 19 | -------------------------------------------------------------------------------- /Resources/Images.xcassets/AppIcons.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images": [ 3 | { 4 | "size": "29x29", 5 | "scale": "1x", 6 | "idiom": "iphone" 7 | }, 8 | { 9 | "size": "29x29", 10 | "scale": "2x", 11 | "idiom": "iphone" 12 | }, 13 | { 14 | "size": "29x29", 15 | "scale": "3x", 16 | "idiom": "iphone" 17 | }, 18 | { 19 | "size": "40x40", 20 | "scale": "2x", 21 | "idiom": "iphone" 22 | }, 23 | { 24 | "size": "40x40", 25 | "scale": "3x", 26 | "idiom": "iphone" 27 | }, 28 | { 29 | "size": "57x57", 30 | "scale": "1x", 31 | "idiom": "iphone" 32 | }, 33 | { 34 | "size": "57x57", 35 | "scale": "2x", 36 | "idiom": "iphone" 37 | }, 38 | { 39 | "size": "60x60", 40 | "scale": "2x", 41 | "idiom": "iphone" 42 | }, 43 | { 44 | "size": "60x60", 45 | "scale": "3x", 46 | "idiom": "iphone" 47 | }, 48 | { 49 | "size": "29x29", 50 | "scale": "1x", 51 | "idiom": "ipad" 52 | }, 53 | { 54 | "size": "29x29", 55 | "scale": "2x", 56 | "idiom": "ipad" 57 | }, 58 | { 59 | "size": "40x40", 60 | "scale": "1x", 61 | "idiom": "ipad" 62 | }, 63 | { 64 | "size": "40x40", 65 | "scale": "2x", 66 | "idiom": "ipad" 67 | }, 68 | { 69 | "size": "50x50", 70 | "scale": "1x", 71 | "idiom": "ipad" 72 | }, 73 | { 74 | "size": "50x50", 75 | "scale": "2x", 76 | "idiom": "ipad" 77 | }, 78 | { 79 | "size": "72x72", 80 | "scale": "1x", 81 | "idiom": "ipad" 82 | }, 83 | { 84 | "size": "72x72", 85 | "scale": "2x", 86 | "idiom": "ipad" 87 | }, 88 | { 89 | "size": "76x76", 90 | "scale": "1x", 91 | "idiom": "ipad" 92 | }, 93 | { 94 | "size": "76x76", 95 | "scale": "2x", 96 | "idiom": "ipad" 97 | }, 98 | { 99 | "size": "120x120", 100 | "scale": "1x", 101 | "idiom": "car" 102 | } 103 | ], 104 | "info": { 105 | "version": 1, 106 | "author": "xcode" 107 | } 108 | } -------------------------------------------------------------------------------- /Resources/LaunchScreen.xib: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 21 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | -------------------------------------------------------------------------------- /Resources/Touch_ID-512.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MikeCodesDotNET/SecureMyApp/91ed4518285fa4ab37fd5ca95f44a4b14ae8df04/Resources/Touch_ID-512.png -------------------------------------------------------------------------------- /SecureMyApp.csproj: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Debug 5 | iPhoneSimulator 6 | {FEACFBD2-3405-455C-9665-78FE426C6842};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} 7 | {1C55335D-3C6E-432D-B55D-F2AD679B6400} 8 | Exe 9 | SecureMyApp 10 | Resources 11 | SecureMyApp 12 | 13 | 14 | true 15 | full 16 | false 17 | bin\iPhoneSimulator\Debug 18 | DEBUG;ENABLE_TEST_CLOUD; 19 | prompt 20 | 4 21 | false 22 | i386 23 | None 24 | true 25 | true 26 | 27 | 28 | full 29 | true 30 | bin\iPhone\Release 31 | prompt 32 | 4 33 | Entitlements.plist 34 | ARMv7, ARM64 35 | false 36 | iPhone Developer 37 | 38 | 39 | full 40 | true 41 | bin\iPhoneSimulator\Release 42 | prompt 43 | 4 44 | i386 45 | false 46 | None 47 | 48 | 49 | true 50 | full 51 | false 52 | bin\iPhone\Debug 53 | DEBUG;ENABLE_TEST_CLOUD; 54 | prompt 55 | 4 56 | false 57 | ARMv7, ARM64 58 | Entitlements.plist 59 | true 60 | iPhone Developer 61 | true 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | ViewController.cs 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | -------------------------------------------------------------------------------- /SecureMyApp.sln: -------------------------------------------------------------------------------- 1 |  2 | Microsoft Visual Studio Solution File, Format Version 12.00 3 | # Visual Studio 2012 4 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SecureMyApp", "SecureMyApp.csproj", "{1C55335D-3C6E-432D-B55D-F2AD679B6400}" 5 | EndProject 6 | Global 7 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 8 | Debug|iPhoneSimulator = Debug|iPhoneSimulator 9 | Release|iPhone = Release|iPhone 10 | Release|iPhoneSimulator = Release|iPhoneSimulator 11 | Debug|iPhone = Debug|iPhone 12 | Debug|Any CPU = Debug|Any CPU 13 | Release|Any CPU = Release|Any CPU 14 | EndGlobalSection 15 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 16 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Debug|Any CPU.ActiveCfg = Debug|iPhoneSimulator 17 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Debug|Any CPU.Build.0 = Debug|iPhoneSimulator 18 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Debug|iPhone.ActiveCfg = Debug|iPhone 19 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Debug|iPhone.Build.0 = Debug|iPhone 20 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Debug|iPhoneSimulator.ActiveCfg = Debug|iPhoneSimulator 21 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Debug|iPhoneSimulator.Build.0 = Debug|iPhoneSimulator 22 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Release|Any CPU.ActiveCfg = Release|iPhone 23 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Release|Any CPU.Build.0 = Release|iPhone 24 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Release|iPhone.ActiveCfg = Release|iPhone 25 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Release|iPhone.Build.0 = Release|iPhone 26 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Release|iPhoneSimulator.ActiveCfg = Release|iPhoneSimulator 27 | {1C55335D-3C6E-432D-B55D-F2AD679B6400}.Release|iPhoneSimulator.Build.0 = Release|iPhoneSimulator 28 | EndGlobalSection 29 | EndGlobal 30 | -------------------------------------------------------------------------------- /SecureMyApp.userprefs: -------------------------------------------------------------------------------- 1 |  -------------------------------------------------------------------------------- /ViewController.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | 3 | using UIKit; 4 | using Foundation; 5 | using LocalAuthentication; 6 | 7 | namespace SecureMyApp 8 | { 9 | public partial class ViewController : UIViewController 10 | { 11 | 12 | const string serviceId = "MySecureApp"; 13 | NSError error; 14 | LAContext context = new LAContext(); 15 | 16 | public ViewController(IntPtr handle) 17 | : base(handle) 18 | { 19 | } 20 | 21 | public override void ViewDidLoad() 22 | { 23 | base.ViewDidLoad(); 24 | // Perform any additional setup after loading the view, typically from a nib. 25 | 26 | var hasLogin = NSUserDefaults.StandardUserDefaults.BoolForKey("hasLogin"); 27 | 28 | if (hasLogin) 29 | { 30 | btnSignUp.Hidden = true; 31 | } 32 | else 33 | { 34 | btnLogin.Hidden = true; 35 | btnTouchId.Hidden = true; 36 | } 37 | 38 | var storedUsername = NSUserDefaults.StandardUserDefaults.StringForKey("username"); 39 | if (!string.IsNullOrEmpty(storedUsername)) 40 | tbxUsername.Text = storedUsername; 41 | 42 | 43 | //Setup Touch ID button 44 | btnTouchId.Hidden = true; 45 | if (context.CanEvaluatePolicy(LAPolicy.DeviceOwnerAuthenticationWithBiometrics, out error)) 46 | btnTouchId.Hidden = false; 47 | } 48 | 49 | public override void DidReceiveMemoryWarning() 50 | { 51 | base.DidReceiveMemoryWarning(); 52 | // Release any cached data, images, etc that aren't in use. 53 | } 54 | 55 | async partial void btnLogin_TouchUpInside(UIButton sender) 56 | { 57 | if (string.IsNullOrEmpty(tbxUsername.Text) || string.IsNullOrEmpty(tbxPassword.Text)) 58 | { 59 | var alert = new UIAlertView("Oops!", "You must enter both a username and password", null, "Oops", null); 60 | alert.Show(); 61 | return; 62 | } 63 | 64 | if (CheckLogin(tbxUsername.Text, tbxPassword.Text)) 65 | { 66 | var newVC = new UIViewController(); 67 | await PresentViewControllerAsync(newVC, true); 68 | } 69 | else 70 | { 71 | var alert = new UIAlertView("Login problem", "wrong username", null, "Oops...again", null); 72 | alert.Show(); 73 | } 74 | 75 | } 76 | 77 | partial void btnSignUp_TouchUpInside(UIButton sender) 78 | { 79 | if (string.IsNullOrEmpty(tbxUsername.Text) || string.IsNullOrEmpty(tbxPassword.Text)) 80 | { 81 | var alert = new UIAlertView("Oops!", "You must enter both a username and password", null, "Oops", null); 82 | alert.Show(); 83 | return; 84 | } 85 | 86 | tbxUsername.ResignFirstResponder(); 87 | tbxPassword.ResignFirstResponder(); 88 | 89 | var hasLoginKey = NSUserDefaults.StandardUserDefaults.BoolForKey("hasLogin"); 90 | if (!hasLoginKey) 91 | NSUserDefaults.StandardUserDefaults.SetValueForKey(new NSString(tbxUsername.Text), new NSString("username")); 92 | 93 | Helpers.KeychainHelpers.SetPasswordForUsername(tbxUsername.Text, tbxPassword.Text, serviceId, Security.SecAccessible.Always, true); 94 | NSUserDefaults.StandardUserDefaults.SetBool(true, "hasLogin"); 95 | NSUserDefaults.StandardUserDefaults.Synchronize(); 96 | 97 | var newVC = new UIViewController(); 98 | PresentViewController(newVC, true, null); 99 | } 100 | 101 | bool CheckLogin(string username, string password) 102 | { 103 | if (password == Helpers.KeychainHelpers.GetPasswordForUsername(username, serviceId, true) && username == NSUserDefaults.StandardUserDefaults.ValueForKey(new NSString("username")).ToString()) 104 | return true; 105 | else 106 | { 107 | return false; 108 | } 109 | 110 | } 111 | 112 | partial void btnTouchId_TouchUpInside(UIButton sender) 113 | { 114 | //Lets double check the device supports Touch ID 115 | if (context.CanEvaluatePolicy(LAPolicy.DeviceOwnerAuthenticationWithBiometrics, out error)) 116 | { 117 | var replyHandler = new LAContextReplyHandler((success, error) => 118 | { 119 | InvokeOnMainThread(() => 120 | { 121 | if (success) 122 | { 123 | var newVC = new UIViewController(); 124 | PresentViewController(newVC, true, null); 125 | } 126 | else 127 | { 128 | var alert = new UIAlertView("OOPS!", "Something went wrong.", null, "Oops", null); 129 | alert.Show(); 130 | } 131 | }); 132 | }); 133 | context.EvaluatePolicy(LAPolicy.DeviceOwnerAuthenticationWithBiometrics, "Logging in with Touch ID", replyHandler); 134 | } 135 | else 136 | { 137 | var alert = new UIAlertView("Error", "TouchID not available", null, "BOOO!", null); 138 | alert.Show(); 139 | } 140 | 141 | } 142 | } 143 | } 144 | 145 | -------------------------------------------------------------------------------- /ViewController.designer.cs: -------------------------------------------------------------------------------- 1 | // WARNING 2 | // 3 | // This file has been generated automatically by Xamarin Studio from the outlets and 4 | // actions declared in your storyboard file. 5 | // Manual changes to this file will not be maintained. 6 | // 7 | using Foundation; 8 | using System; 9 | using System.CodeDom.Compiler; 10 | using UIKit; 11 | 12 | namespace SecureMyApp 13 | { 14 | [Register ("ViewController")] 15 | partial class ViewController 16 | { 17 | [Outlet] 18 | [GeneratedCode ("iOS Designer", "1.0")] 19 | UIButton btnLogin { get; set; } 20 | 21 | [Outlet] 22 | [GeneratedCode ("iOS Designer", "1.0")] 23 | UIButton btnSignUp { get; set; } 24 | 25 | [Outlet] 26 | [GeneratedCode ("iOS Designer", "1.0")] 27 | UIButton btnTouchId { get; set; } 28 | 29 | [Outlet] 30 | [GeneratedCode ("iOS Designer", "1.0")] 31 | UITextField tbxPassword { get; set; } 32 | 33 | [Outlet] 34 | [GeneratedCode ("iOS Designer", "1.0")] 35 | UITextField tbxUsername { get; set; } 36 | 37 | [Action ("btnLogin_TouchUpInside:")] 38 | [GeneratedCode ("iOS Designer", "1.0")] 39 | partial void btnLogin_TouchUpInside (UIButton sender); 40 | 41 | [Action ("btnSignUp_TouchUpInside:")] 42 | [GeneratedCode ("iOS Designer", "1.0")] 43 | partial void btnSignUp_TouchUpInside (UIButton sender); 44 | 45 | [Action ("btnTouchId_TouchUpInside:")] 46 | [GeneratedCode ("iOS Designer", "1.0")] 47 | partial void btnTouchId_TouchUpInside (UIButton sender); 48 | 49 | void ReleaseDesignerOutlets () 50 | { 51 | if (btnLogin != null) { 52 | btnLogin.Dispose (); 53 | btnLogin = null; 54 | } 55 | if (btnSignUp != null) { 56 | btnSignUp.Dispose (); 57 | btnSignUp = null; 58 | } 59 | if (btnTouchId != null) { 60 | btnTouchId.Dispose (); 61 | btnTouchId = null; 62 | } 63 | if (tbxPassword != null) { 64 | tbxPassword.Dispose (); 65 | tbxPassword = null; 66 | } 67 | if (tbxUsername != null) { 68 | tbxUsername.Dispose (); 69 | tbxUsername = null; 70 | } 71 | } 72 | } 73 | } 74 | -------------------------------------------------------------------------------- /packages/NUnit.2.6.3/license.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MikeCodesDotNET/SecureMyApp/91ed4518285fa4ab37fd5ca95f44a4b14ae8df04/packages/NUnit.2.6.3/license.txt -------------------------------------------------------------------------------- /packages/Xamarin.UITest.0.7.1/Xamarin.UITest-License.rtf: -------------------------------------------------------------------------------- 1 | {\rtf1\ansi\ansicpg1252\cocoartf1265\cocoasubrtf210 2 | {\fonttbl\f0\fswiss\fcharset0 ArialMT;\f1\froman\fcharset0 TimesNewRomanPSMT;} 3 | {\colortbl;\red255\green255\blue255;\red0\green0\blue255;} 4 | {\info 5 | {\author Joseph Hill} 6 | {\*\company Orrick}}\vieww21420\viewh16600\viewkind1\viewscale200 7 | \deftab709 8 | \pard\pardeftab709\ri0\qr 9 | 10 | \f0\b\fs20 \cf0 \ 11 | \pard\pardeftab709\ri0 12 | \cf0 Xamarin.UITest\ 13 | Xamarin\'99 Software License Agreement\ 14 | \ 15 | \pard\pardeftab709\ri0\qj 16 | 17 | \fs16 \cf0 PLEASE READ THIS AGREEMENT CAREFULLY. BY INSTALLING, DOWNLOADING OR OTHERWISE USING THE SOFTWARE (INCLUDING ITS COMPONENTS), YOU AGREE TO THE TERMS OF THIS AGREEMENT. IF YOU DO NOT AGREE WITH THESE TERMS, DO NOT DOWNLOAD, INSTALL OR USE THE SOFTWARE. \ 18 | \ 19 | 1. RIGHTS AND LICENSES\ 20 | \ 21 | \pard\tx720\pardeftab709\ri0\qj 22 | 23 | \b0 \cf0 1.1. This Xamarin Software License Agreement (\'93Agreement\'94) is a legal agreement between You (an entity or a person) and Xamarin Inc. (\'93Xamarin\'94). The software product identified in the title of this Agreement, any media and accompanying documentation (collectively the \'93Software\'94) is protected by the copyright laws and treaties of the United States (\'93U.S.\'94) and other countries and is subject to the terms of this Agreement. Any update or support release to the Software that You may download or receive that is not accompanied by a license agreement expressly superseding this Agreement is Software and governed by this Agreement. If the Software is an update or support release, then You must have validly licensed the version and quantity of the Software being updated or supported in order to install or use the update or support release. If Software You download or receive hereunder is an update or support release for a prior version of Xamarin.UITest software You had that was subject to the terms of a prior Xamarin software license agreement that differs from this Agreement and may apply to such Software You download or receive hereunder, then this Agreement supersedes such prior license agreement but only with respect to such Software downloaded or received hereunder.\ 24 | \ 25 | \pard\pardeftab709\ri0\qj 26 | \cf0 1.2. \ul Components; Other License Terms.\ulnone The Software may be comprised of numerous components that may be accompanied by separate license terms. In that case, the Software is a collective work of Xamarin; although Xamarin may not own the copyright to every component of the Software, Xamarin owns the collective work copyright for the Software.\ 27 | \ 28 | Some of the components may be open source packages, developed independently, and accompanied by separate license terms. Your license rights with respect to any individual components accompanied by separate license terms are defined by those terms; nothing in this agreement shall restrict, limit, or otherwise affect any rights or obligations You may have, or conditions to which You may be subject, under such license terms.\ 29 | \ 30 | 1.3. \ul Instances.\ulnone "Instance" means the initial copy of the Software necessary for use of the Software, and each additional copy (or partial copy) of the Software stored or loaded in memory or virtual memory. \ 31 | \ 32 | 1.4. \ul Software License Grant.\ulnone Subject to the terms and conditions of this Agreement, Xamarin hereby grants to You a world-wide, nonexclusive, non-transferable license to internally use the Software, during the term of this Agreement.\ 33 | \pard\pardeftab709\ri0 34 | \cf0 \ 35 | 1.5. 36 | \b 37 | \b0 \ul Other License Terms and Restrictions 38 | \b \ulnone .\ 39 | \pard\pardeftab709\ri0\qj 40 | 41 | \b0 \cf0 \ 42 | The Software is protected by the copyright laws and treaties of the United States ("U.S.") and other countries and is subject to the terms of this Agreement. The Software is licensed to You, not sold.\ 43 | \ 44 | The Software may be bundled with other software programs ("Bundled Programs"). Your license rights with respect to Bundled Programs accompanied by separate license terms are defined by those terms; nothing in this Agreement shall restrict, limit, or otherwise affect any rights or obligations You may have, or conditions to which You may be subject, under such license terms.\'a0 \ 45 | \pard\pardeftab709\ri0 46 | \cf0 \ 47 | Xamarin reserves all rights not expressly granted to You. You may not: \ 48 | (1) reverse engineer, decompile, or disassemble any Software provided that to the extent the foregoing prohibitions are expressly prohibited by applicable statutory law, Xamarin shall retain the maximum protection available against reverse engineering, decompiling, or disassembly under applicable law; \ 49 | (2) assign, sublicense, distribute, or otherwise transfer any Software to any third party (without limitation, this prohibits You from (a) bundling any Software (including any Xamarin tools, libraries, or runtime) into a competing platform and (b) distributing Xamarin tools, libraries, or runtimes as library, source project, or other unfinished work;\ 50 | (3) reproduce any Software; \ 51 | (4) create derivative works of, modify, adapt or translate any Software; \ 52 | (5) use any Software to provide services for any third party; \ 53 | (6) lease, rent, loan, share or otherwise use, or permit use of, any Software by or for any third party; \ 54 | (7) remove any proprietary notices on or in any Software; \ 55 | (8) use any Software in a manner not in accordance with its documentation; or\ 56 | (9) use any Software in an illegal or fraudulent manner.\ 57 | \pard\pardeftab709\ri0\qj 58 | \cf0 \ 59 | 1.6. \ul Evaluation Software 60 | \b \ulnone . 61 | \b0 If the Software is an evaluation version or is provided to You for evaluation purposes, then Your license to use the Software is limited solely to internal evaluation purposes and in accordance with the terms of the evaluation offering under which You received the Software, including any limited evaluation period that may apply (which may also be indicated within the Software). Upon expiration of the evaluation period, You must discontinue use of the Software, return to an original state any actions performed by the Software, and delete the Software entirely from Your system. The Software may contain an automatic disabling mechanism that prevents its use after a certain period of time, so You should back up Your system and take other measures to prevent any loss of files or data. Without limiting the above, You may not use Evaluation Software to create an App.\ 62 | \ 63 | \pard\pardeftab709\ri0\qj 64 | 65 | \b \cf0 2. MAINTENANCE AND SUPPORT\ 66 | \pard\pardeftab709\ri0 67 | 68 | \b0 \cf0 \ 69 | \pard\pardeftab709\ri0\qj 70 | \cf0 Xamarin has no obligation to provide support or maintenance for the Software. If Xamarin does provide any such support or maintenance and no separate agreement specifically applies to such support or maintenance, then the terms of this Agreement will govern the provision of such support or maintenance services (\'93Services\'93) and Xamarin may cease Services, in whole or part, at any time. For more information on Xamarin's current support offerings, see {\field{\*\fldinst{HYPERLINK "http://support.xamarin.com"}}{\fldrslt \cf2 \ul \ulc2 http://support.xamarin.com}}. 71 | \b \ 72 | \ 73 | 3. OWNERSHIP \ 74 | 75 | \b0 \ 76 | No title to or ownership of the Software is transferred to You. Xamarin and/or its licensors retain all right, title and interest in and to all intellectual property rights in the Software and Services, including any adaptations or copies thereof. You acquire only a conditional license to use the Software.\ 77 | \ 78 | \pard\pardeftab709\ri0\qj 79 | 80 | \b \cf0 4. WARRANTY DISCLAIMER\ 81 | \pard\pardeftab709\ri0\qj 82 | 83 | \b0 \cf0 \ 84 | 4.1. \ul Software.\ulnone THE SOFTWARE IS PROVIDED \'93AS IS\'94 WITHOUT ANY WARRANTIES OF ANY KIND.\ 85 | \ 86 | THE SOFTWARE IS NOT DESIGNED, MANUFACTURED OR INTENDED FOR USE OR DISTRIBUTION WITH ON-LINE CONTROL EQUIPMENT IN HAZARDOUS ENVIRONMENTS REQUIRING FAIL-SAFE PERFORMANCE, SUCH AS IN THE OPERATION OF NUCLEAR FACILITIES, AIRCRAFT NAVIGATION, COMMUNICATION, OR CONTROL SYSTEMS, DIRECT LIFE SUPPORT MACHINES, WEAPONS SYSTEMS, OR OTHER USES IN WHICH FAILURE OF THE SOFTWARE COULD LEAD DIRECTLY TO DEATH, PERSONAL INJURY, OR SEVERE PHYSICAL OR ENVIRONMENTAL DAMAGE.\ 87 | \ 88 | THE SOFTWARE IS ONLY COMPATIBLE WITH CERTAIN COMPUTERS AND OPERATING SYSTEMS. Call Xamarin or Your reseller for information about compatibility.\ 89 | \ 90 | 4.2. \ul Services\ulnone . THE SERVICES (IF ANY) ARE PROVIDED \'93AS IS\'94 WITHOUT ANY WARRANTIES OF ANY KIND. As files may be altered or damaged in the course of Xamarin providing technical services, You agree to take appropriate measures to isolate and back up Your systems.\ 91 | \ 92 | 4.3. \ul Non-Xamarin Products\ulnone . The Software may include or be bundled with hardware or other software programs or services licensed or sold by an entity other than Xamarin. XAMARIN DOES NOT WARRANT NON-XAMARIN PRODUCTS OR SERVICES. ANY SUCH PRODUCTS OR SERVICES ARE PROVIDED ON AN \'93AS IS\'94 BASIS. WARRANTY SERVICE IF ANY FOR NON-XAMARIN PRODUCTS IS PROVIDED BY THE PRODUCT LICENSOR IN ACCORDANCE WITH THE APPLICABLE LICENSOR WARRANTY.\ 93 | \ 94 | 4.4. \ul General Disclaimer\ulnone . EXCEPT AS OTHERWISE RESTRICTED BY LAW, XAMARIN DISCLAIMS AND EXCLUDES ANY AND ALL IMPLIED WARRANTIES, INCLUDING ANY WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, TITLE OR NON-INFRINGEMENT. XAMARIN MAKES NO WARRANTIES, REPRESENTATIONS OR PROMISES. XAMARIN DOES NOT WARRANT THAT THE SOFTWARE OR SERVICES WILL SATISFY YOUR REQUIREMENTS OR THAT THE OPERATION OF THE SOFTWARE OR SERVICES WILL BE UNINTERRUPTED. Some jurisdictions do not allow certain disclaimers and limitations of warranties, so portions of the above limitations may not apply to You. You may also have other rights which vary by state or jurisdiction. \ 95 | \ 96 | \pard\pardeftab709\ri0\qj 97 | 98 | \b \cf0 5. LIMITATION OF LIABILITY\ 99 | \pard\pardeftab709\ri0\qj 100 | 101 | \b0 \cf0 \ 102 | 5.1. \ul Consequential Losses\ulnone . NEITHER XAMARIN NOR ANY OF ITS LICENSORS, SUBSIDIARIES, OR EMPLOYEES WILL IN ANY CASE BE LIABLE FOR ANY SPECIAL, INCIDENTAL, CONSEQUENTIAL, INDIRECT, TORT, ECONOMIC OR PUNITIVE DAMAGES ARISING OUT OF OR RELATING TO THIS AGREEMENT OR THE USE OF OR INABILITY TO USE THE SOFTWARE OR SERVICES, INCLUDING LOSS OF PROFITS, BUSINESS OR DATA, EVEN IF ADVISED OF THE POSSIBILITY OF THOSE DAMAGES.\ 103 | \ 104 | 5.2. \ul Direct Damages\ulnone . IN NO EVENT WILL XAMARIN'S AGGREGATE LIABILITY FOR DIRECT DAMAGES ARISING OUT OF OR RELATING TO THIS AGREEMENT OR THE USE OF OR INABILITY TO USE THE SOFTWARE OR SERVICES (WHETHER IN ONE INSTANCE OR A SERIES OF INSTANCES) EXCEED FIFTY UNITED STATES DOLLARS ($50 (U.S.)). \ 105 | \ 106 | 5.3. \ul Exclusions\ulnone . The above exclusions and limitations will not apply to claims relating to death or personal injury. In those jurisdictions that do not allow the exclusion or limitation of damages, Xamarin's liability shall be limited or excluded to the maximum extent allowed within those jurisdictions.\ 107 | \ 108 | \pard\pardeftab709\ri0\qj 109 | 110 | \b \cf0 6. GENERAL TERMS\ 111 | \pard\pardeftab709\ri0\qj 112 | 113 | \b0 \cf0 \ 114 | 6.1. \ul Term\ulnone . This Agreement becomes effective on the date You legally acquire the Software and will automatically terminate on Your breach any of the terms of this Agreement. \ul \ 115 | \ulnone 6.2. \ul Benchmark Testing\ulnone . This benchmark testing restriction applies to You if You are a software developer or licensor or if You are performing testing on the Software at the direction of or on behalf of a software developer or licensor. You may not, without Xamarin's prior written consent not to be unreasonably withheld, publish or disclose to any third party the results of any benchmark test of the Software. If You are a licensor of products that are functionally similar to or compete with the Software (\'93Similar Products\'94), or are acting on behalf of such a licensor, and You publish or disclose benchmark information on the Software in violation of this restriction, then notwithstanding anything to the contrary in the Similar Product's end user license agreement, and in addition to any other remedies Xamarin may have, Xamarin shall have the right to perform benchmark testing on Similar Products and to disclose and publish that benchmark information and You hereby represent that You have authority to grant such right to Xamarin.\ 116 | 6.3. \ul Open Source\ulnone . Nothing in this Agreement shall restrict, limit or otherwise affect any rights or obligations You may have, or conditions to which You may be subject, under any applicable open source licenses to any open source code contained in the Software. \ 117 | 6.4. \ul Assignment; Transfer\ulnone . Neither this Agreement, nor any rights or obligations hereunder, may be transferred, assigned or delegated without the prior written approval of Xamarin. Any such transfer, assignment or delegation made in contravention of this paragraph shall be null and void.\ 118 | 6.5. \ul Law and Jurisdiction\ulnone . This Agreement is and will be governed by and construed under the laws of the State of California, U.S., without giving effect to any conflicts of laws provision thereof or of any other jurisdiction that would produce a contrary result. Any action arising out of or relating to this Agreement may be brought before the courts of competent jurisdiction of the State of California, U.S., and You consent to the jurisdiction of such courts and waive any objections of improper venue or inconvenient forum. You consent to service of process by mail, nationally-recognized courier service, fax or email, to the contact information you provided to Xamarin at the time of your acquisition of the Software or thereafter. \ 119 | 6.6. \ul Entire Agreement\ulnone . This Agreement sets forth the entire understanding and agreement between You and Xamarin and may be amended or modified only by a written agreement agreed to by You and an authorized representative of Xamarin. NO LICENSOR, DISTRIBUTOR, DEALER, RETAILER, RESELLER, SALES PERSON, OR EMPLOYEE IS AUTHORIZED TO MODIFY THIS AGREEMENT OR TO MAKE ANY REPRESENTATION OR PROMISE THAT IS DIFFERENT FROM, OR IN ADDITION TO, THE TERMS OF THIS AGREEMENT. \ 120 | 6.7. \ul Waiver\ulnone . No waiver of any right under this Agreement will be effective unless in writing, signed by a duly authorized representative of the party to be bound. No waiver of any past or present right arising from any breach or failure to perform will be deemed to be a waiver of any future right arising under this Agreement.\ 121 | 6.8. \ul Severability\ulnone . If any provision in this Agreement is invalid or unenforceable, that provision will be construed, limited, modified or, if necessary, severed, to the extent necessary, to eliminate its invalidity or unenforceability, and the other provisions of this Agreement will remain unaffected. \ 122 | 6.9. \ul Export Compliance\ulnone . Any Software or technical information received under this Agreement (collectively, \'93Received Items\'94) may be subject to U.S. export controls and the trade laws of other countries. You agree to comply with all applicable export control regulations and to obtain any required licenses or classification to export, re-export or import Received Items. You may not use or otherwise export or re-export the Received Items except as authorized by U.S. law and the law of each jurisdiction that applies to Your activities. Without limiting the foregoing, You agree not to export or re-export any Received Items to (a) entities or persons on the then-current U.S. Treasury Department's list of Specially Designated Nationals, the then-current U.S. Department of Commerce Denied Person\'92s List or Entity List, or any other U.S. export exclusion list that is then applicable or (b) any embargoed or terrorist country as specified in the U.S. export laws. By installing, downloading or otherwise using the Received Items, You represent and warrant that You are not located in any such embargoed or terrorist country or on any such exclusion list. In addition, You agree not to use any Received Items for any purposes prohibited by United States law, including the development, design, manufacture or production of nuclear, missile, or chemical or biological weapons. Upon request, Xamarin will provide You specific information regarding applicable restrictions. However, Xamarin assumes no responsibility for Your failure to obtain any necessary export approvals.\ul \ 123 | \ulnone 6.10. \ul U.S. Government Restricted Rights\ulnone . Use, duplication, or disclosure by the U.S. Government is subject to the restrictions in FAR 52.227-14 (June 1987) Alternate III (June 1987), FAR 52.227-19 (June 1987), or DFARS 252.227-7013 (b) (3) (Nov 1995), or applicable successor clauses. Contractor/Manufacturer is Xamarin Inc., 430 Pacific Avenue, San Francisco, CA 94133.\ 124 | 6.11. \ul Headings; Interpretation.\ulnone Headings are provided for convenience only and will not be used to interpret the substance of this Agreement. The use of \'93include,\'94 \'93includes,\'94 or \'93including\'94 herein will be read as if followed by the phrase \'93without limitation.\'94\ 125 | 6.12. \ul Trademarks\ulnone . Nothing in this Agreement shall be construed as conferring any right to You to use any name, logo, or other trademark of Xamarin, its affiliates or licensors.\ 126 | 6.13. \ul Other\ulnone . The application of the United Nations Convention of Contracts for the International Sale of Goods is expressly excluded.\ 127 | \ 128 | \'a9 2014 Xamarin Inc. All Rights Reserved.\ 129 | \ 130 | Xamarin is a trademark of Xamarin Inc. in the United States and other countries. \ 131 | \pard\pardeftab709\ri0\qj 132 | 133 | \f1\fs24 \cf0 \ 134 | \pard\pardeftab709\ri0\qj 135 | 136 | \f0\fs18 \cf0 20140512 137 | \f1\fs24 \ 138 | } -------------------------------------------------------------------------------- /packages/Xamarin.UITest.0.7.1/tools/test-cloud.exe: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MikeCodesDotNET/SecureMyApp/91ed4518285fa4ab37fd5ca95f44a4b14ae8df04/packages/Xamarin.UITest.0.7.1/tools/test-cloud.exe -------------------------------------------------------------------------------- /packages/repositories.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | --------------------------------------------------------------------------------