gpt4 book ai didi

java - 如何全局保存一个变量 token 并每 10 小时更新一次

转载 作者:行者123 更新时间:2023-11-29 04:22:51 24 4
gpt4 key购买 nike

我有一个 Java 应用程序,我需要在其中使用登录凭据对 API 进行休息调用以获取 token ,该 token 有一个到期日期,即从请求时起 10 小时。所有其他对其 API 的调用都需要使用该 token 进行调用。

我需要保存 token ,以便每 10 小时只进行一次登录调用,我该如何实现?我试过创建一个单例类。但是,我认为多个线程可能会在到期时间内尝试刷新 token 。

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

public class CredentialsHolder {

private static CredentialsHolder instance = null;
private String loginToken;
private Date loginTokenExpiry;

private static final String API_BASE_URL_V1 = "https://api.com/rest";
private static final String API_LOGIN_TOKEN_PATH = "token";
private static final String API_USER_NAME = "userName";
private static final String API_PASSWORD = "password";

public static synchronized CredentialsHolder getInstance() {
if(instance == null)
instance = new CredentialsHolder();
return instance;
}

private CredentialsHolder() {
setAPICredentials();
}

private void refreshToken() {
setAPICredentials();
}

private void setAPICredentials() {
if (Calendar.getInstance().after(toCalendar(loginTokenExpiry))) {
Map headers = new HashMap();
headers.put("userName", API_USER_NAME);
headers.put("password", API_PASSWORD);
Map criteria = new HashMap();
criteria.put("headers", headers);
criteria.put("url", API_BASE_URL_V1 + API_LOGIN_TOKEN_PATH);
Map response = new ExternalAPICaller().httpGet(criteria);
Map responseHeaders = ((Map) response.get("headers"));
System.out.println(responseHeaders);
loginToken = (String) (responseHeaders.get("Token"));
try {
loginTokenExpiry = new SimpleDateFormat("MM/dd/yyyy h:mm:ss a").parse((String) (responseHeaders.get("TokenExpiry")));
} catch (ParseException e) {
e.printStackTrace();
loginTokenExpiry = null;
}
}
}

public String getAccessToken() {
if (Calendar.getInstance().after(toCalendar(loginTokenExpiry)))
refreshToken();
return loginToken;
}

public static Calendar toCalendar(Date date){
Calendar cal = Calendar.getInstance();
cal.setTime(date);
cal.add(Calendar.HOUR, -1);
return cal;
}
}

最佳答案

你可以使用 ScheduledExecutorService为了这。来自示例文档:

import static java.util.concurrent.TimeUnit.*;
class BeeperControl {
private final ScheduledExecutorService scheduler =
Executors.newScheduledThreadPool(1);

public void beepForAnHour() {
final Runnable beeper = new Runnable() {
public void run() { System.out.println("beep"); }
};
final ScheduledFuture<?> beeperHandle =
scheduler.scheduleAtFixedRate(beeper, 10, 10, SECONDS);
scheduler.schedule(new Runnable() {
public void run() { beeperHandle.cancel(true); }
}, 60 * 60, SECONDS);
}
}

您可以创建此 ExecutorService 的实例,并告诉它在某个时间间隔刷新 token 。

但也许更简单的解决方案是使用线程同步来确保在多个线程竞争 token 时只刷新一个 token 。 ReentrantLockSemaphore 可用于确保只有一个线程正在刷新 token 。

关于java - 如何全局保存一个变量 token 并每 10 小时更新一次,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48025160/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com