You seem to just store the access tokens server-side and use it's string value to determine whether it is cached to avoid validating the signature again. In theory I don't see anything wrong with this approach although it somehow wrecks the advantages you get from the statelessness provided by bearer tokens. In practice I see a few partially potential issues ...
To solve the initial problem of storing the CAPTCHA answer without server-side state is, you want a signed and encrypted token. When you generate a CAPTCHA on the server side, you take the solution string, information about the request the CAPTCHA is being used for, and a validity period, and combine them into a token structure of some sort (e.g. JSON). You ...
When the client solves the CAPTCHA, you send them a cryptographically signed token/cookie (perhaps a JWT?) which contains:
Their username/unique identifier
An expiration timestamp (however long you want the CAPTCHA to be valid for).
Optionally their IP address
When they make subsequent requests that include this token (in a cookie or a header or whatever), ...
All that means is that remote systems are connecting to your RDP ports and probably trying different usernames and passwords. This is a known and expected side effect of making your RDP port open to the Internet; see What are the security risks of RDP?.
At a minimum, make sure your server is fully patched and that you're using strong passwords.
It is probably not compromised - yet. But someone is trying to compromise it by connecting and presumably bruteforcing passwords.
Consider moving the RDP port to another port number, or enumerating the IPs that should be allowed to connect and block the others through a firewall.