dumbmatter / fakeIndexedDB

A pure JS in-memory implementation of the IndexedDB API
Apache License 2.0
562 stars 69 forks source link

Index on Date type does not work #101

Closed asarbu closed 3 months ago

asarbu commented 3 months ago

I have the following use case that does not work in Fake IndexedDb:

  1. Create a normal FakeIndexedDb
  2. Create an Object Store with an index on a field of type "Date" static upgradeSpendingsDb(db, oldVersion, newVersion, objectStores) { if (!newVersion) { return; } if (oldVersion < newVersion) { objectStores.forEach((objectStore) => { const store = db.createObjectStore(objectStore, { autoIncrement: true }); store.createIndex('byCreatedOn', 'createdOn', { unique: false }); }); } }
    1. Create a class that contains a Date field: class CustomObject() { id = undefined; createdOn = undefined; constructor(id, createdOn) { this.id = id; this.createdOn = createdOn; } }
    2. Store an object in that store store.put(new CustomObject(1, new Date()));
    3. Retrieve the object using an index: const fromDate = new Date(forYear, forMonth, 1); const toDate = new Date(forYear, forMonth + 1, 1); const keyRange = IDBKeyRange.bound(fromDate, toDate, false, true);
    4. Result from cursor is always empty.
    5. The fetch works if I use strings/numbers instead of dates

Is there any other way to build the range or is this a problem in the library?

dumbmatter commented 3 months ago

Can you give a minimal reproduction I can actually run? Otherwise it's hard to know if the bug is where you think it is, or possibly caused by something else in your code. So it's often difficult to try to reproduce bugs without code I can run.

Also, if you want to know if this is a difference in behavior between IndexedDB and fake-indexeddb, you could run the same code in the browser and see if it behaves differently there.

asarbu commented 3 months ago

Hello!

Sure, no problem. I am putting the Visual Studio Code project attached here. Please run npm install and run the Jest tests. For debugging I used the provided launch,json. Please let me know if there is anything else I can help you with.

PS: The code I have attached works in browser.

Best regards, Sebastian

IndexedDB_Bug.zip

dumbmatter commented 3 months ago

Same bug as #98, if you upgrade to the latest version then it works.

Well, you also have to uncomment those useFakeTimers lines or it hangs forever, I'm not sure what they are doing, but messing with how Node's internal scheduling functions work is tricky business with fake-indexeddb.

asarbu commented 3 months ago

It is strange that fake indexeddb halts. This did not happen in the past, when dates were not working. I suggest analyzing the behaviour further

asarbu commented 3 months ago

But thank you for solving my problem.

dumbmatter commented 3 months ago

It's kind of a nightmare to handle every possible case of different ways people modify the built-in Node.js timers. v6 changed how that worked #92 which maybe helped in some situations and hurt in others? idk.

At the end of the day, I have to use something to schedule async events. Best solution is for people to just not modify the built-in timers. I know sometimes that's impossible to avoid, but when you're doing stuff like that, you have to be aware that you might break things.

asarbu commented 3 months ago

Hello! Just in case somebody sees this in the future, If you want the Jest test to stop halting, add the advanceTimers flag. jest.useFakeTimers({ advanceTimers: true }).setSystemTime(new Date(2002, 0, 2));