grails 与 JDO - 如何正确使用 persistenceManager
我正在使用谷歌应用程序引擎和 grails 创建一个应用程序。我设置了一个控制器供我的 Flex 应用程序调用。控制器调用服务来获取列表并将其发送回 Flex。
Flex 客户端能够一次性取回数据。另外,如果我在浏览器中调用该操作,我也可以调用该操作并取回数据。我发现的问题是它无法多次调用它,因为应用程序正在使用 JDO,并且在第一次调用后我收到一条错误,指出 persistenceManager 已关闭。
我读过一些帖子,向您展示如何设置单个吨并在需要时获取 persistanceManager 的实例,但这似乎也不起作用。
这是我第一次使用 JDO,我可以使用一些建议来让这些服务在一致的基础上工作。
以下是实际查询数据存储的服务的代码。
package com.dlish.fulcrum
import com.dlish.fulcrum.PMF
import org.springframework.beans.factory.InitializingBean
import com.google.appengine.api.datastore.*
import com.dlish.fulcrum.Show
class VenueBlastService {
static transactional = true
def grailsApplication
def setting
void afterPropertiesSet()
{
this.setting = grailsApplication.config.setting
}
def persistenceManager
def getAllShows() {
def query = persistenceManager.newQuery( Show )
def showInstanceList = query.execute()
return showInstanceList
}
}
I am creating an application with google app engine and grails. I have a Controller set up for my Flex application to call. The Controller calls a service to get a list back and send it back to Flex.
The Flex client is able to get the data back one time. Also If I call the action in the browser I can call the action and get data back as well. The problem that I am finding is that it is not able to call it more than once because the app is using JDO and after the first call I get an error saying that the persistenceManager has been closed.
I have read some posts that show you how to set up a single ton and just get an instance of the persistanceManager when you need it but this does not seem to work either.
This is my first time working with JDO and I could use some advice one getting these services to work on a consistant bases.
Here is the code from the service that is actually querying the datastore.
package com.dlish.fulcrum
import com.dlish.fulcrum.PMF
import org.springframework.beans.factory.InitializingBean
import com.google.appengine.api.datastore.*
import com.dlish.fulcrum.Show
class VenueBlastService {
static transactional = true
def grailsApplication
def setting
void afterPropertiesSet()
{
this.setting = grailsApplication.config.setting
}
def persistenceManager
def getAllShows() {
def query = persistenceManager.newQuery( Show )
def showInstanceList = query.execute()
return showInstanceList
}
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
grails 应用程序引擎插件在请求范围内创建 persistenceManager 对象。默认情况下,服务是单例的,这意味着它们创建一次而不是每个请求。因此,如果您为服务提供 persistenceManager 实例变量,则第一个请求将具有有效的 persistenceManager,但所有后续调用都将具有关闭的 persistenceManager,因为您的服务仍在引用第一个请求中的管理器。
有两种方法可以解决此问题:
1) 更改服务范围。您可以通过在服务类中放置以下内容来完成此操作:
2) 当您调用服务方法时,将 persistenceManager 从控制器传递到服务
The grails app-engine plugin creates the persistenceManager object in the request scope. By default, services are singletons, which means they are created once instead of per request. Thus, if you give your service a persistenceManager instance variable, the first request will have a valid persistenceManager, but all subsequent calls will have a closed persistenceManager, because your service is still referencing the manager from the first request.
There are two ways to fix this:
1) Change the scope of your service. You can do this by placing the following in your service class:
2) pass the persistenceManager from your controller to the service when you call the service method
这与我的控制器的代码非常相似。除了我不使用 transactional = true 之外,为什么你想要这个你只是在读?您使用的是哪个版本的应用程序引擎插件?
这是我的 jdoconfig.xml:
This is very similar to my Controller's code. Except I don't use the transactional = true, why do you want this you're only doing a read? What version of the app-engine plugin are you using?
Here's my jdoconfig.xml: