DocumentReference.set() (other operations as well) can synchronously throw errors before returning a Promise. #2293
Labels
api: firestore
Issues related to the googleapis/nodejs-firestore API.
priority: p2
Moderately-important priority. Fix may not be included in next release.
type: bug
Error or flaw in code with unintended results or allowing sub-optimal usage patterns.
This is the client library for firestore.
I don't believe so.
Environment details
firebase-admin
version: 12.7.0Steps to reproduce
Run this code:
Run each of the functions in main() by themselves and see for yourselves. The first function does not work because the function throws synchronously after a promise has been added to the event loop. The second one works because the error is thrown before a promise can be added to the event loop.
Here's another example for further clarity:
Does not work for the same reason.
It needs to be converted to this, and there's more than one way to do this, but:
I can think of two solutions to this:
All methods that return a promise for DocumentReferences that perform sync work before returning a promise need to be wrapped in a promise, i.e. have the
async
keyword added to them. Or at least the wrappers that call those methods in firebase-admin/firestore need them. Or something to that effect.Update the docs everywhere to indicate that it can throw synchronously... Which just feels... wrong.
Unless someone can find a way of how doing this would break code, I think option 1's the best bet.
And for the sake of entertaining the argument that your props should always be defined, yes your props should be never undefined, sure, but there are always bugs in software, bugs you don't expect to have happen.
So when your system inevitably has a bug arise that's the result of bleedover from a different failure, and the props end up being undefined, and when your catch block is not executed the way you think it will because you were expecting a promise to either resolve or reject, very bad things happen. e.g. server crashes that can leave data in an inconsistent state. If that data controls infrastructure, things get expensive and dangerous financially.
This does open a broader discussion around if this nuance of javascript makes sense from a DX perspective, there should be lint rules for this at a minimum. I actually feel like this is a gap in ECMA and could imagine a world where JS engines throw a static error before running the code if this situation is discovered.
Here's a link to the line of code that's the root of the issue:
nodejs-firestore/dev/src/write-batch.ts
Line 338 in d559080
What's everyone's take on this?
Best,
Aaron
The text was updated successfully, but these errors were encountered: