После обновления версии django мои тесты не увенчались успехом.
Трассировка ошибки выглядит как
ERROR:mobile.tokenapi.http:: Traceback (most recent call last):
File "/home/y700/projects/otipo-upd/otipo/as_site/apps/mobile/decorators.py", line 12, in wrapped
response = func(*args, **kwargs)
File "/home/y700/projects/otipo-upd/otipo/as_site/apps/assignation/assignmentstats/views.py", line 75, in settings
rate_settings = serializer.save(data, uws)
File "/home/y700/projects/otipo-upd/otipo/as_site/apps/assignation/assignmentstats/serializers.py", line 75, in save
settings = HourRateSettings.objects.get_or_create(user_settings=uws)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/models/manager.py", line 146, in get_or_create
return self.get_query_set().get_or_create(**kwargs)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/models/query.py", line 501, in get_or_create
six.reraise(*exc_info)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/models/query.py", line 491, in get_or_create
obj.save(force_insert=True, using=self.db)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/models/base.py", line 546, in save
force_update=force_update, update_fields=update_fields)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/models/base.py", line 650, in save_base
result = manager._insert([self], fields=fields, return_id=update_pk, using=using, raw=raw)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/models/manager.py", line 215, in _insert
return insert_query(self.model, objs, fields, **kwargs)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/models/query.py", line 1675, in insert_query
return query.get_compiler(using=using).execute_sql(return_id)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/models/sql/compiler.py", line 943, in execute_sql
cursor.execute(sql, params)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/backends/mysql/base.py", line 127, in execute
six.reraise(utils.IntegrityError, utils.IntegrityError(*tuple(e.args)), sys.exc_info()[2])
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/django/db/backends/mysql/base.py", line 120, in execute
return self.cursor.execute(query, args)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/MySQLdb/cursors.py", line 209, in execute
res = self._query(query)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/MySQLdb/cursors.py", line 315, in _query
db.query(q)
File "/home/y700/Env/otipo_upd/local/lib/python2.7/site-packages/MySQLdb/connections.py", line 226, in query
_mysql.connection.query(self, query)
IntegrityError: (1048, "Column 'rate' cannot be null")
По какой-то причине значение поля тарифа не передается в функцию создания нового экземпляра.
функция создания
@token_required
@mobile_response
def settings(request, workspace_id):
uws = get_object_or_404(UserWorkspaceSettings, workspace_id=workspace_id, user=request.user)
serializer = RateSettingsSerializer()
if request.method == 'POST':
data = json.loads(request.POST.get('data'))
form = RateSettingsForm(data=data)
hour_forms = [
HourTypeSettingsForm(data=type_rate, workspace=uws.workspace)
for type_rate in data.get('type_rates', [])]
if form.is_valid() and all([f.is_valid() for f in hour_forms]):
rate_settings = serializer.save(data, uws)
return serializer.item(rate_settings)
else:
errors = [dict(form.errors.items())] + [dict(f.errors.items()) for f in hour_forms]
return {'success': False, 'errors': errors}
if not hasattr(uws, 'hour_rate_settings'):
raise Http404
return serializer.item(uws.hour_rate_settings)
urls.py
url(r'^user-settings/(?P<workspace_id>\d+)/rates/$', 'settings', name='assignmentstats_rate_settings'),
serializers.py
class RateSettingsSerializer(object):
def item(self, settings):
return {
'rate': settings.rate,
'type_rates': [{
'hour_type': hour_type.hour_type.id,
'rate': hour_type.rate,
} for hour_type in settings.type_settings.all()]
}
def save(self, data, uws):
settings = HourRateSettings.objects.get_or_create(user_settings=uws)
if hasattr(uws, 'hour_rate_settings'):
settings = uws.hour_rate_settings
settings.rate = data.get('rate')
settings.save()
for type_rate in data.get('type_rates', []):
hrs = get_object_or_None(
HourTypeSettings, rate_settings=settings, hour_type_id=type_rate.get('hour_type'))
if hrs is None:
hrs = HourTypeSettings(rate_settings=settings, hour_type_id=type_rate.get('hour_type'))
hrs.rate = type_rate.get('rate')
hrs.save()
return settings
Я прочитал Django 1.5Примечания к выпуску, но не вижу проблемы. На django 1.4 этот код работает правильно.
UPD
models.py
class HourRateSettings(models.Model):
user_settings = models.OneToOneField(
'assignation.UserWorkspaceSettings', related_name='hour_rate_settings')
rate = models.PositiveSmallIntegerField()