这是一个简单的问题,但我对django-rest-framework非常新.
我想知道是否有任何方法可以从序列化器访问模型上定义的方法.
说我有一个模特
class Listing(models.Model):
listingid = models.BigIntegerField(primary_key=True)
mappingid = models.BigIntegerField()
projectlevelid = models.IntegerField()
subsellerid = models.IntegerField()
iscreatedbyadmin = models.BooleanField(default=None, null=True)
createdon = models.DateTimeField(auto_now_add=True, editable=False)
validationstatus = models.SmallIntegerField(default=0)
def is_project(self):
""" Returns True if listing is of Project Type (projectlevelid=6) else False"""
if self.projectlevelid == 6:
return True
else:
return False
def get_project_info(self):
"""Returns False if listing is not mapped to a project, else returns the project info"""
if self.is_project() == False:
return False
return models.Project.objects.get(projectid=self.mappingid)
Run Code Online (Sandbox Code Playgroud)
串行器是否可能
class ListingSerializer(serializers.ModelSerializer):
class …Run Code Online (Sandbox Code Playgroud) 我正在尝试在 django-rest-framework 中编写自定义异常处理程序,代码与示例中给出的相同:
from rest_framework.views import exception_handler
def custom_exception_handler(exc, context):
# Call REST framework's default exception handler first,
# to get the standard error response.
response = exception_handler(exc, context)
# Now add the HTTP status code to the response.
if response is not None:
response.data['status_code'] = response.status_code
return response
Run Code Online (Sandbox Code Playgroud)
但是在从视图中引发异常时,这不起作用,而是抛出以下消息:
custom_exception_handler() missing 1 required positional argument: 'context'
我尝试将第一个参数设置为None,如下所示:
def custom_exception_handler(exc, context=None):
但这种情况发生了:
exception_handler() takes 1 positional argument but 2 were given
所以看起来rest_framework.views.exception_handler只需要一个参数。
确实是这样的:
def exception_handler(exc):
""" …Run Code Online (Sandbox Code Playgroud) 一般而言,我对django和python还是陌生的,我试图学习rest_framework来创建RESTful API。
所以我有一个这样的模型:
class Listing(models.Model):
listingid = models.BigIntegerField(primary_key=True)
sellerid = models.IntegerField()
createdon = models.DateTimeField(auto_now_add=True, editable=False)
expirydate = models.DateTimeField(null=True)
validationstatus = models.SmallIntegerField(default=0)
listingstatus = models.SmallIntegerField(
choices=((0, 'Active'),
(1, 'Hidden'),
(2, 'Suspended'),
(4, 'Expired'),
(5, 'Deleted'),
),
default=0)
Run Code Online (Sandbox Code Playgroud)
现在我需要验证该expirydate总是比更大createdon日期。
我知道我可以在视图中执行此操作,我想那不是一个好主意,因为现在验证仅存在于视图中。
这样就剩下了序列化器和模型。
我知道我可以重写save方法来像这样检查它:
class MasterListing(models.Model):
# fields here..
def save(self, *args, **kwargs):
if self.expirydate > self.createdon:
super().save(*args, **kwargs)
return ValidationError("Expiry date cannot be greater than created date ("++")")
Run Code Online (Sandbox Code Playgroud)
但是我不知道这是否是一个好主意,因为现在我提出了一个程序员可能忘记抓住的错误。我也不确定在运行此方法时是否会填充字段。
我在文档中读到的另一种clean方法是我不太了解的方法。
在使用rest_framework时,有人可以指导我如何处理这种情况吗?
到目前为止,我已经阅读了一些有关验证的内容:
我们有一个db.py定义了 peewee 数据库的文件:
db = PostgresqlExtDatabase('mom',
user=DB_CONFIG['username'],
password=DB_CONFIG['password'],
host=DB_CONFIG['host'],
port=DB_CONFIG['port'],
threadlocals=True,
register_hstore=False,
autocommit=True,
autorollback=True,
cursor_factory=DictCursor)
Run Code Online (Sandbox Code Playgroud)
调用db.execute("SOME RAW SQL UPDATE QUERY")按预期工作。但是begin在此之前调用 a并不会阻止数据库被修改。
db.begin()
db.execute("SOME RAW SQL UPDATE QUERY") # <- Does not wait, db is updated immediately here
db.commit()
Run Code Online (Sandbox Code Playgroud)
我这样做对吗?
如果一个事务已经在进行中,我基本上需要将原始 sql 嵌套在一个事务中,否则如果没有begin调用任何事务,则立即执行它。
这工作,如果我做的预期db.set_autocommit(False),然后execute_sql再commit()。
它也适用于atomic()上下文管理器。
给予一定的情况下,我工作的一个Web应用程序,物流,和我们的代码库使用瓶和SQLAlchemy的scoped_session使用autocommit设置为true。它不使用SQLAlchemy的ORM(因为..历史原因),而是只使用Session对象和它的
execute(),begin(),begin_nested(),rollback()和remove()方法。
它的实现方式是Session = …