Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/google-app-engine/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Google app engine 云数据存储client.GetAll类型不匹配,但client.Get有效_Google App Engine_Go_Google Cloud Datastore - Fatal编程技术网

Google app engine 云数据存储client.GetAll类型不匹配,但client.Get有效

Google app engine 云数据存储client.GetAll类型不匹配,但client.Get有效,google-app-engine,go,google-cloud-datastore,Google App Engine,Go,Google Cloud Datastore,我正在appengine中编写一个go应用程序,它连接并从数据存储实体返回一些信息。我遇到一个问题,client.Get正在使用预定义的结构,但是client.GetAll正在抛出类型不匹配(反之亦然) 我将以下结构与这两种结构一起使用: type myStruct struct { ID int64 Field1 string Field2 string Release_Date time.Ti

我正在
appengine
中编写一个
go
应用程序,它连接并从
数据存储
实体返回一些信息。我遇到一个问题,
client.Get
正在使用预定义的结构,但是
client.GetAll
正在抛出类型不匹配(反之亦然)

我将以下结构与这两种结构一起使用:

type myStruct struct {
    ID              int64
    Field1          string
    Field2          string
    Release_Date    time.Time
}
Release\u Date
定义为
time.time
(如果
int
,则失败):

Release\u Date
定义为
time.time
(如果
int
)时,此操作失败:

错误:

数据存储:无法将字段“release\u date”加载到“myStruct”中:类型不匹配:int与time.time

(当我交换
发布日期
定义时,反之亦然)

你知道怎么回事吗?这是个bug吗

其他信息:

我查看了实体仪表板,其中列出了数据类型为
data/Time
,当我使用
Get
检索实体时,它会很好地加载到结构中,我可以在代码中使用对象


我不知道为什么这不起作用。

所以这不是一个优雅的解决方案,但对我来说是有效的

我认为原因是我创建的第一个实体有一个类型为
int
的字段
Release\u Date
,但后来我使用类型
Date/Time
添加了实体。在测试过程中,我删除了
int
类型为
Release\u Date
的实体,因此剩下的实体只有
Date/Time
。尽管没有
Release\u Date
类型为
int
的实体,但我的代码在服务器端失败。它一直希望该字段的类型为
int

我的理论是,实体定义是在我第一次创建实体时建立的,并且在以后更改数据类型时没有更新,即使没有实体仍然使用type
int

因此,我最终做的是备份我的实体,删除所有实体,然后在
Release\u Date
字段中重新添加只有
Date/Time
的实体。一旦我这么做了,一切都很顺利。我仍然具有与上面所示相同的大小写(即我的
Struct
使用
字段
,但我的查询使用
字段


这可能是一件容易复制的事情,但我还没来得及去做。如果其他人有时间进行测试,请添加评论,否则我将最终提交一份bug报告。

您确定每个记录都有一个发布日期,即时间。时间?这似乎是最有可能的原因-实际上有一条(或多条)记录带有该字段的int,并且实际上有一些记录带有time.time,因此无论您选择哪一条,当您执行
GetAll
时,它都会失败,因为它会找到至少一条不匹配的记录。我检查了(我现在只测试了三个实体)再仔细检查一下。它们都是相同的数据类型。这里没有足够的信息提供帮助——看起来@dave对实体的描述是正确的,不是所有实体都以相同的方式存储,或者可能有两种不同的实体类型。在
Get
示例中,我们看不到如何创建密钥(
k
),因此我们不知道这是否使用了与
GetAll
示例相同的
“myEntityType”
。尽管如此,从您的错误消息中我们知道,您已经将一些实体的发布日期存储为
int
,一些存储为
time.time
。此外,我还从未见过
NewQuery
Project
Order
以及小写参数,因为它们只适用于导出的类型和字段。我不确定数据存储包是否只是不区分大小写地对待它们(因为这些只是引用您已经存储的东西的字符串参数,这是完全可能的),但在我看来,这是不寻常的,不协调的。我在创建
k
的地方添加了这些参数。我还取消了数据存储中的所有条目,并添加了一个条目(有趣的是,这意味着您必须重建索引)对数据类型进行三重检查。您引用的参数是我的数据存储中的命名字段,因此它们应该匹配大小写,不是吗?
k := db.datastoreKey(id)
myStruct := &myStruct{}
if err := db.client.Get(ctx, k, myStruct ); err != nil {
        return nil, fmt.Errorf("datastore: %v", err)
}

func (db *datastoreDB) datastoreKey(id int64) *datastore.Key {
    return datastore.IDKey("myEntityType", id, nil)
}
var myStructs []*myStruct 
q := datastore.NewQuery("myEntityType").
            Project("field1", "field2", "release_date").
            Order("field1")
keys, err := db.client.GetAll(ctx, q, &myStructs)
if err != nil {
        return nil, fmt.Errorf("datastore: %v", err)
}