- mongodb - 在 MongoDB mapreduce 中,如何展平值对象?
- javascript - 对象传播与 Object.assign
- html - 输入类型 ="submit"Vs 按钮标签它们可以互换吗?
- sql - 使用 MongoDB 而不是 MS SQL Server 的优缺点
我有一个 PostgreSQL 8.4 数据库,其中包含一些表和 View ,这些表和 View 本质上是对某些表的连接。我使用 NetBeans 7.2(如 here 所述)创建从这些 View 和表派生的基于 REST 的服务,并将它们部署到 Glassfish 3.1.2.2 服务器。
还有另一个进程异步更新一些用于构建 View 的表中的内容。我可以直接查询 View 和表并查看这些更改是否正确发生。但是,从基于 REST 的服务中提取时,这些值与数据库中的值不同。我假设这是因为 JPA 在 Glassfish 服务器上缓存了数据库内容的本地副本,并且 JPA 需要刷新关联的实体。
我尝试向 NetBeans 生成的 AbstractFacade 类添加几个方法:
public abstract class AbstractFacade<T> {
private Class<T> entityClass;
private String entityName;
private static boolean _refresh = true;
public static void refresh() { _refresh = true; }
public AbstractFacade(Class<T> entityClass) {
this.entityClass = entityClass;
this.entityName = entityClass.getSimpleName();
}
private void doRefresh() {
if (_refresh) {
EntityManager em = getEntityManager();
em.flush();
for (EntityType<?> entity : em.getMetamodel().getEntities()) {
if (entity.getName().contains(entityName)) {
try {
em.refresh(entity);
// log success
}
catch (IllegalArgumentException e) {
// log failure ... typically complains entity is not managed
}
}
}
_refresh = false;
}
}
...
}
doRefresh()
来自每个
find
NetBeans 生成的方法。通常发生的是
IllegalArgumentsException
抛出说明类似
Can not refresh not managed object: EntityTypeImpl@28524907:MyView [ javaType: class org.my.rest.MyView descriptor: RelationalDescriptor(org.my.rest.MyView --> [DatabaseTable(my_view)]), mappings: 12].
的东西
最佳答案
我建议添加一个 @Startup
@Singleton
与 PostgreSQL 数据库建立 JDBC 连接并使用 LISTEN
and NOTIFY
的类处理缓存失效。
更新 :Here's another interesting approach, using pgq and a collection of workers for invalidation .
失效信号
在正在更新的表上添加一个触发器,发送 NOTIFY
每当更新实体时。在 PostgreSQL 9.0 及以上版本 NOTIFY
可以包含有效负载,通常是行 ID,因此您不必使整个缓存失效,只需更改已更改的实体即可。在不支持有效负载的旧版本上,您可以将无效条目添加到带时间戳的日志表中,您的助手类在获得 NOTIFY
时查询该日志表。 ,或者只是使整个缓存无效。
您现在的助手类(class) LISTEN
s 上 NOTIFY
触发器发送的事件。当它收到 NOTIFY
事件,它可以使单个缓存条目无效(见下文),或刷新整个缓存。您可以使用 PgJDBC's listen/notify support 监听来自数据库的通知。 .您将需要解开任何管理的连接池java.sql.Connection
进入底层 PostgreSQL 实现,以便您可以将其转换为 org.postgresql.PGConnection
并调用 getNotifications()
在上面。
替代 LISTEN
和 NOTIFY
,您可以在计时器上轮询更改日志表,并在问题表上设置触发器,将更改的行 ID 和更改时间戳附加到更改日志表。除了需要为每种 DB 类型使用不同的触发器之外,这种方法将是可移植的,但它效率低下且不及时。它将需要频繁的低效轮询,并且仍然具有监听/通知方法没有的时间延迟。在 PostgreSQL 中,您可以使用 UNLOGGED
表以稍微降低这种方法的成本。
缓存级别
EclipseLink/JPA 有几个级别的缓存。
一级缓存位于 EntityManager
等级。如果实体附加到 EntityManager
来自 persist(...)
, merge(...)
, find(...)
等,然后是 EntityManager
在同一 session 中再次访问该实体时,无论您的应用程序是否仍然引用它,都需要返回该实体的相同实例。如果您的数据库内容已更改,则此附加实例将不会是最新的。
二级缓存(可选)位于 EntityManagerFactory
级别,是一种更传统的缓存。不清楚您是否启用了二级缓存。检查您的 EclipseLink 日志和您的 persistence.xml
.您可以使用 EntityManagerFactory.getCache()
访问二级缓存;见 Cache
.
@thedayofcondor 展示了如何刷新二级缓存:
em.getEntityManagerFactory().getCache().evictAll();
evict(java.lang.Class cls, java.lang.Object primaryKey)
逐出单个对象称呼:
em.getEntityManagerFactory().getCache().evict(theClass, thePrimaryKey);
@Startup
使用它
@Singleton
NOTIFY
监听器仅使那些已更改的条目无效。
EntityManager
,附加和分离的实体等工作。一种选择是始终对有问题的表使用分离的实体,您使用新的
EntityManager
每当您获取实体时。这个问题:
EntityManager
缓存是您的问题,因为 RESTful Web 服务通常使用短
EntityManager
实现 session 。如果您正在使用扩展的持久性上下文,或者您正在创建和管理自己的
EntityManager
,这可能只是一个问题。 session 而不是使用容器管理的持久性。
关于java - 后端数据库异步更改时如何刷新JPA实体?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13258976/
我有一个使用 css 列的下拉菜单,当我使用 jquery slide() 时,它会调整下拉框的大小,并重排内容直到达到完整高度。 这是一个工作示例 https://codepen.io/peterg
我有一个带有嵌套 ScrollViewer 的 Expander,如下所示: 代码(简化版)
我想在所有 ajax 调用之后调用一些 javascript 函数。我知道如何调用每个单独的 ajax 调用中的函数,如下所示: function xyz() { if (window.XMLHttp
我想将值从应用程序端传递到 api。在此 api 调用中传递图像、名字、电子邮件、电话和位置。在 Debug模式下,检查值不会被传递。 代码下方 File file = null;
我正在尝试在使用reportlab生成的pdf中的表格后插入分页符,我正在使用以下函数生成pdf: def render_to_pdf(template_src, context_dict): t
CBPeripheralManager 是否有推荐的方法来终止连接。到目前为止我发现的最好的方法就是干脆不响应动态值,然后 BLE 堆栈似乎关闭了连接,但这似乎很粗糙。 一定有更好的方法吗? 最佳答案
我的 API 的 REST 端位于以下地址:http://test.jll.aplikacje-dedykowane.pl/rest/warehouse/all 。现在,我尝试返回在此页面准备的 JS
我有以下 CPP 代码。我想做的是,当我的 native 端发生错误时,我会通知 Java 该错误。我用了How can I catch SIGSEGV (segmentation fault) an
限制对象的方法之一是像这样给函数添加限制 def ten_objects(): obj = Model.objects.all()[0:10] # limit to 10 retur
我目前在电信公司实习,这是一个专业,也是本科生。我有很多选择。据我所知,我知道独立应用程序端的 c、c++、c#、java 语言,在移动端我尝试进入 android 世界,也知道 php、mysql、
我想让我的边框底部看起来像这样: 有一个 flex 的末端。目前它看起来像这样: 我尝试使用的 CSS 是 border-bottom-right-radius: 10px;。代码如下所示:
我有一个 Flutter 项目,突然间,据我所知,我没有做任何特别的事情..Android 端开始显示错误,我完全迷路了,我完全不知道哪里出了问题,也不知道为什么会这样。 这就是我打开 android
我有一个自定义对象列表 (List) 。我需要将此数据发送到 React Native 端以显示在平面列表中。我该怎么做?这个列表出现在 类 NativeToReact(reactContext:Re
我有这个代码: #if defined(NOT_STANDALONE) JNIEXPORT void JNICALL sumTraces (JNIEnv* env, jclass caller,
我有一个定义一对多模型关系的 Django 应用程序。模型如下所示: from django.db import models # Create your models here. class Str
我有以下代码,它根据 IFrame 内容的大小调整 IFrame 的大小: function setIframeHeight(id) {
如何创建自定义过滤器 angularjs javascript Controller 端?我想通过 SegmentId 在名为段的数组中搜索,以创建过滤器,该过滤器通过 SegmentId 在段数组搜
我的代码在 netbeans 8.0.2 中我几乎尝试了所有方法,但没有结果。请帮助我。如何在 netbeans 中显示它? 最佳答案 您只需单击源包(源文件),它就会显示您的项目文件。 关于java
我想这是纯 C++ 问题和 OpenGL 问题之间的一种交叉。我有一个统一的缓冲区,并在其中分配 sizeof(ShaderData) 字节的空间。我在着色器的 GPU 端使用 std140 布局。
我对 Hadoop 中 reduce 端的文件合并过程的理解有问题,因为它在“Hadoop:权威指南”(Tom White)中有所描述。引用它: When all the map outputs ha
我是一名优秀的程序员,十分优秀!