Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Misahin Modul ke Dalem File yang Beda

Sejauh ini, semua contoh di bab ini mendefinisikan beberapa modul di dalem satu file. Pas modulnya jadi makin gede, kita mungkin mau mindahin definisi mereka ke file terpisah biar kodenya lebih gampang dinavigasi.

Sebagai contoh, yuk kita mulai dari kode di Listing 7-17 yang punya beberapa modul restoran. Kita bakal ngekstrak modul-modulnya ke dalem file bukannya punya semua modul didefinisikan di file crate root. Di kasus ini, file crate root-nya adalah src/lib.rs, tapi prosedur ini juga berlaku buat binary crates yang mana file crate root-nya adalah src/main.rs.

Pertama kita bakal ngekstrak modul front_of_house ke dalem filenya sendiri. Hapus kode di dalem kurung kurawal buat modul front_of_house, nyisain cuma deklarasi mod front_of_house; aja, jadi src/lib.rs isinya cuma kode yang ditunjukin di Listing 7-21. Perhatiin ya kalau ini nggak bakal bisa di-compile sampe kita bikin file src/front_of_house.rs di Listing 7-22.

Filename: src/lib.rs
mod front_of_house;

pub use crate::front_of_house::hosting;

pub fn eat_at_restaurant() {
    hosting::add_to_waitlist();
}
Listing 7-21: Mendeklarasikan modul front_of_house yang body-nya bakal ada di src/front_of_house.rs

Selanjutnya, taruh kode yang tadinya ada di dalem kurung kurawal ke file baru namanya src/front_of_house.rs, kayak yang ditunjukin di Listing 7-22. Compiler tau buat nyari di file ini karena dia nemu deklarasi modul di crate root dengan nama front_of_house.

Filename: src/front_of_house.rs
pub mod hosting {
    pub fn add_to_waitlist() {}
}
Listing 7-22: Definisi di dalem modul front_of_house di src/front_of_house.rs

Perhatiin ya kalau kita cuma perlu load (muat) file pake deklarasi mod sekali aja di pohon modul kita. Begitu compiler tau filenya adalah bagian dari project (dan tau di mana letak kode itu di pohon modul gara-gara tempat kita naruh statement mod), file lain di project kita harus ngerujuk ke kode di file yang di-load pake path ke tempat di mana dia dideklarasikan, kayak yang udah dibahas di bagian “Paths (Jalur) buat Ngerujuk Item di Pohon Modul”. Dengan kata lain, mod itu bukan operasi “include” kayak yang mungkin kita liat di bahasa pemrograman lainnya.

Selanjutnya, kita bakal ngekstrak modul hosting ke dalem filenya sendiri. Prosesnya agak beda karena hosting adalah anak modul dari front_of_house, bukan dari modul root. Kita bakal naruh file buat hosting di direktori baru yang namanya ngikutin leluhurnya di pohon modul, di kasus ini src/front_of_house.

Buat mulai mindahin hosting, kita ubah src/front_of_house.rs biar isinya cuma deklarasi dari modul hosting aja:

Filename: src/front_of_house.rs
pub mod hosting;

Terus kita bikin direktori src/front_of_house sama file hosting.rs buat nampung definisi yang dibikin di modul hosting:

Filename: src/front_of_house/hosting.rs
pub fn add_to_waitlist() {}

Kalau kita malah naruh hosting.rs di direktori src, compiler bakal ngarepin kode hosting.rs ada di modul hosting yang dideklarasikan di crate root, dan bukan dideklarasikan sebagai anak dari modul front_of_house. Aturan compiler soal file mana yang harus dicek buat kode modul mana bikin direktori dan file jadi lebih mirip (match) sama pohon modulnya.

Alternate File Paths (Path File Alternatif)

Sejauh ini kita udah ngebahas path file yang paling idiomatik yang dipake sama compiler Rust, tapi Rust juga support gaya path file yang lebih lama. Buat modul namanya front_of_house yang dideklarasikan di crate root, compiler bakal nyari kode modulnya di:

  • src/front_of_house.rs (yang baru aja kita bahas)
  • src/front_of_house/mod.rs (gaya lama, tetep di-support path-nya)

Buat modul namanya hosting yang merupakan submodul dari front_of_house, compiler bakal nyari kode modulnya di:

  • src/front_of_house/hosting.rs (yang baru aja kita bahas)
  • src/front_of_house/hosting/mod.rs (gaya lama, tetep di-support path-nya)

Kalau kita pake kedua gaya ini buat modul yang sama, kita bakal dapet error compiler. Pake campuran kedua gaya buat modul yang beda di project yang sama itu dibolehin, tapi mungkin bakal ngebingungin orang yang lagi navigasi project kita.

Kekurangan utama dari gaya yang pake file namanya mod.rs adalah project kita bisa berakhir dengan banyak file yang namanya mod.rs, yang bisa ngebingungin pas kita ngebuka mereka semua di editor secara bersamaan.

Kita udah mindahin kode tiap modul ke file yang terpisah, dan pohon modulnya tetep sama. Pemanggilan fungsi di eat_at_restaurant bakal jalan tanpa modifikasi apa pun, walaupun definisinya sekarang tinggal di file yang beda. Teknik ini ngebolehin kita mindahin modul ke file baru seiring ukurannya makin gede.

Perhatiin ya kalau statement pub use crate::front_of_house::hosting di src/lib.rs juga nggak berubah, dan use juga nggak punya pengaruh apa pun ke file mana yang di-compile sebagai bagian dari crate-nya. Keyword mod mendeklarasikan modul, dan Rust nyari di file dengan nama yang sama kayak modulnya buat nyari kode yang masuk ke modul itu.

Ringkasan

Rust ngebolehin kita misahin sebuah package jadi beberapa crates dan sebuah crate jadi beberapa modul biar kita bisa ngerujuk ke item yang didefinisikan di satu modul dari modul lain. Kita bisa lakuin ini dengan nentuin absolute atau relative paths. Path-path ini bisa dibawa ke dalem scope pake statement use biar kita bisa pake path yang lebih pendek buat banyak pemakaian item itu di scope tersebut. Kode modul itu private secara default, tapi kita bisa bikin definisinya jadi public dengan nambahin keyword pub.

Di bab berikutnya, kita bakal liat beberapa struktur data koleksi (collection) di standard library yang bisa kita pake di dalem kode kita yang udah terorganisir dengan rapi.