我在Django中有以下管理命令,它使用来自外部源的数据更新记录:
class Command(BaseCommand):
def handle(self, *args, **options):
field_mappings = {
'first_name': 'Voornaam',
'initials': 'Voorletters',
'last_name_prefix': 'Voorvoegsel',
'last_name': 'Achternaam',
'sex': 'Geslacht',
'DOB': ['Geboortedatum', 'convert_DOB'],
'street': 'Straat',
'house_number': 'Huisnummer',
'zipcode': 'Postcode',
'city': 'Woonplaats',
'country': 'Land',
'phone_number': 'Telefoonnummer',
'phone_number_mobile': 'MobielTelefoonnummer',
'email_address': 'Emailadres',
'insurer_name': 'NaamVerzekeraar',
'insurance_policy_number': 'PolisnummerVerzekering',
'gp_name': 'NaamHuisarts',
}
patients = Patient.objects.all()
for patient in patients:
result = Query(patient.pharmacy, 'patient_by_bsn', {'BSN': patient.BSN}).run()
for x, y in field_mappings.items():
if type(y) == list:
pass
else:
setattr(patient, x, result[y]['0'])
patient.save()
print('Patient {}-{} updated'.format(patient.pharmacy.vv_id, patient.vv_id))
@staticmethod
def convert_DOB(value):
return timezone.datetime.utcfromtimestamp(value).date()
大多数字段都可以在不先转换数据的情况下保存,但是某些字段(如DOB)需要转换(在本例中是从UNIX时间戳转换为Python datetime.date
)。它当前在pass
下面显示if type(y) == list
的位置我希望首先通过列出的函数运行值,以便保存convert_DOB(value)
而不是原始值 - 我该怎么做?
答案 0 :(得分:1)
首先在映射中不要使用转换函数的名称,而是使用函数本身,即:
def convert_DOB(dob):
# your code here
# ...
field_mappings = {
# ...
'DOB': ['Geboortedatum', convert_DOB],
# ...
}
然后你只需要将值传递给函数并检索结果:
for attrname, sourcekey in field_mappings.items():
if isinstance(sourcekey, list):
# unpack the list (assumes length 2)
sourcekey, converter = key
value = result[sourcekey]['0']
# convert the value
value = converter(value)
else:
# no conversion needed
value = result[sourcekey]['0']
# done
setattr(patient, attrname, value)
请注意,从纯语义POV开始,您应该使用元组而不是列表 - 列表应该是位置不重要的同质集合,元组是异质集合,其中poistion很重要。在你的情况下,位置确实很重要,因为第一项是结果dict的关键,第二项是转换函数的关键。
此外,您使用field_mappings
的方式建议您可以用(attrname,key_or_key_converter)元组列表替换它,因为您只迭代dict的(键,值)对。