App Engine: 如何“重置”数据存储?

29

嗯,我正在使用App Engine(Java)进行开发,在尝试了很多次部署后,我需要重置数据存储。由于添加了很多随机数据以测试性能,而且实体也发生了很多变化,所以我需要删除所有的数据、表和索引。

我应该怎么做?

14个回答

31

很抱歉打扰了这个主题,但是我想给像我这样的新手添加一条提示(在谷歌文档中找到了答案):

如果你想一次性重置本地数据存储区(例如在使用Eclipse进行开发时),请关闭服务器,找到项目中的文件“local_db.bin”(应该在WEB-INF/appengine-generated/目录下),并将其删除。

对于Java来说,效果很好,但尚未尝试Python。

++


Intellij路径:PROJECT_ROOT\out\artifacts\PROJECT_NAME_war_exploded\WEB-INF\appengine-generated\local_db.bin - unify
这是本地开发的正确答案。目前在GCE中,您应该使用Datastore Admin,它允许您删除一个或多个表。 - Dominic Tracey

17

清空开发服务器数据存储

开发网络服务器会使用一个本地的数据存储版本来测试应用程序,使用临时文件。只要这些临时文件存在,数据就会一直保留下来,而且除非你要求它这样做,否则Web服务器不会重置这些文件。

如果你想在启动服务器之前让开发服务器擦除它的数据存储,请在启动服务器时使用--clear_datastore选项:

dev_appserver.py --clear_datastore helloworld/

使用数据存储


非常老的帖子,我知道...但是,在GoogleAppEngineLauncher的“应用程序设置”菜单中,至少在Mac OS X版本1.8.8中,还有一个复选框“启动时清除DataStore”。 - pierroz
2
如果您使用的是Mac电脑,您可能需要使用--clear_datastore=1 - Eric Walker

16

在SQL中,没有内建的DROP TABLE或TRUNCATE TABLE等命令。您需要在应用程序中创建一个“删除所有内容”的页面,然后通过脚本反复调用该页面。在该页面中,您需要尽可能多地删除实体,但在请求超时之前仍能完成。确切的代码取决于您使用JDO/JPA还是低级API。(使用低级API将更快,因为可以使用批处理操作。)

这个之前的SO问题基本相同,只是针对Python。


我正在使用JPA。这会同时删除索引吗? - Damian
2
每次删除内容时,都需要更新索引,否则使用索引的查询将返回错误数据。因此,当您删除实体X时,指向X的所有索引条目也应该被删除。最终,当您删除所有实体时,您将拥有空的索引。 - Peter Recore
5
首先使用 appcfg 删除索引是个好主意,这会加速删除过程并减少 CPU 更新那些你本来就要删除的索引所需的资源消耗。 - Nick Johnson

9

只需执行一个无过滤器的查询以获取所有实体,并逐个删除它们。

import javax.servlet.http.*;

import com.google.appengine.api.datastore.DatastoreService;
import com.google.appengine.api.datastore.DatastoreServiceFactory;
import com.google.appengine.api.datastore.Entity;
import com.google.appengine.api.datastore.PreparedQuery;
import com.google.appengine.api.datastore.Query;

public class MyServlet extends HttpServlet {
        public void doGet(HttpServletRequest req, HttpServletResponse resp)
            throws IOException {

        DatastoreService datastore = 
                    DatastoreServiceFactory.getDatastoreService();

    Query mydeleteq = new Query();
    PreparedQuery pq = datastore.prepare(mydeleteq);
    for (Entity result : pq.asIterable()) {
        datastore.delete(result.getKey());      
    }   
}

当本地嵌入数据存储时,这非常有效,而无需真正启动服务器的开销。 - Dr. Max Völkel
2
将 datastore.delete(result.getKey()); 放在 try/catch(IllegalArgumentException e) {} 中,以避免以 __ 开头和结尾的键名被删除,因为这些键名是保留的,不能被删除。 - M.ES

4

非常抱歉这么晚才回复,但我只是在尝试做同样的事情...

我登录了我的账户(appengine.google.com)并找到了通过管理员工具(datastore/dataviewer)浏览数据存储的选项... 这允许创建/更新/删除。


9
如果你在URL中调整limit=20参数,你就可以增加限制。在我的情况下,将其增加到100让我可以通过几个请求删除一大块数据(并且节省了编写工具/页面的时间)。 - Michael Twomey

2
根据GAE文档,您可以在JDO中删除多个对象,只需使用对象集合调用PersistenceManager的deletePersistentAll(...)方法即可。
PersistenceManager pm = PMF.get().getPersistenceManager();

Query query = pm.newQuery("select from " + Your.class);

List<Your> objs = (List<Your>) query.execute();

pm.deletePersistentAll(objs);

2

现在,删除应用程序的所有数据(或部分数据)已成为管理控制台的一部分。

要启用此功能,请在您的app.yaml文件中启用以下内置项:

builtins:
- datastore_admin: on

将以下内容添加到app.yaml中,即可在您的应用程序管理控制台中启用“数据存储管理”页面。

1
如果你在项目中使用maven,只需执行"mvn clean install"命令即可。当然,这会重置本地的数据存储。

你说得对,这真是个烦恼。每次我想要一个干净的构建时,数据库都会被清空。我只想要新代码,不想每次都重新创建数据! - Teddy

1

虽然这与Java开发无关,但由于这里缺乏文档,以下是如何在Go中完成此操作:

keys, _ := datastore.NewQuery("").KeysOnly().GetAll(c, nil)
datastore.DeleteMulti(c, keys)

1

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接