2011-04-11 151 views
2

我定义在GAE一个简单的类保持用户配置文件数据是这样的:KindError在谷歌应用程序引擎

class User(db.Model): 
    email = db.EmailProperty() 
    role = db.StringProperty(default=roles.USER) 
    first_name = db.StringProperty() 
    last_name = db.StringProperty() 
... 

我使用的memcache保持会话信息。 memcache数据看起来像这样{ 'key': 'agpjYW5kaXJhdGVzcgoLEgRVc2VyGCMM'}。我从cookie获取session_id值。当我试图让链接到饼干这样的用户信息:

session_id = request['session_id'] 
data = memcache.get(session_id) 
user = User.get(data['key']) 

我得到KindError例外:

KindError: Kind 'User' is not a subclass of kind 'User' 

我知道这个用户是否存在,存在内存缓存。用户类只在我的项目中定义过一次。为什么会发生此错误,我该如何使其工作?

更新:我试着用db.get()而不是User.get()它工作。那么,有什么问题呢?

回答

0

App Engine框架将一个名为'User'的类定义为Users API的一部分。另外,你有相同名字的你自己的班级。发生异常时,您正在尝试使用其中一个,但获取另一个。

为了避免这种情况,请重命名您的模型。您还应该小心如何使用Python导入模块。相反的:

from google.appengine.api.users import User 

或者更糟:

from google.appengine.api.users import * 

你应该使用:

from google.appengine.api import users 

,然后参考users.User,这是毫不含糊的。

+0

这些是非常有用的说明。我会根据你的建议更新我的代码。谢谢! – 2011-04-14 09:33:56

1

Model.get()确实检查提供的密钥是否是正确的种类,如documentation中所定义。如果不是正确的类型,它会抛出一个KindError

db.get()不会做任何类型检查,因此如果存在于数据存储中,将会使用提供的值成功,但不一定会返回用户实体。

因此您需要检查您的memcache中的密钥实际上是否为User类型。你确定它在某个时刻不会被其他模型的关键字覆盖吗?

+0

看来这个问题是进口。在不同的模块中我使用了不同的导入语句一个从lib.utils.profiles中使用的导入用户,它运行良好,因为它包含模块的整个路径。另一个从utils.profiles中使用导入用户,它引发了一个异常。 – 2011-04-11 11:51:00

0

这个问题在我看来,比这个更微妙。我得到这个调用Model.get()错误(我检索顶级单对象,总是在那里):

datastore = GDSDatastore.get(gds.Key.from_path(*path)) 

所以我研究了这个代码:

datastore = gds.get(gds.Key.from_path(*path)) 
if not(datastore is None or isinstance(datastore, GDSDatastore)): 
    logger.error("KindError isinstance(GDSDatastore)=%s class=%s" % (isinstance(datastore, GDSDatastore), datastore.__class__.__name__)) 
    raise gds.KindError('Kind %r is not a GDSDatastore instance' % 
        (datastore.kind())) 

绝大多数的时候,我没有错误,但今天我得到了这个有趣的日志:现在

KindError isinstance(GDSDatastore)=False class=GDSDatastore 

,这令我颇为奇特。

(注:GDSDatastore在本地定义:类GDSDatastore(gds.Model))