timecop icon indicating copy to clipboard operation
timecop copied to clipboard

Doesn't work for `Rails.cache` with `expires_in`

Open AlexWayfer opened this issue 3 years ago • 1 comments

pry: main > Rails.cache.write('test', true, unless_exist: true, expires_in: 15.seconds)
# => true
pry: main > Rails.cache.write('test', true, unless_exist: true, expires_in: 15.seconds)
# => false
pry: main > Timecop.travel(15.minutes.from_now) { Rails.cache.write('test', true, unless_exist: true, expires_in: 15.seconds) }
# => false

## wait these 15 seconds...

pry: main > Timecop.travel(15.minutes.from_now) { Rails.cache.write('test', true, unless_exist: true, expires_in: 15.seconds) }
# => true

Tested with both memory_store and redis_store.

AlexWayfer avatar Jan 10 '22 12:01 AlexWayfer

Hi @AlexWayfer I wouldn't expect this to work for the redis_store. Timecop is only mocking out the time for your current ruby process. I don't know the details of memory_store so I can't say what to expect. When you do the first time

Timecop.travel(15.minutes.from_now) { Rails.cache.write('test', true, unless_exist: true, expires_in: 15.seconds) }

You're telling redis to hold onto that key until 15 minutes and 15 seconds from now. Your redis server is running in another process. It has the real system time. So when you call the second time

Timecop.travel(15.minutes.from_now) { Rails.cache.write('test', true, unless_exist: true, expires_in: 15.seconds) }

It has only been 15 seconds. Redis still has a cache key with 15 minutes of TTL. I guess since it doesn't work for memory_store that however rails implements memory_store it is getting the real system time instead of using the ruby interface for getting now.

joshuacronemeyer avatar Mar 07 '22 17:03 joshuacronemeyer

closing for lack of activity. Please re-open if necessary.

joshuacronemeyer avatar Aug 06 '23 20:08 joshuacronemeyer