swift 4 / firebase Super Simple read / write. Can't read - ios

Super newbie! I just want to practice reading and writing for Firebase. My write code works! I've consulted dozens of examples online and still can't get the read portion working.
As a newbie, I've also tried some simple debug techniques but no help.
Exactly how do I fix this code so that the read happens (and I know it happened because the code prints to terminal)?
I'd really like a Swift 4 based solution, thanks.
My repo
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
var ref:DatabaseReference!
var refHandle:DatabaseHandle!
ref = Database.database().reference()
ref.child("test").setValue("name: Bruce")
//Nothing below works
refHandle = ref.child("test").observe(DataEventType.childAdded, with: { (snapshot) in
let info = snapshot.value as? String
print(info as Any)
})
}
Note that my Firebase DB is enabled for READ and WRITE. I have also tried observeSingleInsance (or whatever it is when you read just once).
I know the write works because i can see the data in the Firebase console

I believe your problem is in setValue("name: Bruce"), where you set the node "test" to "name: Bruce", as opposed to "name": "Bruce"
if you change that to say
updateChildValues(["name": "Bruce"])
surely it would work.

Go to your Firebase console, and perform following steps which is identify in image.

Read like that as you currently trying to listen to child add , so replace childAdded with value , Also you should wait until write process happens and then read , suppose launch app again for read only
refHandle = ref.child("test").observeSingleEvent(of: .value, with: { (snapshot) in
let info = snapshot.value as? String
print(info as Any)
})

Do you have this enabled? Then try changing it to
Database.database().isPersistenceEnabled = false
Otherwise try this and print the snapshot you get (You don't actually need the handle):
ref.child("test").observe(.value, with: { (snapshot) in
print(snapshot)
})

Related

Retrieving user info from firebase

I know this question is asked a lot, but none of the solutions seem to be working for me(I have been trying multiple solutions from threads like Read data from firebase swift but it doesnt print anything to my console).
I am trying to retrieve the type of user from my database, but I dont know how to.
func pushUserInfo(){
let ref = Database.database().reference()
let infoDict = ["First name": firstName.text!, "Last name": lastName.text!, "hours": 0, "isUser" : "user"] as [String : Any]
let users = ref.child("users").child(username)
users.setValue(infoDict)
}
The part that says ["type": "user"] has two options, either "user" or admin
The screenshot above is of the Firebase realtime database.
I am trying to retrieve the type of the user, but I have no idea how. Please help me figure this out, and if possible, explain the code, because I dont really understand too much about Firebase in general. I tried reading their firebase docs, but I still dont really get it.
It looks like you're setting the data fine except that your username property appears to be a concatenated string of two optionals (maybe firstName.text and lastName.text. So this will make it impossible to query. The first step is to unwrap these into a string:
let username = "\(firstName.text!) \(lastName.text!)"
Once you've done that, you can query for that data like this:
let username = "\(firstName.text!) \(lastName.text!)"
let ref = Database.database().reference().child("users/\(username)")
ref.observeSingleEvent(of: .value, with: { (snapshot) in
// Now you can access the type value
let value = snapshot.value as? NSDictionary
let type = value?["type"] as? String ?? ""
}) { (error) in
print(error.localizedDescription)
}
You may also want to reconsider having spaces in your property names (maybe use lastName instead of last name). It will be easier for your code later on.

How to get child from Firebase nodes?

I've been following this chat app tutorial with Swift, but now I want to be able to remove a post/message, so I want to be able to get to the specific child node to remove it, I've been trying like crazy a lot of things but nothing seems to work, I want to think I'm on the right path but I'm not pretty sure since I'm pretty new at coding.
I already got the Message Id, but in order to remove it I need to access to its parent.
#IBAction func buttonmessage(_ sender: Any) {
let feedMessageRef = Database.database().reference().child("feedMessages")
print(feedMessageRef)
}
})
That's pretty much my code, I can access the feedMessages node, but I can't access the next node. And this is how my firebase structure looks like. I want to be able to get the "-5440543187537959509", and somehow delete it.
feedMessages
-5440543187537959509
-LnmwFyZeTYbqLJgH6uf
date: 1567443980.238851
from:"N3gVh9oXhPcrxeJzPWGjtqB0ka42"
read: true
text: "Testing with mando"
to: "2LGYNCH4rFMJnKv3nQnvjcLyLhv1"
-LnmwIQg6WeVAHxrWt0x
date: 1567443990.295638
from: "N3gVh9oXhPcrxeJzPWGjtqB0ka42"
read: true
text: "Huh?"
to: "2LGYNCH4rFMJnKv3nQnvjcLyLhv1"
Ok, so I got this from reading the documentation and other Stack Overflow posts., now my code looks like this.
#IBAction func buttonmessage(_ sender: Any) {
let feedMessagesRef = Database.database().reference().child("feedMessages").observe(.value) { (snapshot) in
for childSnap in snapshot.children.allObjects {
let snap = childSnap as! DataSnapshot
print(snap.key)
let changedText = (snap.value as? NSDictionary)?["text"] as? String ?? "ChangedText"
print(changedText)
}
}
}
I managed to print the number that I wanted, which is a node from the firebase, but now I'm stuck on what's the next step to delete a post
Hope you guys can help me please, Thanks a lot!

Traversing a firebase database

Swift 3.x iOS 10.
Trying to understand Databases in firebase. Imported some JSON data into my app and managed to read it back. This the code.
let rootRef = Database.database().reference(withPath: "0")
print("\(rootRef.key)")
let nextRef = rootRef.child("identity")
print("\(nextRef)")
nextRef.observe(.value, with: { snapshot in
print("\(snapshot.value)")
})
Which works, my data looks like this ...
But how to do this if I want to traverse the database, looking at record 2, record 3 etc etc where I am not sure how many records I actually got.
Ok, I found it, well something that works...
let rootRef = Database.database().reference()
rootRef.observe(.value, with: { snapshot in
print("dump \(snapshot.children.allObjects)")
})
I post for posterity :)

Firebase Read to Swift NSArray / or String Swift 3.0

I am working on a project that reads from a Dictionary .plist that is located in the documents directory. I am currently migrating to Firebase. I have the "Write" working to -> Firebase. I also have the "Read" from <- Firebase working. The challenge that I am having is re-formatting the data the way I need it, in order to run it through my RegEx filter. I am not sure what to use to do this, a Parser or what... Just need some direction on the best way to pull the values out from the Firebase data that I read. I have spent about 10 hours trying different ways of formatting the Firebase data, but constantly get errors telling me that I can't change "Any" to "String" or "Any" to "Array". If you have not noticed, I am not a seasoned coder...
I am using Swift 3.0
This is the code that I have. (Note: I have the Firebase SDK installed and this code is just in the viewDidLoad func. for now). Also, I am using an NSObject Class that is outside of my viewDidLoad() for Post.
Thank you
var posts = [Post]()
class Post: NSObject {
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
//This is the code that reads from FireBase
let ref = Database.database().reference().child("List").queryOrderedByValue()
ref.observe(.value, with: { snapshot in
print(snapshot.value ?? "can't print Values")//snapshot.value is what prints out to the console
self.posts = []
if let snapshots = snapshot.children.allObjects as? [DataSnapshot] {
for snap in snapshots {
if let postDict = snap.value as? Dictionary<String, AnyObject> {
let post = Post()
post.setValuesForKeys(postDict)
self.posts.append(post)
}
}
}
})
}
The output of the code in the viewDidLoad() produces this output to the console
{"-KmUr43ZPycmz7G3IBlA" = "Adding something";
"-KmUr6M3F6HSEIAMbaVa" = "This is my next one";
"-KmUr8xe2vDtLMZn84kP" = "Emoji";
"-KmWaviTHnzD_EBatRU8" = "next definition";
"-KmYMTqVXHhanJkkId4r" = "Rich is Cool";}
I would like to pull out the values of the above output two different ways
and that is as an Array / NSMutableArray, and a String / NSMutableString
This is what I would like the Array to look like
["Adding something", "This is my next one", Emoji", "next definition", "Rich is Cool"]
This is what I would like the String to look like
Adding something, This is my next one, Emoji, next definition, Rich is Cool
Thank you so much for taking a look at this

iOS Swift: retrieve an entry from the database for the user currently logged in

How do I retrieve a value (other than username and user id, which seem easier to get) for the current user from the database.
Ironically, I can set the value as follows and that works just fine:
let databaseRef = FIRDatabase.database().reference()
userID = (FIRAuth.auth()?.currentUser?.uid)! as String
databaseRef.child("users").child(userID!).child("TermCond").setValue("Yes")
But for the life of me I cannot work out what to put instead of setValue if I simply want to retrieve the current TermCond value. I thought just using value as for example in
let DesiredValue = databaseRef.child("users").child(userID!).child("TermCond").value as? String
Would suffice, but nothing works. I am confused why retrieving the value should be more difficult than setting it.
To "read" a value from Firebase, you need to add a reference listener that gets called every time that value changes.
In your case, that could be something like:
let databaseRef = FIRDatabase.database().reference()
databaseRef.child("users").child(userID!).child("TermCond").observe(FIRDataEventType.value, with: { (snapshot) in
let desiredValue = snapshot.value as? String
})
This block of code will get triggered every time your value changes. If you only want to read it once, you can use observeSingleEvent:of:with instead of observe:with.
This is as described in the Firebase documentation: https://firebase.google.com/docs/database/ios/read-and-write
I recommend you read their entire Documentation to get an idea of how Firebase works, as it is very different from traditional databases.
I can also recommend the following tutorial if you'd like to learn a bit more about the Firebase Database and how it works: https://www.raywenderlich.com/139322/firebase-tutorial-getting-started-2
I've solved this now (based on Aleksander's reply). The way I did it is as follows.
databaseRef.child("users").child(userID!).observeSingleEvent(of: .value, with: { (snapshot) in
let value = snapshot.value as? NSDictionary
self.desiredValue = value?["TermCond"] as? String ?? ""
self.LabelToShow.text = self.desiredValue!
}) { (error) in
print(error.localizedDescription)
}
This works absolutely fine and shows the value of TermCond in the LabelToShow on my iOS screen.

Resources