refresh token bug in JWT method

according to this article
one method to secure the JWT is refreshToken:

in center auth server, we maintain a table like this:

table auth_tokens(

The following is work flow:

User request the login API with phone and we verified it, after that, the auth server send one token, and register the token ( add one row in the table. )

When the token expired, user request the exchange API with the old token. Firstly the auth server validate the old token as normal except expire checking, then create the token hash value, then lookup above table by user id:

  • a. If found record and user_id and jwt_hash is match, then issue new
    token and update the table.

    b. If found record, but user_id and jwt_hash is not match , it means
    someone has use the token exchanged new token before. The token be
    hacked, delete records by user_id and response with alert

    c. if not found record, user need login again or only input password.
    when use changed the password or login out, delete record by user id.

To use token continuously ,both legal user and hacker need exchange new token continuously, but only one can success, when one fail, both need login again at next exchange time.

So if hacker got the token, it can be used short time, but can’t exchange new one if legal user exchanged new one next time, because the token valid period is short, it is more security.

If there is no hacker, normal user also need exchange new token periodically ,such as every 30 minutes, this is just like login automatically. The extra load is not high and we can adjust expire time for our application.

but imagine this senario:

For example, a hacker got the Bob’s token, and he knows Bob is sleep at 1:00 am to 6:00 am,
So, the hacker can use the toke at night continuously until Bob get up next day and use the application.

one solution is at the night, user should enter user and pass instead of token but this is not good solution in my idea!
do you know better solution?

Thanks in advance