60 lines
1.6 KiB
C++
60 lines
1.6 KiB
C++
|
|
#include "jwt.h"
|
||
|
|
#include <jwt-cpp/jwt.h>
|
||
|
|
#include <stdexcept>
|
||
|
|
|
||
|
|
namespace scar {
|
||
|
|
|
||
|
|
std::string JWT::generate(const std::string& username, const std::string& secret,
|
||
|
|
std::chrono::seconds expiration) {
|
||
|
|
auto now = std::chrono::system_clock::now();
|
||
|
|
auto exp_time = now + expiration;
|
||
|
|
|
||
|
|
return jwt::create()
|
||
|
|
.set_issuer(ISSUER)
|
||
|
|
.set_type("JWT")
|
||
|
|
.set_issued_at(now)
|
||
|
|
.set_expires_at(exp_time)
|
||
|
|
.set_payload_claim("username", jwt::claim(username))
|
||
|
|
.sign(jwt::algorithm::hs256{secret});
|
||
|
|
}
|
||
|
|
|
||
|
|
bool JWT::verify(const std::string& token, const std::string& secret) {
|
||
|
|
try {
|
||
|
|
auto verifier = jwt::verify()
|
||
|
|
.allow_algorithm(jwt::algorithm::hs256{secret})
|
||
|
|
.with_issuer(ISSUER);
|
||
|
|
|
||
|
|
auto decoded = jwt::decode(token);
|
||
|
|
verifier.verify(decoded);
|
||
|
|
|
||
|
|
return true;
|
||
|
|
} catch (const std::exception&) {
|
||
|
|
return false;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
std::string JWT::extractUsername(const std::string& token) {
|
||
|
|
try {
|
||
|
|
auto decoded = jwt::decode(token);
|
||
|
|
if (decoded.has_payload_claim("username")) {
|
||
|
|
return decoded.get_payload_claim("username").as_string();
|
||
|
|
}
|
||
|
|
} catch (const std::exception&) {
|
||
|
|
// Fall through
|
||
|
|
}
|
||
|
|
return "";
|
||
|
|
}
|
||
|
|
|
||
|
|
bool JWT::isExpired(const std::string& token) {
|
||
|
|
try {
|
||
|
|
auto decoded = jwt::decode(token);
|
||
|
|
auto exp = decoded.get_expires_at();
|
||
|
|
auto now = std::chrono::system_clock::now();
|
||
|
|
return exp < now;
|
||
|
|
} catch (const std::exception&) {
|
||
|
|
return true;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
} // namespace scar
|