Penghapusan di toko buku jarang datang satu-satu: buku habis terjual perlu dikeluarkan dari katalog, dan diskon musim berakhir untuk seluruh kategori sekaligus. Method deleteMany(filter) menghapus semua document yang cocok dengan filter dalam satu perintah — alat paling ampuh sekaligus paling berisiko di keluarga CRUD, karena satu filter longgar bisa mengosongkan collection dalam sekejap.

Menghapus Banyak Document Sekaligus #

Bentuk deleteMany() identik dengan deleteOne() — hanya filter — tetapi cakupannya semua kecocokan, bukan yang pertama. Kita siapkan data contoh, kali ini beserta satu index tambahan yang akan menunjukkan perbedaan penting di bagian akhir Chapter:

js
use latihan_crud2
db.buku.drop()
db.buku.insertMany([
  { judul: "Laskar Pelangi", penulis: "Andrea Hirata", harga: 95000, stok: 12, kategori: "Fiksi", tag: ["novel", "bestseller"], rating: 4.6 },
  { judul: "Bumi Manusia", penulis: "Pramoedya Ananta Toer", harga: 110000, stok: 8, kategori: "Fiksi", tag: ["novel", "klasik"], rating: 4.8 },
  { judul: "Atomic Habits", penulis: "James Clear", harga: 135000, stok: 20, kategori: "Pengembangan Diri", tag: ["nonfiksi", "bestseller"], rating: 4.7 },
  { judul: "Filosofi Teras", penulis: "Henry Manampiring", harga: 89000, stok: 0, kategori: "Pengembangan Diri", tag: ["nonfiksi"], rating: 4.5 },
  { judul: "Clean Code", penulis: "Robert C. Martin", harga: 165000, stok: 5, kategori: "Teknologi", tag: ["pemrograman", "bestseller"], rating: 4.4 }
])
db.buku.createIndex({ judul: 1 })

Output yang Dihasilkan:

text
switched to db latihan_crud2
true
{
  acknowledged: true,
  insertedIds: {
    '0': ObjectId('6ad38837a9c5ef1475bf88fa'),
    '1': ObjectId('6ad38837a9c5ef1475bf88fb'),
    '2': ObjectId('6ad38837a9c5ef1475bf88fc'),
    '3': ObjectId('6ad38837a9c5ef1475bf88fd'),
    '4': ObjectId('6ad38837a9c5ef1475bf88fe')
  }
}
judul_1

Skenario pertama: buku dengan stok habis dikeluarkan dari katalog. Filosofi Teras adalah satu-satunya yang berstok 0:

js
db.buku.deleteMany({ stok: 0 })
db.buku.countDocuments({})

Output yang Dihasilkan:

text
{ acknowledged: true, deletedCount: 1 }
4

deletedCount kini menjadi sumber kebenaran hasil massal: satu document cocok dan terhapus, tinggal empat. Skenario kedua menyasar kategori — seluruh novel Fiksi ditarik dari katalog:

js
db.buku.deleteMany({ kategori: "Fiksi" })
db.buku.countDocuments({})

Output yang Dihasilkan:

text
{ acknowledged: true, deletedCount: 2 }
2

Dua document — Laskar Pelangi dan Bumi Manusia — terhapus sekaligus. Filter di sini mendukung seluruh peralatan query yang sudah kita kuasai: operator perbandingan ($gte, $lt), logika ($or), hingga operator array ($in) — semakin presisi filter, semakin terkendali penghapusannya.

Catatan praktis dari aplikasi nyata: banyak toko justru menghindari penghapusan fisik. Pola soft delete menandai document lewat updateMany() — misalnya { $set: { status: "nonaktif" } } — sehingga riwayat penjualan tetap tersambung, sementara query katalog tinggal menambahkan filter status: "aktif". deleteMany() paling cocok untuk data yang memang kedaluwarsa: sesi login lama, log yang sudah diarsipkan, atau isi keranjang yang lama ditinggalkan.

Menghapus Seluruh Isi Collection #

Filter kosong {} berarti “semua document”. Perintah berikut mengosongkan collection buku tanpa konfirmasi apa pun:

js
db.buku.deleteMany({})
db.buku.countDocuments({})
show collections

Output yang Dihasilkan:

text
{ acknowledged: true, deletedCount: 2 }
0
buku

Dua document terakhir terhapus, countDocuments() melapor 0 — tetapi perhatikan baris buku dari show collections: collection-nya masih ada. Yang hilang hanya isinya. Index pun selamat, dan itu bisa kita buktikan:

js
db.buku.getIndexes()

Output yang Dihasilkan:

text
[
  {
    v: 2,
    key: { _id: 1 },
    name: '_id_',
    collation: { locale: 'simple' }
  },
  {
    v: 2,
    key: { judul: 1 },
    name: 'judul_1',
    collation: { locale: 'simple' }
  }
]

Index _id_ bawaan dan index judul_1 yang kita buat di awal tetap menempel pada collection yang kosong.

deleteMany({}) atau drop() #

MongoDB menyediakan jalur kedua untuk mengosongkan: drop(). Keduanya sama-sama membuang seluruh document, tetapi drop() ikut membuang collection beserta seluruh index-nya:

js
db.buku.drop()
db.buku.getIndexes()

Output yang Dihasilkan:

text
true
Uncaught 
MongoServerError[NamespaceNotFound]: ns does not exist: latihan_crud2.buku

Setelah drop(), nama collection latihan_crud2.buku tidak lagi dikenal server — getIndexes() langsung menolak dengan galat NamespaceNotFound. Operasi tulis berikutnya pada nama yang sama akan membuat collection baru, tanpa index judul_1 lama. Pilihan antara keduanya:

AspekdeleteMany({})db.buku.drop()
DocumentSemua terhapusSemua terhapus
CollectionTetap ada, siap dipakai lagiIkut terhapus
IndexTetap adaTerhapus — harus dibuat ulang
Cocok untukMengosongkan data, mempertahankan strukturMembuang collection beserta strukturnya

Sebagai penutup, jatuhkan database latihan:

js
db.dropDatabase()

Output yang Dihasilkan:

text
{ ok: 1, dropped: 'latihan_crud2' }

Rangkuman #

  • deleteMany(filter) menghapus semua document yang cocok; deletedCount melapor jumlahnya.
  • Filter mendukung operator query lengkap — presisi filter adalah satu-satunya pengendali cakupan penghapusan.
  • deleteMany({}) mengosongkan collection tanpa konfirmasi; collection dan index tetap ada.
  • drop() membuang collection beserta seluruh index; nama collection baru dibuat bersih pada pemakaian berikutnya.
  • Keduanya tanpa undo — uji filter dengan find() lebih dulu, dan periksa konteks db sebelum menekan Enter.

CRUD masih menyisakan satu pola gabungan: upsert, yang menjadikan kegagalan menemukan document justru menjadi penyisipan.