MongoDB’de updateOne() filtreyle eşleşen tek bir belgeyi günceller; $set ise o belgede yalnızca belirttiğin alanları değiştirir veya alan yoksa ekler. Belge, alan-değer çiftlerinden oluşan bir kayıttır; koleksiyon, belgelerin tutulduğu yapıdır. MongoDB’nin updateOne() belgelerinde yöntemin filtreye göre tek belgeyi güncellediği açıklanır.
updateOne filtre ve güncelleme belgesiyle nasıl çalışır?
updateOne(filter, update) çağrısında filter, hangi belgenin seçileceğini; update ise seçilen belgeye hangi değişikliğin uygulanacağını belirtir. Operatör, güncelleme belgesindeki değişiklik türünü belirten ifadedir. Örneğin $set, belirtilen alanların değerini ayarlar.
Filtre birden fazla belgeyle eşleşse bile updateOne() yalnızca bir belgeyi günceller. Hangi belgenin seçileceğine ilişkin bir sıralama varsayımı yapmamak için mümkün olduğunda _id veya benzersiz bir kayıt numarası gibi tek bir belgeyi belirleyen alan kullan.
Uygulama, kullanıcıdan gelen veriyi doğrudan filtre nesnesi olarak kabul ederse kullanıcı beklenen bir değer yerine {$ne: null} gibi bir operatör gönderebilir; bu da filtre koşulunun anlamını değiştirebilir. Filtre alanlarını ve veri türlerini uygulamada belirle, kullanıcı girdisini değer olarak işle; eşitlik koşullarında $eq kullanımı bu riski azaltmaya yardımcı olabilir.
$set mevcut alanı nasıl değiştirir ve yeni alan ekler?

$set, güncelleme belgesinde yazdığın alanı yeni değerine ayarlar. Alan belge içinde zaten varsa değerini değiştirir; yoksa belgeye ekler. Başka alanları güncelleme belgesinde belirtmediğin sürece değiştirmez.
Aşağıdaki mongosh örneğinde filtre, ogrenciNo değeri belirli olan belgeyi seçer; güncelleme belgesi ise e-posta alanının değerini tanımlar:
const filtre = {
ogrenciNo: { $eq: "20240017" }
};
const guncelleme = {
$set: {
email: "[email protected]"
}
};
db.ogrenciler.updateOne(filtre, guncelleme);
Belge eşleşirse ve email alanı mevcutsa yeni e-posta adresi bu alanın değerini alır. Alan yoksa $set onu belgeye ekler. MongoDB’nin $set başvuru belgesi, operatörün bu davranışını ve iç içe alanları noktalı gösterimle belirtme yöntemini açıklar.
$inc ve $unset hangi alan güncellemelerinde kullanılır?
$inc, alanın mevcut sayısal değerine verilen miktarı ekler. Ders sayısı veya puan gibi sayaçlarda artışı uygulama tarafında hesaplamadan yapmak için kullanabilirsin. Alan henüz yoksa MongoDB onu artırılacak miktarla oluşturur. $unset ise belgede artık tutulması gerekmeyen geçici ya da eski bir alanı kaldırır.
Aşağıdaki örnek, eşleşen belgenin lessonCount değerini bir artırır ve temporaryNote alanını siler. Başlangıç değeri 4 ise güncellemeden sonra ders sayısı 5 olur. $unset içindeki boş metin, alanın kaldırılmasını sağlar.
db.courses.updateOne(
{ _id: "course-101" },
{
$inc: { lessonCount: 1 },
$unset: { temporaryNote: "" }
}
)
$inc sayısal alanlardaki artış veya azalışlarda, $unset ise artık kullanılmayacak alanları kaldırırken uygundur. Alanın mevcut değeri sayısal değilse $inc kullanmadan önce veri türünü kontrol et.
matchedCount ve modifiedCount nasıl yorumlanır?

matchedCount, filtreyle eşleşen belge sayısını; modifiedCount ise içeriği gerçekten değişen belge sayısını gösterir. Örneğin e-posta alanını $set ile güncellediğinde sonuç nesnesinde matchedCount: 1 ve modifiedCount: 1 görülmesi, bir belgenin eşleştiğini ve e-posta değerinin değiştiğini anlatır.
db.users.updateOne(
{ _id: "user-42" },
{ $set: { email: "[email protected]" } }
)
Filtre eşleşir ve yeni e-posta mevcut değerle aynıysa sonuç matchedCount: 1, modifiedCount: 0 olabilir. Bu, eşleşen bir belge bulunduğunu fakat verinin değişmediğini gösterir. Her iki değer de 0 ise filtre hiçbir belgeyle eşleşmemiştir; filtredeki alanları ve değerleri gözden geçir. updateOne() sonucunda bu iki sayım ayrı ayrı döndürülür.
updateMany ve upsert ne zaman kullanılmalı?
updateMany(), filtreyle eşleşen bütün belgeleri günceller. Birden fazla belgeyi aynı kuralla değiştirmek istediğinde kullanabilirsin; örneğin aşağıdaki işlem, durum alanı “beklemede” olan belgelerin her birine arsivlendi alanını ekler veya değerini değiştirir.
db.siparisler.updateMany(
{ durum: "beklemede" },
{ $set: { arsivlendi: true } }
)
Filtreyi boş belge olarak, yani {} biçiminde verirsen koleksiyondaki tüm belgeler eşleşir. Bu nedenle işlemi uygulamadan önce filtreyi küçük bir test koleksiyonunda veya sınırlı bir örnek üzerinde doğrula. MongoDB’nin updateMany() belgelerinde yöntemin eşleşen belgelerin tümüne uygulandığı açıklanır.
upsert: true ise eşleşme bulunmadığında yeni bir belge eklenmesine izin verir. Örneğin bir kullanıcı ayarını güncellerken kullanıcı için henüz belge yoksa ayar belgesini oluşturabilirsin:
db.ayarlar.updateOne(
{ kullaniciId: 42 },
{ $set: { tema: "koyu" } },
{ upsert: true }
)
upsert, updateMany() ile de kullanılabilir; ancak filtre hiçbir belgeyle eşleşmezse oluşturulan belge tektir. Bu seçenek, eşleşmeyen tüm kayıtları topluca eklemek anlamına gelmez.
Operatörsüz güncelleme ve hatalı filtre nasıl önlenir?
updateOne() içindeki güncelleme belgesi, $set gibi bir güncelleme operatörü içermelidir. { durum: "tamamlandı" } gibi düz bir alan-değer belgesi, mevcut belgeyi alan bazında güncellemek için uygun değildir. Belgenin tamamını yeni içerikle değiştirmek istiyorsan replaceOne() kullan; bu iki işlemin davranışını eski update() yöntemiyle karıştırma. MongoDB’nin updateOne() belgeleri, güncelleme operatörlü belge kullanımını ve belge değiştirme yöntemi olarak replaceOne() seçeneğini açıklar.
Filtre hiçbir belgeyle eşleşmezse varsayılan davranışta belge güncellenmez. upsert: true eklemek bu sonucu değiştirip yeni belge oluşturabileceğinden, filtredeki alan ve değerleri işlemden önce dikkatle kontrol et.
Kullanıcıdan gelen nesneyi doğrulamadan doğrudan filtreye koymak da risklidir. Nesne beklenen metin değerinin yerine { "$ne": null } gibi bir sorgu operatörü taşıyabilir ve eşleşme kapsamını değiştirebilir. Girdinin türünü doğrula, izin verilen alanları belirle ve filtreyi uygulama kodunda bu değerlere göre oluştur. Bu yaklaşım, MongoDB’nin güvenilmeyen girdilerle sorgu oluşturma önerileriyle uyumludur.
Sık Sorulan Sorular
matchedCount 1 ve modifiedCount 0 ne anlama gelir?
Filtreyle bir belge eşleşmiş, ancak güncelleme belge üzerinde bir değişiklik yapmamıştır. Örneğin alan zaten yazdığın değere sahipse bu sonuç görülebilir.
updateOne eşleşen belge bulamazsa ne olur?
Varsayılan ayarda hiçbir belge güncellenmez ve yeni belge eklenmez. Eşleşme bulunmadığında belge oluşturmak için işlem seçeneklerinde upsert: true belirtmelisin.
Güvenli bir güncelleme için filtreyi, hedeflediğin belge sayısını ve kullanacağın güncelleme yöntemini birlikte değerlendir.