尝试保存Django用户模型实例时,出现了TransactionManagementError,并且在其post_save信号中,我正在保存一些将用户作为外键的模型。
使用信号时,上下文和错误与此问题djangoTransactionManagementError]非常相似
但是,在这种情况下,错误 仅在单元测试 时发生。
它在手动测试中效果很好,但是单元测试失败。
有什么我想念的吗?
以下是代码片段:
views.py
@csrf_exempt
def mobileRegister(request):
if request.method == 'GET':
response = {"error": "GET request not accepted!!"}
return HttpResponse(json.dumps(response), content_type="application/json",status=500)
elif request.method == 'POST':
postdata = json.loads(request.body)
try:
# Get POST data which is to be used to save the user
username = postdata.get('phone')
password = postdata.get('password')
email = postdata.get('email',"")
first_name = postdata.get('first_name',"")
last_name = postdata.get('last_name',"")
user = User(username=username, email=email,
first_name=first_name, last_name=last_name)
user._company = postdata.get('company',None)
user._country_code = postdata.get('country_code',"+91")
user.is_verified=True
user._gcm_reg_id = postdata.get('reg_id',None)
user._gcm_device_id = postdata.get('device_id',None)
# Set Password for the user
user.set_password(password)
# Save the user
user.save()
信号
def create_user_profile(sender, instance, created, **kwargs):
if created:
company = None
companycontact = None
try: # Try to make userprofile with company and country code provided
user = User.objects.get(id=instance.id)
rand_pass = random.randint(1000, 9999)
company = Company.objects.get_or_create(name=instance._company,user=user)
companycontact = CompanyContact.objects.get_or_create(contact_type="Owner",company=company,contact_number=instance.username)
profile = UserProfile.objects.get_or_create(user=instance,phone=instance.username,verification_code=rand_pass,company=company,country_code=instance._country_code)
gcmDevice = GCMDevice.objects.create(registration_id=instance._gcm_reg_id,device_id=instance._gcm_reg_id,user=instance)
except Exception, e:
pass
tests.py
class AuthTestCase(TestCase):
fixtures = ['nextgencatalogs/fixtures.json']
def setUp(self):
self.user_data={
"phone":"0000000000",
"password":"123",
"first_name":"Gaurav",
"last_name":"Toshniwal"
}
def test_registration_api_get(self):
response = self.client.get("/mobileRegister/")
self.assertEqual(response.status_code,500)
def test_registration_api_post(self):
response = self.client.post(path="/mobileRegister/",
data=json.dumps(self.user_data),
content_type="application/json")
self.assertEqual(response.status_code,201)
self.user_data['username']=self.user_data['phone']
user = User.objects.get(username=self.user_data['username'])
# Check if the company was created
company = Company.objects.get(user__username=self.user_data['phone'])
self.assertIsInstance(company,Company)
# Check if the owner's contact is the same as the user's phone number
company_contact = CompanyContact.objects.get(company=company,contact_type="owner")
self.assertEqual(user.username,company_contact[0].contact_number)
追溯:
======================================================================
ERROR: test_registration_api_post (nextgencatalogs.apps.catalogsapp.tests.AuthTestCase)
----------------------------------------------------------------------
Traceback (most recent call last):
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/nextgencatalogs/apps/catalogsapp/tests.py", line 29, in test_registration_api_post
user = User.objects.get(username=self.user_data['username'])
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/ngcvenv/lib/python2.7/site-packages/django/db/models/manager.py", line 151, in get
return self.get_queryset().get(*args, **kwargs)
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/ngcvenv/lib/python2.7/site-packages/django/db/models/query.py", line 301, in get
num = len(clone)
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/ngcvenv/lib/python2.7/site-packages/django/db/models/query.py", line 77, in __len__
self._fetch_all()
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/ngcvenv/lib/python2.7/site-packages/django/db/models/query.py", line 854, in _fetch_all
self._result_cache = list(self.iterator())
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/ngcvenv/lib/python2.7/site-packages/django/db/models/query.py", line 220, in iterator
for row in compiler.results_iter():
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/ngcvenv/lib/python2.7/site-packages/django/db/models/sql/compiler.py", line 710, in results_iter
for rows in self.execute_sql(MULTI):
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/ngcvenv/lib/python2.7/site-packages/django/db/models/sql/compiler.py", line 781, in execute_sql
cursor.execute(sql, params)
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/ngcvenv/lib/python2.7/site-packages/django/db/backends/util.py", line 47, in execute
self.db.validate_no_broken_transaction()
File "/Users/gauravtoshniwal1989/Developer/Web/Server/ngc/ngcvenv/lib/python2.7/site-packages/django/db/backends/__init__.py", line 365, in validate_no_broken_transaction
"An error occurred in the current transaction. You can't "
TransactionManagementError: An error occurred in the current transaction. You can't execute queries until the end of the 'atomic' block.
----------------------------------------------------------------------
我本人也遇到了同样的问题。这是由于在新版本的Django中如何处理事务的古怪之处,加上故意触发异常的单元测试。
我有一个单元测试,通过有意触发IntegrityError异常来检查以确保实施了唯一的列约束:
def test_constraint(self):
try:
# Duplicates should be prevented.
models.Question.objects.create(domain=self.domain, slug='barks')
self.fail('Duplicate question allowed.')
except IntegrityError:
pass
do_more_model_stuff()
在Django 1.4中,这可以正常工作。但是,在Django 1.5 /
1.6中,每个测试都包装在一个事务中,因此,如果发生异常,它将破坏该事务,直到您明确地将其回滚为止。因此,该事务中任何进一步的ORM操作(例如my
do_more_model_stuff()
)都将因该django.db.transaction.TransactionManagementError
异常而失败。
就像评论中提到的caio一样,解决方案是使用transaction.atomic
如下方式捕获您的异常:
from django.db import transaction
def test_constraint(self):
try:
# Duplicates should be prevented.
with transaction.atomic():
models.Question.objects.create(domain=self.domain, slug='barks')
self.fail('Duplicate question allowed.')
except IntegrityError:
pass
这样可以防止故意抛出的异常破坏整个单元测试的事务。
问题内容: 我在尝试保存Django用户模型实例时收到TransactionManagementError,并在其post_save信号中保存了一些将用户作为外键的模型。 使用信号时,上下文和错误与此问题django TransactionManagementError非常相似 但是,在这种情况下,错误仅在单元测试时发生。 它在手动测试中效果很好,但是单元测试失败。 有什么我想念的吗? 以下是代码
在试图保存Django用户模型实例时,我遇到TransactionManagementError,在它的post_save信号中,我正在保存一些将用户作为外键的模型。 上下文和错误与使用信号时的django TransactionManagementError问题非常相似 然而,在这种情况下,错误仅在单元测试时发生。 它在手动测试中运行良好,但单元测试失败。 有什么我遗漏的吗? 以下是代码片段:
所以,我的问题是,我正在尝试为我的应用程序进行单元测试。我有两个服务,我们叫它们Foo和Bar,Foo只是Bar的代理。 因此,Foo服务的路由器如下所示: 向Bar服务发出请求的处理程序如下所示: 当我这样写测试时: 它永远冻结了......嗯,我想这是因为它周围的一些协程魔法,但是因为我在这方面还是新手,我不明白这里到底发生了什么。有什么帮助吗?
问题内容: 我正在使用Google Reflections库查询类路径中的某些资源。这些资源与我的项目中的类位于相同的位置。 我编写了一些单元测试,这些单元测试在Eclipse中作为单元测试执行时会成功,但是当我尝试使用Maven(例如使用a )执行它们时,它们无法按预期运行。经过一些调试之后,显然的问题在于,当用Maven执行时,Reflections库无法找到资源所在的类路径URL。 我得出了
有史以来最奇怪的事情是:我从一个模块运行一个程序,该模块调用另一个模块的一些函数。问题是,相同的代码在使用基本函数时可以完美运行,但第三个函数只有在unittest类内部使用时才会失败,消息如下: NoSuchElementException:消息:没有这样的元素:无法定位元素:{“方法”:“xpath”,“选择器”:”//*[@id=“app_skeleton”]/tbody/tr[6]/td/
我的角应用程序正常运行时工作正常,但在我进行单元测试时似乎执行了两次(使用Karma 它的实例化如下: 浏览器控制台的输出如下: “在浏览器中运行的应用程序” "配置" “运行” 但是单元测试的输出如下: INFO [karma]: Karma v0.12.31 服务器在 http://localhost:9876/ 启动 [..因果报应/幻觉之类的..] 日志:“在浏览器中运行的应用程序” WA