package com.xly.erp.common.security; import com.xly.erp.common.config.StubSecurityProperties; import com.xly.erp.common.exception.BizException; import io.jsonwebtoken.Jwts; import io.jsonwebtoken.JwtException; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; import javax.crypto.SecretKey; import javax.crypto.spec.SecretKeySpec; import java.nio.charset.StandardCharsets; import java.time.Duration; import java.util.Date; @Component public class JwtUtil { public static final Duration ACCESS_TTL = Duration.ofHours(8); public static final Duration REFRESH_TTL = Duration.ofDays(30); private final SecretKey key; public JwtUtil(String secret) { this.key = new SecretKeySpec(secret.getBytes(StandardCharsets.UTF_8), "HmacSHA256"); } @Autowired public JwtUtil(StubSecurityProperties props) { this(props.getJwtSecret()); } public String sign(String userNo) { return sign(userNo, ACCESS_TTL); } public String signRefresh(String userNo) { return sign(userNo, REFRESH_TTL); } public String sign(String userNo, Duration ttl) { Date now = new Date(); return Jwts.builder() .subject(userNo) .issuedAt(now) .expiration(new Date(now.getTime() + ttl.toMillis())) .signWith(key) .compact(); } public String parse(String token) { try { return Jwts.parser() .verifyWith(key) .build() .parseSignedClaims(token) .getPayload() .getSubject(); } catch (JwtException | IllegalArgumentException e) { throw new BizException(20001, "未认证或 token 已失效"); } } }