98

I'm trying to check if the a user default exists, seen below:

func userAlreadyExist() -> Bool {
    var userDefaults : NSUserDefaults = NSUserDefaults.standardUserDefaults()

    if userDefaults.objectForKey(kUSERID) {
        return true
    }

    return false
}

However, no mater what it will always return true even when the object doesn't exist yet? Is this the right way for checking existence ?

FelixSFD
  • 6,052
  • 10
  • 43
  • 117
Fudgey
  • 3,793
  • 7
  • 32
  • 53

10 Answers10

152

Astun has a great answer. See below for the Swift 3 version.

func isKeyPresentInUserDefaults(key: String) -> Bool {
    return UserDefaults.standard.object(forKey: key) != nil
}
Prajeet Shrestha
  • 7,978
  • 3
  • 34
  • 63
user7248923
  • 1,556
  • 1
  • 9
  • 2
38

I copy/pasted your code but Xcode 6.1.1 was throwing some errors my way, it ended up looking like this and it works like a charm. Thanks!

func userAlreadyExist(kUsernameKey: String) -> Bool {
    return NSUserDefaults.standardUserDefaults().objectForKey(kUsernameKey) != nil
}

Swift 5:

if UserDefaults.standard.object(forKey: "keyName") != nil {
  //Key exists
}
papesky
  • 637
  • 1
  • 8
  • 20
Astun
  • 481
  • 4
  • 3
21

Yes this is right way to check the optional have nil or any value objectForKey method returns AnyObject? which is Implicit optional.

So if userDefaults.objectForKey(kUSERID) have any value than it evaluates to true. if userDefaults.objectForKey(kUSERID) has nil value than it evaluates to false.

From swift programming guide

If Statements and Forced Unwrapping You can use an if statement to find out whether an optional contains a value. If an optional does have a value, it evaluates to true; if it has no value at all, it evaluates to false.

Now there is a bug in simulators than after setting key in userDefaults they always remain set no matter you delete your app.You need to reset simulator.

Reset your Simulator check this method before setting key in userDefaults or remove key userDefaults.removeObjectForKey(kUSERID) from userDefaults and it will return NO.On devices it is resolved in iOS8 beta4.

codester
  • 36,891
  • 10
  • 74
  • 72
  • " `objectForKey` method returns `AnyObject!` which is Implicit optional " This is wrong it returns `AnyObject?` – Leo Dabus Jan 07 '16 at 17:32
  • 1
    @LeoDabus Swift has changed so many times. Thanks BTW I have changed that. – codester Jan 08 '16 at 06:41
  • as of 10/25/2016 the line in the docs now say "You can use an if statement to find out whether an optional contains a value by comparing the optional against nil. You perform this comparison with the “equal to” operator (==) or the “not equal to” operator (!=)." Xcode 7.3.1 will show a compilation error if you try to `if anOptional { }` and it will suggest you test using == nil or != nil – wyu Oct 25 '16 at 16:00
17

This is essentially the same as suggested in other answers but in a more convenient way (Swift 3+):

extension UserDefaults {
    static func contains(_ key: String) -> Bool {
        return UserDefaults.standard.object(forKey: key) != nil
    }
}

usage: if UserDefaults.contains(kUSERID) { ... }

Nomad Developer
  • 473
  • 4
  • 14
Sir Codesalot
  • 7,045
  • 2
  • 50
  • 56
  • then it makes sense to make the function static because you're accessing a singleton _standard_: `static func contains(key: String) -> Bool`. Otherwise, makes more sense to make `return self.object(forKey: key) != nil` – Nomad Developer Feb 16 '20 at 06:21
6

Simple Code to check whether value stored in UserDefault.

let userdefaults = UserDefaults.standard
if let savedValue = userdefaults.string(forKey: "key"){
   print("Here you will get saved value")       
} else {
   print("No value in Userdefault,Either you can save value here or perform other operation")
   userdefaults.set("Here you can save value", forKey: "key")
}
Sudhi 9135
  • 745
  • 8
  • 17
6

Many of the solutions here are valid. Still, I think they solve the wrong problem.

Usually, code like this is used to check if a value is set so another default value can be used:

if isKeyPresentInUserDefaults(key: "username") {
    return UserDefaults.standard.string(forKey: "username")
} else {
    return "No username was set"
}

You shouldn't care if a key is set or not. There is a far more elegant approach for having default values in UserDefaults:

UserDefault.standard.register(defaults: ["username": "No username was set"])

If you run this code at app launch, subsequent calls to UserDefaults.standard.string(forKey: "username") will return the default value of "No username was set" if no value was set for the key yet.

Xavier Lowmiller
  • 1,381
  • 1
  • 15
  • 24
  • 1
    Plus, be aware of this: "The contents of the registration domain are not written to disk; you need to call this method each time your application starts." – klados Feb 08 '22 at 07:34
2

for swift 3.2

func userAlreadyExist(kUsernameKey: String) -> Bool {
    return UserDefaults.standard.object(forKey: kUsernameKey) != nil
}
Johny D Good
  • 427
  • 1
  • 8
  • 26
0
public class PreferencesUtils {

    private init() {

    }

    public static func setBoolData(boolValue: Bool, dataName: String) {
        UserDefaults.standard.set(boolValue, forKey: dataName)
    }

    public static func getBoolData(dataName: String)-> Bool{

        let defaults = UserDefaults.standard

        if(defaults.value(forKey: dataName) != nil) {
            return defaults.value(forKey: dataName)! as! Bool

        } else {
            return false
        }
    }

    public static func saveStringData(data: String, dataName: String){
        let preferences = UserDefaults.standard
        preferences.set(data, forKey: dataName)
        let didSave = preferences.synchronize()
        if !didSave {
            debugPrint("Not saved yet")
        }
    }

    public static func getSavedStringData(dataName: String)-> String{
        let defaults = UserDefaults.standard
        if(defaults.value(forKey: dataName) != nil){
            return defaults.value(forKey: dataName) as! String
        } else {
            return ""
        }
    }

    public static func saveIntData(data : Int, dataName: String){
        let preferences = UserDefaults.standard
        preferences.set(data, forKey: dataName)
        let didSave = preferences.synchronize()
        if !didSave {
            debugPrint("Not saved yet")
        }
    }

    public static func getSavedIntData(dataName: String) -> Int {
        let defaults = UserDefaults.standard
        if(defaults.value(forKey: dataName) != nil){
            return defaults.value(forKey: dataName) as! Int
        }else{
            return 0
        }
    }

}

Or you can try this library: Link

Jamil Hasnine Tamim
  • 4,389
  • 27
  • 43
0
func keyExists(key: String) -> Bool {
    guard let _ = UserDefaults.standard.object(forKey: key) {
     return false;
    }

   return true;
}
Andrea Leganza
  • 447
  • 7
  • 7
  • Please don't post only code as answer, but also provide an explanation what your code does and how it answers the question. Answers with an explanation are usually more helpful and of better quality, and are more likely to attract upvotes. – Mark Rotteveel May 03 '20 at 07:45
-1
    override func viewDidLoad(){
    super.viewDidLoad()
    if  UserDefaults.standard.string(forKey: "CHARRY") == "CHARRY"{
        print("true")
    }else{
        print("false")
    }
}
M Hamayun zeb
  • 448
  • 4
  • 10