2016-01-07 42 views
5

Django ve py-sqlite3 belgelerinde okudum her şey, dişli erişim ile iyi olmalıdır. (Doğru?) Ancak bu kod pasajı benim için başarısız. Ana iş parçasındaki işlemler çalışır, ancak oluşturduğum iş parçacığı (lar) ında değil. İşte var:Django/sqlite3 "OperationalError: iş parçacığı yok" iş parçacığı üzerinde

File "C:\Python27\lib\site-packages\django-1.9-py2.7.egg\django\db\backends\sq lite3\base.py", line 323, in execute return Database.Cursor.execute(self, query, params)

OperationalError: no such table: thrtest_mymodel

Sorun nedir?

Django'yu ya da onu düzeltmek için gerekli olan şeyleri tam olarak izlemek için neler olduğunu nasıl izlerim? Django’daki başarısızlık noktası oldukça kararsızdır. Gördüğü tabloların nasıl göründüğünü veya ana ve diğer konular arasında nasıl bir farklılık arayacağımı anlayamıyorum.

from django.db import models 

# Super-simple model 
class MyModel(models.Model): 
    message  = models.CharField('Message', max_length=200, blank=True) 

#Test 
from django.test import TestCase 

import time 
import threading 
import random 


done = threading.Event() 
nThreads = 1 


def InsertRec(msg): 
    rec = MyModel.objects.create(message=msg) 
    rec.save() 


def InsertThread(): 
    try: 
     msgNum = 1 
     thrName = threading.currentThread().name 
     print 'Starting %s' % thrName 
     while not done.wait(random.random() * 0.1): 
      msgNum += 1 
      msg = '%s: %d' % (thrName, msgNum) 
      print msg 
      InsertRec(msg) 
    finally: 
     done.set() 
    pass 


class ThreadTestRun(TestCase): 

    def testRunIt(self): 
     nThisThread = 10 
     msgSet = set() 
     for x in xrange(nThisThread): 
      msg = 'Some message %d' % x 
      InsertRec(msg) # From main thread: works! 
      msgSet.add(msg) 
     self.assertEqual(MyModel.objects.count(), nThisThread) 
     # We use sets because .all() doesn't preserve the original order. 
     self.assertEqual(msgSet, set([r.message for r in MyModel.objects.all()])) 
     thrSet = set() 
     for thrNum in xrange(nThreads): 
      t = threading.Thread(name='Thread %d' % thrNum, target=InsertThread) 
      t.start() 
      thrSet.add(t) 

     done.wait(10.) 
     done.set() 
     for t in thrSet: 
      t.join() 

Güncelleme:

DATABASES = { 
    'default': { 
     'ENGINE': 'django.db.backends.sqlite3', 
     'NAME': ':memory:', # os.path.join(BASE_DIR, 'db.sqlite3'), 
     'TEST_NAME' : ':memory:', 
    }, 
} 

Güncelleme: Burada settings.py gelen VERİTABANLARINI olan Django'nın bilet # 12118 ile ilgili olarak, ben olsun ':memory:' kullanarak aynı belirtiler ya da disk dosyası (TEST_NAME).

Django 1.9, Python 2.7.11. (Django 1.6 de aynı semptomlar.)

+0

DATABASES ayarlarınız neye benziyor? –

+0

Bu, 1.8.x ve 1.9.x. https://code.djangoproject.com/ticket/12118 – Krab

cevap

3
değiştirme

senin böyle DATABASES:

DATABASES = { 
    'default': { 
     'ENGINE': 'django.db.backends.sqlite3', 
     'NAME': ':memory:', 
     'TEST' : 
      { 
       'NAME': 'test_db', 
      } 
    }, 
} 

Bu yerine bellekte bunu yaratma, diskte gerçek sqlite db oluşturmak için django zorlayacaktır. Ayrıca, django.test.testcases.TransactionTestCase'dan itibaren iş parçacığıyla ilgili sınama durumlarınızı devraldığınızdan emin olun. Bunu yapmazsanız, iş parçacıkları başka bir iş parçacığından yapılan veritabanı değişikliklerini görmez.

+0

Cevabınız için teşekkürler. Ancak bu, denediğim yapılandırmalardan biridir (yukarıdaki son güncelleme - eski django sürümü, "TEST_NAME" ve "TEST" ifadelerini kullanmaktadır: {'NAME': ...}). Sadece bir şeyleri kontrol eden ve tüm işleri tamamlayan testler, ama ortada aniden çok çalışmakta olan çok iş parçacıklı testim, veritabanının değiştiğini ve tüm tabloların gittiğini bildiriyor. Veritabanı otomatik olarak geri alındı ​​gibi. – JimB

+0

garip:/son bir seçenek olarak '--keepdb' tuşuyla testten sonra veritabanını tutmak için django diyebilirsiniz. – eviltnan

+0

Günümü kurtardınız –