AppSearch

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

AppSearch में इंडेक्स करने और खोजने की प्रोसेस दिखाने वाला डायग्राम

AppSearch में ये सुविधाएं मिलती हैं:

  • यह मोबाइल के लिए स्टोरेज की सुविधा है. यह तेज़ी से काम करती है और इसमें कम I/O का इस्तेमाल होता है
  • बड़े डेटा सेट को इंडेक्स करने और क्वेरी करने की बेहतर सुविधा मिलती है
  • कई भाषाओं में उपलब्ध है, जैसे कि अंग्रेज़ी और स्पैनिश
  • प्रासंगिकता के हिसाब से रैंकिंग और इस्तेमाल के आधार पर स्कोरिंग की जाती है

I/O का कम इस्तेमाल होने की वजह से, AppSearch में SQLite की तुलना में बड़े डेटासेट को इंडेक्स करने और खोजने में कम समय लगता है. AppSearch, अलग-अलग टाइप की क्वेरी को आसान बनाता है. इसके लिए, यह सिंगल क्वेरी का इस्तेमाल करता है. वहीं, SQLite कई टेबल के अलग-अलग डेटा एक साथ नतीजों को मर्ज करता है.

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

सेटअप

अपने ऐप्लिकेशन में AppSearch का इस्तेमाल करने के लिए, अपने ऐप्लिकेशन की build.gradle फ़ाइल में ये डिपेंडेंसी जोड़ें:

ग्रूवी

dependencies {
    def appsearch_version = "1.2.0-alpha02"

    implementation "androidx.appsearch:appsearch:$appsearch_version"
    // Use kapt instead of annotationProcessor if writing Kotlin classes
    annotationProcessor "androidx.appsearch:appsearch-compiler:$appsearch_version"

    implementation "androidx.appsearch:appsearch-local-storage:$appsearch_version"
    // PlatformStorage is compatible with Android 12+ devices and supports sharing data
    // with other apps. Feature support varies by device. Before calling an API that
    // requires a feature, check Features.isFeatureSupported().
    implementation "androidx.appsearch:appsearch-platform-storage:$appsearch_version"

    // PlayServicesStorage is compatible with all devices that support Google Play Services on
    // all API levels. It offers similar capabilities to PlatformStorage and is the
    // recommended solution for lower API levels on which PlatformStorage is not supported.
    implementation "androidx.appsearch:appsearch-play-services-storage:$appsearch_version"
}

Kotlin

dependencies {
    val appsearch_version = "1.2.0-alpha02"

    implementation("androidx.appsearch:appsearch:$appsearch_version")
    // Use annotationProcessor instead of kapt if writing Java classes
    kapt("androidx.appsearch:appsearch-compiler:$appsearch_version")

    implementation("androidx.appsearch:appsearch-local-storage:$appsearch_version")
    // PlatformStorage is compatible with Android 12+ devices and supports sharing data
    // with other apps. Feature support varies by device. Before calling an API that
    // requires a feature, check Features.isFeatureSupported().
    implementation("androidx.appsearch:appsearch-platform-storage:$appsearch_version")

    // PlayServicesStorage is compatible with all devices that support Google Play Services on
    // all API levels. It offers similar capabilities to PlatformStorage and is the
    // recommended solution for lower API levels on which PlatformStorage is not supported.
    implementation("androidx.appsearch:appsearch-play-services-storage:$appsearch_version")

}

AppSearch के सिद्धांत

इस डायग्राम में, AppSearch के कॉन्सेप्ट और उनके इंटरैक्शन के बारे में बताया गया है.

डायग्राम
क्लाइंट ऐप्लिकेशन की आउटलाइन और AppSearch के इन कॉन्सेप्ट के साथ उसके इंटरैक्शन: AppSearch डेटाबेस, स्कीमा, स्कीमा टाइप, दस्तावेज़, सेशन, और खोज. पहली इमेज. AppSearch के कॉन्सेप्ट का डायग्राम: AppSearch डेटाबेस, स्कीमा, स्कीमा टाइप, दस्तावेज़, सेशन, और खोज.

डेटाबेस और सेशन

AppSearch डेटाबेस, दस्तावेज़ों का एक कलेक्शन होता है. यह डेटाबेस स्कीमा के मुताबिक होता है. क्लाइंट ऐप्लिकेशन, अपने ऐप्लिकेशन का कॉन्टेक्स्ट और डेटाबेस का नाम देकर डेटाबेस बनाते हैं. डेटाबेस को सिर्फ़ वह ऐप्लिकेशन खोल सकता है जिसने उन्हें बनाया है. डेटाबेस खोले जाने पर, डेटाबेस के साथ इंटरैक्ट करने के लिए एक सेशन शुरू होता है. सेशन, AppSearch API को कॉल करने का एंट्री पॉइंट होता है. यह तब तक खुला रहता है, जब तक क्लाइंट ऐप्लिकेशन इसे बंद नहीं कर देता.

स्कीमा और स्कीमा के टाइप

स्कीमा, AppSearch डेटाबेस में डेटा के संगठन के स्ट्रक्चर को दिखाता है.

स्कीमा, स्कीमा टाइप से बना होता है. ये टाइप, यूनीक डेटा को दिखाते हैं. स्कीमा टाइप में ऐसी प्रॉपर्टी शामिल होती हैं जिनमें नाम, डेटा टाइप, और एलिमेंट की संख्या शामिल होती है. डेटाबेस स्कीमा में स्कीमा टाइप जोड़ने के बाद, उस स्कीमा टाइप के दस्तावेज़ बनाए जा सकते हैं और डेटाबेस में जोड़े जा सकते हैं.

दस्तावेज़

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

दस्तावेज़ों में, उन्हें बनाने का टाइमस्‍टैंप, टाइम-टू-लिव (TTL), और एक स्कोर शामिल होता है. इस स्कोर का इस्तेमाल, दस्तावेज़ों को वापस पाने के दौरान उनकी रैंकिंग तय करने के लिए किया जा सकता है. दस्तावेज़ को एक स्कीमा टाइप भी असाइन किया जाता है. इससे दस्तावेज़ में मौजूद अतिरिक्त डेटा प्रॉपर्टी के बारे में पता चलता है.

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

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

AppSearch, खोज के लिए पसंद के मुताबिक बनाने की सुविधा देता है. जैसे, फ़िल्टर, पेज के साइज़ का कॉन्फ़िगरेशन, और स्निपेटिंग.

प्लैटफ़ॉर्म स्टोरेज, लोकल स्टोरेज या Play Services का स्टोरेज

AppSearch, स्टोरेज के लिए तीन विकल्प उपलब्ध कराता है: LocalStorage, PlatformStorage, और PlayServicesStorage. LocalStorage की मदद से, आपका ऐप्लिकेशन एक खास इंडेक्स को मैनेज करता है. यह इंडेक्स, आपके ऐप्लिकेशन की डेटा डायरेक्ट्री में मौजूद होता है. PlatformStorage और PlayServicesStorage, दोनों की मदद से आपका ऐप्लिकेशन, पूरे सिस्टम के लिए बनाए गए सेंट्रल इंडेक्स में योगदान देता है. PlatformStorage का इंडेक्स, सिस्टम सर्वर में होस्ट किया जाता है. वहीं, PlayServicesStorage का इंडेक्स, Google Play services के स्टोरेज में होस्ट किया जाता है. इन सेंट्रल इंडेक्स में मौजूद डेटा का ऐक्सेस, आपके ऐप्लिकेशन के डेटा और उस डेटा तक ही सीमित होता है जिसे किसी दूसरे ऐप्लिकेशन ने आपके साथ साफ़ तौर पर शेयर किया है. स्टोरेज के ये सभी विकल्प एक ही एपीआई का इस्तेमाल करते हैं. साथ ही, डिवाइस के वर्शन के हिसाब से इन्हें बदला जा सकता है.

ध्यान रखें कि स्टोरेज के विकल्प और डिवाइस के हिसाब से, सुविधा की उपलब्धता अलग-अलग होती है. ज़्यादा जानकारी के लिए, सुविधा की उपलब्धता देखना लेख पढ़ें.

यहां दिया गया कोड, Android 12 (एपीआई लेवल 31) और इसके बाद के वर्शन पर PlatformStorage सेशन बनाता है. साथ ही, इससे पहले के वर्शन पर PlayServicesStorage या LocalStorage सेशन बनाता है:

Kotlin

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
    appSearchSessionFuture.setFuture(
        PlatformStorage.createSearchSession(
            PlatformStorage.SearchContext.Builder(mContext, DATABASE_NAME)
               .build()
        )
    )
} else {
    if (usePlayServicesStorageBelowS) {
        appSearchSessionFuture.setFuture(
            PlayServicesStorage.createSearchSession(
                PlayServicesStorage.SearchContext.Builder(mContext, DATABASE_NAME)
                    .build()
            )
        )
    } else {
        appSearchSessionFuture.setFuture(
            LocalStorage.createSearchSession(
                LocalStorage.SearchContext.Builder(mContext, DATABASE_NAME)
                    .build()
            )
        )
    }
}

Java

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
    mAppSearchSessionFuture.setFuture(PlatformStorage.createSearchSession(
            new PlatformStorage.SearchContext.Builder(mContext, DATABASE_NAME)
                    .build()));
} else {
    if (usePlayServicesStorageBelowS) {
        mAppSearchSessionFuture.setFuture(PlayServicesStorage.createSearchSession(
                new PlayServicesStorage.SearchContext.Builder(mContext, DATABASE_NAME)
                        .build()));
    } else {
        mAppSearchSessionFuture.setFuture(LocalStorage.createSearchSession(
                new LocalStorage.SearchContext.Builder(mContext, DATABASE_NAME)
                        .build()));
    }
}

PlatformStorage और PlayServicesStorage का इस्तेमाल करके, आपका ऐप्लिकेशन अन्य ऐप्लिकेशन के साथ सुरक्षित तरीके से डेटा शेयर कर सकता है. इससे वे ऐप्लिकेशन आपके ऐप्लिकेशन के डेटा में भी खोज कर सकते हैं. सिर्फ़ पढ़ने के लिए ऐप्लिकेशन का डेटा शेयर करने की अनुमति, सर्टिफ़िकेट हैंडशेक का इस्तेमाल करके दी जाती है. इससे यह पक्का किया जाता है कि दूसरे ऐप्लिकेशन के पास डेटा पढ़ने की अनुमति है. इस एपीआई के बारे में ज़्यादा जानने के लिए, setSchemaTypeVisibilityForPackage() का दस्तावेज़ पढ़ें.

इसके अलावा, PlatformStorage की मदद से, इंडेक्स किए गए डेटा को सिस्टम यूज़र इंटरफ़ेस (यूआई) की स्क्रीन पर दिखाया जा सकता है. ऐप्लिकेशन, सिस्टम यूज़र इंटरफ़ेस (यूआई) की सरफ़ेस पर अपने कुछ या सभी डेटा को दिखाने से ऑप्ट आउट कर सकते हैं. setSchemaTypeDisplayedBySystem() के दस्तावेज़ में, इस एपीआई के बारे में ज़्यादा जानें.

सुविधाएं LocalStorage (Android 5.0 या इसके बाद के वर्शन के साथ काम करता है) PlatformStorage (Android 12 और इसके बाद के वर्शन के साथ काम करता है) PlayServicesStorage (Android 5.0 और इसके बाद के वर्शन के साथ काम करता है)
पूरे टेक्स्ट की खोज करने की बेहतर सुविधा
कई भाषाओं में उपलब्ध
बाइनरी साइज़ कम किया गया
एक ऐप्लिकेशन से दूसरे ऐप्लिकेशन के साथ डेटा शेयर करना
सिस्टम यूज़र इंटरफ़ेस (यूआई) के प्लैटफ़ॉर्म पर डेटा दिखाने की सुविधा
किसी भी साइज़ और संख्या में दस्तावेज़ों को इंडेक्स किया जा सकता है
बाइंडर की अतिरिक्त लेटेंसी के बिना, तेज़ी से काम करना

LocalStorage और PlatformStorage में से किसी एक को चुनते समय, कुछ और बातों का भी ध्यान रखना ज़रूरी है. PlatformStorage, AppSearch सिस्टम सर्विस पर Jetpack API को रैप करता है. इसलिए, LocalStorage का इस्तेमाल करने की तुलना में, APK के साइज़ पर कम असर पड़ता है. हालांकि, इसका मतलब यह भी है कि AppSearch सिस्टम सर्विस को कॉल करते समय, AppSearch की कार्रवाइयों में अतिरिक्त बाइंडर इंतज़ार का समय लगता है. PlatformStorage की मदद से, AppSearch किसी ऐप्लिकेशन के इंडेक्स किए जा सकने वाले दस्तावेज़ों की संख्या और साइज़ को सीमित करता है. इससे, एक बेहतर सेंट्रल इंडेक्स बनाया जा सकता है. PlayServicesStorage में भी PlatformStorage की तरह ही सीमाएं हैं. साथ ही, यह सिर्फ़ उन डिवाइसों पर काम करता है जिन पर Google Play services मौजूद है.

सुविधा की उपलब्धता देखें

हालांकि, स्टोरेज के सभी विकल्प एक ही एपीआई का इस्तेमाल करते हैं, लेकिन कुछ सुविधाएं हर स्टोरेज विकल्प या हर डिवाइस पर उपलब्ध नहीं होती हैं. एपीआई के रेफ़रंस में, @RequiresFeature एनोटेशन उन एपीआई की पहचान करता है जिनके लिए इनमें से किसी एक सुविधा की ज़रूरत होती है. साथ ही, Features क्लास, हर सुविधा के लिए एक कॉन्सटेंट तय करती है. उदाहरण के लिए, INDEXING_TYPE_RANGE के लिए Features.NUMERIC_SEARCH ज़रूरी है.

PlatformStorage के लिए, सुविधा की उपलब्धता डिवाइस के Android वर्शन पर निर्भर करती है. Android 13 (एपीआई लेवल 33) से, इस सुविधा की उपलब्धता इस बात पर भी निर्भर करती है कि डिवाइस को Google Play के सिस्टम अपडेट मिले हैं या नहीं. उदाहरण के लिए, PlatformStorage में नंबर के हिसाब से खोज (Features.NUMERIC_SEARCH), हूबहू खोज (Features.VERBATIM_SEARCH), और जॉइन (Features.JOIN_SPEC_AND_QUALIFIED_ID) की सुविधा सिर्फ़ इन डिवाइसों पर काम करती है:

  • Android 14 (एपीआई लेवल 34) या इसके बाद के वर्शन पर काम करने वाले डिवाइस.
  • Android 13 (एपीआई लेवल 33) पर काम करने वाले वे डिवाइस जिनमें Google Play का ज़रूरी सिस्टम अपडेट इंस्टॉल किया गया हो.

ये सुविधाएं, Android 12 या Android 12L (एपीआई लेवल 31 और 32) पर काम करने वाले डिवाइसों पर काम नहीं करती हैं.

किसी दस्तावेज़ में इंडेक्स की गई प्रॉपर्टी की ज़्यादा से ज़्यादा संख्या भी डिवाइस और स्टोरेज के विकल्प के हिसाब से अलग-अलग होती है. रनटाइम के दौरान सीमा जानने के लिए, getMaxIndexedProperties() को कॉल करें.

किसी सुविधा के काम करने का तरीका तय करने के लिए, सिर्फ़ Android वर्शन पर भरोसा न करें. किसी सुविधा की ज़रूरत वाले एपीआई को कॉल करने से पहले, पुष्टि करें कि वह सुविधा काम करती है. इसके लिए, AppSearchSession.getFeatures() से मिलने वाले Features ऑब्जेक्ट पर isFeatureSupported() को कॉल करें. अगर ज़रूरी सुविधा काम नहीं करती है, तो कार्रवाई पूरी नहीं हो पाती और गड़बड़ी का मैसेज दिखता है. उदाहरण के लिए, अगर किसी स्कीमा में INDEXING_TYPE_RANGE प्रॉपर्टी शामिल है, तो वह उन डिवाइसों पर काम नहीं करेगा जो Features.NUMERIC_SEARCH के साथ काम नहीं करते.

यहां दिया गया कोड यह जांच करता है कि खुला हुआ AppSearchSession, अंकों के हिसाब से खोजने की सुविधा के साथ काम करता है या नहीं:

Kotlin

val features = session.features
if (features.isFeatureSupported(Features.NUMERIC_SEARCH)) {
    // Numeric search is supported. You can index properties with
    // LongPropertyConfig.INDEXING_TYPE_RANGE and enable numeric search with
    // SearchSpec.Builder.setNumericSearchEnabled(true).
} else {
    // Numeric search isn't supported. Set a schema without range-indexed
    // properties, or switch to a different storage option.
}

Java

Features features = session.getFeatures();
if (features.isFeatureSupported(Features.NUMERIC_SEARCH)) {
    // Numeric search is supported. You can index properties with
    // LongPropertyConfig.INDEXING_TYPE_RANGE and enable numeric search with
    // SearchSpec.Builder.setNumericSearchEnabled(true).
} else {
    // Numeric search isn't supported. Set a schema without range-indexed
    // properties, or switch to a different storage option.
}

AppSearch का इस्तेमाल शुरू करना

इस सेक्शन में दिए गए उदाहरण में, AppSearch API का इस्तेमाल करके, नोट सेव करने वाले किसी काल्पनिक ऐप्लिकेशन के साथ इंटिग्रेट करने का तरीका बताया गया है.

दस्तावेज़ की क्लास लिखना

AppSearch के साथ इंटिग्रेट करने के लिए, सबसे पहले एक दस्तावेज़ क्लास लिखनी होगी. इसमें, डेटाबेस में डाले जाने वाले डेटा के बारे में जानकारी दी जाएगी. @Document एनोटेशन का इस्तेमाल करके, किसी क्लास को दस्तावेज़ क्लास के तौर पर मार्क करें.दस्तावेज़ क्लास के इंस्टेंस का इस्तेमाल करके, डेटाबेस में दस्तावेज़ों को सेव किया जा सकता है और उन्हें वापस पाया जा सकता है.

यहां दिया गया कोड, Note ऑब्जेक्ट के टेक्स्ट को इंडेक्स करने के लिए, @Document.StringProperty एनोटेट किए गए फ़ील्ड के साथ Note दस्तावेज़ क्लास को तय करता है.

Kotlin

@Document
public data class Note(

    // Required field for a document class. All documents MUST have a namespace.
    @Document.Namespace
    val namespace: String,

    // Required field for a document class. All documents MUST have an Id.
    @Document.Id
    val id: String,

    // Optional field for a document class, used to set the score of the
    // document. If this is not included in a document class, the score is set
    // to a default of 0.
    @Document.Score
    val score: Int,

    // Optional field for a document class, used to index a note's text for this
    // document class.
    @Document.StringProperty(indexingType = AppSearchSchema.StringPropertyConfig.INDEXING_TYPE_PREFIXES)
    val text: String
)

Java

@Document
public class Note {

  // Required field for a document class. All documents MUST have a namespace.
  @Document.Namespace
  private final String namespace;

  // Required field for a document class. All documents MUST have an Id.
  @Document.Id
  private final String id;

  // Optional field for a document class, used to set the score of the
  // document. If this is not included in a document class, the score is set
  // to a default of 0.
  @Document.Score
  private final int score;

  // Optional field for a document class, used to index a note's text for this
  // document class.
  @Document.StringProperty(indexingType = StringPropertyConfig.INDEXING_TYPE_PREFIXES)
  private final String text;

  Note(@NonNull String id, @NonNull String namespace, int score, @NonNull String text) {
    this.id = Objects.requireNonNull(id);
    this.namespace = Objects.requireNonNull(namespace);
    this.score = score;
    this.text = Objects.requireNonNull(text);
  }

  @NonNull
  public String getNamespace() {
    return namespace;
  }

  @NonNull
  public String getId() {
    return id;
  }

  public int getScore() {
    return score;
  }

  @NonNull
  public String getText() {
     return text;
  }
}

कोई डेटाबेस खोलना

दस्तावेज़ों के साथ काम करने से पहले, आपको एक डेटाबेस बनाना होगा. यहां दिया गया कोड, notes_app नाम से एक नया डेटाबेस बनाता है और AppSearchSession के लिए ListenableFuture हासिल करता है. यह डेटाबेस से कनेक्शन को दिखाता है और डेटाबेस से जुड़े कामों के लिए एपीआई उपलब्ध कराता है.

Kotlin

val context: Context = getApplicationContext()
val sessionFuture = LocalStorage.createSearchSession(
    LocalStorage.SearchContext.Builder(context, /*databaseName=*/"notes_app")
    .build()
)

Java

Context context = getApplicationContext();
ListenableFuture<AppSearchSession> sessionFuture = LocalStorage.createSearchSession(
       new LocalStorage.SearchContext.Builder(context, /*databaseName=*/ "notes_app")
               .build()
);

कोई स्कीमा सेट करना

डेटाबेस में दस्तावेज़ डालने और उससे दस्तावेज़ वापस पाने से पहले, आपको स्कीमा सेट करना होगा. डेटाबेस स्कीमा में अलग-अलग तरह का स्ट्रक्चर्ड डेटा होता है. इसे "स्कीमा टाइप" कहा जाता है. यहां दिया गया कोड, स्कीमा टाइप के तौर पर दस्तावेज़ क्लास देकर स्कीमा सेट करता है.

Kotlin

val setSchemaRequest = SetSchemaRequest.Builder().addDocumentClasses(Note::class.java)
    .build()
val setSchemaFuture = Futures.transformAsync(
    sessionFuture,
    { session ->
        session?.setSchema(setSchemaRequest)
    }, mExecutor
)

Java

SetSchemaRequest setSchemaRequest = new SetSchemaRequest.Builder().addDocumentClasses(Note.class)
       .build();
ListenableFuture<SetSchemaResponse> setSchemaFuture =
       Futures.transformAsync(sessionFuture, session -> session.setSchema(setSchemaRequest), mExecutor);

डेटाबेस में कोई दस्तावेज़ डालना

स्कीमा टाइप जोड़ने के बाद, उस टाइप के दस्तावेज़ों को डेटाबेस में जोड़ा जा सकता है. यहां दिया गया कोड, Note दस्तावेज़ क्लास बिल्डर का इस्तेमाल करके, स्कीमा टाइप Note का दस्तावेज़ बनाता है. यह दस्तावेज़ के नेमस्पेस user1 को सेट करता है, ताकि इस सैंपल के किसी भी उपयोगकर्ता को दिखाया जा सके. इसके बाद, दस्तावेज़ को डेटाबेस में डाला जाता है. साथ ही, पुट ऑपरेशन के नतीजे को प्रोसेस करने के लिए, एक लिसनर अटैच किया जाता है.

Kotlin

val note = Note(
    namespace="user1",
    id="noteId",
    score=10,
    text="Buy fresh fruit"
)

val putRequest = PutDocumentsRequest.Builder().addDocuments(note).build()
val putFuture = Futures.transformAsync(
    sessionFuture,
    { session ->
        session?.put(putRequest)
    }, mExecutor
)

Futures.addCallback(
    putFuture,
    object : FutureCallback<AppSearchBatchResult<String, Void>?> {
        override fun onSuccess(result: AppSearchBatchResult<String, Void>?) {

            // Gets map of successful results from Id to Void
            val successfulResults = result?.successes

            // Gets map of failed results from Id to AppSearchResult
            val failedResults = result?.failures
        }

        override fun onFailure(t: Throwable) {
            Log.e(TAG, "Failed to put documents.", t)
        }
    },
    mExecutor
)

Java

Note note = new Note(/*namespace=*/"user1", /*id=*/
                "noteId", /*score=*/ 10, /*text=*/ "Buy fresh fruit!");

PutDocumentsRequest putRequest = new PutDocumentsRequest.Builder().addDocuments(note)
       .build();
ListenableFuture<AppSearchBatchResult<String, Void>> putFuture =
       Futures.transformAsync(sessionFuture, session -> session.put(putRequest), mExecutor);

Futures.addCallback(putFuture, new FutureCallback<AppSearchBatchResult<String, Void>>() {
   @Override
   public void onSuccess(@Nullable AppSearchBatchResult<String, Void> result) {

     // Gets map of successful results from Id to Void
     Map<String, Void> successfulResults = result.getSuccesses();

     // Gets map of failed results from Id to AppSearchResult
     Map<String, AppSearchResult<Void>> failedResults = result.getFailures();
   }

   @Override
   public void onFailure(@NonNull Throwable t) {
      Log.e(TAG, "Failed to put documents.", t);
   }
}, mExecutor);

इस सेक्शन में बताए गए सर्च ऑपरेटर का इस्तेमाल करके, इंडेक्स किए गए दस्तावेज़ों को खोजा जा सकता है. यहां दिया गया कोड, user1 नेमस्पेस से जुड़े दस्तावेज़ों के डेटाबेस में, "fruit" शब्द के लिए क्वेरी करता है.

Kotlin

val searchSpec = SearchSpec.Builder()
    .addFilterNamespaces("user1")
    .build();

val searchFuture = Futures.transform(
    sessionFuture,
    { session ->
        session?.search("fruit", searchSpec)
    },
    mExecutor
)
Futures.addCallback(
    searchFuture,
    object : FutureCallback<SearchResults> {
        override fun onSuccess(searchResults: SearchResults?) {
            iterateSearchResults(searchResults)
        }

        override fun onFailure(t: Throwable?) {
            Log.e("TAG", "Failed to search notes in AppSearch.", t)
        }
    },
    mExecutor
)

Java

SearchSpec searchSpec = new SearchSpec.Builder()
       .addFilterNamespaces("user1")
       .build();

ListenableFuture<SearchResults> searchFuture =
       Futures.transform(sessionFuture, session -> session.search("fruit", searchSpec),
       mExecutor);

Futures.addCallback(searchFuture,
       new FutureCallback<SearchResults>() {
           @Override
           public void onSuccess(@Nullable SearchResults searchResults) {
               iterateSearchResults(searchResults);
           }

           @Override
           public void onFailure(@NonNull Throwable t) {
               Log.e(TAG, "Failed to search notes in AppSearch.", t);
           }
       }, mExecutor);

SearchResults को बार-बार दोहराएं

खोजों से SearchResults इंस्टेंस मिलता है. इससे SearchResult ऑब्जेक्ट के पेजों को ऐक्सेस किया जा सकता है. हर SearchResult में, उससे मेल खाने वाला GenericDocument होता है. यह दस्तावेज़ का सामान्य फ़ॉर्म होता है, जिसमें सभी दस्तावेज़ों को बदला जाता है. नीचे दिए गए कोड से, खोज के नतीजों का पहला पेज मिलता है. साथ ही, नतीजे को वापस Note दस्तावेज़ में बदल दिया जाता है.

Kotlin

Futures.transform(
    searchResults?.nextPage,
    { page: List<SearchResult>? ->
        // Gets GenericDocument from SearchResult.
        val genericDocument: GenericDocument = page!![0].genericDocument
        val schemaType = genericDocument.schemaType
        val note: Note? = try {
            if (schemaType == "Note") {
                // Converts GenericDocument object to Note object.
                genericDocument.toDocumentClass(Note::class.java)
            } else null
        } catch (e: AppSearchException) {
            Log.e(
                TAG,
                "Failed to convert GenericDocument to Note",
                e
            )
            null
        }
        note
    },
    mExecutor
)

Java

Futures.transform(searchResults.getNextPage(), page -> {
  // Gets GenericDocument from SearchResult.
  GenericDocument genericDocument = page.get(0).getGenericDocument();
  String schemaType = genericDocument.getSchemaType();

  Note note = null;

  if (schemaType.equals("Note")) {
    try {
      // Converts GenericDocument object to Note object.
      note = genericDocument.toDocumentClass(Note.class);
    } catch (AppSearchException e) {
      Log.e(TAG, "Failed to convert GenericDocument to Note", e);
    }
  }

  return note;
}, mExecutor);

कोई दस्तावेज़ हटाना

जब उपयोगकर्ता कोई नोट मिटाता है, तो ऐप्लिकेशन डेटाबेस से उससे जुड़ा Note दस्तावेज़ मिटा देता है. इससे यह पक्का होता है कि नोट अब क्वेरी में नहीं दिखेगा. यहां दिया गया कोड, आईडी के हिसाब से डेटाबेस से Note दस्तावेज़ को हटाने का अनुरोध करता है.

Kotlin

val removeRequest = RemoveByDocumentIdRequest.Builder("user1")
    .addIds("noteId")
    .build()

val removeFuture = Futures.transformAsync(
    sessionFuture, { session ->
        session?.remove(removeRequest)
    },
    mExecutor
)

Java

RemoveByDocumentIdRequest removeRequest = new RemoveByDocumentIdRequest.Builder("user1")
       .addIds("noteId")
       .build();

ListenableFuture<AppSearchBatchResult<String, Void>> removeFuture =
       Futures.transformAsync(sessionFuture, session -> session.remove(removeRequest), mExecutor);

डिस्क पर सेव करें

डेटाबेस में किए गए अपडेट, समय-समय पर डिस्क में सेव किए जाने चाहिए. इसके लिए, requestFlush() को कॉल करें. यहां दिया गया कोड, लिसनर के साथ requestFlush() को कॉल करता है, ताकि यह पता लगाया जा सके कि कॉल सफल रहा या नहीं.

Kotlin

val requestFlushFuture = Futures.transformAsync(
    sessionFuture,
    { session -> session?.requestFlush() }, mExecutor
)

Futures.addCallback(requestFlushFuture, object : FutureCallback<Void?> {
    override fun onSuccess(result: Void?) {
        // Success! Database updates have been persisted to disk.
    }

    override fun onFailure(t: Throwable) {
        Log.e(TAG, "Failed to flush database updates.", t)
    }
}, mExecutor)

Java

ListenableFuture<Void> requestFlushFuture = Futures.transformAsync(sessionFuture,
        session -> session.requestFlush(), mExecutor);

Futures.addCallback(requestFlushFuture, new FutureCallback<Void>() {
    @Override
    public void onSuccess(@Nullable Void result) {
        // Success! Database updates have been persisted to disk.
    }

    @Override
    public void onFailure(@NonNull Throwable t) {
        Log.e(TAG, "Failed to flush database updates.", t);
    }
}, mExecutor);

किसी सेशन को बंद करना

जब कोई ऐप्लिकेशन किसी डेटाबेस ऑपरेशन को कॉल नहीं करेगा, तो AppSearchSession को बंद कर देना चाहिए. यहां दिया गया कोड, पहले खोले गए AppSearch सेशन को बंद करता है और सभी अपडेट को डिस्क में सेव करता है.

Kotlin

val closeFuture = Futures.transform<AppSearchSession, Unit>(sessionFuture,
    { session ->
        session?.close()
        Unit
    }, mExecutor
)

Java

ListenableFuture<Void> closeFuture = Futures.transform(sessionFuture, session -> {
   session.close();
   return null;
}, mExecutor);

अन्य संसाधन

AppSearch के बारे में ज़्यादा जानने के लिए, ये अतिरिक्त संसाधन देखें:

सैंपल

  • Android AppSearch Sample (Kotlin), नोट लेने वाला एक ऐप्लिकेशन है. यह उपयोगकर्ता के नोट को इंडेक्स करने के लिए, AppSearch का इस्तेमाल करता है. साथ ही, उपयोगकर्ताओं को उनके नोट खोजने की सुविधा देता है.

सुझाव/राय दें या शिकायत करें

इन संसाधनों का इस्तेमाल करके, अपने सुझाव, शिकायत या राय और आइडिया हमारे साथ शेयर करें:

Issue Tracker

बग की शिकायत करें, ताकि हम उन्हें ठीक कर सकें.