2012-07-25 31 views
7

nesnesinde nesne değişiminin devre dışı bırakılması bir web uygulaması olmayan projede SQLAlchemy kullanıyorum. Farklı nesnelerin sayısını veritabanından yükleyen ve bunları yerel olarak değiştiren bir sunucu uygulamasıdır, ancak bu güncelleştirmeleri her yayımlandığında veritabanına kaydetmek istemez. Daha önce bazı web projeleri için Django ORM ile çalışıyordum ve elde etmeye çalıştığım şeylere daha uygun buldum. Django ORM'de istediğim her şeyi kaydetmeden kaydetmek istemediğim her bir nesneyi .save() yapabilirim. SQLAlchemy'de bunun neden böyle çalıştığını anlıyorum, ama bunu Django'ya benzer şekilde nasıl yapabilirim?SQLAlchemy


Güncelleme: , daha kolay elde etmek çalışıyorum anlamak yapmak için ben size bir örnek vereceğiz.

Bu aslında işler:

a = MyModel.query.get(1) 
b = MyModel.query.get(1) 

a.somefield = 1 
b.somefield = 2 

a.save() 
# I didn't want to save b, changes of b weren't committed 

Aslında kaydedilir ne fazla kontrol elde etmek istiyorum:

a = MyModel.query.get(1) 
b = MyModel.query.get(1) 

a.somefield = 1 
b.somefield = 2 

# this will save both of changed models 
session.commit() 

Bu ben çalışmak istiyorum nasıl. Her bir nesnenin değişikliklerini her 5 dakikada bir kaydetmek istiyorum.

+0

Kendi çözümünüzü buldunuz mu? Eğer varsa lütfen paylaşın. –

cevap

2

Gibi bir şey kullanıyorum:

class BaseModel(object): 
    def save(self, commit=True): 
     # this part can be optimized. 
     try: 
      db.session.add(self) 
     except FlushError: 
      # In case of an update operation. 
      pass 

     if commit: 
      db.session.commit() 

    def delete(self, commit=True): 
     db.session.delete(self) 

     if commit: 
      db.session.commit() 

ve sonra ben olarak benim modellerini tanımlayın:

class User(db.Model, BaseModel) 

Yani, şimdi ben yapabilirsiniz:

u = User(username='foo', password='bar') 
u.save() 

Bu başarmak planladıklarını nedir?

2

Durumunuzu anladığımdan emin değilim. Bu noktada Django yılında

,

foo = MyModel(field1='value1', field2='value2') 
foo.save() 

veya sqlalchemy olarak alternatif

foo = MyModel.objects.create(field1='value1', field2='value2') 

,

foo = MyModel(field1='value1', field2='value2') 
session.add(foo) 

yalnızca oturuma nesne ekledik ve Özellik henüz İşlemi gerçekleştirdi. Sen

session.commit() 

istendi neyse değişiklikler yapılması bu link o bakmak ancak sonra işlemek gerekir. Bence Django ORM'den SqlAlchemy'a geçişi kolaylaştıracak. Böyle bir durum için

GÜNCELLEME

, birden oturumları kullanabilirsiniz.

engine = create_engine("postgresql+psycopg2://user:[email protected]/test") 
metadata = MetaData(bind=engine) 
Session = sessionmaker(bind=engine) 
session1 = Session() 
session2 = Session() 
Base = declarative_base() 
class User(Base): 
    __tablename__ = 'users' 
    id = Column(Integer, primary_key=True) 
    name = Column(String) 
    age = Column(Integer) 
    def __init__(self, name, age): 
     self.name = name 
     self.age = age 
    def __repr__(self): 
     return "<User('%s','%s')>" % (self.name, self.age) 
Base.metadata.create_all(engine) 

'Test' db'de bir 'kullanıcı' tablosu oluşturuldu. Ayrıca, 2 oturum nesnesi, 1. oturum ve 2. oturum başlatıldı.

a = User('foo','10') 
b = User('bar', '20') 
session1.add(a) 
session1.add(b) 
session1.commit() 

tablo kullanıcıları artık 2 kayıtları 'foo' rekor session1 ve oturum2 kullanarak 'bar' sing getiriliyor

1: foo, 10 
2: bar, 20 

sahip olacaktır.

foo.age = 11 
bar.age = 21 

Şimdi 2 kayıtlarına

foo = session1.query(User).filter(User.name == "foo").first() 
bar = session2.query(User).filter(User.name == "bar").first() 

yapma değişirse foo değişiklikleri tek başına, üzerinde taşımak istiyorsanız

session1.commit() 

ve bar için

,

session2.commit() 
+0

Neyi başarmaya çalıştığımı açıklığa kavuşturmak için sorumu düzenledim. – kjagiello

+0

Uygulamamda saklayacağım her nesne için bir oturuma ihtiyacım olacak ve benim durumumda oldukça büyük bir yük olacak gibi görünüyor. – kjagiello

0

Eski bir yayını karıştırmaya değil, ama

Diyorsun ki:

Ben her değişiklikleri kaydetmek istiyor

her 5 dakika kadar itiraz ediyorum. Yani

neden Celery gibi bir zamanlayıcı kullanmaz (I pyramid_celery kullanın)

Bununla her 5 dakikada nesne kaydedebilir, Sen bir dekoratör ekleyebilirsiniz yani.

@periodic_task(run_every=crontab(minute="*/5") 
def somefunction(): 
    #your code here 

Bu Özellikle, güncel olduğundan emin olmak için veritabanınızı güncellemeniz gerektiğinde harika çalışıyor (sisteminizi kullanan birçok kullanıcı olması durumunda)

Birinin size yardımcı olmasını umuyorum ile her 5 dakikada bir parçası tasarrufu.