验证 属性 失败 google 数据存储

Validating property failed google datastore

我有以下基于 ndb.Model 的模型。我正在尝试验证模型,date_of_birth 属性。

from google.appengine.ext import ndb


class CFCSocialUser(ndb.Model):

    def clean_dob(value):
        if value.year < 1900:
            raise Exception("Year cannot be less than 1900")

    username = ndb.StringProperty()
    userid = ndb.IntegerProperty()
    email = ndb.StringProperty()
    date_of_birth = ndb.DateProperty(validator=clean_dob)

    @staticmethod
    def create_new_user(name, email, date_of_birth):
        app = CFCSocialUser(username=name,
                            email=email,
                            date_of_birth=date_of_birth)
        app.put()

以下是我的单元测试,应该测试验证。

from datetime import date

from unittest import TestCase
from google.appengine.ext import ndb
from google.appengine.ext import testbed
from mainsite.rainbow.models.CFCSocialUser import CFCSocialUser


def create_user_before_1900():
    user = CFCSocialUser.create_new_user(name="Vinay Joseph",
                                         email="xxx@xxx.com",
                                         date_of_birth=date(1899, 3, 11))


class TestCFCSocialUser(TestCase):
    def setUp(self):
        self.testbed = testbed.Testbed()
        self.testbed.activate()
        self.testbed.init_datastore_v3_stub()
        ndb.get_context().clear_cache()

    def tearDown(self):
        self.testbed.deactivate()

    def test_validation(self):
        self.assertRaises(Exception, create_user_before_1900())

当我尝试运行我的单元测试

时出现以下错误
======================================================================
ERROR: test_validation (tests.test_CFCSocialUser.TestCFCSocialUser)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/Users/vinay/App-Engine/Rainbow/cfc-social-media-website/tests/test_CFCSocialUser.py", line 26, in test_validation
    self.assertRaises(Exception, create_user_before_1900())
  File "/Users/vinay/App-Engine/Rainbow/cfc-social-media-website/tests/test_CFCSocialUser.py", line 12, in create_user_before_1900
    date_of_birth=date(1899, 3, 11))
  File "/Users/vinay/App-Engine/Rainbow/cfc-social-media-website/mainsite/rainbow/models/CFCSocialUser.py", line 19, in create_new_user
    date_of_birth=date_of_birth)
  File "/Users/vinay/google-cloud-sdk/platform/google_appengine/google/appengine/ext/ndb/model.py", line 2947, in __init__
    self._set_attributes(kwds)
  File "/Users/vinay/google-cloud-sdk/platform/google_appengine/google/appengine/ext/ndb/model.py", line 2993, in _set_attributes
    prop._set_value(self, value)
  File "/Users/vinay/google-cloud-sdk/platform/google_appengine/google/appengine/ext/ndb/model.py", line 1145, in _set_value
    value = self._do_validate(value)
  File "/Users/vinay/google-cloud-sdk/platform/google_appengine/google/appengine/ext/ndb/model.py", line 1094, in _do_validate
    newvalue = self._validator(self, value)
TypeError: clean_dob() takes exactly 1 argument (2 given)

clean_dob() 是一个实例成员函数,应该得到一个 self 作为第一个参数。

喜欢:

class MyModel(ndb.Model):
  def clean_dob(self, value):
    pass

或者您可以将其定义为静态方法:

class MyModel(ndb.Model):
  @staticmethod
  def clean_dob(value):
    pass

或移出class:

def clean_dob(value):
  pass

class MyModel(ndb.Model):
  # ...

A​​pp Engine docs 说验证器函数是用两个参数调用的:propvalue,因此您需要将函数更改为:

def clean_dob(prop, value):
    if value.year < 1900:
        raise Exception("Year cannot be less than 1900")

prop 参数是正在验证的 属性 的实例,而不是模型 class,因此它应该作为独立函数放在 class 主体之外。将它留在 class 中会使代码读者感到困惑,他们可能会认为它是模型的实例方法。