I am trying to see if I can pass field name as a variable in get_or_create (since I have a function where the key in the kwargs can vary)
Like so:
def convert_value(cell_value, field_to_lookup):
rem_obj, created = Rem.objects.get_or_create(field_to_lookup=cell_value)
print ('created? ',created)
return rem_obj
The above wont work since it would look for 'field_to_lookup' as the key.
This post suggests using getattr but not sure if that'll be applicable in this case since I will again need to assign the output to a variable
This post helped. Now passing the field-value pair as dict which allows passing variables for field names. Here's the code:
def convert_value(cell_value, field_to_lookup):
rem_obj, created = Rem.objects.get_or_create(**{field_to_lookup:cell_value})
print ('created? ',created)
return rem_obj
Alternatively, I could directly just pass the dict to the function.
Related
I'm attempting to create a function to allow updates to fields based on the front-end input.
The handler would receive a profile_updates dictionary with two keys. Each will contain a list of key/value pairs.
list_of_updates['custom_permissions'] = [{"is_staff":"True"},{"other_permission":"False"}]
def update_profile(message):
list_of_updates = message['profile_updates']
user_update_id = message['user_id']
for update in list_of_updates['custom_permissions']:
for key, value in update.iteritems():
User.objects.filter(id=user_update_id).update(key=value)
I would like to make 'key' a variable fed from the .iteritems().
Appreciate anyone's input on how, or if, this is possible.
You don't need to loop through the dict. You can pass it as a kwarg expansion.
def update_profile(message):
list_of_updates = message['profile_updates']
user_update_id = message['user_id']
for update in list_of_updates['custom_permissions']:
User.objects.filter(id=user_update_id).update(**update)
Here is the code:
variable=field_name
send_address_purchase=res_brw.variable (so i need res_brw.field_name)
How could i dynamically access field by variable value?
Don't use eval, use getattr instead:
variable = field_name
send_address_purchase = getattr(res_brw, variable)
I'm trying to use get_or_create for some fields in my forms, but I'm getting a 500 error when I try to do so.
One of the lines looks like this:
customer.source = Source.objects.get_or_create(name="Website")
The error I get for the above code is:
Cannot assign "(<Source: Website>, False)": "Customer.source"
must be a "Source" instance.
From the documentation get_or_create:
# get_or_create() a person with similar first names.
p, created = Person.objects.get_or_create(
first_name='John',
last_name='Lennon',
defaults={'birthday': date(1940, 10, 9)},
)
# get_or_create() didn't have to create an object.
>>> created
False
Explanation:
Fields to be evaluated for similarity, have to be mentioned outside defaults. Rest of the fields have to be included in defaults. In case CREATE event occurs, all the fields are taken into consideration.
It looks like you need to be returning into a tuple, instead of a single variable, do like this:
customer.source,created = Source.objects.get_or_create(name="Website")
get_or_create returns a tuple.
customer.source, created = Source.objects.get_or_create(name="Website")
get_or_create() returns a tuple:
customer.source, created = Source.objects.get_or_create(name="Website")
created → has a boolean value, is created or not.
customer.source → has an object of get_or_create() method.
Following #Tobu answer and #mipadi comment, in a more pythonic way, if not interested in the created flag, I would use:
customer.source, _ = Source.objects.get_or_create(name="Website")
The issue you are encountering is a documented feature of get_or_create.
When using keyword arguments other than "defaults" the return value of get_or_create is an instance. That's why it is showing you the parens in the return value.
you could use customer.source = Source.objects.get_or_create(name="Website")[0] to get the correct value.
Here is a link for the documentation:
http://docs.djangoproject.com/en/dev/ref/models/querysets/#get-or-create-kwargs
get_or_create method would actually return a tuple.
The trick with the get_or_create method is that it actually returns a tuple of (object, created). The first element is an instance of the model you are trying to retrieve and the second is a boolean flag to tell if the instance was created or not. True means the instance was created by the get_or_create method and False means it was retrieved from the database
So you can do something like to get the source instance
``` customer.source = Source.objects.get_or_create(name="Website")[0]
```
Important warning.
you should take care of the following before using the get_or_create , https://docs.djangoproject.com/en/4.0/ref/models/querysets/.
....
Warning
This method is atomic assuming that the database enforces uniqueness of the keyword arguments (see unique or unique_together). If the fields used in the keyword arguments do not have a uniqueness constraint, concurrent calls to this method may result in multiple rows with the same parameters being inserted.
I've looked at documentation, and have searched Google extensively, and haven't found a solution to my problem.
This is my readRSS function (note that 'get' is a method of Kenneth Reitz's requests module):
def readRSS(name, loc):
linkList = []
linkTitles = list(ElementTree.fromstring(get(loc).content).iter('title'))
linkLocs = list(ElementTree.fromstring(get(loc).content).iter('link'))
for title, loc in zip(linkTitles, linkLocs):
linkList.append((title.text, loc.text))
return {name: linkList}
This is one of my MongoAlchemy classes:
class Feed(db.Document):
feedname = db.StringField(max_length=80)
location = db.StringField(max_length=240)
lastupdated = datetime.utcnow()
def __dict__(self):
return readRSS(self.feedname, self.location)
As you can see, I had to call the readRSS function within a function of the class, so I could pass self, because it's dependent on the fields feedname and location.
I want to know if there's a different way of doing this, so I can save the readRSS return value to a field in the Feed document. I've tried assigning the readRSS function's return value to a variable within the function __dict__ -- that didn't work either.
I have the functionality working in my app, but I want to save the results to the Document to lessen the load on the server (the one I am getting my RSS feed from).
Is there a way of doing what I intend to do or am I going about this all wrong?
I found out the answer. I needed to make use of a computed_field decorator, where the first argument was the structure of my return value and deps was a set which contained the fields that this field was dependent on. I then passed the dependent fields into a function's arguments and there you have it.
#fields.computed_field(db.KVField(db.StringField(), db.ListField(db.TupleField(db.StringField()))), deps=[feedname, location])
def getFeedContent(a=[feedname, location]):
return readRSS(a['feedname'], a['location'])
Thanks anyway, everyone.
I'm trying to use get_or_create for some fields in my forms, but I'm getting a 500 error when I try to do so.
One of the lines looks like this:
customer.source = Source.objects.get_or_create(name="Website")
The error I get for the above code is:
Cannot assign "(<Source: Website>, False)": "Customer.source"
must be a "Source" instance.
From the documentation get_or_create:
# get_or_create() a person with similar first names.
p, created = Person.objects.get_or_create(
first_name='John',
last_name='Lennon',
defaults={'birthday': date(1940, 10, 9)},
)
# get_or_create() didn't have to create an object.
>>> created
False
Explanation:
Fields to be evaluated for similarity, have to be mentioned outside defaults. Rest of the fields have to be included in defaults. In case CREATE event occurs, all the fields are taken into consideration.
It looks like you need to be returning into a tuple, instead of a single variable, do like this:
customer.source,created = Source.objects.get_or_create(name="Website")
get_or_create returns a tuple.
customer.source, created = Source.objects.get_or_create(name="Website")
get_or_create() returns a tuple:
customer.source, created = Source.objects.get_or_create(name="Website")
created → has a boolean value, is created or not.
customer.source → has an object of get_or_create() method.
Following #Tobu answer and #mipadi comment, in a more pythonic way, if not interested in the created flag, I would use:
customer.source, _ = Source.objects.get_or_create(name="Website")
The issue you are encountering is a documented feature of get_or_create.
When using keyword arguments other than "defaults" the return value of get_or_create is an instance. That's why it is showing you the parens in the return value.
you could use customer.source = Source.objects.get_or_create(name="Website")[0] to get the correct value.
Here is a link for the documentation:
http://docs.djangoproject.com/en/dev/ref/models/querysets/#get-or-create-kwargs
get_or_create method would actually return a tuple.
The trick with the get_or_create method is that it actually returns a tuple of (object, created). The first element is an instance of the model you are trying to retrieve and the second is a boolean flag to tell if the instance was created or not. True means the instance was created by the get_or_create method and False means it was retrieved from the database
So you can do something like to get the source instance
``` customer.source = Source.objects.get_or_create(name="Website")[0]
```
Important warning.
you should take care of the following before using the get_or_create , https://docs.djangoproject.com/en/4.0/ref/models/querysets/.
....
Warning
This method is atomic assuming that the database enforces uniqueness of the keyword arguments (see unique or unique_together). If the fields used in the keyword arguments do not have a uniqueness constraint, concurrent calls to this method may result in multiple rows with the same parameters being inserted.