栋dong的个人站点
解决HttpCookie不支持序列化的方法
如果我们需要将某些cookie进行序列化时,我们发现默认的java.net.HttpCookie,没有实现Serializable,这使得我们不能对他进行直接的序列化,本文将试图去解决它
自定义序列化与反序列化
这似乎是一个很好的方法,but我尝试多次,均失败告终
新建一个类去实现
既然原装的不能实现,我们新建一个类让他支持序列化,我们在需要调用cookie的时候给他转换回去
import com.fasterxml.jackson.annotation.JsonTypeInfo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.io.Serializable;
import java.net.HttpCookie;
@JsonTypeInfo(use = JsonTypeInfo.Id.CLASS, include = JsonTypeInfo.As.PROPERTY, property = "@class")
@Data
@NoArgsConstructor
@AllArgsConstructor
public class SerializableHttpCookie implements Serializable {
private static final long serialVersionUID = 1L;
private String name;
private String value;
private String domain;
private String path;
private long maxAge;
private boolean secure;
private int version;
// 从 HttpCookie 构造
public SerializableHttpCookie(HttpCookie cookie) {
this.name = cookie.getName();
this.value = cookie.getValue();
this.domain = cookie.getDomain();
this.path = cookie.getPath();
this.maxAge = cookie.getMaxAge();
this.secure = cookie.getSecure();
this.version = cookie.getVersion();
}
// 转换回 HttpCookie public HttpCookie toHttpCookie() {
HttpCookie cookie = new HttpCookie(name, value);
cookie.setDomain(domain);
cookie.setPath(path);
cookie.setMaxAge(maxAge);
cookie.setSecure(secure);
cookie.setVersion(version);
return cookie;
}
}
这里放了一些常用的属性,并且实现了一部分转换,
我们注意到一个不常用的注解
- @JsonTypeInfo(use = JsonTypeInfo.Id.CLASS, include = JsonTypeInfo.As.PROPERTY, property = "@class")
这个注解主要是为了避免一个报错,在嵌套序列化时,可以确保子类实例在序列化时保留具体类型信息,这样在反序列化时可以恢复为正确的子类实例。
考虑到我们日常使用HttpCookie经常会是ArrayList,所以我新写了一个工具类,同时也将apache.http.client.CookieStore也转为自定义类
package love.foreverlink.util;
import love.foreverlink.entity.SerializableHttpCookie;
import org.apache.http.client.CookieStore;
import org.apache.http.cookie.Cookie;
import java.net.HttpCookie;
import java.util.ArrayList;
import java.util.List;
public class CookieUtils {
// 将 ArrayList<HttpCookie> 转换为 ArrayList<SerializableHttpCookie>
public static ArrayList<SerializableHttpCookie> toSerializableCookieList(List<HttpCookie> httpCookies) {
ArrayList<SerializableHttpCookie> serializableCookies = new ArrayList<>();
if (httpCookies != null) {
for (HttpCookie httpCookie : httpCookies) {
serializableCookies.add(new SerializableHttpCookie(httpCookie));
}
}
return serializableCookies;
}
//org.apache.http.client.CookieStore转为ArrayList<SerializableHttpCookie>
public static ArrayList<SerializableHttpCookie> toSerializableCookieList(CookieStore httpCookies) {
ArrayList<SerializableHttpCookie> serializableCookies = new ArrayList<>();
// 从 CookieStore 获取所有 cookies
List<Cookie> cookies = httpCookies.getCookies();
// 遍历每一个 Cookie 并转换为 SerializableHttpCookie
for (Cookie cookie : cookies) {
SerializableHttpCookie serializableCookie = new SerializableHttpCookie(cookie.getName(), cookie.getValue(), cookie.getDomain(), cookie.getPath(), cookie.getExpiryDate() != null ? cookie.getExpiryDate().getTime() : -1, cookie.isSecure(), cookie.getVersion());
serializableCookies.add(serializableCookie);
}
return serializableCookies;
}
// 将 ArrayList<SerializableHttpCookie> 转换为 ArrayList<HttpCookie>
public static ArrayList<HttpCookie> toHttpCookieList(List<SerializableHttpCookie> serializableCookies) {
ArrayList<HttpCookie> httpCookies = new ArrayList<>();
if (serializableCookies != null) {
for (SerializableHttpCookie serializableCookie : serializableCookies) {
httpCookies.add(serializableCookie.toHttpCookie());
}
}
return httpCookies;
}
}
解决HttpCookie不支持序列化的方法最先出现在栋dong的个人站点。