231 lines
12 KiB
Python
231 lines
12 KiB
Python
import json
|
||
import os
|
||
import sys
|
||
from datetime import date, timedelta
|
||
from decimal import Decimal
|
||
from io import BytesIO
|
||
from itertools import groupby
|
||
|
||
import requests
|
||
from PIL import ImageFont, ImageDraw, Image
|
||
from sqlalchemy import update
|
||
|
||
from db import MysqlSession
|
||
from db.mysql import ViewErrorReview, ZxPhhd, ZxPhrec, ZxIeResult, ZxIeSettlement, ZxIeDischarge, ZxIeCost
|
||
from ucloud import ufile
|
||
from util import image_util
|
||
|
||
|
||
def main(pk_phhd=None):
|
||
session = MysqlSession()
|
||
error_query = (session.query(ZxPhhd.pk_phhd, ZxPhhd.cXm, ViewErrorReview.pk_yljg, ViewErrorReview.pk_yljg_ocr,
|
||
ViewErrorReview.pk_ylks, ViewErrorReview.pk_ylks_ocr, ViewErrorReview.cdoctor,
|
||
ViewErrorReview.cdoctor_ocr, ViewErrorReview.czyh, ViewErrorReview.czyh_ocr,
|
||
ViewErrorReview.dzyrq, ViewErrorReview.dzyrq_ocr, ViewErrorReview.dcyrq,
|
||
ViewErrorReview.dcyrq_ocr, ViewErrorReview.input_cxm, ViewErrorReview.input_cxm_ocr,
|
||
ViewErrorReview.ffsylfy, ViewErrorReview.ffsylfy_ocr, ViewErrorReview.fgrzfje1,
|
||
ViewErrorReview.fgrzfje1_ocr, ViewErrorReview.fgezfje2, ViewErrorReview.fgezfje2_ocr,
|
||
ViewErrorReview.fgrzfje, ViewErrorReview.fgrzfje_ocr, ViewErrorReview.yb_type,
|
||
ViewErrorReview.yb_type_ocr, ViewErrorReview.cjsd_id, ViewErrorReview.cjsd_id_ocr,
|
||
ViewErrorReview.fage, ViewErrorReview.fage_ocr, ZxPhhd.problem_note)
|
||
.join(ZxPhhd, ViewErrorReview.pk_phhd == ZxPhhd.pk_phhd, isouter=True))
|
||
if pk_phhd:
|
||
error_query = error_query.filter(ZxPhhd.pk_phhd == pk_phhd)
|
||
else:
|
||
today = date.today()
|
||
error_query = (error_query.filter(ZxPhhd.problem_note.is_(None))
|
||
.filter(ViewErrorReview.creationtime >= today)
|
||
.filter(ViewErrorReview.creationtime < today + timedelta(days=1))
|
||
.order_by(ViewErrorReview.creationtime.desc()))
|
||
error_review = error_query.limit(1).one_or_none()
|
||
if error_review is None:
|
||
print("没有需要检查的记录")
|
||
sys.exit()
|
||
|
||
pk_phhd = error_review.pk_phhd
|
||
# 文件路径
|
||
directory = f"./review_error_check/{pk_phhd}"
|
||
if not os.path.exists(directory):
|
||
os.makedirs(directory)
|
||
|
||
json_result = {
|
||
"pk_phhd": pk_phhd,
|
||
"cXm": error_review.cXm
|
||
}
|
||
|
||
settlement_query = session.query(ZxIeSettlement.pk_ie_settlement)
|
||
discharge_query = session.query(ZxIeDischarge.pk_ie_discharge)
|
||
cost_query = session.query(ZxIeCost.pk_ie_cost)
|
||
|
||
if error_review.pk_yljg != error_review.pk_yljg_ocr:
|
||
json_result["医院pk_yljg"] = error_review.pk_yljg
|
||
json_result["pk_yljg_ocr"] = error_review.pk_yljg_ocr
|
||
discharge_query = discharge_query.add_columns(ZxIeDischarge.hospital, ZxIeDischarge.pk_yljg)
|
||
if error_review.pk_ylks != error_review.pk_ylks_ocr:
|
||
json_result["科室pk_ylks"] = error_review.pk_ylks
|
||
json_result["pk_ylks_ocr"] = error_review.pk_ylks_ocr
|
||
discharge_query = discharge_query.add_columns(ZxIeDischarge.department, ZxIeDischarge.pk_ylks)
|
||
if error_review.cdoctor != error_review.cdoctor_ocr:
|
||
json_result["医生cdoctor"] = error_review.cdoctor
|
||
json_result["cdoctor_ocr"] = error_review.cdoctor_ocr
|
||
discharge_query = discharge_query.add_column(ZxIeDischarge.doctor)
|
||
if error_review.czyh != error_review.czyh_ocr:
|
||
json_result["住院号czyh"] = error_review.czyh
|
||
json_result["czyh_ocr"] = error_review.czyh_ocr
|
||
settlement_query = settlement_query.add_column(ZxIeSettlement.admission_id)
|
||
discharge_query = discharge_query.add_column(ZxIeDischarge.admission_id)
|
||
if error_review.dzyrq != error_review.dzyrq_ocr:
|
||
json_result["入院日期dzyrq"] = error_review.dzyrq
|
||
json_result["dzyrq_ocr"] = error_review.dzyrq_ocr
|
||
settlement_query = settlement_query.add_columns(ZxIeSettlement.admission_date_str,
|
||
ZxIeSettlement.admission_date)
|
||
discharge_query = discharge_query.add_columns(ZxIeDischarge.admission_date_str, ZxIeDischarge.admission_date)
|
||
cost_query = cost_query.add_columns(ZxIeCost.admission_date_str, ZxIeCost.admission_date)
|
||
if error_review.dcyrq != error_review.dcyrq_ocr:
|
||
json_result["出院日期dcyrq"] = error_review.dcyrq
|
||
json_result["dcyrq_ocr"] = error_review.dcyrq_ocr
|
||
settlement_query = settlement_query.add_columns(ZxIeSettlement.discharge_date_str,
|
||
ZxIeSettlement.discharge_date)
|
||
discharge_query = discharge_query.add_columns(ZxIeDischarge.discharge_date_str, ZxIeDischarge.discharge_date)
|
||
cost_query = cost_query.add_columns(ZxIeCost.discharge_date_str, ZxIeCost.discharge_date)
|
||
if error_review.input_cxm != error_review.input_cxm_ocr:
|
||
json_result["姓名input_cxm"] = error_review.input_cxm
|
||
json_result["input_cxm_ocr"] = error_review.input_cxm_ocr
|
||
settlement_query = settlement_query.add_column(ZxIeSettlement.name)
|
||
discharge_query = discharge_query.add_column(ZxIeDischarge.name)
|
||
cost_query = cost_query.add_column(ZxIeCost.name)
|
||
if error_review.ffsylfy != error_review.ffsylfy_ocr:
|
||
json_result["费用总额ffsylfy"] = error_review.ffsylfy
|
||
json_result["ffsylfy_ocr"] = error_review.ffsylfy_ocr
|
||
settlement_query = settlement_query.add_columns(ZxIeSettlement.medical_expenses_str,
|
||
ZxIeSettlement.medical_expenses)
|
||
cost_query = cost_query.add_columns(ZxIeCost.medical_expenses_str, ZxIeCost.medical_expenses)
|
||
if error_review.fgrzfje1 != error_review.fgrzfje1_ocr:
|
||
json_result["个人现金支付fgrzfje1"] = error_review.fgrzfje1
|
||
json_result["fgrzfje1_ocr"] = error_review.fgrzfje1_ocr
|
||
settlement_query = settlement_query.add_columns(ZxIeSettlement.personal_cash_payment_str,
|
||
ZxIeSettlement.personal_cash_payment)
|
||
if error_review.fgezfje2 != error_review.fgezfje2_ocr:
|
||
json_result["个人账户支付fgezfje2"] = error_review.fgezfje2
|
||
json_result["fgezfje2_ocr"] = error_review.fgezfje2_ocr
|
||
settlement_query = settlement_query.add_columns(ZxIeSettlement.personal_account_payment_str,
|
||
ZxIeSettlement.personal_account_payment)
|
||
if error_review.fgrzfje != error_review.fgrzfje_ocr:
|
||
json_result["个人自费fgrzfje"] = error_review.fgrzfje
|
||
json_result["fgrzfje_ocr"] = error_review.fgrzfje_ocr
|
||
settlement_query = settlement_query.add_columns(ZxIeSettlement.personal_funded_amount_str,
|
||
ZxIeSettlement.personal_funded_amount)
|
||
if error_review.yb_type != error_review.yb_type_ocr:
|
||
json_result["医保类型yb_type"] = error_review.yb_type
|
||
json_result["yb_type_ocr"] = error_review.yb_type_ocr
|
||
settlement_query = settlement_query.add_columns(ZxIeSettlement.medical_insurance_type_str,
|
||
ZxIeSettlement.medical_insurance_type)
|
||
if error_review.cjsd_id != error_review.cjsd_id_ocr:
|
||
json_result["结算单号cjsd_id"] = error_review.cjsd_id
|
||
json_result["cjsd_id_ocr"] = error_review.cjsd_id_ocr
|
||
settlement_query = settlement_query.add_column(ZxIeSettlement.settlement_id)
|
||
if error_review.fage != error_review.fage_ocr:
|
||
json_result["年龄fage"] = error_review.fage
|
||
json_result["fage_ocr"] = error_review.fage_ocr
|
||
discharge_query = discharge_query.add_column(ZxIeDischarge.age)
|
||
|
||
settlement = settlement_query.filter(ZxIeSettlement.pk_phhd == pk_phhd).one_or_none()
|
||
if settlement is not None:
|
||
json_result["settlement"] = settlement._asdict()
|
||
discharge = discharge_query.filter(ZxIeDischarge.pk_phhd == pk_phhd).one_or_none()
|
||
if discharge is not None:
|
||
json_result["discharge"] = discharge._asdict()
|
||
cost = cost_query.filter(ZxIeCost.pk_phhd == pk_phhd).one_or_none()
|
||
if cost is not None:
|
||
json_result["cost"] = cost._asdict()
|
||
|
||
phrecs = session.query(ZxPhrec.pk_phrec, ZxPhrec.pk_phhd, ZxPhrec.cRectype, ZxPhrec.cfjaddress).filter(
|
||
ZxPhrec.pk_phhd == pk_phhd).all()
|
||
for phrec in phrecs:
|
||
img_name = phrec.cfjaddress
|
||
img_path = ufile.get_private_url(img_name)
|
||
|
||
response = requests.get(img_path)
|
||
image = Image.open(BytesIO(response.content)).convert("RGB")
|
||
font_size = image.width * image.height / 200000
|
||
font = ImageFont.truetype("./font/simfang.ttf", size=font_size)
|
||
|
||
ie_result = session.query(ZxIeResult.id, ZxIeResult.content, ZxIeResult.rotation_angle, ZxIeResult.x_offset,
|
||
ZxIeResult.y_offset).filter(ZxIeResult.pk_phrec == phrec.pk_phrec).all()
|
||
if not ie_result:
|
||
no_ie_directory = f"{directory}/0"
|
||
if not os.path.exists(no_ie_directory):
|
||
os.makedirs(no_ie_directory)
|
||
image.save(f"{no_ie_directory}/{img_name}")
|
||
|
||
for _, group_results in groupby(ie_result, key=lambda x: x.id):
|
||
draw = ImageDraw.Draw(image)
|
||
for ocr_item in group_results:
|
||
result = json.loads(ocr_item.content)
|
||
rotation_angle = ocr_item.rotation_angle
|
||
x_offset = ocr_item.x_offset
|
||
y_offset = ocr_item.y_offset
|
||
for key in result:
|
||
for value in result[key]:
|
||
box = value["bbox"][0]
|
||
|
||
if rotation_angle:
|
||
box = image_util.invert_rotate_rectangle(box, (image.width / 2, image.height / 2),
|
||
rotation_angle)
|
||
if x_offset:
|
||
box[0] += x_offset
|
||
box[2] += x_offset
|
||
if y_offset:
|
||
box[1] += y_offset
|
||
box[3] += y_offset
|
||
|
||
draw.rectangle(box, outline="red", width=2) # 绘制矩形
|
||
draw.text((box[0], box[1] - font_size), key, fill="blue", font=font) # 在矩形上方绘制文本
|
||
draw.text((box[0], box[3]), value["text"], fill="blue", font=font) # 在矩形下方绘制文本
|
||
ie_directory = f"{directory}/{ocr_item.id}"
|
||
os.makedirs(ie_directory, exist_ok=True)
|
||
image.save(f"{ie_directory}/{img_name}")
|
||
session.close()
|
||
|
||
# 自定义JSON处理器
|
||
def default(obj):
|
||
if isinstance(obj, Decimal):
|
||
return float(obj)
|
||
if isinstance(obj, date):
|
||
return obj.strftime("%Y-%m-%d")
|
||
|
||
with open(f"{directory}/result.json", "w", encoding="utf-8") as json_file:
|
||
json.dump(json_result, json_file, indent=4, ensure_ascii=False, default=default)
|
||
|
||
return pk_phhd
|
||
|
||
|
||
if __name__ == '__main__':
|
||
pk_phhd = main()
|
||
while True:
|
||
check_finish = input(f"{pk_phhd}是否完成(是/否):")
|
||
if check_finish == "是":
|
||
"""
|
||
错误描述的写法:
|
||
1. 查看result.json,以含中文的key中的中文为现在的key
|
||
2. 为方便输入,key之后跟中文冒号
|
||
3. 冒号之后写错误原因,原因最好是固定的几种写法
|
||
4. 可以在原因后跟中文括号,并在括号中进行补充说明
|
||
5. 写完错误原因以中文分号结尾,最后一个可以不加分号
|
||
举例:
|
||
错误描述:医院:未知错误;科室:还是未知错误(补充说明)
|
||
"""
|
||
error_descript = input("错误描述:")
|
||
break
|
||
elif check_finish == "否":
|
||
sys.exit()
|
||
else:
|
||
print("无效输入!请输入“是”或者“否”")
|
||
|
||
session = MysqlSession()
|
||
update_error = update(ZxPhhd).where(ZxPhhd.pk_phhd == pk_phhd).values(problem_note=error_descript)
|
||
session.execute(update_error)
|
||
session.commit()
|
||
session.close()
|
||
print(f"【{pk_phhd}】错误分析已完成。错误描述:{error_descript}")
|