2009-06-02 6 views

Odpowiedz

25
class Foo(models.Model): 
    a = models.CharField(max_length=42) 

class Bar(models.Model): 
    b = models.CharField(max_length=42) 
    a = models.ForeignKey(Foo, default=lambda: Foo.objects.get(id=1)) 
+0

Czy jesteś tym samym człowiekiem z tego artykułu? Jeśli nie, rozważ dodanie linku. http://djangodays.com/2009/05/11/django-foreign-key-default-value-example/ – Paolo

+0

Używanie nazw symboli w modelach dla wartości domyślnych jest dość powszechnym zastosowaniem. Nie pamiętam witryny, ale zmieniono fragment kodu na krótszy wzór. –

+0

To powinna być zaakceptowana odpowiedź. – dhilipsiva

1

Jak dla mnie, dla Django 1.7 swojej pracy tylko pk:

category = models.ForeignKey(Category, editable=False, default=1)

jednak pamiętać, że migracja wygląda

migrations.AlterField(
      model_name='item', 
      name='category', 
      field=models.ForeignKey(default=1, editable=False, to='item.Category'), 
      preserve_default=True, 
     ), 

tak, nie sądzę to ma działać z dynamicznym użytkownikiem pk.

-2
class table1(models.Model): 
    id = models.AutoField(primary_key=True) 
    agentname = models.CharField(max_length=20) 

class table1(models.Model): 
    id = models.AutoField(primary_key=True) 
    lastname = models.CharField(max_length=20) 
    table1 = models.ForeignKey(Property) 
+0

Proszę podać wyjaśnienie do kodu, dlaczego ta odpowiedź na pytanie? – MeanGreen

0
def get_user_default_id(): 
    return 1 

created_by = models.ForeignKey(User, default=get_user_default_id) 
+0

również dodaj opis. –

7

Oto rozwiązanie, które będzie działać w Django 1.7. Zamiast dostarczać domyślną w definicji pola, ustawić ją jako null stanie, ale overide funkcję „Zapisz”, aby wypełnić go po raz pierwszy (gdy jest to null):

class Foo(models.Model): 
    a = models.CharField(max_length=42) 

class Bar(models.Model): 
    b = models.CharField(max_length=42) 
    a = models.ForeignKey(Foo, null=True) 

    def save(self, *args, **kwargs): 
     if self.a is None: # Set default reference 
      self.a = Foo.objects.get(id=1) 
     super(Bar, self).save(*args, **kwargs) 
+0

Czy naprawdę chcesz, aby pole było zerowe? Myślę, że obiekt nie jest jeszcze zapisany, tj. nie ma jeszcze id, nie jest "wyczyszczony", chyba że umieścisz "full_clean" przed super (.. save .. Więc zmienię warunek na if self.id jest None: i powinno działać bez null = True –

+0

@MilanoSlesarik możesz mieć rację, dlatego, że umieściłem go tam na pierwszym miejscu, jest to, że było to nowe pole, które dodałem do istniejącego modelu (z istniejącymi rekordowymi wierszami), więc musiałem pozwolić, aby było null: –

+0

@o_c Nie jest dobrym pomysłem, ponieważ zapisywanie (..) nie jest wywoływane z aktualizacji wsadowej QuerySets .., chyba że jawnie zapętlisz się po każdym zwróconym elemencie i zapisz wywołanie, które następnie pokonuje cel zastosowania aktualizacji wsadowej w pierwszej kolejności (i deweloperzy mają tendencję do zapominania.) – strangetimes

2

Robiłem to podobnie do @o_c, ale wolałbym używać get_or_create niż zwykłego pk.

class UserSettings(models.Model): 
    name = models.CharField(max_length=64, unique=True) 
    # ... some other fields 

    @staticmethod 
    def get_default_user_settings(): 
     user_settings, created = UserSettings.objects.get_or_create(
      name = 'Default settings' 
     ) 
     return user_settings 

class SiteUser(...): 
    # ... some other fields 

    user_settings = models.ForeignKey(
     to=UserSettings, 
     on_delete=models.SET_NULL, 
     null=True 
    ) 

    def save(self, *args, **kwargs): 
     if self.user_settings is None: 
      self.user_settings = UserSettings.get_default_params() 
     super(SiteUser, self).save(*args, **kwargs) 
+0

Ta odpowiedź powinna być wyższa, bo jest prosta i sprytna. –

1

Jest to niewielka modyfikacja odpowiedzi z o_c. Powinno to zaoszczędzić ci jedno trafienie w bazie danych. Uwaga w metodzie składowania Używam self.a_id = 1 zamiast self.a = Foo.objects.get (id = 1). Ma taki sam efekt bez konieczności wysyłania zapytań do Foo.

class Foo(models.Model): 
    a = models.CharField(max_length=42) 

class Bar(models.Model): 
    b = models.CharField(max_length=42) 
    a = models.ForeignKey(Foo, null=True) 

    def save(self, *args, **kwargs): 
     if self.a is None: # Set default reference 
      self.a_id = 1 
     super(Bar, self).save(*args, **kwargs) 
5

Dla Django 1.7 lub nowszego,

Wystarczy utworzyć obiekt ForeignKey i zapisz go. "domyślna" wartość może być identyfikatorem obiektu, który powinien być domyślnie połączony.

Na przykład

created_by = models.ForeignKey(User, default=1) 
Powiązane problemy