将 byte[] 映射到 jOOQ 中的 BLOB 在查询中变为 NULL
Mapping byte[] to BLOB in jOOQ becoming NULL in the query
我正在尝试将 Java 中的 byte[]
映射到我的 MySQL 数据库中的 BLOB 字段。这是相关代码:
public void update(IUser data) {
UserRecordExt user = <get user>;
// copy other fields over
user.from(data, USER.OTHERFIELD, USER.OTHERFIELD2);
if (data instanceof IUserExt) {
String avatar = ((IUserExt) data).getAvatarUrl();
if (avatar != null) {
user.setAvatarUrl(avatar);
}
}
/* **** */
user.update();
}
IUser
是jOOQ为我们的SQLtable. 生成的接口
IUserExt
是该接口的扩展,支持我们的 API 用来临时存储数据的 avatarUrl
。
UserRecordExt
扩展了 UserRecord
并实现了 IUserExt
.
getAvatarUrl()
从我们的 API 调用中接收到一个 base64 编码的字符串。
setAvatarUrl() converts this string to a
byte[], and stores it under
UserRecordExt.avatar`.
我要保存到的数据库字段是 avatar
,当我在调试器中到达 /* **** */
时,我可以看到 avatar
属性 存在并且是填充的 byte[]
.
我的问题是,当调用 user.update()
时,我可以在控制台中看到生成的 SQL 查询已将 avatar
设置为 NULL
。我完全不知道这可能是什么原因,在这里对 jOOQ 有点失去信心,因为我希望在我调用要写入数据库的更新时我的 user
对象中存在任何字段。
有什么想法吗?
这是 setAvatarUrl()
的代码:
public void setAvatarUrl(String avatarUrl) {
try {
this.avatar = avatarUrl.getBytes("UTF-8");
} catch (UnsupportedEncodingException e) {
System.err.println("failed to getBytes() on avatar");
}
}
(错误消息不是应该如何处理异常,但是查看日志这不是失败点。byte[]
生成正常。)
您当前方法的问题在于:
public void setAvatarUrl(String avatarUrl) {
try {
this.avatar = avatarUrl.getBytes("UTF-8");
} catch (UnsupportedEncodingException e) {
System.err.println("failed to getBytes() on avatar");
}
}
您显然在子类型 UserRecordExt
中添加了某种 avatar
字段。但是当你调用 update()
时,jOOQ 应该如何知道它呢?该值实际上并不是记录的一部分。
更好的实施方式是:
public void setAvatarUrl(String avatarUrl) {
try {
// This will actually set the AVATAR value on the record itself!
super.setAvatar(avatarUrl.getBytes("UTF-8"));
} catch (UnsupportedEncodingException e) {
System.err.println("failed to getBytes() on avatar");
}
}
以上内容现在可能会回答您的问题。另一方面:
- 这不是您通过网络下载资源的方式。这只会生成 URL 的二进制表示,而不是其内容 ;-)
- 我个人认为你不应该在数据访问层中实现这种逻辑,但讨论超出了这个问题的范围。
我正在尝试将 Java 中的 byte[]
映射到我的 MySQL 数据库中的 BLOB 字段。这是相关代码:
public void update(IUser data) {
UserRecordExt user = <get user>;
// copy other fields over
user.from(data, USER.OTHERFIELD, USER.OTHERFIELD2);
if (data instanceof IUserExt) {
String avatar = ((IUserExt) data).getAvatarUrl();
if (avatar != null) {
user.setAvatarUrl(avatar);
}
}
/* **** */
user.update();
}
IUser
是jOOQ为我们的SQLtable. 生成的接口
IUserExt
是该接口的扩展,支持我们的 API 用来临时存储数据的avatarUrl
。UserRecordExt
扩展了UserRecord
并实现了IUserExt
.getAvatarUrl()
从我们的 API 调用中接收到一个 base64 编码的字符串。setAvatarUrl() converts this string to a
byte[], and stores it under
UserRecordExt.avatar`.
我要保存到的数据库字段是 avatar
,当我在调试器中到达 /* **** */
时,我可以看到 avatar
属性 存在并且是填充的 byte[]
.
我的问题是,当调用 user.update()
时,我可以在控制台中看到生成的 SQL 查询已将 avatar
设置为 NULL
。我完全不知道这可能是什么原因,在这里对 jOOQ 有点失去信心,因为我希望在我调用要写入数据库的更新时我的 user
对象中存在任何字段。
有什么想法吗?
这是 setAvatarUrl()
的代码:
public void setAvatarUrl(String avatarUrl) {
try {
this.avatar = avatarUrl.getBytes("UTF-8");
} catch (UnsupportedEncodingException e) {
System.err.println("failed to getBytes() on avatar");
}
}
(错误消息不是应该如何处理异常,但是查看日志这不是失败点。byte[]
生成正常。)
您当前方法的问题在于:
public void setAvatarUrl(String avatarUrl) {
try {
this.avatar = avatarUrl.getBytes("UTF-8");
} catch (UnsupportedEncodingException e) {
System.err.println("failed to getBytes() on avatar");
}
}
您显然在子类型 UserRecordExt
中添加了某种 avatar
字段。但是当你调用 update()
时,jOOQ 应该如何知道它呢?该值实际上并不是记录的一部分。
更好的实施方式是:
public void setAvatarUrl(String avatarUrl) {
try {
// This will actually set the AVATAR value on the record itself!
super.setAvatar(avatarUrl.getBytes("UTF-8"));
} catch (UnsupportedEncodingException e) {
System.err.println("failed to getBytes() on avatar");
}
}
以上内容现在可能会回答您的问题。另一方面:
- 这不是您通过网络下载资源的方式。这只会生成 URL 的二进制表示,而不是其内容 ;-)
- 我个人认为你不应该在数据访问层中实现这种逻辑,但讨论超出了这个问题的范围。