Hapus kode yang tidak digunakan

Dalam codelab ini, tingkatkan performa aplikasi berikut dengan menghapus dependensi yang tidak digunakan dan tidak dibutuhkan.

Screenshot aplikasi

Ukur

Sebaiknya ukur terlebih dahulu seberapa baik performa situs web menambahkan pengoptimalan.

  • Untuk melihat pratinjau situs, tekan Lihat Aplikasi. Lalu tekan Layar penuh layar penuh.

Lanjutkan dan klik anak kucing favorit Anda! Firebase Realtime Database saat ini digunakan dalam aplikasi ini, itulah sebabnya skor diperbarui secara real-time dan disinkronkan dengan setiap orang yang menggunakan aplikasi. 🐈

  1. Tekan `Control+Shift+J` (atau `Command+Option+J` di Mac) untuk membuka DevTools.
  2. Klik tab Jaringan.
  3. Centang kotak Disable cache.
  4. Muat ulang aplikasi.

Ukuran paket asli 992 KB

JavaScript senilai hampir 1 MB dikirimkan untuk memuat aplikasi sederhana ini.

Lihat peringatan project di DevTools.

  • Klik tab Konsol.
  • Pastikan bahwa Warnings diaktifkan pada dropdown tingkat di samping Input Filter.

Filter peringatan

  • Lihat peringatan yang ditampilkan.

Peringatan konsol

Firebase, yang merupakan salah satu library samaritan yang baik dengan memberikan peringatan untuk memberitahu pengembang agar tidak mengimpor seluruh paket tetapi hanya komponen yang digunakan. Dengan kata lain, ada library yang tidak digunakan yang dapat dihapus dalam aplikasi ini untuk memuatnya dengan lebih cepat.

Ada kalanya {i>library<i} tertentu digunakan, tetapi mungkin ada alternatif yang lebih sederhana. Konsep untuk menghapus library yang tidak diperlukan adalah yang akan dibahas nanti dalam tutorial ini.

Menganalisis paket

Ada dua dependensi utama dalam aplikasi:

  • Firebase: platform yang menyediakan sejumlah layanan yang berguna untuk aplikasi iOS, Android, atau web. Di sini, laporan Real-Time Database digunakan untuk menyimpan dan menyinkronkan informasi untuk setiap anak kucing secara {i>real time<i}.
  • Moment.js: library utilitas yang memudahkan Anda menangani tanggal di JavaScript. Tanggal lahir setiap anak kucing disimpan di Database Firebase, dan moment digunakan untuk menghitung usianya dalam hitungan minggu.

Bagaimana hanya dua dependensi dapat berkontribusi pada ukuran paket yang hampir berukuran 1 MB? Konten yang dibuat salah satu alasannya adalah bahwa setiap dependensi dapat memiliki miliknya sendiri dependensi, sehingga ada lebih dari hanya dua jika setiap kedalaman/cabang dependensi "tree" akan dipertimbangkan. Aplikasi mudah menjadi besar relatif cepat jika banyak dependensi disertakan.

Menganalisis pemaket untuk mendapatkan ide yang lebih baik tentang apa yang terjadi. Ada beberapa berbagai alat yang dibuat oleh komunitas yang dapat membantu melakukan hal ini, seperti webpack-bundle-analyzer

Paket untuk alat ini sudah disertakan dalam aplikasi sebagai devDependency.

"devDependencies": {
  //...
  "webpack-bundle-analyzer": "^2.13.1"
},

Artinya, dapat digunakan langsung di file konfigurasi webpack. Impor di awal webpack.config.js:

const path = require("path");

//...
const BundleAnalyzerPlugin = require("webpack-bundle-analyzer")
  .BundleAnalyzerPlugin;

Sekarang tambahkan sebagai plugin di bagian paling akhir file dalam array plugins:

module.exports = {
  //...
  plugins: [
    //...
    new BundleAnalyzerPlugin()
  ]
};

Saat aplikasi dimuat ulang, Anda akan melihat visualisasi seluruh aplikasi paket aplikasi, bukan aplikasi itu sendiri.

Penganalisis Paket Webpack

Tidak se Imut seperti melihat beberapa anak kucing 👀, tapi itu sangat membantu. Mengarahkan kursor ke salah satu paket akan menunjukkan ukurannya yang diwakili dalam tiga cara yang berbeda:

Ukuran statistik Ukuran sebelum minifikasi atau kompresi.
Ukuran terurai Ukuran paket sebenarnya dalam paket setelah dikompilasi. Webpack versi 4 (yang digunakan dalam aplikasi ini) meminimalkan file yang dikompilasi secara otomatis itulah sebabnya ini lebih kecil dari statistik ukuran.
Ukuran file gzip Ukuran paket setelah dikompresi dengan encoding gzip. Ini Topik ini dibahas dalam panduan terpisah.

Dengan alat webpack-bundle-analyzer, Anda lebih mudah untuk mengidentifikasi paket yang tidak diperlukan yang merupakan sebagian besar dari paket itu.

Menghapus paket yang tidak digunakan

Visualisasi menunjukkan bahwa paket firebase terdiri dari banyak paket lainnya dari sekedar {i>database<i}. Ini mencakup paket tambahan seperti:

  • firestore
  • auth
  • storage
  • messaging
  • functions

Ini semua adalah layanan luar biasa yang disediakan oleh Firebase (dan merujuk pada dokumentasi untuk mempelajari lebih lanjut), tetapi tidak ada satu pun yang digunakan dalam aplikasi, jadi tidak ada alasan untuk mengimpor semuanya.

Kembalikan perubahan di webpack.config.js untuk melihat aplikasi lagi:

  • Hapus BundleAnalyzerPlugin di daftar plugin:
plugins: [
  //...
  new BundleAnalyzerPlugin()
];
  • Sekarang hapus impor yang tidak terpakai dari bagian atas file:
const path = require("path");

//...
const BundleAnalyzerPlugin = require('webpack-bundle-analyzer').BundleAnalyzerPlugin;

Sekarang aplikasi akan dimuat secara normal. Ubah src/index.js untuk memperbarui Impor Firebase.

import firebase from 'firebase';
import firebase from 'firebase/app';
import 'firebase/database';

Sekarang saat aplikasi dimuat ulang, peringatan DevTools tidak akan ditampilkan. Membuka Panel Jaringan DevTools juga menunjukkan pengurangan ukuran paket yang bagus:

Ukuran paket dikurangi menjadi 480 KB

Lebih dari setengah ukuran paket telah dihapus. Firebase menyediakan berbagai dan memberikan opsi kepada pengembang untuk hanya menyertakan layanan yang benar-benar diperlukan. Dalam aplikasi ini, hanya firebase/database yang digunakan untuk menyimpan dan menyinkronkan semua data. Impor firebase/app, yang menyiapkan platform API untuk setiap layanan yang berbeda, selalu diperlukan.

Banyak library populer lainnya, seperti lodash, juga memungkinkan developer untuk secara selektif mengimpor bagian yang berbeda dari paketnya. Tanpa melakukan banyak usaha, memperbarui impor library dalam aplikasi untuk hanya menyertakan apa yang sedang digunakan dapat menghasilkan peningkatan performa yang signifikan.

Meskipun ukuran paket telah berkurang sedikit, masih ada lebih banyak pekerjaan yang harus dilakukan! 😈

Menghapus paket yang tidak diperlukan

Tidak seperti Firebase, mengimpor bagian dari library moment tidak dapat dilakukan sebagai dengan mudah, tetapi mungkin dapat dihapus sepenuhnya?

Ulang tahun setiap anak kucing lucu disimpan dalam format Unix (milidetik) di di database Firebase.

Tanggal lahir disimpan dalam format Unix

Ini adalah stempel waktu pada tanggal dan waktu tertentu yang diwakili oleh jumlah dalam milidetik yang telah berlalu sejak 1 Januari 1970 pukul 00:00 UTC. Jika saat ini tanggal dan waktu dapat dihitung dalam format yang sama, sebuah fungsi kecil untuk menemukan setiap anak kucing dalam minggu mungkin dapat disusun.

Seperti biasa, cobalah untuk tidak menyalin dan menempel seperti yang Anda ikuti di sini. Mulai dengan menghapus moment dari impor di src/index.js.

import firebase from 'firebase/app';
import 'firebase/database';
import * as moment from 'moment';

Ada pemroses peristiwa Firebase yang menangani perubahan nilai dalam database kami:

favoritesRef.on("value", (snapshot) => { ... })

Di atas ini, tambahkan {i>function<i} kecil untuk menghitung jumlah minggu dari tanggal tertentu:

const ageInWeeks = birthDate => {
  const WEEK_IN_MILLISECONDS = 1000 * 60 * 60 * 24 * 7;
  const diff = Math.abs((new Date).getTime() - birthDate);
  return Math.floor(diff / WEEK_IN_MILLISECONDS);
}

Pada fungsi ini, perbedaan dalam milidetik antara tanggal saat ini dan waktu (new Date).getTime() dan tanggal lahir (argumen birthDate, sudah dalam milidetik) dihitung dan dibagi dengan jumlah milidetik dalam satu minggu.

Terakhir, semua instance moment dapat dihapus dalam pemroses peristiwa dengan memanfaatkan fungsi ini:

favoritesRef.on("value", (snapshot) => {
  const { kitties, favorites, names, birthDates } = snapshot.val();
  favoritesScores = favorites;

  kittiesList.innerHTML = kitties.map((kittiePic, index) => {
    const birthday = moment(birthDates[index]);

    return `
      <li>
        <img src=${kittiePic} onclick="favKittie(${index})">
        <div class="extra">
          <div class="details">
            <p class="name">${names[index]}</p>
            <p class="age">${moment().diff(birthday, 'weeks')} weeks old</p>
            <p class="age">${ageInWeeks(birthDates[index])} weeks old</p>
          </div>
          <p class="score">${favorites[index]} ❤</p>
        </div>
      </li>
    `})
});

Sekarang, muat ulang aplikasi dan lihat panel Jaringan sekali lagi.

Ukuran paket dikurangi menjadi 225 KB

Ukuran paket kami berkurang lebih dari setengahnya lagi!

Kesimpulan

Dengan codelab ini, Anda akan memiliki pemahaman yang baik tentang cara menganalisis paket tertentu dan mengapa sangat berguna untuk menghapus paket yang tidak digunakan atau tidak dibutuhkan paket. Sebelum Anda mulai mengoptimalkan aplikasi dengan teknik ini, hal ini penting untuk diketahui bahwa ini bisa jauh lebih kompleks dalam analisis data aplikasi.

Sehubungan dengan menghapus library yang tidak digunakan, cobalah untuk mencari tahu bagian mana dari paket yang digunakan dan bagian mana yang tidak. Untuk penampilan misterius paket yang sepertinya sedang tidak digunakan di mana pun, mundur selangkah dan memeriksanya dependensi tingkat atas mana yang mungkin membutuhkannya. Cobalah untuk menemukan cara yang mungkin memisahkan mereka satu sama lain.

Sehubungan dengan menghapus library yang tidak diperlukan, segalanya bisa lebih rumit. Penting untuk bekerja sama dengan tim Anda dan melihat apakah dapat menyederhanakan bagian-bagian codebase. Menghapus moment di ini aplikasi mungkin tampak menjadi hal yang tepat untuk dilakukan setiap saat, tetapi apa jika ada zona waktu dan lokalitas berbeda yang perlu ditangani? Atau bagaimana jika ada manipulasi tanggal yang lebih rumit? Banyak hal bisa menjadi sangat rumit saat memanipulasi dan mengurai tanggal/waktu, dan library seperti moment dan date-fns menyederhanakannya secara signifikan.

Semuanya merupakan imbal balik, dan penting untuk mengukur apakah hal itu sepadan dengan hasilnya kompleksitas dan upaya untuk meluncurkan solusi khusus daripada mengandalkan library pihak ketiga.