将Google Gloud数据存储区实体从一个名称空间复制到另一个名称空间

时间:2018-04-14 07:58:51

标签: java google-app-engine google-cloud-platform google-cloud-datastore

我正在使用java将Google Cloud Datastore实体从一个名称空间复制到另一个名称空间:

Key newKey = Key.newBuilder(oldEntity.getKey()).setNamespace(NEW_NAMESPACE).build();
datastore.put(Entity.newBuilder(oldEntity).setKey(newKey).build());

由于实体具有由数据存储生成的数字ID,并且复制实体的ID需要保持不变,我还需要让数据存储区分配这些ID,为此我正在使用DatastoreService.allocateIdRange

但是这给了我一个错误:

  

超出最大分配ID

这是否意味着没有办法实现我想要实现的目标?

编辑1

分配ID的代码:

@POST
public void post(
        @QueryParam("namespace") String namespace,
        @QueryParam("kind") String kind,
        @QueryParam("id") long id,
        @QueryParam("parentKind") String parentKind,
        @QueryParam("parentName") String parentName,
        @QueryParam("parentId") Long parentId
) {
    NamespaceManager.set(namespace);
    DatastoreService ds = DatastoreServiceFactory.getDatastoreService();
    Key parent = null;
    if (parentKind != null) {
        if (parentName != null)
            parent = KeyFactory.createKey(parentKind, parentName);
        else
            parent = KeyFactory.createKey(parentKind, parentId);
    }
    ds.allocateIdRange(new KeyRange(parent, kind, id, id));
}

2 个答案:

答案 0 :(得分:0)

我认为你可以跳过密钥创建。这是我更新名称空间的代码:

GoogleCloudDatastore gds = new GoogleCloudDatastore();
Datastore ds = gds.getCredentials();

final KeyFactory keyFactory = ds.newKeyFactory().setKind(entityKind).setNamespace(NAME_SPACE);
Key newKey = ds.allocateId(oldEntity.getKey);
Entity newEntity= Entity.newBuilder(newKey).set("someParameterName", someParameterValue).build();

希望这有帮助。

答案 1 :(得分:0)

以下是Google问题跟踪器上提供的answer

  

allocateIdRange仅适用于Sequential连续ID,而不适用于Sequential ID范围之上的Scattered ID。

     

正如'Best Practices'文档中所述,如果需要,建议向Datastore发送'allocateIds'请求以查找并分配连续的range of unique IDs并使用这些请求来保存实体,而不是首先将实体保存到数据存储区,这些实体是自动分配的Scattered IDs,不能使用allocateIdRange进行分配。