feat: 导入阈值数据库
This commit is contained in:
parent
0cacd9448c
commit
213684ca40
|
|
@ -0,0 +1,33 @@
|
||||||
|
# Generated by Django 3.0.4 on 2023-12-07 13:00
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
import django.db.models.deletion
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('cms', '0011_alter_source_name'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.RemoveField(
|
||||||
|
model_name='threshold',
|
||||||
|
name='is_perception',
|
||||||
|
),
|
||||||
|
migrations.RemoveField(
|
||||||
|
model_name='threshold',
|
||||||
|
name='is_recognition',
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='threshold',
|
||||||
|
name='source',
|
||||||
|
field=models.ForeignKey(default=1, on_delete=django.db.models.deletion.CASCADE, to='cms.Source', verbose_name='来源'),
|
||||||
|
preserve_default=False,
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='threshold',
|
||||||
|
name='threshold_type',
|
||||||
|
field=models.CharField(blank=True, max_length=50, null=True, verbose_name='阈值类型'),
|
||||||
|
),
|
||||||
|
]
|
||||||
|
|
@ -0,0 +1,18 @@
|
||||||
|
# Generated by Django 3.0.4 on 2023-12-07 13:37
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('cms', '0012_auto_20231207_2100'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AlterField(
|
||||||
|
model_name='threshold',
|
||||||
|
name='chinese_name',
|
||||||
|
field=models.CharField(max_length=50, verbose_name='中文名'),
|
||||||
|
),
|
||||||
|
]
|
||||||
|
|
@ -0,0 +1,23 @@
|
||||||
|
# Generated by Django 3.0.4 on 2023-12-07 13:46
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('cms', '0013_auto_20231207_2137'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='threshold',
|
||||||
|
name='toxicity',
|
||||||
|
field=models.FloatField(blank=True, null=True, verbose_name='毒性'),
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='threshold',
|
||||||
|
name='toxicity_type',
|
||||||
|
field=models.CharField(blank=True, max_length=50, null=True, verbose_name='毒性类型'),
|
||||||
|
),
|
||||||
|
]
|
||||||
|
|
@ -48,14 +48,16 @@ class Source(CommonModel):
|
||||||
|
|
||||||
|
|
||||||
class Threshold(CommonModel):
|
class Threshold(CommonModel):
|
||||||
is_perception = models.BooleanField('是否感知阈值', null=True, blank=True)
|
source = models.ForeignKey(Source, verbose_name='来源', on_delete=models.CASCADE)
|
||||||
is_recognition = models.BooleanField('是否识别阈值', null=True, blank=True)
|
|
||||||
compound_cate = models.CharField('化合物分类', max_length=10)
|
compound_cate = models.CharField('化合物分类', max_length=10)
|
||||||
odor_type = models.CharField('气味类型', null=True, blank=True, max_length=50)
|
odor_type = models.CharField('气味类型', null=True, blank=True, max_length=50)
|
||||||
chinese_name = models.CharField('中文名', max_length=20)
|
threshold_type = models.CharField('阈值类型', null=True, blank=True, max_length=50)
|
||||||
|
toxicity_type = models.CharField('毒性类型', null=True, blank=True, max_length=50)
|
||||||
|
chinese_name = models.CharField('中文名', max_length=50)
|
||||||
ppm = models.FloatField('ppm值')
|
ppm = models.FloatField('ppm值')
|
||||||
ppm_sign = models.CharField('ppm符号标记', max_length=10, default='=')
|
ppm_sign = models.CharField('ppm符号标记', max_length=10, default='=')
|
||||||
mass = models.FloatField('质量浓度')
|
mass = models.FloatField('质量浓度')
|
||||||
|
toxicity = models.FloatField('毒性', null=True, blank=True)
|
||||||
mass_sign = models.CharField('质量浓度符号标记', max_length=10, default='=')
|
mass_sign = models.CharField('质量浓度符号标记', max_length=10, default='=')
|
||||||
molecular = models.FloatField('分子质量')
|
molecular = models.FloatField('分子质量')
|
||||||
cas = models.CharField('cas号', max_length=20)
|
cas = models.CharField('cas号', max_length=20)
|
||||||
|
|
|
||||||
|
|
@ -39,6 +39,7 @@ class SourceSerializer(serializers.ModelSerializer):
|
||||||
|
|
||||||
|
|
||||||
class ThresholdSerializer(serializers.ModelSerializer):
|
class ThresholdSerializer(serializers.ModelSerializer):
|
||||||
|
source_ = SourceSerializer(source='source', read_only=True)
|
||||||
class Meta:
|
class Meta:
|
||||||
model = Threshold
|
model = Threshold
|
||||||
fields = '__all__'
|
fields = '__all__'
|
||||||
|
|
|
||||||
|
|
@ -7,7 +7,7 @@ from rest_framework.response import Response
|
||||||
from rest_framework.viewsets import ModelViewSet
|
from rest_framework.viewsets import ModelViewSet
|
||||||
from rest_framework.exceptions import ParseError
|
from rest_framework.exceptions import ParseError
|
||||||
from django.conf import settings
|
from django.conf import settings
|
||||||
from openpyxl import load_workbook
|
from openpyxl import load_workbook, Workbook
|
||||||
from django.db import transaction
|
from django.db import transaction
|
||||||
# Create your views here.
|
# Create your views here.
|
||||||
|
|
||||||
|
|
@ -74,8 +74,8 @@ class MaterialViewSet(ModelViewSet):
|
||||||
|
|
||||||
class SourceViewSet(ModelViewSet):
|
class SourceViewSet(ModelViewSet):
|
||||||
perms_map = [
|
perms_map = [
|
||||||
{'get': '*'}, {'post': 'threshold'},
|
{'get': '*'}, {'post': 'threshold_update'},
|
||||||
{'put': 'threshold'}, {'delete': 'threshold'}]
|
{'put': 'threshold_update'}, {'delete': 'threshold_update'}]
|
||||||
queryset = Source.objects.filter(is_delete=0)
|
queryset = Source.objects.filter(is_delete=0)
|
||||||
serializer_class = SourceSerializer
|
serializer_class = SourceSerializer
|
||||||
search_fields = ['name','author']
|
search_fields = ['name','author']
|
||||||
|
|
@ -84,14 +84,15 @@ class SourceViewSet(ModelViewSet):
|
||||||
|
|
||||||
class ThresholdViewSet(ModelViewSet):
|
class ThresholdViewSet(ModelViewSet):
|
||||||
perms_map = [
|
perms_map = [
|
||||||
{'get': '*'}, {'post': 'threshold'},
|
{'get': '*'}, {'post': 'threshold_update'},
|
||||||
{'put': 'threshold'}, {'delete': 'threshold'}]
|
{'put': 'threshold_update'}, {'delete': 'threshold_update'}]
|
||||||
queryset = Threshold.objects.filter(is_delete=0)
|
queryset = Threshold.objects.filter(is_delete=0)
|
||||||
serializer_class = ThresholdSerializer
|
serializer_class = ThresholdSerializer
|
||||||
search_fields = ['chinese_name','cas', 'compound_cate', 'odor_type']
|
search_fields = ['chinese_name','cas', 'compound_cate', 'odor_type']
|
||||||
filterset_fields = ['is_perception', 'is_recognition']
|
filterset_fields = ['source']
|
||||||
|
|
||||||
@action(methods=['post'], detail=False, perms_map=[{'post':'threshold'}], serializer_class=PathSerializer)
|
@action(methods=['post'], detail=False, perms_map=[{'post':'threshold'}], serializer_class=PathSerializer)
|
||||||
|
@transaction.atomic
|
||||||
def daoru(self, request, *args, **kwargs):
|
def daoru(self, request, *args, **kwargs):
|
||||||
'''导入excel
|
'''导入excel
|
||||||
|
|
||||||
|
|
@ -104,12 +105,12 @@ class ThresholdViewSet(ModelViewSet):
|
||||||
self.handle_xlsx(vdata['path'])
|
self.handle_xlsx(vdata['path'])
|
||||||
return Response()
|
return Response()
|
||||||
|
|
||||||
@transaction.atomic
|
|
||||||
def handle_xlsx(self, path):
|
def handle_xlsx(self, path):
|
||||||
full_path = settings.BASE_DIR + path
|
full_path = settings.BASE_DIR + path
|
||||||
if not path.endswith('.xlsx'):
|
if not path.endswith('.xlsx'):
|
||||||
raise ParseError('请提供xlsx格式文件')
|
raise ParseError('请提供xlsx格式文件')
|
||||||
wb = load_workbook(full_path, data_only=True)
|
wb = load_workbook(full_path, data_only=True)
|
||||||
|
# 先导入来源
|
||||||
source_sheet = wb.get_sheet_by_name('来源表')
|
source_sheet = wb.get_sheet_by_name('来源表')
|
||||||
i = 3
|
i = 3
|
||||||
sources_dict = {}
|
sources_dict = {}
|
||||||
|
|
@ -121,7 +122,65 @@ class ThresholdViewSet(ModelViewSet):
|
||||||
item['publish_year'] = int(source_sheet[f'e{i}'].value)
|
item['publish_year'] = int(source_sheet[f'e{i}'].value)
|
||||||
except BaseException:
|
except BaseException:
|
||||||
pass
|
pass
|
||||||
source, is_created = Source.objects.update_or_create(defaults=item, name=item['name'])
|
source, is_created = Source.objects.get_or_create(defaults=item, name=item['name'])
|
||||||
sources_dict[str(source_sheet[f'a{i}'].value)] = source
|
sources_dict[str(source_sheet[f'a{i}'].value)] = source
|
||||||
i = i + 1
|
i = i + 1
|
||||||
print(sources_dict)
|
# self.handle_other_sheet(wb, '醇类', sources_dict)
|
||||||
|
# self.handle_other_sheet(wb, '醛类', sources_dict)
|
||||||
|
# self.handle_other_sheet(wb, '酸类', sources_dict)
|
||||||
|
# self.handle_other_sheet(wb, '酯类', sources_dict)
|
||||||
|
# self.handle_other_sheet(wb, '酮类', sources_dict)
|
||||||
|
# self.handle_other_sheet(wb, '醚类', sources_dict)
|
||||||
|
# self.handle_other_sheet(wb, '酚类', sources_dict)
|
||||||
|
# self.handle_other_sheet(wb, '苯系物', sources_dict)
|
||||||
|
# self.handle_other_sheet(wb, '卤代烃', sources_dict)
|
||||||
|
self.handle_other_sheet(wb, '烷烃类', sources_dict)
|
||||||
|
self.handle_other_sheet(wb, '烯烃类', sources_dict)
|
||||||
|
self.handle_other_sheet(wb, '硫化物', sources_dict)
|
||||||
|
self.handle_other_sheet(wb, '胺类', sources_dict)
|
||||||
|
self.handle_other_sheet(wb, '其他', sources_dict)
|
||||||
|
|
||||||
|
def handle_other_sheet(self, wb: Workbook, name, sources_dict):
|
||||||
|
sheet = wb.get_sheet_by_name(name)
|
||||||
|
i = 2
|
||||||
|
early_name = ''
|
||||||
|
early_cas = ''
|
||||||
|
while sheet[f'b{i}'].value:
|
||||||
|
item = {}
|
||||||
|
chinese_name = sheet[f'a{i}'].value
|
||||||
|
if chinese_name:
|
||||||
|
early_name = chinese_name
|
||||||
|
else:
|
||||||
|
chinese_name = early_name
|
||||||
|
item['chinese_name'] = chinese_name
|
||||||
|
ppm = sheet[f'b{i}'].value
|
||||||
|
if isinstance(ppm, str):
|
||||||
|
if '<' in ppm or '<' in ppm:
|
||||||
|
item['ppm_sign'] = '<'
|
||||||
|
elif '>' in ppm or '>'in ppm:
|
||||||
|
item['ppm_sign'] = '>'
|
||||||
|
ppm = float(ppm.replace('>', '').replace('<', '').replace('>', '').replace('<', ''))
|
||||||
|
item['ppm'] = ppm
|
||||||
|
mass = sheet[f'c{i}'].value
|
||||||
|
if isinstance(mass, str):
|
||||||
|
if '<' in mass or '<' in mass:
|
||||||
|
item['mass_sign'] = '<'
|
||||||
|
elif '>' in mass or '>'in mass:
|
||||||
|
item['mass_sign'] = '>'
|
||||||
|
mass = float(mass.replace('>', '').replace('<', '').replace('>', '').replace('<', ''))
|
||||||
|
item['mass'] = mass
|
||||||
|
item['molecular'] = sheet[f'd{i}'].value
|
||||||
|
cas = sheet[f'e{i}'].value
|
||||||
|
if cas:
|
||||||
|
early_cas = cas
|
||||||
|
else:
|
||||||
|
cas = early_cas
|
||||||
|
item['cas'] = cas
|
||||||
|
item['odor_type'] = sheet[f'f{i}'].value
|
||||||
|
item['threshold_type'] = sheet[f'g{i}'].value
|
||||||
|
item['source'] = sources_dict[str(sheet[f'h{i}'].value)]
|
||||||
|
item['compound_cate'] = name
|
||||||
|
Threshold.objects.get_or_create(defaults=item,
|
||||||
|
chinese_name=chinese_name,
|
||||||
|
ppm=ppm, mass=mass)
|
||||||
|
i = i + 1
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,18 @@
|
||||||
|
# Generated by Django 3.0.4 on 2023-12-07 13:00
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('rbac', '0007_alter_userprofile_first_name'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AlterField(
|
||||||
|
model_name='userprofile',
|
||||||
|
name='first_name',
|
||||||
|
field=models.CharField(blank=True, max_length=30, verbose_name='first name'),
|
||||||
|
),
|
||||||
|
]
|
||||||
Loading…
Reference in New Issue