[2.4. Database row caching](https://livebook.manning.com/book/redis-in-action/chapter-2/59) ; 'delay' order set should remove row_id value
zput opened this issue · comments
def schedule_row_cache(conn, row_id, delay):
conn.zadd('delay:', row_id, delay) #A
conn.zadd('schedule:', row_id, time.time()) #39
def cache_rows(conn):
while not QUIT:
next = conn.zrange('schedule:', 0, 0, withscores=True) #A
now = time.time()
if not next or next[0][1] > now:
time.sleep(.05) #B
continue
row_id = next[0][0]
delay = conn.zscore('delay:', row_id) #C
if delay <= 0:
conn.zrem('delay:', row_id) #D
conn.zrem('schedule:', row_id) #D
conn.delete('inv:' + row_id) #D
continue
row = Inventory.get(row_id) #E
conn.zadd('schedule:', row_id, now + delay) #F
conn.set('inv:' + row_id, json.dumps(row.to_dict())) #53
if i just want to cache one row_id data in 5s.
whether i need to add one line like this:
def cache_rows(conn):
while not QUIT:
next = conn.zrange('schedule:', 0, 0, withscores=True) #A
now = time.time()
if not next or next[0][1] > now:
time.sleep(.05) #B
continue
row_id = next[0][0]
delay = conn.zscore('delay:', row_id) #C
if delay <= 0:
conn.zrem('delay:', row_id) #D
conn.zrem('schedule:', row_id) #D
conn.delete('inv:' + row_id) #D
continue
row = Inventory.get(row_id) #E
conn.zadd('schedule:', row_id, now + delay) #F
conn.zadd('delay:', row_id, 0) # **** I added one line in this ****
conn.set('inv:' + row_id, json.dumps(row.to_dict())) #53
if not, this origin code will loop to cache this row_id corresponding data
I am sorry for not seeing / responding sooner, you are right, this is a bug. Not sure how it passes tests, unless we're not testing it.
Actually looking more in-context, and at your comment, it seems like you are asking a question, not reporting a bug.
If you need this to run for 5 seconds, you can:
def cache_rows(conn, run_for=5):
end = time.time() + run_for
while not QUIT and time.time() <= end:
next = conn.zrange('schedule:', 0, 0, withscores=True) #A
now = time.time()
if not next or next[0][1] > now:
time.sleep(.05) #B
continue
row_id = next[0][0]
delay = conn.zscore('delay:', row_id) #C
if delay <= 0:
conn.zrem('delay:', row_id) #D
conn.zrem('schedule:', row_id) #D
conn.delete('inv:' + row_id) #D
continue
row = Inventory.get(row_id) #E
conn.zadd('schedule:', row_id, now + delay) #F
conn.set('inv:' + row_id, json.dumps(row.to_dict())) #53
That will ensure that your while loop doesn't run for longer than 5 seconds.