diff --git a/src/main/java/com/hiczp/bilibili/api/interceptor/ErrorResponseConverterInterceptor.java b/src/main/java/com/hiczp/bilibili/api/interceptor/ErrorResponseConverterInterceptor.java index 4cdb1e0..c0cf386 100644 --- a/src/main/java/com/hiczp/bilibili/api/interceptor/ErrorResponseConverterInterceptor.java +++ b/src/main/java/com/hiczp/bilibili/api/interceptor/ErrorResponseConverterInterceptor.java @@ -24,13 +24,18 @@ public class ErrorResponseConverterInterceptor implements Interceptor { JsonObject jsonObject = InterceptorHelper.getJsonInBody(response); JsonElement code = jsonObject.get("code"); //code 字段不存在 - if (code == null) { + if (code == null || code.isJsonNull()) { return response; } //code 为 0 - if (code.getAsInt() == ServerErrorCode.Common.OK) { + try { + if (code.getAsInt() == ServerErrorCode.Common.OK) { + return response; + } + } catch (NumberFormatException e) { //如果 code 不是数字的话直接返回 return response; } + //打印 body LOGGER.error("Get error response below: \n{}", new GsonBuilder() diff --git a/src/main/java/com/hiczp/bilibili/api/web/BilibiliWebAPI.java b/src/main/java/com/hiczp/bilibili/api/web/BilibiliWebAPI.java index b3b0cfc..938fcf4 100644 --- a/src/main/java/com/hiczp/bilibili/api/web/BilibiliWebAPI.java +++ b/src/main/java/com/hiczp/bilibili/api/web/BilibiliWebAPI.java @@ -2,6 +2,7 @@ package com.hiczp.bilibili.api.web; import com.hiczp.bilibili.api.BaseUrlDefinition; import com.hiczp.bilibili.api.interceptor.AddFixedHeadersInterceptor; +import com.hiczp.bilibili.api.interceptor.ErrorResponseConverterInterceptor; import com.hiczp.bilibili.api.web.cookie.SimpleCookieJar; import com.hiczp.bilibili.api.web.live.LiveService; import okhttp3.Cookie; @@ -53,7 +54,8 @@ public class BilibiliWebAPI { .cookieJar(cookieJar) .addInterceptor(new AddFixedHeadersInterceptor( "User-Agent", browserProperties.getUserAgent() - )); + )) + .addInterceptor(new ErrorResponseConverterInterceptor()); interceptors.forEach(okHttpClientBuilder::addInterceptor); diff --git a/src/main/java/com/hiczp/bilibili/api/web/cookie/SimpleCookieJar.java b/src/main/java/com/hiczp/bilibili/api/web/cookie/SimpleCookieJar.java index c655da3..0ad96f6 100644 --- a/src/main/java/com/hiczp/bilibili/api/web/cookie/SimpleCookieJar.java +++ b/src/main/java/com/hiczp/bilibili/api/web/cookie/SimpleCookieJar.java @@ -4,41 +4,49 @@ import okhttp3.Cookie; import okhttp3.CookieJar; import okhttp3.HttpUrl; +import javax.annotation.Nonnull; import java.util.ArrayList; import java.util.List; import java.util.Map; +import java.util.Vector; import java.util.concurrent.ConcurrentHashMap; import java.util.stream.Collectors; public class SimpleCookieJar implements CookieJar { - private Map> cookiesMap; + private final Map> cookiesMap; public SimpleCookieJar() { cookiesMap = new ConcurrentHashMap<>(); } - public SimpleCookieJar(Map> cookiesMap) { - this.cookiesMap = new ConcurrentHashMap<>(cookiesMap); + public SimpleCookieJar(@Nonnull Map> cookiesMap) { + this(); + cookiesMap.forEach((domain, cookies) -> + this.cookiesMap.put(domain, new Vector<>(cookies)) + ); } @Override public void saveFromResponse(HttpUrl url, List cookies) { cookies.forEach(cookie -> { String domain = cookie.domain(); - List savedCookies = cookiesMap.get(domain); - if (savedCookies == null) { - savedCookies = new ArrayList<>(); - savedCookies.add(cookie); - cookiesMap.put(domain, savedCookies); - } else { - for (Cookie savedCookie : savedCookies) { - if (savedCookie.name().equals(cookie.name())) { - savedCookies.remove(savedCookie); - break; - } + List savedCookies; + synchronized (cookiesMap) { + savedCookies = cookiesMap.get(domain); + if (savedCookies == null) { + savedCookies = new Vector<>(); + savedCookies.add(cookie); + cookiesMap.put(domain, savedCookies); + return; } - savedCookies.add(cookie); } + for (int i = savedCookies.size() - 1; i >= 0; i--) { + Cookie current = savedCookies.get(i); + if (current.name().equals(cookie.name())) { + savedCookies.remove(current); + } + } + savedCookies.add(cookie); }); } @@ -47,13 +55,15 @@ public class SimpleCookieJar implements CookieJar { return getCookiesForHost(url.host()); } - public List getCookiesForHost(String host) { + public List getCookiesForHost(@Nonnull String host) { List cookieList = new ArrayList<>(); cookiesMap.forEach((domain, cookies) -> { if (host.endsWith(domain)) { + //移除过期的 cookies for (int i = cookies.size() - 1; i >= 0; i--) { - if (cookies.get(i).expiresAt() < System.currentTimeMillis()) { - cookies.remove(i); + Cookie current = cookies.get(i); + if (current.expiresAt() < System.currentTimeMillis()) { + cookies.remove(current); } } cookieList.addAll(cookies); diff --git a/src/main/java/com/hiczp/bilibili/api/web/live/LiveService.java b/src/main/java/com/hiczp/bilibili/api/web/live/LiveService.java index def0680..23b620e 100644 --- a/src/main/java/com/hiczp/bilibili/api/web/live/LiveService.java +++ b/src/main/java/com/hiczp/bilibili/api/web/live/LiveService.java @@ -1,6 +1,7 @@ package com.hiczp.bilibili.api.web.live; import com.hiczp.bilibili.api.web.live.entity.SendHeartBeatResponseEntity; +import com.hiczp.bilibili.api.web.live.entity.UserInfoEntity; import retrofit2.Call; import retrofit2.http.GET; import retrofit2.http.Query; @@ -15,4 +16,14 @@ public interface LiveService { default Call sendHeartBeat() { return sendHeartBeat(System.currentTimeMillis()); } + + //获取用户信息 + //成功时, code 为 "REPONSE_OK" + //未登录时返回 500 + @GET("User/getUserInfo") + Call getUserInfo(@Query("ts") long timestamp); + + default Call getUserInfo() { + return getUserInfo(System.currentTimeMillis()); + } } diff --git a/src/main/java/com/hiczp/bilibili/api/web/live/entity/UserInfoEntity.java b/src/main/java/com/hiczp/bilibili/api/web/live/entity/UserInfoEntity.java new file mode 100644 index 0000000..9153de4 --- /dev/null +++ b/src/main/java/com/hiczp/bilibili/api/web/live/entity/UserInfoEntity.java @@ -0,0 +1,191 @@ +package com.hiczp.bilibili.api.web.live.entity; + +import com.google.gson.annotations.SerializedName; + +public class UserInfoEntity { + /** + * code : REPONSE_OK + * msg : ok + * data : {"uname":"czp3009","face":"http://i2.hdslb.com/bfs/face/4f65e79399ad5a1bf3f877851b2f819d5870b494.jpg","silver":22528,"gold":0,"achieve":135,"vip":0,"svip":0,"user_level":25,"user_next_level":26,"user_intimacy":926000,"user_next_intimacy":10000000,"user_level_rank":">50000","billCoin":699} + */ + + @SerializedName("code") + private String code; + @SerializedName("msg") + private String msg; + @SerializedName("data") + private Data data; + + public String getCode() { + return code; + } + + public void setCode(String code) { + this.code = code; + } + + public String getMsg() { + return msg; + } + + public void setMsg(String msg) { + this.msg = msg; + } + + public Data getData() { + return data; + } + + public void setData(Data data) { + this.data = data; + } + + public static class Data { + /** + * uname : czp3009 + * face : http://i2.hdslb.com/bfs/face/4f65e79399ad5a1bf3f877851b2f819d5870b494.jpg + * silver : 22528 + * gold : 0 + * achieve : 135 + * vip : 0 + * svip : 0 + * user_level : 25 + * user_next_level : 26 + * user_intimacy : 926000 + * user_next_intimacy : 10000000 + * user_level_rank : >50000 + * billCoin : 699 + */ + + @SerializedName("uname") + private String uname; + @SerializedName("face") + private String face; + @SerializedName("silver") + private int silver; + @SerializedName("gold") + private int gold; + @SerializedName("achieve") + private int achieve; + @SerializedName("vip") + private int vip; + @SerializedName("svip") + private int svip; + @SerializedName("user_level") + private int userLevel; + @SerializedName("user_next_level") + private int userNextLevel; + @SerializedName("user_intimacy") + private int userIntimacy; + @SerializedName("user_next_intimacy") + private int userNextIntimacy; + @SerializedName("user_level_rank") + private String userLevelRank; + @SerializedName("billCoin") + private int billCoin; + + public String getUname() { + return uname; + } + + public void setUname(String uname) { + this.uname = uname; + } + + public String getFace() { + return face; + } + + public void setFace(String face) { + this.face = face; + } + + public int getSilver() { + return silver; + } + + public void setSilver(int silver) { + this.silver = silver; + } + + public int getGold() { + return gold; + } + + public void setGold(int gold) { + this.gold = gold; + } + + public int getAchieve() { + return achieve; + } + + public void setAchieve(int achieve) { + this.achieve = achieve; + } + + public int getVip() { + return vip; + } + + public void setVip(int vip) { + this.vip = vip; + } + + public int getSvip() { + return svip; + } + + public void setSvip(int svip) { + this.svip = svip; + } + + public int getUserLevel() { + return userLevel; + } + + public void setUserLevel(int userLevel) { + this.userLevel = userLevel; + } + + public int getUserNextLevel() { + return userNextLevel; + } + + public void setUserNextLevel(int userNextLevel) { + this.userNextLevel = userNextLevel; + } + + public int getUserIntimacy() { + return userIntimacy; + } + + public void setUserIntimacy(int userIntimacy) { + this.userIntimacy = userIntimacy; + } + + public int getUserNextIntimacy() { + return userNextIntimacy; + } + + public void setUserNextIntimacy(int userNextIntimacy) { + this.userNextIntimacy = userNextIntimacy; + } + + public String getUserLevelRank() { + return userLevelRank; + } + + public void setUserLevelRank(String userLevelRank) { + this.userLevelRank = userLevelRank; + } + + public int getBillCoin() { + return billCoin; + } + + public void setBillCoin(int billCoin) { + this.billCoin = billCoin; + } + } +} diff --git a/src/test/java/com/hiczp/bilibili/api/test/RuleSuite.java b/src/test/java/com/hiczp/bilibili/api/test/RuleSuite.java index 26aab17..0e63997 100644 --- a/src/test/java/com/hiczp/bilibili/api/test/RuleSuite.java +++ b/src/test/java/com/hiczp/bilibili/api/test/RuleSuite.java @@ -22,6 +22,7 @@ import java.nio.file.Paths; SendBulletScreenTest.class, SecurityHelperTest.class, AuthenticatorTest.class, + WebAPITest.class, LogoutTest.class }) public class RuleSuite { diff --git a/src/test/java/com/hiczp/bilibili/api/test/WebAPITest.java b/src/test/java/com/hiczp/bilibili/api/test/WebAPITest.java new file mode 100644 index 0000000..a9e8803 --- /dev/null +++ b/src/test/java/com/hiczp/bilibili/api/test/WebAPITest.java @@ -0,0 +1,33 @@ +package com.hiczp.bilibili.api.test; + +import com.google.gson.Gson; +import com.google.gson.GsonBuilder; +import com.hiczp.bilibili.api.web.BilibiliWebAPI; +import com.hiczp.bilibili.api.web.live.entity.UserInfoEntity; +import org.junit.Test; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.io.IOException; + +public class WebAPITest { + private static final Logger LOGGER = LoggerFactory.getLogger(WebAPITest.class); + private static final Gson GSON = new GsonBuilder().setPrettyPrinting().create(); + private BilibiliWebAPI bilibiliWebAPI; + + public WebAPITest() { + try { + this.bilibiliWebAPI = Config.getBilibiliAPI().getBilibiliWebAPI(); + } catch (IOException e) { + e.printStackTrace(); + } + } + + @Test + public void getUserInfo() throws IOException { + UserInfoEntity userInfoEntity = bilibiliWebAPI.getLiveService().getUserInfo() + .execute() + .body(); + LOGGER.info("User info below: \n{}", GSON.toJson(userInfoEntity)); + } +}