2012-10-18 33 views
12

आपके समय के लिए धन्यवाद।Django - सहेजने के तरीके को ओवरराइड करते समय पुराने और नए मूल्य के बीच दुविधा की जांच करें

मैं Django 1.4 पर हूं, और मेरे पास निम्न कोड है: यह मेरे Quest मॉडल के लिए अतिव्यापी बचत विधि है।

@commit_on_success 
def save(self, *args, **kwargs): 
    from ib.quest.models.quest_status_update import QuestStatusUpdate 
    created = not self.pk 

    if not created: 
     quest = Quest.objects.get(pk=self) 
     # CHECK FOR SOME OLD VALUE 
    super(Quest, self).save(*args, **kwargs) 

मुझे ऐसा करने का एक स्मार्ट तरीका नहीं मिला। यह ऑब्जेक्ट के लिए एक नई क्वेरी बनाने के लिए मुझे बहुत मूर्खतापूर्ण लगता है कि मैं वर्तमान में पुराने इंस्टेंस मान को खोजने के लिए अद्यतन कर रहा हूं।

क्या ऐसा करने का कोई बेहतर तरीका है?

सभी को धन्यवाद। ताकि आप अपने आप ऐसा कर या किसी अन्य क्वेरी से पहले बचाने के लिए प्रदर्शन करने की जरूरत है

फ्रांसिस्को

+0

अद्यतन और सहेजने का संदर्भ क्या है? अर्थात। मॉडल या मॉडलफॉर्म आदि के माध्यम से सीधे एक दृश्य में? – jondykeman

+0

अच्छा, क्या यह वास्तव में प्रासंगिक है? मैं एक उदाहरण अद्यतन करने, सहेजने की विधि पर हूँ। लेकिन वैसे भी, यह कॉल एक दृश्य से बना है, और वहां मैंने 'quest.save()' – Francisco

+0

कहा है, मुझे यकीन नहीं है कि ऐसा करने का एक साफ तरीका है। आप पुराने ऑब्जेक्ट को 'सेव()' विधि में पास कर सकते हैं या इसे 'सेव()' में पूछ सकते हैं जैसा कि आप कर रहे हैं। – Rohan

उत्तर

9

Django मॉडल उदाहरण के पुराने मूल्यों को कैश नहीं है।

एक आम पैटर्न का उपयोग करने के लिए है एक पूर्व बचाने के संकेत (या इस कोड को सीधे अपने को बचाने() विधि में, के रूप में आपके द्वारा किए गए डाल): आप में से एक कैश रखना चाहते हैं

old_instance = MyModel.objects.get(pk=instance.pk) 
# compare instance with old_instance, and maybe decide whether to continue 

पुराने मूल्यों, तो आप शायद करना होगा कि आपके विचार कोड में:

from copy import deepcopy 
object = MyModel.objects.get(pk=some_value) 
cache = deepcopy(object) 

# Do something with object, and then compare with cache before saving 

रूप में अच्छी तरह a recent discussion इस बारे में Django-डेवलपर्स पर नहीं था, कुछ अन्य संभावित समाधानों के साथ।

+0

समाधान के लिए धन्यवाद। यह काम करता है लेकिन यदि आप 'save_as' का उपयोग करते हैं तो पीके को' कोई नहीं 'पर सेट किया जाता है। इसके लिए कोई कामकाज? –

1

मैं django-reversion सिग्नल का उपयोग करके पुराने मानों में अंतर की जांच कर रहा हूं, लेकिन एक ही तर्क सहेजने वाले सिग्नल पर लागू होगा। मेरे लिए अंतर यह है कि मैं बचाना चाहता हूं कि क्षेत्र बचाया गया था या नहीं।

def __init__(self, *args, **kwargs): 
    super(MyModel, self).__init__(*args, **kwargs) 
    self.old_my_field = self.my_field 

def save(self, *args, **kwargs): 
    print self.old_my_field 
    print self.my_field 

आप शायद deepcopy उपयोग कर सकते हैं या कुछ और बचाने के लिए और हटाने के तरीकों में बाद में उपयोग के लिए पूरी वस्तु को कॉपी करने के लिए एक जैसे:

@receiver(reversion.pre_revision_commit) 
def it_worked(sender, **kwargs): 
    currentVersion = kwargs.pop('versions')[0].field_dict 
    fieldList = currentVersion.keys() 
    fieldList.remove('id') 
    commentDict = {} 
    print fieldList 
    try: 
     pastVersion = reversion.get_for_object(kwargs.pop('instances')[0])[0].field_dict 
    except IndexError: 
     for field in fieldList: 
      commentDict[field] = "Created" 
     comment = commentDict 
    except TypeError: 
     for field in fieldList: 
      commentDict[field] = "Deleted" 
     comment = commentDict 
    else: 
     for field in fieldList: 
      try: 
       pastTest = pastVersion[field] 
      except KeyError: 
       commentDict[field] = "Created" 
      else:  
       if currentVersion[field] != pastTest: 
        commentDict[field] = "Changed" 
       else: 
        commentDict[field] = "Unchanged" 
     comment = commentDict 
    revision = kwargs.pop('revision') 
    revision.comment = comment 
    revision.save() 
    kwargs['revision'] = revision 
    sender.save_revision 
12

आप init विधि के अंदर पुराने मूल्य स्टोर कर सकते हैं।

+0

सुपर सरल और पढ़ने के लिए आसान है। इसके अलावा यह पूरी तरह से काम करता है। उत्कृष्ट समाधान –

 संबंधित मुद्दे

  • कोई संबंधित समस्या नहीं^_^