Od MongoDB 4.4 możesz użyć $bsonSize
operator potoku agregacji, który zwraca rozmiar danego dokumentu w bajtach.
$bsonSize
akceptuje dowolne poprawne wyrażenie, o ile jest ono rozpoznawane jako obiekt lub null
.
Przykład
Załóżmy, że mamy kolekcję o nazwie bars
z następującym dokumentem:
{ "_id" : 1, "name" : "Boardwalk Social", "location" : { "type" : "Point", "coordinates" : [ -16.919297718553366, 145.77675259719823 ] }, "categories" : [ "Bar", "Restaurant", "Hotel" ], "reviews" : [ { "name" : "Steve", "date" : "20 December, 2020", "rating" : 5, "comments" : "Great vibe." }, { "name" : "Lisa", "date" : "25 October, 2020", "rating" : 3, "comments" : "They just raised their prices :(" }, { "name" : "Kim", "date" : "21 October, 2020", "rating" : 4, "comments" : "Nice for Friday happy hour" } ] }
Widzimy, że location
pole zawiera dokument. Oraz reviews
pole zawiera tablicę dokumentów.
Użyjmy $bsonSize
operator, aby sprawdzić rozmiar location
pole:
db.bars.aggregate([
{
$project: {
"locationSize": { $bsonSize: "$location" }
}
}
])
Wynik:
{ "_id" : 1, "locationSize" : 61 }
W tym przypadku rozmiar location
pole ma 61 bajtów.
Obiekty w tablicach
Oto przykład pobierania rozmiaru dokumentu, który jest elementem tablicy:
db.bars.aggregate([
{
$project: {
"review": { $arrayElemAt: [ "$reviews", 0 ] },
"reviewSize": { $bsonSize: { $arrayElemAt: [ "$reviews", 0 ] } }
}
}
]).pretty()
Wynik:
{ "_id" : 1, "review" : { "name" : "Steve", "date" : "20 December, 2020", "rating" : 5, "comments" : "Great vibe." }, "reviewSize" : 91 }
W tym przypadku używamy $arrayElemAt
aby zwrócić rzeczywistą recenzję, a następnie ponownie zwrócić rozmiar tej recenzji.
Tablice MongoDB są liczone od zera, więc recenzja jest pierwszą recenzją.
Pobierz rozmiar dokumentu najwyższego poziomu
Możemy użyć $$ROOT
zmienna systemowa odwołująca się do dokumentu najwyższego poziomu – lub dokumentu głównego. To jest dokument, który jest obecnie przetwarzany przez potok.
Dlatego możemy przekazać $$ROOT
zmienna na $bsonSize
aby uzyskać rozmiar całego dokumentu, który jest aktualnie przetwarzany.
Przykład:
db.bars.aggregate([
{
$project: {
"rootSize": { $bsonSize: "$$ROOT" }
}
}
])
Wynik:
{ "_id" : 1, "rootSize" : 502 }
W tym przypadku dokument ma 502 bajty.
Niewłaściwe typy danych
Jak wspomniano, $bsonSize
akceptuje dowolne poprawne wyrażenie, o ile prowadzi do obiektu lub null
.
Oto przykład tego, co się stanie, jeśli podasz wyrażenie, które jest tłumaczone na inny typ BSON:
db.bars.aggregate([
{
$project: {
"nameSize": { $bsonSize: "$name" }
}
}
])
Wynik:
Error: command failed: { "ok" : 0, "errmsg" : "$bsonSize requires a document input, found: string", "code" : 31393, "codeName" : "Location31393" } : aggregate failed : [email protected]/mongo/shell/utils.js:25:13 [email protected]/mongo/shell/assert.js:18:14 [email protected]/mongo/shell/assert.js:618:17 [email protected]/mongo/shell/assert.js:708:16 [email protected]/mongo/shell/db.js:266:5 [email protected]/mongo/shell/collection.js:1046:12 @(shell):1:1
W tym przypadku próbowaliśmy znaleźć rozmiar ciągu, ale nie jest to jeden z obsługiwanych typów BSON, więc pojawia się błąd.
Jednak nie wszystko jest stracone. Możemy użyć $binarySize
aby uzyskać rozmiar łańcucha.
Uzyskaj całkowity rozmiar wszystkich dokumentów w kolekcji
Załóżmy, że mamy kolekcję o nazwie cats
z następującymi dokumentami:
{ "_id" : 1, "name" : "Scratch", "born" : "March, 2020" } { "_id" : 2, "name" : "Meow", "weight" : 30 } { "_id" : 3, "name" : "Fluffy", "height" : 15 } { "_id" : 4, "name" : "Sox", "weight" : 40 } { "_id" : 5, "name" : null, "weight" : 20 } { "_id" : 6, "height" : 20, "born" : ISODate("2021-01-03T23:30:15.123Z") }
Jak wcześniej pokazano, możemy użyć $$ROOT
aby zwrócić aktualnie przetwarzany dokument najwyższego poziomu:
db.cats.aggregate([
{
$project: {
"rootSize": { $bsonSize: "$$ROOT" }
}
}
])
Wynik:
{ "_id" : 1, "rootSize" : 58 } { "_id" : 2, "rootSize" : 49 } { "_id" : 3, "rootSize" : 51 } { "_id" : 4, "rootSize" : 48 } { "_id" : 5, "rootSize" : 40 } { "_id" : 6, "rootSize" : 48 }
Ale możemy też uzyskać suma rozmiar wszystkich dokumentów w kolekcji.
Możemy to osiągnąć w następujący sposób:
db.cats.aggregate([
{
$group: {
"_id": null,
"rootSize": { $sum: { $bsonSize: "$$ROOT" } }
}
}
])
Wynik:
{ "_id" : null, "rootSize" : 294 }
Tutaj pogrupowaliśmy wyniki za pomocą $group
operatora i podanie _id
z null
. Mogliśmy użyć dowolnej innej wartości stałej.
Użyliśmy również $sum
aby obliczyć łączne rozmiary różnych dokumentów.
Widzimy, że łączny rozmiar wszystkich dokumentów w kolekcji to 294, co możemy potwierdzić, dodając wyniki z poprzedniego przykładu.
Metoda Object.bsonSize()
Innym sposobem na uzyskanie rozmiaru dokumentu jest użycie Object.bsonSize()
metoda.