Apple प्लैटफ़ॉर्म पर डेटा की सूचियों की मदद से काम करना

FIRDatabaseReference पाना

डेटाबेस से डेटा पढ़ने या उसमें बदलाव करने के लिए, आपके पास FIRDatabaseReference का एक इंस्टेंस होना चाहिए:

Swift

ध्यान दें: Firebase का यह प्रॉडक्ट, ऐप्लिकेशन क्लिप टारगेट पर उपलब्ध नहीं है.
var ref: DatabaseReference!

ref = Database.database().reference()

Objective-C

ध्यान दें: Firebase का यह प्रॉडक्ट, App Clip के टारगेट पर उपलब्ध नहीं है.
@property (strong, nonatomic) FIRDatabaseReference *ref;

self.ref = [[FIRDatabase database] reference];

सूचियां पढ़ना और उनमें बदलाव करना

डेटा की सूची में जोड़ना

एक से ज़्यादा उपयोगकर्ताओं वाले ऐप्लिकेशन में, सूची में डेटा जोड़ने के लिए childByAutoId तरीके का इस्तेमाल करें. जब भी तय Firebase संदर्भ में किसी नए बच्चे को जोड़ा जाता है, तब childByAutoId वाला तरीका एक यूनीक कुंजी जनरेट करता है. सूची में मौजूद हर नए एलिमेंट के लिए, अपने-आप जनरेट हुई इन कुंजियों का इस्तेमाल करके, कई क्लाइंट एक ही समय पर एक ही जगह पर चाइल्ड एलिमेंट जोड़ सकते हैं. ऐसा करने पर, डेटा को लिखने में कोई समस्या नहीं होती. childByAutoId से जनरेट की गई यूनीक कुंजी, टाइमस्टैंप पर आधारित होती है. इसलिए, सूची के आइटम अपने-आप क्रम से व्यवस्थित हो जाते हैं.

बच्चे के लिए अपने-आप जनरेट हुई कुंजी की वैल्यू पाने या डेटा सेट करने के लिए, childByAutoId तरीके से मिले नए डेटा के रेफ़रंस का इस्तेमाल किया जा सकता है. childByAutoId रेफ़रंस पर getKey कॉल करने से, अपने-आप जनरेट हुई कुंजी मिलती है.

अपने-आप जनरेट होने वाली इन कुंजियों का इस्तेमाल करके, अपने डेटा स्ट्रक्चर को आसानी से फ़्लैट किया जा सकता है. ज़्यादा जानकारी के लिए, डेटा फ़ैन-आउट का उदाहरण देखें.

बच्चों के लिए बने इवेंट सुनें

चाइल्ड इवेंट, किसी ऑपरेशन से किसी नोड के चाइल्ड पर होने वाले खास ऑपरेशन के जवाब में ट्रिगर होते हैं. जैसे, childByAutoId तरीके से जोड़ा गया नया चाइल्ड या updateChildValues तरीके से अपडेट किया गया चाइल्ड.

इवेंट प्रकार आम तौर पर इस्तेमाल
FIRDataEventTypeChildAdded आइटम की सूचियां वापस पाएं या आइटम की सूची में जोड़े गए आइटम सुनें. यह इवेंट, हर मौजूदा चाइल्ड के लिए एक बार ट्रिगर होता है. इसके बाद, तय किए गए पाथ में हर बार नया चाइल्ड जोड़े जाने पर, यह इवेंट फिर से ट्रिगर होता है. नए बच्चे का डेटा इकट्ठा करने के बाद, उसे सुनने वाले को एक स्नैपशॉट भेजा जाता है.
FIRDataEventTypeChildChanged सूची में मौजूद आइटम में हुए बदलावों को सुनें. जब भी किसी चाइल्ड नोड में बदलाव किया जाता है, तो यह इवेंट ट्रिगर होता है. इसमें चाइल्ड नोड के डिससेंडेंट में किए गए सभी बदलाव भी शामिल हैं. इवेंट लिसनर को भेजे गए स्नैपशॉट में, चाइल्ड के लिए अपडेट किया गया डेटा होता है.
FIRDataEventTypeChildRemoved किसी सूची से आइटम हटाए जाने की जानकारी सुनना. यह इवेंट तब ट्रिगर होता है, जब किसी चाइल्ड को तुरंत हटाया जाता है. कॉलबैक ब्लॉक में भेजे गए स्नैपशॉट में, हटाए गए चाइल्ड का डेटा होता है.
FIRDataEventTypeChildMoved किसी सूची में आइटम के क्रम में होने वाले बदलावों को सुनना. जब भी किसी अपडेट की वजह से बच्चे का क्रम बदल जाता है, तो यह इवेंट ट्रिगर होता है. इसका इस्तेमाल, queryOrderedByChild या queryOrderedByValue के हिसाब से क्रम में लगाए गए डेटा के साथ किया जाता है.

डेटाबेस में किसी खास नोड में हुए बदलावों को सुनने के लिए, इन सभी तरीकों का इस्तेमाल किया जा सकता है. उदाहरण के लिए, किसी पोस्ट की टिप्पणियों में गतिविधि की निगरानी करने के लिए, कोई सोशल ब्लॉगिंग ऐप्लिकेशन एक साथ इन तरीकों का इस्तेमाल कर सकता है, जैसा कि यहां दिखाया गया है:

Swift

ध्यान दें: Firebase का यह प्रॉडक्ट, ऐप्लिकेशन क्लिप टारगेट पर उपलब्ध नहीं है.
// Listen for new comments in the Firebase database
commentsRef.observe(.childAdded, with: { (snapshot) -> Void in
  self.comments.append(snapshot)
  self.tableView.insertRows(
    at: [IndexPath(row: self.comments.count - 1, section: self.kSectionComments)],
    with: UITableView.RowAnimation.automatic
  )
})
// Listen for deleted comments in the Firebase database
commentsRef.observe(.childRemoved, with: { (snapshot) -> Void in
  let index = self.indexOfMessage(snapshot)
  self.comments.remove(at: index)
  self.tableView.deleteRows(
    at: [IndexPath(row: index, section: self.kSectionComments)],
    with: UITableView.RowAnimation.automatic
  )
})

Objective-C

ध्यान दें: Firebase का यह प्रॉडक्ट, ऐप्लिकेशन क्लिप टारगेट पर उपलब्ध नहीं है.
// Listen for new comments in the Firebase database
[_commentsRef
              observeEventType:FIRDataEventTypeChildAdded
              withBlock:^(FIRDataSnapshot *snapshot) {
                [self.comments addObject:snapshot];
                [self.tableView insertRowsAtIndexPaths:@[
                  [NSIndexPath indexPathForRow:self.comments.count - 1 inSection:kSectionComments]
                ]
                                      withRowAnimation:UITableViewRowAnimationAutomatic];
              }];
// Listen for deleted comments in the Firebase database
[_commentsRef
 observeEventType:FIRDataEventTypeChildRemoved
 withBlock:^(FIRDataSnapshot *snapshot) {
   int index = [self indexOfMessage:snapshot];
   [self.comments removeObjectAtIndex:index];
   [self.tableView deleteRowsAtIndexPaths:@[[NSIndexPath indexPathForRow:index inSection:kSectionComments]]
                         withRowAnimation:UITableViewRowAnimationAutomatic];
 }];

वैल्यू इवेंट के लिए सुनना

डेटा की सूचियों को पढ़ने के लिए, चाइल्ड इवेंट सुनने का सुझाव दिया जाता है. हालांकि, कुछ मामलों में सूची के रेफ़रंस पर वैल्यू इवेंट सुनना फ़ायदेमंद होता है.

डेटा की सूची में FIRDataEventTypeValue ऑब्ज़र्वर को अटैच करने पर, डेटा की पूरी सूची एक ही DataSnapshot के तौर पर दिखेगी. इसके बाद, अलग-अलग बच्चों को ऐक्सेस करने के लिए, इस सूची को लूप किया जा सकता है.

अगर क्वेरी के लिए सिर्फ़ एक मैच है, तब भी स्नैपशॉट एक सूची होती है. इसमें सिर्फ़ एक आइटम होता है. आइटम को ऐक्सेस करने के लिए, आपको नतीजे पर बार-बार क्लिक करना होगा:

Swift

ध्यान दें: Firebase का यह प्रॉडक्ट, ऐप्लिकेशन क्लिप टारगेट पर उपलब्ध नहीं है.
_commentsRef.observe(.value) { snapshot in
  for child in snapshot.children {
    ...
  }
}

Objective-C

ध्यान दें: Firebase का यह प्रॉडक्ट, App Clip के टारगेट पर उपलब्ध नहीं है.
[_commentsRef
              observeEventType:FIRDataEventTypeValue
              withBlock:^(FIRDataSnapshot *snapshot) {
                // Loop over children
                NSEnumerator *children = [snapshot children];
                FIRDataSnapshot *child;
                while (child = [children nextObject]) {
                  // ...
                }
              }];

यह पैटर्न तब काम आ सकता है, जब आपको एक ही कार्रवाई में सूची के सभी चाइल्ड एंट्री को फ़ेच करना हो. इससे, बच्चे के जोड़े गए अतिरिक्त इवेंट को सुनने के बजाय, उन्हें फ़ेच किया जा सकता है.

डेटा को क्रम से लगाना और फ़िल्टर करना

Realtime Database FIRDatabaseQuery क्लास का इस्तेमाल करके, कुंजी, वैल्यू या चाइल्ड की वैल्यू के हिसाब से क्रम से लगाए गए डेटा को वापस पाया जा सकता है. क्रम में लगाए गए नतीजों को, किसी खास संख्या के नतीजों या कुंजियों या वैल्यू की सीमा के हिसाब से भी फ़िल्टर किया जा सकता है.

डेटा को क्रम से लगाना

क्रम से लगाए गए डेटा को वापस पाने के लिए, क्रम से लगाने के लिए इनमें से किसी एक तरीके का इस्तेमाल करें, ताकि यह तय किया जा सके कि नतीजों को किस क्रम में लगाया जाए:

तरीका इस्तेमाल
queryOrderedByKey नतीजों को चाइल्ड बटन के हिसाब से क्रम में लगाएं.
queryOrderedByValue नतीजों को चाइल्ड वैल्यू के हिसाब से क्रम में लगाएं.
queryOrderedByChild किसी खास चाइल्ड की की या नेस्ट किए गए चाइल्ड पाथ की वैल्यू के हिसाब से नतीजों को क्रम में लगाएं.

एक बार में, क्रम से लगाने के लिए सिर्फ़ एक तरीके का इस्तेमाल किया जा सकता है. एक ही क्वेरी में, क्रम से लगाने के तरीके को कई बार कॉल करने पर गड़बड़ी का मैसेज मिलता है.

इस उदाहरण में बताया गया है कि किसी उपयोगकर्ता की सबसे लोकप्रिय पोस्ट की सूची को, स्टार की संख्या के हिसाब से कैसे क्रम में लगाया जा सकता है:

Swift

ध्यान दें: Firebase का यह प्रॉडक्ट, ऐप्लिकेशन क्लिप टारगेट पर उपलब्ध नहीं है.
// My top posts by number of stars
let myTopPostsQuery = ref.child("user-posts").child(getUid()).queryOrdered(byChild: "starCount")

Objective-C

ध्यान दें: Firebase का यह प्रॉडक्ट, ऐप्लिकेशन क्लिप टारगेट पर उपलब्ध नहीं है.
// My top posts by number of stars
FIRDatabaseQuery *myTopPostsQuery = [[[self.ref child:@"user-posts"]
                                      child:[super getUid]]
                                     queryOrderedByChild:@"starCount"];

यह क्वेरी, उपयोगकर्ता के यूज़र आईडी के आधार पर, डेटाबेस के पाथ से उपयोगकर्ता की पोस्ट को वापस लाती है. साथ ही, हर पोस्ट को मिले स्टार की संख्या के हिसाब से उन्हें क्रम में लगाती है. आईडी का इस्तेमाल इंडेक्स कुंजियों के तौर पर करने की इस तकनीक को डेटा फ़ैन आउट कहा जाता है. इसके बारे में ज़्यादा जानने के लिए, अपने डेटाबेस का स्ट्रक्चर तैयार करें लेख पढ़ें.

queryOrderedByChild तरीके को कॉल करने पर, नतीजों को क्रम में लगाने के लिए चाइल्ड की कुंजी तय की जाती है. इस उदाहरण में, पोस्ट को हर पोस्ट में "starCount" चाइल्ड की वैल्यू के हिसाब से क्रम में लगाया गया है. अगर आपके पास ऐसा डेटा है जो कुछ ऐसा दिखता है, तो नेस्ट किए गए बच्चों के मुताबिक क्वेरी का क्रम भी तय किया जा सकता है:

"posts": {
  "ts-functions": {
    "metrics": {
      "views" : 1200000,
      "likes" : 251000,
      "shares": 1200,
    },
    "title" : "Why you should use TypeScript for writing Cloud Functions",
    "author": "Doug",
  },
  "android-arch-3": {
    "metrics": {
      "views" : 900000,
      "likes" : 117000,
      "shares": 144,
    },
    "title" : "Using Android Architecture Components with Firebase Realtime Database (Part 3)",
    "author": "Doug",
  }
},

इस मामले में, हम सूची के एलिमेंट को metrics बटन के नीचे नेस्ट की गई वैल्यू के हिसाब से क्रम में लगा सकते हैं. इसके लिए, हमें queryOrderedByChild कॉल में नेस्ट किए गए चाइल्ड के रिलेटिव पाथ की जानकारी देनी होगी.

Swift

ध्यान दें: Firebase का यह प्रॉडक्ट, ऐप्लिकेशन क्लिप टारगेट पर उपलब्ध नहीं है.
 
let postsByMostPopular = ref.child("posts").queryOrdered(byChild: "metrics/views")

Objective-C

ध्यान दें: Firebase का यह प्रॉडक्ट, App Clip के टारगेट पर उपलब्ध नहीं है.
 
FIRDatabaseQuery *postsByMostPopular = [[ref child:@"posts"] queryOrderedByChild:@"metrics/views"];

अन्य डेटा टाइप को क्रम से लगाने के तरीके के बारे में ज़्यादा जानने के लिए, क्वेरी डेटा को क्रम से लगाने का तरीका लेख पढ़ें.

डेटा फ़िल्टर करना

डेटा को फ़िल्टर करने के लिए, क्वेरी बनाते समय, सीमित या रेंज वाले किसी भी तरीके को क्रम से लगाने के तरीके के साथ जोड़ा जा सकता है.

तरीका इस्तेमाल
queryLimitedToFirst इससे, क्रम से लगाई गई नतीजों की सूची में सबसे पहले से दिखाए जाने वाले आइटम की ज़्यादा से ज़्यादा संख्या तय की जाती है.
queryLimitedToLast क्रम से लगाए गए नतीजों की सूची के आखिर से दिखाए जाने वाले आइटम की ज़्यादा से ज़्यादा संख्या सेट करता है.
queryStartingAtValue चुने गए क्रम के तरीके के आधार पर, तय की गई कुंजी या वैल्यू से ज़्यादा या उसके बराबर वाले आइटम दिखाता है.
queryStartingAfterValue वे आइटम दिखाएं जो बताए गए कुंजी या वैल्यू से ज़्यादा हों. यह चुने गए क्रम के हिसाब से तय होता है.
queryEndingAtValue चुने गए ऑर्डर के हिसाब से, बताई गई कुंजी या वैल्यू से कम या उसके बराबर के आइटम दिखाएं.
queryEndingBeforeValue वे आइटम दिखाएं जो बताए गए बटन या वैल्यू से कम हों. यह चुने गए ऑर्डर के हिसाब से तरीके के हिसाब से तय होता है.
queryEqualToValue चुने गए ऑर्डर के हिसाब से, चुने गए तरीके के हिसाब से, बताई गई कुंजी या वैल्यू के बराबर की वैल्यू वाले आइटम दिखाएं.

क्रम के हिसाब से क्रम में लगाने वाले तरीकों के उलट, एक से ज़्यादा सीमा या रेंज फ़ंक्शन को जोड़ा जा सकता है. उदाहरण के लिए, नतीजों को वैल्यू की तय सीमा तक सीमित करने के लिए, queryStartingAtValue और queryEndingAtValue तरीकों को जोड़ा जा सकता है.

नतीजों की संख्या सीमित करना

किसी कॉलबैक के लिए, सिंक किए जाने वाले बच्चों की ज़्यादा से ज़्यादा संख्या सेट करने के लिए, queryLimitedToFirst और queryLimitedToLast तरीकों का इस्तेमाल किया जा सकता है. उदाहरण के लिए, अगर 100 की सीमा सेट करने के लिए queryLimitedToFirst का इस्तेमाल किया जाता है, तो शुरुआत में आपको ज़्यादा से ज़्यादा 100 FIRDataEventTypeChildAdded कॉलबैक मिलते हैं. अगर आपके Firebase डेटाबेस में 100 से कम आइटम स्टोर हैं, तो हर आइटम के लिए FIRDataEventTypeChildAdded कॉलबैक ट्रिगर होता है.

आइटम में बदलाव होने पर, आपको क्वेरी में शामिल होने वाले आइटम के लिए FIRDataEventTypeChildAdded कॉलबैक और उससे बाहर निकलने वाले आइटम के लिए FIRDataEventTypeChildRemoved कॉलबैक मिलते हैं, ताकि कुल संख्या 100 पर बनी रहे.

यहां दिए गए उदाहरण में दिखाया गया है कि ब्लॉगिंग ऐप्लिकेशन, सभी उपयोगकर्ताओं की सबसे हाल की 100 पोस्ट की सूची कैसे पा सकता है:

Swift

ध्यान दें: Firebase का यह प्रॉडक्ट, ऐप्लिकेशन क्लिप टारगेट पर उपलब्ध नहीं है.
// Last 100 posts, these are automatically the 100 most recent
// due to sorting by push() keys
let recentPostsQuery = (ref?.child("posts").queryLimited(toFirst: 100))!

Objective-C

ध्यान दें: Firebase का यह प्रॉडक्ट, ऐप्लिकेशन क्लिप टारगेट पर उपलब्ध नहीं है.
// Last 100 posts, these are automatically the 100 most recent
// due to sorting by push() keys
FIRDatabaseQuery *recentPostsQuery = [[self.ref child:@"posts"] queryLimitedToFirst:100];

बटन या वैल्यू के हिसाब से फ़िल्टर करना

क्वेरी के लिए आर्बिट्रेरी, शुरू, खत्म होने, और समतुल्य पॉइंट चुनने के लिए, queryStartingAtValue, queryStartingAfterValue, queryEndingAtValue, queryEndingBeforeValue, और queryEqualToValue का इस्तेमाल किया जा सकता है. यह एट्रिब्यूट, डेटा को पेज पर दिखाने या बच्चों के लिए ऐसे आइटम ढूंढने के लिए फ़ायदेमंद हो सकता है जिनकी कोई खास वैल्यू हो.

क्वेरी डेटा को क्रम से लगाने का तरीका

इस सेक्शन में बताया गया है कि FIRDatabaseQuery क्लास में, क्रम से लगाने के हर तरीके के हिसाब से डेटा को कैसे क्रम में लगाया जाता है.

queryOrderedByKey

डेटा को क्रम से लगाने के लिए queryOrderedByKey का इस्तेमाल करने पर, डेटा को बढ़ते क्रम में दिखाया जाता है.

  1. जिन बच्चों के पास कुंजी होती है उन्हें 32-बिट वाले पूर्णांक के तौर पर पार्स किया जा सकता है, उन्हें बढ़ते क्रम में क्रम में लगाया जाता है.
  2. इसके बाद, उन बच्चों की जानकारी दिखती है जिनके लिए कुंजी के तौर पर स्ट्रिंग वैल्यू दी गई है. इन बच्चों की जानकारी को वर्णमाला के क्रम में, बढ़ते क्रम में लगाया जाता है.

queryOrderedByValue

queryOrderedByValue का इस्तेमाल करने पर, बच्चों को उनकी वैल्यू के हिसाब से क्रम में लगाया जाता है. ऑर्डर की शर्त वही होती है जो queryOrderedByChild में होती है. हालांकि, नोड की वैल्यू का इस्तेमाल तय चाइल्ड कुंजी की वैल्यू के बजाय किया जाता है.

queryOrderedByChild

queryOrderedByChild का इस्तेमाल करने पर, उस डेटा को इस क्रम में लगाया जाता है जिसमें चुनी गई चाइल्ड कुंजी शामिल होती है:

  1. तय की गई चाइल्ड कुंजी के लिए nil वैल्यू वाले बच्चे पहले आते हैं.
  2. तय की गई चाइल्ड कुंजी के लिए false मान वाले बच्चों के आगे आएं. अगर एक से ज़्यादा चाइल्ड एलिमेंट की वैल्यू false है, तो उन्हें की के हिसाब से लेक्सिकोग्राफ़ी के हिसाब से क्रम में लगाया जाता है.
  3. इसके बाद, उन बच्चों की जानकारी दिखती है जिनके लिए तय की गई चाइल्ड कुंजी की वैल्यू true है. अगर कई चाइल्ड एलिमेंट की वैल्यू true है, तो उन्हें कीवर्ड के हिसाब से, वर्णमाला के क्रम में क्रम से लगाया जाता है.
  4. इसके बाद, संख्या वाली वैल्यू वाले बच्चे आते हैं. इन्हें बढ़ते क्रम में लगाया जाता है. अगर कई चाइल्ड के लिए, तय किए गए चाइल्ड नोड की संख्या वाली वैल्यू एक जैसी है, तो उन्हें कीवर्ड के हिसाब से क्रम में लगाया जाता है.
  5. स्ट्रिंग, संख्याओं के बाद आती हैं. इन्हें बढ़ते हुए क्रम में, कोशिकीय तरीके से क्रम में लगाया जाता है. अगर कई चाइल्ड के लिए, तय किए गए चाइल्ड node की एक ही वैल्यू है, तो उन्हें कीवर्ड के हिसाब से, वर्णमाला के क्रम में लगाया जाता है.
  6. ऑब्जेक्ट आखिर में आते हैं और उन्हें कीवर्ड के हिसाब से, बढ़ते क्रम में लगाया जाता है.

लिसनर को अलग करना

ViewController को छोड़ने पर, ऑब्ज़र्वर अपने-आप डेटा सिंक करना बंद नहीं करते. अगर किसी ऑब्ज़र्वर को सही तरीके से नहीं हटाया जाता है, तो वह डेटा को लोकल मेमोरी में सिंक करता रहता है. साथ ही, इवेंट हैंडलर क्लोज़र में कैप्चर किए गए सभी ऑब्जेक्ट को बनाए रखता है. इससे मेमोरी लीक हो सकती है. जब किसी ऑब्ज़र्वर की ज़रूरत न हो, तो removeObserverWithHandle तरीके में उससे जुड़े FIRDatabaseHandle को पास करके उसे हटाएं.

किसी रेफ़रंस में कॉलबैक ब्लॉक जोड़ने पर, FIRDatabaseHandle दिखता है. इन हैंडल का इस्तेमाल, कॉलबैक ब्लॉक को हटाने के लिए किया जा सकता है.

अगर डेटाबेस रेफ़रंस में कई लिसनर जोड़े गए हैं, तो कोई इवेंट होने पर हर लिसनर को कॉल किया जाता है. उस जगह पर डेटा सिंक होने की सुविधा बंद करने के लिए, आपको removeAllObservers तरीका इस्तेमाल करके, उस जगह पर मौजूद सभी ऑब्ज़र्वर हटाने होंगे.

किसी लिसनर पर removeObserverWithHandle या removeAllObservers को कॉल करने से, उसके चाइल्ड नोड पर रजिस्टर किए गए लिसनर अपने-आप नहीं हटते. उन्हें हटाने के लिए, आपको उन रेफ़रंस या हैंडल पर भी नज़र रखनी होगी.

अगले चरण