0

I take data from Firestore by user id. I need to display data in a TextFormField and be able to update it immediately on button click. There was a problem, because I'm not building a list, but I need to display data for only one id. How do I correctly access the firestore elements, to the id, I need to get these lines, only this code does not work for me var noteInfo = snapshot.data!.docs.data()!; String docID = snapshot.data!.docs.id; String title = noteInfo['title']; You need to refer to elements only without [index] I will sharpen that I do not have a list. Does anyone know how to contact them correctly? I will be grateful for help

firestore_repository

final FirebaseFirestore _firestore = FirebaseFirestore.instance;
final CollectionReference _mainCollection = _firestore.collection('users');

class Database {
  static String? userUid;

  static Future<void> addItem({
    required String bisName,
    required String bisAddress,
    required String contactName,
    required String contactEmail,
    required String phoneNumber,
    required String progName,
    // required String progYears,
  }) async {
    DocumentReference documentReference =
        _mainCollection.doc(userUid).collection('info').doc();

    Map<String, dynamic> data = <String, dynamic>{
      'bisName': bisName,
      'bisAddress': bisAddress,
      'contactName': contactName,
      'contactEmail': contactEmail,
      'phoneNumber': phoneNumber,
      'progName': progName,
      // 'progYears': progYears,
    };

    await documentReference
        .set(data)
        .whenComplete(() => print('User info added to the database'))
        .catchError((e) => print(e));
  }

  static Future<void> updateItem({
    required String bisName,
    required String bisAddress,
    required String contactName,
    required String contactEmail,
    required String phoneNumber,
    required String progName,
    required String docId,
  }) async {
    DocumentReference documentReference =
        _mainCollection.doc(userUid).collection('info').doc(docId);

    Map<String, dynamic> data = <String, dynamic>{
      'bisName': bisName,
      'bisAddress': bisAddress,
      'contactName': contactName,
      'contactEmail': contactEmail,
      'phoneNumber': phoneNumber,
      'progName': progName,
    };

    await documentReference
        .update(data)
        .whenComplete(() => print('User info updated to the database'))
        .catchError((e) => print(e));
  }

  static Stream<QuerySnapshot> readItems() {
    CollectionReference usersInfoCollection =
        _mainCollection.doc(userUid).collection('info');

    return usersInfoCollection.snapshots();
  }

  static Future<void> deleteItem({
    required String docId,
  }) async {
    DocumentReference documentReference =
        _mainCollection.doc(userUid).collection('info').doc(docId);

    await documentReference
        .delete()
        .whenComplete(() => print('User info deleted to the database'))
        .catchError((e) => print(e));
  }
}

profile_screen

class ProfileScreen extends StatefulWidget {
  @override
  State<ProfileScreen> createState() => _ProfileScreen();
}

class _ProfileScreen extends State<ProfileScreen> {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
        body: SingleChildScrollView(
      child: Container(
        child: Padding(
          padding: const EdgeInsets.all(50),
          child: StreamBuilder<QuerySnapshot>(
              stream: Database.readItems(),
              builder: (context, snapshot) {
                if (snapshot.hasError) {
                  return Text('Something went wrong');
                } else if (snapshot.hasData || snapshot.data != null) {
                  return _userInfo(snapshot);
                }
              }
        ),
      ),
    )));
  }

  Widget _userInfo(AsyncSnapshot<QuerySnapshot> snapshot) {
    var userInfo = snapshot.data!.docs;
    // String docId = snapshot.data.docs;
    return Column(
      mainAxisAlignment: MainAxisAlignment.center,
      children: [
        Form(
          child: Row(
            mainAxisAlignment: MainAxisAlignment.center,
            children: [
              SizedBox(
                width: MediaQuery.of(context).size.width * 0.2,
                child: TextFormField(
                  decoration: InputDecoration(
                    labelText: "Business Name".toUpperCase(),
                    labelStyle: TextStyle(
                        color: primaryColor, fontWeight: FontWeight.w700),
                    enabledBorder: UnderlineInputBorder(
                      borderSide: BorderSide(
                        color: secondaryColor,
                      ),
                    ),
                    focusedBorder: UnderlineInputBorder(
                        borderSide: BorderSide(
                      color: primaryColor,
                    )),
                  ),
                ),
              ),
4
  • do you only need one element form the info collection or all items in the collection? if one then you can add .limit(1) to the query Commented Feb 21, 2022 at 12:45
  • var noteInfo = snapshot.data!.docs.data()!; You need to refer to elements only without [index] I will sharpen that I do not have a list Commented Feb 21, 2022 at 12:51
  • then there is a missleading code there, because CollectionReference usersInfoCollection = _mainCollection.doc(userUid).collection('info'); shows you want for a userUid the collection info what a list is. so then my answer is right according to your code, but you code is incorrect to what you want Commented Feb 21, 2022 at 12:59
  • Please, could you tell me how to pull data from firestore in my case and show it not in ListView but in TextFormField? Can this be done? Commented Feb 21, 2022 at 13:10

1 Answer 1

1

according to the comments:

to save properties in the firestore i would do this by adding a document with documentId info to the user document.

The the query would look like this: _mainCollection.doc(userUid).doc('info');

and in the widget:

var noteInfo = snapshot.data!.data()!;
String docID = snapshot.data!.id;
String title = noteInfo['title'];

old answer:

try this:

var noteInfo = snapshot.data!.docs[index].data()!;
String docID = snapshot.data!.docs[index].id; String title = noteInfo['title'];

you need the index because the docs is of type List<QueryDocumentSnapshot<Map<String, dynamic>>> and with .data() you get the Map of the contents.

where the index is the zero based index of the element you want to get from the info collection

Sign up to request clarification or add additional context in comments.

8 Comments

And if I don’t have a list, but just the data, I need to show one user at a time in the TextFormField. Well then I can not use [index] produces an error.
i understand but you get a collection with _mainCollection.doc(userUid).collection('info'); from one user. as i mention in the answer the info collection is of type List<QueryDocumentSnapshot<...>>, for a more correct answer you have to describe the database model a bit
Please, could you tell me how to pull data from firestore in my case and show it not in ListView but in TextFormField? Can this be done?
therefore i need additional infos. what is the content of the collection info? or is info only a document in the user document?
There is currently no data in the Firestore. The data I want to write is in the firestore_repository. I need that when the user registers, he can enter his data in the TextFormField and by clicking on the button this data is written to the Firestore. And so that the user could log in at any moment, his data was displayed in the TextFormField and he could edit / change them and press the button again and the data would be updated. Here is how the application works
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.