sqlite: remove the null prototype from result rows
Nessuno ha ancora preso questa issue.
- Lingua principale
- JavaScript
- Stelle
- 122k
- Fork
- 37.3k
- Merge medio
- 4g 2h
- PR unite (30g)
- 283
Descrizione
Current behavior
Rows returned by get(), all() and iterate() are created with a null prototype. The V8 API that does this produces dictionary-mode objects, and V8 will not cache a prototype transition on a dictionary map, so every row also gets its own freshly allocated hidden class. Rows from the same statement therefore share no shape: they are slow to build, and every property access on them in user code is megamorphic.
Proposal
Drop the null prototype and build rows with v8::DictionaryTemplate, cached per statement. Rows become ordinary objects, and every row of a statement shares one hidden class.
Pros
all()is 10–37% faster depending on the query; reading the rows afterwards is far cheaper still.- Consistent with
run(), which already returns an ordinary object, and withbetter-sqlite3.
Cons
- Semver-major.
- Rows can no longer be indexed by untrusted keys without
Object.hasOwn()—row.toStringandrow.constructorstart resolving throughObject.prototype. - User code comparing rows against
{ __proto__: null, ... }breaks.
Prototype pollution is not a concern either way: rows are built by defining own properties directly, so a __proto__ column is an own property and never reaches Object.prototype.
I have benchmarks and a working implementation if there is interest.
Guida per i contributori
Apri la guida per i contributori
Come iniziare
- Leggi tutta la issue e poi la guida ai contributi del progetto.
- Commenta sulla issue per dire che te ne occupi tu — evita che due persone facciano lo stesso lavoro.
- Fai un fork del repository e lavora su un branch.
- Apri una pull request che faccia riferimento al numero della issue.
Direzione di ricerca
Inizia individuando le implementazioni di get(), all(), iterate() e la gestione esistente dei risultati di run(), quindi leggi come vengono usati la V8 API e v8::DictionaryTemplate. Esamina i benchmark proposti e l’implementazione funzionante menzionati nell’issue. Il lavoro è completo quando sono stati valutati il comportamento degli oggetti ordinari, la forma di riga condivisa, le prestazioni e i problemi di compatibilità di semver-major.
Scritto dal modello di indicizzazione a partire dal testo della issue.
Valutazione
- Stack tecnologico
- javascript, sqlite
- Ambito
- backend, databases
- Tipo di issue
- Funzionalità
- Difficoltà
- 5/5
- Tempo stimato
- Più di una settimana
- Stato di attività
- Attiva
- Chiarezza
- Abbastanza chiara
- Idoneità per principianti
- 35/100