Codelab Android Cloud Firestore

1. Ikhtisar

Sasaran

Dalam codelab ini Anda akan membangun aplikasi rekomendasi restoran di Android yang didukung oleh Cloud Firestore. Anda akan belajar cara:

  • Membaca dan menulis data ke Firestore dari aplikasi Android
  • Dengarkan perubahan data Firestore secara realtime
  • Gunakan Firebase Authentication dan aturan keamanan untuk mengamankan data Firestore
  • Tulis kueri Firestore yang kompleks

Prasyarat

Sebelum memulai codelab ini, pastikan Anda memiliki:

  • Android Studio 4.0 atau lebih tinggi
  • Emulator Android
  • Node.js versi 10 atau lebih tinggi
  • Java versi 8 atau lebih tinggi

2. Buat proyek Firebase

  1. Masuk ke konsol Firebase dengan akun Google Anda.
  2. Dalam Firebase konsol , klik proyek Tambah.
  3. Seperti ditunjukkan dalam screen capture di bawah ini, masukkan nama untuk proyek Firebase Anda (misalnya, "Santapan ramah"), dan klik Lanjutkan.

9d2f625aebcab6af.png

  1. Anda mungkin diminta untuk mengaktifkan Google Analytics, untuk tujuan codelab ini, pilihan Anda tidak menjadi masalah.
  2. Setelah sekitar satu menit, proyek Firebase Anda akan siap. Klik Lanjutkan.

3. Siapkan proyek sampel

Unduh kodenya

Jalankan perintah berikut untuk mengkloning kode sampel untuk codelab ini. Ini akan membuat folder bernama friendlyeats-android pada mesin Anda:

$ git clone https://github.com/firebase/friendlyeats-android

Jika Anda tidak memiliki git di mesin Anda, Anda juga dapat mengunduh kodenya langsung dari GitHub.

Impor proyek ke Android Studio. Anda mungkin akan melihat beberapa kesalahan kompilasi atau mungkin peringatan tentang hilang google-services.json berkas. Kami akan memperbaiki ini di bagian berikutnya.

Tambahkan konfigurasi Firebase

  1. Dalam Firebase konsol , pilih Ikhtisar Proyek di nav kiri. Klik tombol Android untuk memilih platform. Ketika diminta untuk nama paket penggunaan com.google.firebase.example.fireeats

73d151ed16016421.png

  1. Klik Register App dan ikuti petunjuk untuk men-download google-services.json file, dan memindahkannya ke dalam app/ folder dari kode contoh. Kemudian klik Next.

4. Siapkan Emulator Firebase

Dalam codelab ini Anda akan menggunakan Firebase Emulator Suite untuk lokal meniru Cloud Firestore dan jasa Firebase lainnya. Ini menyediakan lingkungan pengembangan lokal yang aman, cepat, dan gratis untuk membangun aplikasi Anda.

Instal Firebase CLI

Pertama, Anda akan perlu menginstal Firebase CLI . Cara termudah untuk melakukannya adalah dengan menggunakan npm :

npm install -g firebase-tools

Jika Anda tidak memiliki npm atau Anda mengalami kesalahan, membaca petunjuk instalasi untuk mendapatkan biner mandiri untuk platform Anda.

Setelah Anda menginstal CLI, berjalan firebase --version harus melaporkan versi 9.0.0 atau lebih tinggi:

$ firebase --version
9.0.0

Gabung

Jalankan firebase login untuk menghubungkan CLI untuk akun Google Anda. Ini akan membuka jendela browser baru untuk menyelesaikan proses login. Pastikan untuk memilih akun yang sama dengan yang Anda gunakan saat membuat proyek Firebase sebelumnya.

Dari dalam friendlyeats-android folder run firebase use --add untuk menghubungkan proyek lokal Anda untuk proyek Firebase Anda. Ikuti petunjuk untuk memilih proyek yang Anda buat sebelumnya dan jika diminta untuk memilih alias masuk default .

5. Jalankan aplikasi

Sekarang saatnya menjalankan Firebase Emulator Suite dan aplikasi Android FriendlyEats untuk pertama kalinya.

Jalankan emulator

Dalam terminal Anda dari dalam friendlyeats-android direktori run firebase emulators:start untuk memulai dengan Firebase Emulator. Anda akan melihat log seperti ini:

$ firebase emulators:start
i  emulators: Starting emulators: auth, firestore
i  firestore: Firestore Emulator logging to firestore-debug.log
i  ui: Emulator UI logging to ui-debug.log

┌─────────────────────────────────────────────────────────────┐
│ ✔  All emulators ready! It is now safe to connect your app. │
│ i  View Emulator UI at http://localhost:4000                │
└─────────────────────────────────────────────────────────────┘

┌────────────────┬────────────────┬─────────────────────────────────┐
│ Emulator       │ Host:Port      │ View in Emulator UI             │
├────────────────┼────────────────┼─────────────────────────────────┤
│ Authentication │ localhost:9099 │ http://localhost:4000/auth      │
├────────────────┼────────────────┼─────────────────────────────────┤
│ Firestore      │ localhost:8080 │ http://localhost:4000/firestore │
└────────────────┴────────────────┴─────────────────────────────────┘
  Emulator Hub running at localhost:4400
  Other reserved ports: 4500

Issues? Report them at https://github.com/firebase/firebase-tools/issues and attach the *-debug.log files.

Anda sekarang memiliki lingkungan pengembangan lokal lengkap yang berjalan di mesin Anda! Pastikan untuk membiarkan perintah ini berjalan selama codelab lainnya, aplikasi Android Anda harus terhubung ke emulator.

Hubungkan aplikasi ke Emulator

Buka file FirebaseUtil.java di Android Studio. File ini berisi logika untuk menghubungkan Firebase SDK ke emulator lokal yang berjalan di mesin Anda.

Di bagian atas file, periksa baris ini:

    /** Use emulators only in debug builds **/
    private static final boolean sUseEmulators = BuildConfig.DEBUG;

Kami menggunakan BuildConfig untuk memastikan kita hanya terhubung ke emulator ketika aplikasi kami berjalan dalam debug modus. Ketika kita mengkompilasi aplikasi dalam release modus kondisi ini akan palsu.

Sekarang kita lihat pada getFirestore() metode:

    public static FirebaseFirestore getFirestore() {
        if (FIRESTORE == null) {
            FIRESTORE = FirebaseFirestore.getInstance();

            // Connect to the Cloud Firestore emulator when appropriate. The host '10.0.2.2' is a
            // special IP address to let the Android emulator connect to 'localhost'.
            if (sUseEmulators) {
                FIRESTORE.useEmulator("10.0.2.2", 8080);
            }
        }

        return FIRESTORE;
    }

Kita bisa melihat bahwa itu menggunakan useEmulator(host, port) metode untuk menghubungkan Firebase SDK untuk emulator Firestore lokal. Sepanjang aplikasi kita akan menggunakan FirebaseUtil.getFirestore() untuk mengakses instance ini FirebaseFirestore sehingga kami yakin bahwa kami selalu menghubungkan ke emulator Firestore ketika berjalan di debug modus.

Jalankan aplikasinya

Jika Anda telah menambahkan google-services.json berkas benar, proyek sekarang harus mengkompilasi. Dalam Android Studio klik Build> Rebuild Project dan memastikan bahwa tidak ada kesalahan yang tersisa.

Dalam Android Studio Jalankan aplikasi pada emulator Android Anda. Pada awalnya Anda akan disajikan dengan layar "Masuk". Anda dapat menggunakan email dan kata sandi apa pun untuk masuk ke aplikasi. Proses masuk ini terhubung ke emulator Firebase Authentication, jadi tidak ada kredensial nyata yang dikirimkan.

Sekarang buka Emulator UI dengan menavigasi ke http: // localhost: 4000 di browser web Anda. Kemudian klik pada tab Authentication dan Anda akan melihat account yang baru saja dibuat:

Firebase Auth Emulator

Setelah Anda menyelesaikan proses masuk, Anda akan melihat layar beranda aplikasi:

de06424023ffb4b9.png

Segera kami akan menambahkan beberapa data untuk mengisi layar beranda.

6. Tulis data ke Firestore

Di bagian ini kita akan menulis beberapa data ke Firestore sehingga kita dapat mengisi layar beranda yang saat ini kosong.

Utama objek model dalam aplikasi kita adalah restoran (lihat model/Restaurant.java ). Data Firestore dibagi menjadi dokumen, koleksi, dan subkoleksi. Kami akan menyimpan masing-masing restoran sebagai dokumen koleksi tingkat atas disebut "restaurants" . Untuk mempelajari lebih lanjut tentang model data Firestore, membaca tentang dokumen dan koleksi di dokumentasi .

Untuk tujuan demonstrasi, kami akan menambahkan fungsionalitas di aplikasi untuk membuat sepuluh restoran acak ketika kami mengklik tombol "Tambahkan Item Acak" di menu luapan. Buka file MainActivity.java dan mengisi di onAddItemsClicked() metode:

    private void onAddItemsClicked() {
        // Get a reference to the restaurants collection
        CollectionReference restaurants = mFirestore.collection("restaurants");

        for (int i = 0; i < 10; i++) {
            // Get a random Restaurant POJO
            Restaurant restaurant = RestaurantUtil.getRandom(this);

            // Add a new document to the restaurants collection
            restaurants.add(restaurant);
        }
    }

Ada beberapa hal penting yang perlu diperhatikan tentang kode di atas:

  • Kami mulai dengan mendapatkan referensi ke "restaurants" koleksi. Koleksi dibuat secara implisit saat dokumen ditambahkan, jadi tidak perlu membuat koleksi sebelum menulis data.
  • Dokumen dapat dibuat menggunakan POJO, yang kami gunakan untuk membuat setiap dokumen Restoran.
  • The add() metode menambahkan dokumen ke koleksi dengan ID otomatis dihasilkan, jadi kita tidak perlu menentukan ID unik untuk setiap Restaurant.

Sekarang jalankan aplikasi lagi dan klik tombol "Tambahkan Item Acak" di menu luapan untuk menjalankan kode yang baru saja Anda tulis:

95691e9b71ba55e3.png

Sekarang buka Emulator UI dengan menavigasi ke http: // localhost: 4000 di browser web Anda. Kemudian klik pada tab Firestore dan Anda akan melihat data yang Anda baru saja menambahkan:

Firebase Auth Emulator

Data ini 100% lokal untuk mesin Anda. Faktanya, proyek Anda yang sebenarnya bahkan belum memiliki database Firestore! Ini berarti aman untuk bereksperimen dengan memodifikasi dan menghapus data ini tanpa konsekuensi.

Selamat, Anda baru saja menulis data ke Firestore! Pada langkah selanjutnya kita akan mempelajari cara menampilkan data ini di aplikasi.

7. Menampilkan data dari Firestore

Pada langkah ini kita akan belajar cara mengambil data dari Firestore dan menampilkannya di aplikasi kita. Langkah pertama untuk membaca data dari Firestore adalah untuk menciptakan sebuah Query . Memodifikasi onCreate() metode:

        mFirestore = FirebaseUtil.getFirestore();

        // Get the 50 highest rated restaurants
        mQuery = mFirestore.collection("restaurants")
                .orderBy("avgRating", Query.Direction.DESCENDING)
                .limit(LIMIT);

Sekarang kami ingin mendengarkan kueri, sehingga kami mendapatkan semua dokumen yang cocok dan diberi tahu tentang pembaruan di masa mendatang secara real time. Karena tujuan akhirnya kami adalah untuk mengikat data ini ke RecyclerView , kita perlu membuat RecyclerView.Adapter kelas untuk mendengarkan data.

Buka FirestoreAdapter kelas, yang sebagian telah dilaksanakan sudah. Pertama, mari kita membuat adaptor menerapkan EventListener dan menentukan onEvent fungsi sehingga dapat menerima update untuk query Firestore:

public abstract class FirestoreAdapter<VH extends RecyclerView.ViewHolder>
        extends RecyclerView.Adapter<VH>
        implements EventListener<QuerySnapshot> { // Add this "implements"

    // ...

    // Add this method
    @Override
    public void onEvent(QuerySnapshot documentSnapshots,
                        FirebaseFirestoreException e) {

        // Handle errors
        if (e != null) {
            Log.w(TAG, "onEvent:error", e);
            return;
        }

        // Dispatch the event
        for (DocumentChange change : documentSnapshots.getDocumentChanges()) {
            // Snapshot of the changed document
            DocumentSnapshot snapshot = change.getDocument();

            switch (change.getType()) {
                case ADDED:
                    // TODO: handle document added
                    break;
                case MODIFIED:
                    // TODO: handle document modified
                    break;
                case REMOVED:
                    // TODO: handle document removed
                    break;
            }
        }

        onDataChanged();
    }

  // ...
}

Pada beban awal pendengar akan menerima satu ADDED acara untuk setiap dokumen baru. Karena kumpulan hasil kueri berubah seiring waktu, pendengar akan menerima lebih banyak acara yang berisi perubahan. Sekarang mari kita selesaikan implementasi listener. Pertama menambahkan tiga metode baru: onDocumentAdded , onDocumentModified , dan onDocumentRemoved :

    protected void onDocumentAdded(DocumentChange change) {
        mSnapshots.add(change.getNewIndex(), change.getDocument());
        notifyItemInserted(change.getNewIndex());
    }

    protected void onDocumentModified(DocumentChange change) {
        if (change.getOldIndex() == change.getNewIndex()) {
            // Item changed but remained in same position
            mSnapshots.set(change.getOldIndex(), change.getDocument());
            notifyItemChanged(change.getOldIndex());
        } else {
            // Item changed and changed position
            mSnapshots.remove(change.getOldIndex());
            mSnapshots.add(change.getNewIndex(), change.getDocument());
            notifyItemMoved(change.getOldIndex(), change.getNewIndex());
        }
    }

    protected void onDocumentRemoved(DocumentChange change) {
        mSnapshots.remove(change.getOldIndex());
        notifyItemRemoved(change.getOldIndex());
    }

Kemudian memanggil metode baru dari onEvent :

    @Override
    public void onEvent(QuerySnapshot documentSnapshots,
                        FirebaseFirestoreException e) {

        // ...

        // Dispatch the event
        for (DocumentChange change : documentSnapshots.getDocumentChanges()) {
            // Snapshot of the changed document
            DocumentSnapshot snapshot = change.getDocument();

            switch (change.getType()) {
                case ADDED:
                    onDocumentAdded(change); // Add this line
                    break;
                case MODIFIED:
                    onDocumentModified(change); // Add this line
                    break;
                case REMOVED:
                    onDocumentRemoved(change); // Add this line
                    break;
            }
        }

        onDataChanged();
    }

Akhirnya melaksanakan startListening() metode untuk melampirkan pendengar:

    public void startListening() {
        if (mQuery != null && mRegistration == null) {
            mRegistration = mQuery.addSnapshotListener(this);
        }
    }

Sekarang aplikasi sepenuhnya dikonfigurasi untuk membaca data dari Firestore. Jalankan aplikasi lagi dan Anda akan melihat restoran Anda ditambahkan dalam langkah sebelumnya:

9e45f40faefce5d0.png

Sekarang kembali ke UI Emulator di browser Anda dan edit salah satu nama restoran. Anda akan melihatnya berubah di aplikasi hampir seketika!

8. Urutkan dan filter data

Aplikasi saat ini menampilkan restoran berperingkat teratas di seluruh koleksi, tetapi di aplikasi restoran nyata, pengguna ingin mengurutkan dan memfilter data. Misalnya aplikasi harus dapat menampilkan "Restoran makanan laut terbaik di Philadelphia" atau "Pizza paling murah".

Mengklik bilah putih di bagian atas aplikasi akan menampilkan dialog filter. Di bagian ini kita akan menggunakan kueri Firestore untuk membuat dialog ini berfungsi:

67898572a35672a5.png

Mari kita edit onFilter() metode MainActivity.java . Metode ini menerima Filters objek yang merupakan objek pembantu kita buat untuk menangkap output dari dialog filter. Kami akan mengubah metode ini untuk membuat kueri dari filter:

    @Override
    public void onFilter(Filters filters) {
        // Construct query basic query
        Query query = mFirestore.collection("restaurants");

        // Category (equality filter)
        if (filters.hasCategory()) {
            query = query.whereEqualTo("category", filters.getCategory());
        }

        // City (equality filter)
        if (filters.hasCity()) {
            query = query.whereEqualTo("city", filters.getCity());
        }

        // Price (equality filter)
        if (filters.hasPrice()) {
            query = query.whereEqualTo("price", filters.getPrice());
        }

        // Sort by (orderBy with direction)
        if (filters.hasSortBy()) {
            query = query.orderBy(filters.getSortBy(), filters.getSortDirection());
        }

        // Limit items
        query = query.limit(LIMIT);

        // Update the query
        mQuery = query;
        mAdapter.setQuery(query);

        // Set header
        mCurrentSearchView.setText(Html.fromHtml(filters.getSearchDescription(this)));
        mCurrentSortByView.setText(filters.getOrderDescription(this));

        // Save filters
        mViewModel.setFilters(filters);
    }

Dalam potongan di atas kita membangun Query objek dengan melampirkan where dan orderBy klausul untuk mencocokkan filter yang diberikan.

Jalankan aplikasi lagi dan pilih filter berikut untuk menunjukkan sebagian besar restoran harga rendah yang populer:

7a67a8a400c80c50.png

Anda sekarang akan melihat daftar restoran yang difilter yang hanya berisi opsi harga rendah:

a670188398c3c59.png

Jika Anda telah sampai sejauh ini, Anda sekarang telah membangun aplikasi melihat rekomendasi restoran yang berfungsi penuh di Firestore! Anda sekarang dapat mengurutkan dan memfilter restoran secara real time. Di beberapa bagian berikutnya kami memposting ulasan dan keamanan ke aplikasi.

9. Atur data dalam subkoleksi

Di bagian ini kami akan menambahkan peringkat ke aplikasi sehingga pengguna dapat meninjau restoran favorit (atau paling tidak favorit).

Koleksi dan subkoleksi

Sejauh ini kami telah menyimpan semua data restoran dalam koleksi tingkat atas yang disebut "restoran". Ketika tingkat pengguna restoran kami ingin menambahkan baru Rating objek ke restoran. Untuk tugas ini kita akan menggunakan subkoleksi. Anda dapat menganggap subkoleksi sebagai koleksi yang dilampirkan ke dokumen. Jadi setiap dokumen restoran akan memiliki subkoleksi rating yang penuh dengan dokumen rating. Subkoleksi membantu mengatur data tanpa membuat dokumen kita membengkak atau memerlukan kueri yang rumit.

Untuk mengakses subcollection, panggilan .collection() pada dokumen induk:

CollectionReference subRef = mFirestore.collection("restaurants")
        .document("abc123")
        .collection("ratings");

Anda dapat mengakses dan mengkueri subkoleksi seperti halnya dengan koleksi tingkat atas, tidak ada batasan ukuran atau perubahan kinerja. Anda dapat membaca lebih lanjut tentang model data Firestore sini .

Menulis data dalam sebuah transaksi

Menambahkan Rating ke subcollection yang tepat hanya membutuhkan memanggil .add() , tapi kami juga perlu memperbarui Restaurant nilai rata-rata objek dan jumlah peringkat untuk mencerminkan data baru. Jika kami menggunakan operasi terpisah untuk membuat dua perubahan ini, ada sejumlah kondisi balapan yang dapat mengakibatkan data basi atau salah.

Untuk memastikan bahwa peringkat ditambahkan dengan benar, kami akan menggunakan transaksi untuk menambahkan peringkat ke restoran. Transaksi ini akan melakukan beberapa tindakan:

  • Baca peringkat restoran saat ini dan hitung yang baru
  • Tambahkan peringkat ke subkoleksi
  • Perbarui peringkat rata-rata restoran dan jumlah peringkat

Terbuka RestaurantDetailActivity.java dan melaksanakan addRating fungsi:

    private Task<Void> addRating(final DocumentReference restaurantRef,
                                 final Rating rating) {
        // Create reference for new rating, for use inside the transaction
        final DocumentReference ratingRef = restaurantRef.collection("ratings")
                .document();

        // In a transaction, add the new rating and update the aggregate totals
        return mFirestore.runTransaction(new Transaction.Function<Void>() {
            @Override
            public Void apply(Transaction transaction)
                    throws FirebaseFirestoreException {

                Restaurant restaurant = transaction.get(restaurantRef)
                        .toObject(Restaurant.class);

                // Compute new number of ratings
                int newNumRatings = restaurant.getNumRatings() + 1;

                // Compute new average rating
                double oldRatingTotal = restaurant.getAvgRating() *
                        restaurant.getNumRatings();
                double newAvgRating = (oldRatingTotal + rating.getRating()) /
                        newNumRatings;

                // Set new restaurant info
                restaurant.setNumRatings(newNumRatings);
                restaurant.setAvgRating(newAvgRating);

                // Commit to Firestore
                transaction.set(restaurantRef, restaurant);
                transaction.set(ratingRef, rating);

                return null;
            }
        });
    }

The addRating() mengembalikan fungsi Task mewakili seluruh transaksi. Dalam onRating() pendengar fungsi ditambahkan ke tugas untuk merespon hasil dari transaksi.

Sekarang Jalankan aplikasi lagi dan klik pada salah satu restoran, yang harus membawa layar restaurant detail. Klik tombol + untuk mulai menambahkan review. Tambahkan ulasan dengan memilih sejumlah bintang dan memasukkan beberapa teks.

78fa16cdf8ef435a.png

Menekan Kirim akan memulai transaksi. Ketika transaksi selesai, Anda akan melihat ulasan Anda ditampilkan di bawah dan pembaruan jumlah ulasan restoran:

f9e670f40bd615b0.png

Selamat! Anda sekarang memiliki aplikasi ulasan restoran seluler, lokal, sosial yang dibangun di Cloud Firestore. Kudengar itu sangat populer akhir-akhir ini.

10. Amankan data Anda

Sejauh ini kami belum mempertimbangkan keamanan aplikasi ini. Bagaimana kita tahu bahwa pengguna hanya dapat membaca dan menulis data sendiri yang benar? Firestore datbases dijamin dengan file konfigurasi yang disebut Aturan Keamanan .

Buka firestore.rules berkas, Anda harus melihat berikut:

rules_version = '2';
service cloud.firestore {
  match /databases/{database}/documents {
    match /{document=**} {
      //
      // WARNING: These rules are insecure! We will replace them with
      // more secure rules later in the codelab
      //
      allow read, write: if request.auth != null;
    }
  }
}

Mari perubahan aturan ini untuk mencegah data yang tidak diinginkan acesss atau perubahan, buka firestore.rules berkas dan mengganti isi dengan:

rules_version = '2';
service cloud.firestore {
  match /databases/{database}/documents {
    // Determine if the value of the field "key" is the same
    // before and after the request.
    function isUnchanged(key) {
      return (key in resource.data)
        && (key in request.resource.data)
        && (resource.data[key] == request.resource.data[key]);
    }

    // Restaurants
    match /restaurants/{restaurantId} {
      // Any signed-in user can read
      allow read: if request.auth != null;

      // Any signed-in user can create
      // WARNING: this rule is for demo purposes only!
      allow create: if request.auth != null;

      // Updates are allowed if no fields are added and name is unchanged
      allow update: if request.auth != null
                    && (request.resource.data.keys() == resource.data.keys())
                    && isUnchanged("name");

      // Deletes are not allowed.
      // Note: this is the default, there is no need to explicitly state this.
      allow delete: if false;

      // Ratings
      match /ratings/{ratingId} {
        // Any signed-in user can read
        allow read: if request.auth != null;

        // Any signed-in user can create if their uid matches the document
        allow create: if request.auth != null
                      && request.resource.data.userId == request.auth.uid;

        // Deletes and updates are not allowed (default)
        allow update, delete: if false;
      }
    }
  }
}

Aturan ini membatasi akses untuk memastikan bahwa klien hanya membuat perubahan yang aman. Misalnya pembaruan pada dokumen restoran hanya dapat mengubah peringkat, bukan nama atau data abadi lainnya. Peringkat hanya dapat dibuat jika ID pengguna cocok dengan pengguna yang masuk, yang mencegah spoofing.

Untuk membaca lebih lanjut tentang Aturan Keamanan, mengunjungi dokumentasi .

11. Kesimpulan

Anda sekarang telah membuat aplikasi berfitur lengkap di atas Firestore. Anda telah mempelajari tentang fitur Firestore yang paling penting termasuk:

  • Dokumen dan koleksi
  • Membaca dan menulis data
  • Menyortir dan memfilter dengan kueri
  • Subkoleksi
  • Transaksi

Belajarlah lagi

Untuk terus belajar tentang Firestore, berikut adalah beberapa tempat yang bagus untuk memulai:

Aplikasi restoran di codelab ini didasarkan pada aplikasi contoh "Friendly Eats". Anda dapat menelusuri kode sumber untuk aplikasi yang di sini .

Opsional: Terapkan ke produksi

Sejauh ini aplikasi ini hanya menggunakan Firebase Emulator Suite. Jika Anda ingin mempelajari cara menerapkan aplikasi ini ke proyek Firebase yang sebenarnya, lanjutkan ke langkah berikutnya.

12. (Opsional) Terapkan aplikasi Anda

Sejauh ini aplikasi ini sepenuhnya bersifat lokal, semua data ada di Firebase Emulator Suite. Di bagian ini Anda akan mempelajari cara mengonfigurasi proyek Firebase Anda sehingga aplikasi ini akan berfungsi dalam produksi.

Otentikasi Firebase

Dalam Firebase consle pergi ke bagian Authentication dan menavigasi ke Sign-in tab Provider .

Aktifkan metode masuk Email:

334ef7f6ff4da4ce.png

toko api

Buat database

Arahkan ke bagian Firestore konsol dan klik Create Database:

  1. Ketika diminta tentang Aturan Keamanan memilih untuk memulai di Dikunci Mode, kami akan memperbarui aturan-aturan segera.
  2. Pilih lokasi database yang ingin Anda gunakan untuk aplikasi Anda. Catatan seleksi yang lokasi basis data adalah keputusan yang permanen dan untuk mengubahnya Anda harus membuat proyek baru. Untuk informasi lebih lanjut tentang memilih lokasi proyek, lihat dokumentasi .

Menerapkan Aturan

Untuk menerapkan Aturan Keamanan yang Anda tulis sebelumnya, jalankan perintah berikut di direktori codelab:

$ firebase deploy --only firestore:rules

Hal ini akan menyebarkan isi firestore.rules untuk proyek Anda, yang dapat Anda mengkonfirmasi dengan menavigasi ke tab Aturan di konsol.

Menyebarkan Indeks

Aplikasi FriendlyEats memiliki penyortiran dan pemfilteran yang rumit yang memerlukan sejumlah indeks gabungan khusus. Ini dapat dibuat dengan tangan di Firebase konsol tetapi lebih sederhana untuk menulis definisi mereka di firestore.indexes.json berkas dan menyebarkan mereka menggunakan Firebase CLI.

Jika Anda membuka firestore.indexes.json file yang Anda akan melihat bahwa indeks yang diperlukan telah disediakan:

{
  "indexes": [
    {
      "collectionId": "restaurants",
      "queryScope": "COLLECTION",
      "fields": [
        { "fieldPath": "city", "mode": "ASCENDING" },
        { "fieldPath": "avgRating", "mode": "DESCENDING" }
      ]
    },
    {
      "collectionId": "restaurants",
      "queryScope": "COLLECTION",
      "fields": [
        { "fieldPath": "category", "mode": "ASCENDING" },
        { "fieldPath": "avgRating", "mode": "DESCENDING" }
      ]
    },
    {
      "collectionId": "restaurants",
      "queryScope": "COLLECTION",
      "fields": [
        { "fieldPath": "price", "mode": "ASCENDING" },
        { "fieldPath": "avgRating", "mode": "DESCENDING" }
      ]
    },
    {
      "collectionId": "restaurants",
      "queryScope": "COLLECTION",
      "fields": [
        { "fieldPath": "city", "mode": "ASCENDING" },
        { "fieldPath": "numRatings", "mode": "DESCENDING" }
      ]
    },
    {
      "collectionId": "restaurants",
      "queryScope": "COLLECTION",
      "fields": [
        { "fieldPath": "category", "mode": "ASCENDING" },
        { "fieldPath": "numRatings", "mode": "DESCENDING" }
      ]
    },
    {
      "collectionId": "restaurants",
      "queryScope": "COLLECTION",
      "fields": [
        { "fieldPath": "price", "mode": "ASCENDING" },
        { "fieldPath": "numRatings", "mode": "DESCENDING" }
      ]
    },
    {
      "collectionId": "restaurants",
      "queryScope": "COLLECTION",
      "fields": [
        { "fieldPath": "city", "mode": "ASCENDING" },
        { "fieldPath": "price", "mode": "ASCENDING" }
      ]
    },
    {
      "collectionId": "restaurants",
      "fields": [
        { "fieldPath": "category", "mode": "ASCENDING" },
        { "fieldPath": "price", "mode": "ASCENDING" }
      ]
    }
  ],
  "fieldOverrides": []
}

Untuk menyebarkan indeks ini, jalankan perintah berikut:

$ firebase deploy --only firestore:indexes

Perhatikan bahwa pembuatan indeks tidak instan, Anda dapat memantau kemajuannya di konsol Firebase.

Konfigurasikan aplikasi

Dalam FirebaseUtil kelas kita mengkonfigurasi Firebase SDK untuk connect ke emulator ketika dalam modus debug:

public class FirebaseUtil {

    /** Use emulators only in debug builds **/
    private static final boolean sUseEmulators = BuildConfig.DEBUG;

    // ...
}

Jika Anda ingin menguji aplikasi Anda dengan proyek Firebase yang sebenarnya, Anda dapat:

  1. Bangun aplikasi dalam mode rilis dan jalankan di perangkat.
  2. Mengubah sementara sUseEmulators ke false dan menjalankan aplikasi lagi.

Perhatikan bahwa Anda mungkin perlu untuk Keluar dari aplikasi dan masuk lagi untuk benar terhubung ke produksi.