Atacuri cibernetice bazate pe IA: Cum să detectați, să preveniți și să vă apărați împotriva amenințărilor inteligente

Citește acum
Utilizăm inteligența artificială pentru traducerile site-urilor și, deși ne străduim să fim exacți, este posibil ca acestea să nu fie întotdeauna 100% precise. Apreciem înțelegerea dumneavoastră.

Descoperirea tehnică a Mongoose CVE-2025-23061 și CVE-2024-53900

de OPSWAT
Împărtășește această postare

Mongoose este o bibliotecă Object Data Modeling (ODM) pentru MongoDB care simplifică interacțiunile cu bazele de date în aplicațiile Node.js. Prin furnizarea unei soluții bazate pe schemă, Mongoose permite ca obiectele JavaScript să fie mapate în documente MongoDB, acționând ca un strat de abstractizare care ajută la structurarea datelor pentru o gestionare și validare mai ușoară. Cu caracteristici precum middleware pentru executarea logicii personalizate și un sistem intuitiv de construire a interogărilor, Mongoose îmbunătățește eficiența lucrului cu MongoDB. Mongoose, descris ca "modelare elegantă a obiectelor MongoDB pentru Node.js", a acumulat 27K stele pe GitHub, reflectând utilizarea și aprecierea sa pe scară largă în rândul dezvoltatorilor.

Programul de burse OPSWAT și descoperirea vulnerabilităților critice

ProgramulOPSWAT Critical Infrastructure Cybersecurity Graduate Fellowship, cu sediul în Vietnam, oferă studenților absolvenți experiență practică în securizarea infrastructurilor critice. Ca parte a acestui program, bursierii au ocazia să analizeze și să abordeze vulnerabilitățile de securitate cibernetică, colaborând cu experții OPSWAT pentru a aborda provocări reale în domenii precum detectarea programelor malware, securitatea fișierelor și prevenirea amenințărilor. 

În timpul programului de bursă OPSWAT , participanții investighează și reproduc sistematic CVE-uri cunoscute în diferite produse, biblioteci și sisteme de operare. Ca parte a acestei inițiative, Dat Phung - unul dintre distinșii noștri bursieri - a ales să examineze Mongoose datorită adoptării sale pe scară largă în mediile de producție. În noiembrie 2024, el a descoperit o vulnerabilitate critică în Mongoose în timp ce efectua o analiză aprofundată a bibliotecii. Vulnerabilitatea permitea unui atacator să exploateze valoarea $where, ceea ce putea duce la executarea de cod de la distanță (RCE) pe serverul de aplicații Node.js. La raportarea promptă a problemei la Mongoose, a fost lansat un patch ca parte a versiunii 8.8.3, iar CVE-2024-53900 a fost dezvăluit în National Vulnerability Database (NVD).

Cronologia CVE-2024-53900 & CVE-2025-23061

  • 7 noiembrie 2024: Dat Phung a identificat o vulnerabilitate critică în Mongoose și a trimis un raport de securitate către Snyk. 
  • 26 noiembrie 2024: Mongoose a lansat versiunea 8.8.3 pentru a aborda și remedia această vulnerabilitate. 
  • 2 decembrie 2024: National Vulnerability Database (NVD) a dezvăluit CVE-2024-53900 pentru această vulnerabilitate. 
  • 17 decembrie 2024: La analiza patch-ului Mongoose 8.8.3, Dat Phung a găsit o ocolire care încă permite RCE (Remote Code Execution). Un raport de securitate detaliat a fost trimis către Tidelift. 
  • 13 ianuarie 2025: Mongoose a lansat versiunea 8.9.5, introducând un patch îmbunătățit care a rezolvat în mod eficient bypass-ul. 
  • 15 ianuarie 2025: National Vulnerability Database (NVD) a dezvăluit oficial CVE-2025-23061, subliniind gravitatea vulnerabilității nou identificate.

Metoda Populate() a lui Mongoose

Mongoose oferă, de asemenea, o caracteristică utilă numită populate() care îmbunătățește capacitatea de a lucra cu relațiile dintre documente. În timp ce versiunile MongoDB ≥ 3.2 au operatorul de agregare $lookup pentru îmbinări, populate() de la Mongoose oferă o alternativă mai puternică pentru înlocuirea automată a unei referințe cu datele corespunzătoare din documentele conexe. Acest lucru este deosebit de util pentru gestionarea relațiilor dintre diferite colecții MongoDB, cum ar fi atunci când un document face referire la altul prin _id-ul său. [2] 

Cod JavaScript care definește o schemă Mongoose pentru un autor cu câmpurile nume, vârstă și biografie
Schema autorilor
Cod JavaScript care definește o schemă Mongoose pentru cărți, inclusiv titlul, descrierea, prețul și referințele autorului
Schema cărților
Fragment de cod JavaScript pentru o rută Node.js care recuperează detaliile cărții și completează câmpurile autor sau recenzie
Aplicație Nodejs

La definirea unei scheme în Mongoose, un câmp poate fi setat pentru a face trimitere la un alt model utilizând opțiunea ref. Metoda populate() este apoi utilizată pentru a înlocui câmpul de referință (un ObjectId) cu documentul complet din modelul aferent. De exemplu, într-o aplicație de librărie, câmpul author din bookSchema face trimitere la documentul Author, iar câmpul review face trimitere la documentul Reviews. Metoda populate() permite dezvoltatorilor să înlocuiască câmpul author (care este un ObjectId) cu documentul complet Author atunci când interoghează modelul book.

Funcția populate() permite dezvoltatorilor să înlocuiască câmpul author (care este un ObjectId) cu întregul document Author atunci când interoghează modelul book:

Reprezentarea JSON a unui document MongoDB care stochează detaliile unei cărți fără informații extinse despre autor
Neutilizarea populate()
Reprezentarea JSON a unui document MongoDB cu detalii extinse despre autor utilizând funcția populate
Utilizarea populate()

În plus, metoda populate() a Mongoose acceptă interogări personalizate pentru a defini ce documente conexe sunt preluate și cum sunt acestea preluate. Proprietăți precum match și options permit dezvoltatorilor să filtreze, să sorteze, să limiteze și să sară peste documente conexe, oferind capabilități flexibile de recuperare a datelor.

Cod JavaScript care demonstrează o interogare personalizată utilizând funcția populate a Mongoose pentru a filtra autorii în funcție de vârstă
Interogare personalizată în populate() în Mongoose

Analiza CVE-2024-53900

Ca parte a programului OPSWAT Cybersecurity Graduate Fellowship, în timp ce analiza Mongoose pentru a reproduce CVE-uri cunoscute, Dat Phung a efectuat o revizuire completă a funcționării interne a metodei populate(), care joacă un rol-cheie în gestionarea relațiilor dintre documentele MongoDB. Metoda populate() acceptă atât argumente de tip șir de caractere, cât și de tip obiect, iar dezvoltatorii pot utiliza opțiunea match pentru a aplica filtre specifice asupra datelor recuperate:

Cod JavaScript care prezintă utilizarea operatorului $where pentru a filtra autorii în funcție de vârstă într-o interogare

În exemplul de mai sus, opțiunea match este un obiect filtru care poate include operatori de interogare MongoDB, după cum se detaliază în Operatori de interogare și proiecție - Manual MongoDB v8.0. Un operator notabil este $where, care permite executarea JavaScript direct pe serverul MongoDB. Cu toate acestea, această execuție pe serverul MongoDB este restricționată, suportând doar operații și funcții de bază.

Tabel care enumeră funcțiile și proprietățile JavaScript disponibile pentru operațiunile MongoDB map-reduce

Dat Phung a efectuat o analiză aprofundată a codului sursă Mongoose pentru a înțelege fluxul de lucru al metodei populate(). El a stabilit că, după ce aplicația apelează metoda populate() pe model, este declanșată funcția populate(). În cadrul acestei funcții, Mongoose apelează funcția _execPopulateQuery() , care execută interogarea cu operatorul $where pe serverul MongoDB. Ulterior, toate documentele din colecția străină sunt preluate pentru a fi populate în etapele următoare.

Captură de ecran a unei sesiuni de depanare VS Code care analizează executarea unei interogări Mongoose populate

După extragerea datelor din MongoDB, Mongoose execută funcția callback _done(), care apelează _assign() pentru a pregăti datele înainte de "unirea" celor două modele prin apelarea funcției assignVals().

O sesiune de depanare în VS Code care arată codul JavaScript evidențiat legat de interogarea $where în Mongoose

Vulnerabilitatea poate apărea atunci când datele recuperate sunt prelucrate de funcția assignVals() a Mongoose. Această funcție verifică dacă opțiunea match este un array și, în caz afirmativ, transmite fiecare operator funcției sift(). Funcția sift() , care este importată dintr-o bibliotecă externă cu același nume, procesează aceste interogări local pe serverul de aplicații. Această procesare locală prezintă un risc de securitate, în special atunci când se manipulează date de intrare controlate de utilizator.

O sesiune de depanare VS Code care arată atribuirea variabilelor în interiorul unei funcții JavaScript

Pentru a investiga în continuare acest lucru, Dat Phung a modificat valorile din opțiunea match pentru a se asigura că condițiile sunt îndeplinite, invocând astfel funcția sift() pentru o analiză suplimentară a fluxului de date.

Un fragment de cod JavaScript care demonstrează o interogare Mongoose cu o condiție de filtrare $where

Cu condiția stabilită, operatorul $where a fost ulterior transmis funcției sift().

O sesiune de depanare VS Code care arată valorile filtrate într-o funcție JavaScript

Biblioteca sift este un utilitar JavaScript ușor conceput pentru filtrarea și interogarea colecțiilor de date, cum ar fi matricele sau obiectele JSON, utilizând o sintaxă asemănătoare MongoDB. Conform documentației oficiale, "Sift este o bibliotecă mică pentru utilizarea interogărilor MongoDB în JavaScript". Funcția sift() evaluează operațiile de filtrare de tip MongoDB pe serverul de aplicații în locul serverului de baze de date, ceea ce poate expune sistemul la riscuri de securitate semnificative atunci când procesează intrări care nu sunt de încredere.

Un fragment JavaScript simplu care utilizează Sift.js pentru a filtra o serie de obiecte pe baza criteriilor de vârstă
Un exemplu de cod Sift

Continuându-și analiza, colegul nostru a identificat o problemă în cadrul funcției createDefaultQueryTester() a bibliotecii sift. Această funcție convertește fiecare operație din matricea de potrivire în funcții JavaScript executabile, care sunt apoi utilizate pentru filtrarea și prelucrarea locală a datelor documentului MongoDB. Pentru a realiza acest lucru, createDefaultQueryTester() invocă funcția createNamedOperation(), trecând operații precum $where din matricea de corespondență ca argumente. 

O sesiune de depanare VS Code axată pe operațiunile de interogare și execuția funcțiilor

Pentru fiecare operație din matricea de potrivire, createNamedOperation verifică dacă operația este acceptată și apoi o transmite funcției corespunzătoare.

O sesiune de depanare JavaScript care prezintă operatori de interogare precum $where, $eq și $exists

Dacă operația este $where, se generează o funcție JavaScript utilizând valoarea brută "params", care este derivată din operatorul $where din matricea de potrivire și poate fi controlată de utilizator.

Un fragment JavaScript evidențiat care demonstrează executarea funcției atunci când CSP (Politica de securitate a conținutului) este activată

CVE-2024-53900: Detaliile exploatării

În timp ce MongoDB limitează executarea funcțiilor JavaScript prin operația $where, după cum s-a analizat anterior, funcția sift() permite executarea acestor funcții fără astfel de restricții. Această lipsă de validare și restricționare a intrării introduce o vulnerabilitate de securitate semnificativă, deoarece valoarea "params" - controlată direct de intrarea utilizatorului - poate fi exploatată, putând duce la atacuri de injectare de cod. Pentru a examina mai amănunțit această problemă, Dat Phung a construit următoarea interogare:

Un fragment JavaScript care prezintă o interogare Mongoose care utilizează condiția $where cu o execuție de funcție potențial nesigură

Inițial, interogarea nu a reușit să execute un alt proces, rezultând următoarea eroare:

Un jurnal de erori MongoDB afișează un eșec al execuției serverului din cauza unei referințe globale nedefinite

Această eroare indică faptul că Mongoose încearcă să execute operația $where pe serverul MongoDB înainte de a transmite controlul către funcția sift(). Cu toate acestea, din cauza restricțiilor privind funcțiile JavaScript din clauza $where a MongoDB, apare o eroare, care împiedică executarea interogării. Ca urmare, Mongoose oprește procesul înainte de a ajunge la funcția sift() .

Pentru a ocoli limitarea, colegul nostru a utilizat variabila "global" prezentă pe serverul de aplicații, care nu există pe serverul MongoDB. Această abordare i-a permis să ocolească restricția de pe serverul MongoDB și să permită interogării să ajungă la funcția sift():

Un monitor de calculator care afișează textul "codul nu funcționează", subliniind o problemă în procesul de codificare

Cu această valoare, atunci când Mongoose execută operația $where pe MongoDB, absența variabilei "global" face ca operatorul ternar (typeof global != "undefined" ?global.process.mainModule.constructor._load("child_process").exec("calc") : 1) să returneze 1, împiedicând MongoDB să arunce o eroare. În consecință, interogarea este executată pe serverul MongoDB fără probleme.

Cu toate acestea, atunci când aceeași valoare ajunge la funcția sift(), care rulează pe serverul de aplicații unde este disponibilă variabila "global", aceasta declanșează crearea următoarei funcții:

Un ecran monocrom pe care apare fraza "hello world" în text bold

Demonstrarea conceptului de execuție de cod la distanță (RCE)

În exemplul de aplicație furnizat la începutul blogului, dacă un atacator ar trimite următoarea solicitare, ar putea executa cu succes un atac RCE (Remote Code Execution):

Ecran alb-negru pe care este afișat textul "the new york times" cu un font puternic
Diagrama care ilustrează detaliile tehnice ale vulnerabilităților Mongoose CVE, indicând fluxul de date și punctele de încălcare a securității

Videoclipul demonstrează dovada conceptului pentru CVE-2024-53900 care afectează versiunile Mongoose anterioare versiunii 8.8.3, care nu dispune de validarea adecvată a intrărilor pentru a preveni utilizarea abuzivă a operatorului $where împreună cu biblioteca sift.

Soluție incompletă și CVE-2025-23061

Pe baza raportului de securitate al lui Dat Phung, Mongoose a introdus un patch menit să rezolve vulnerabilitatea identificată anterior (CVE-2024-53900) înainte de dezvăluirea sa publică. Patch-ul relevant(Automattic/mongoose@33679bc) a adăugat o verificare pentru a nu permite utilizarea $where în cadrul proprietății match transmise către populate().

Acest fragment verifică dacă proprietatea match trecută în populate() este un array. Dacă este, codul trece prin fiecare obiect din matrice pentru a vedea dacă acesta conține operatorul $where. Dacă este detectat $where, este generată o eroare, împiedicând propagarea încărcăturii malițioase către funcția riscantă sift().  

Prin urmare, sarcina utilă care exploatează CVE-2024-53900 nu trece această verificare deoarece un obiect din matricea de potrivire conține $where, blocând-o efectiv să ajungă la sift().

În timp ce această actualizare blochează în mod corect utilizarea directă a $where într-un singur nivel de anidare, nu reușește să detecteze $where atunci când este încorporat în interiorul unui operator $or - o structură pe care atât MongoDB, cât și biblioteca sift o acceptă pe deplin.

MongoDB acceptă operatorul $or
Biblioteca Sift acceptă operatorul $or

Ca urmare, un atacator poate anida $where sub $or pentru a eluda verificarea pe un singur nivel a patch-ului. Deoarece Mongoose inspectează doar proprietățile de nivel superior ale fiecărui obiect din matricea de potrivire, sarcina utilă de ocolire rămâne nedetectată și ajunge în cele din urmă la biblioteca de sortare, permițând RCE rău intenționat.

Sarcină utilă utilizată pentru a ocoli remedierea în mongoose 8.8.3

Dovada de concept pentru CVE-2025-23061

Pentru a ilustra natura incompletă a remedierii, Dat Phung a reconstruit aplicația exemplu utilizând o versiune a Mongoose 8.9.4 (mai recentă decât 8.8.3). Prin anidarea $whereîn interiorul unei clauze $or, un atacator poate ocoli cu succes verificarea și poate obține RCE.

Exploatarea proof-of-concept demonstrează modul în care CVE-2025-23061 poate fi declanșat în versiunile Mongoose anterioare versiunii 8.9.5, permițând unui atacator să execute cod arbitrar pe server:

Atenuare și îndrumare

Pentru a atenua vulnerabilitățile discutate mai sus, vă rugăm să vă asigurați că sistemul dumneavoastră este actualizat la cea mai recentă versiune a Mongoose.

MetaDefender Core folosind motorul SBOM poate detecta această vulnerabilitate

OPSWAT MetaDefender Core, echipat cu capabilități avansate SBOMSoftware Bill of Materials), permite organizațiilor să adopte o abordare proactivă în abordarea riscurilor de securitate. Prin scanarea aplicațiilor software și a dependențelor acestora, MetaDefender Core identifică vulnerabilitățile cunoscute, precum CVE-2024-53900 și CVE-2025-23061, în cadrul componentelor enumerate. Acest lucru permite echipelor de dezvoltare și securitate să prioritizeze eforturile de aplicare a patch-urilor, atenuând potențialele riscuri de securitate înainte ca acestea să poată fi exploatate de actori rău intenționați. 

Mai jos este o captură de ecran a CVE-2024-53900 și CVE-2025-23061, care au fost detectate de MetaDefender Core cu SBOM:

În plus, CVE-urile pot fi detectate și de MetaDefender Software Supply Chain, care utilizează MetaDefender Core cu SBOM pentru a identifica aceste vulnerabilități.

Rămâneți la curent cu OPSWAT!

Înscrieți-vă astăzi pentru a primi cele mai recente actualizări ale companiei, povești, informații despre evenimente și multe altele.