feat: OTC 모달에 제품 썸네일 이미지 표시

- product_images.db에서 thumbnail_base64 조회
- drug_code로 이미지 매칭
- 이미지 없으면 💊 placeholder
This commit is contained in:
thug0bin 2026-03-04 23:59:13 +09:00
parent ebf2e8a016
commit 088d88878a
2 changed files with 76 additions and 8 deletions

View File

@ -3,6 +3,8 @@
from flask import Blueprint, jsonify, request, render_template, send_file
import pyodbc
import sqlite3
from pathlib import Path
from datetime import datetime, date
import logging
from PIL import Image, ImageDraw, ImageFont
@ -711,6 +713,8 @@ def get_patient_otc_history(cus_code):
# 각 거래의 품목 조회
purchases = []
all_drug_codes = []
for order in orders:
cursor.execute("""
SELECT
@ -728,12 +732,15 @@ def get_patient_otc_history(cus_code):
items = []
for item_row in cursor.fetchall():
drug_code = item_row.DrugCode or ''
all_drug_codes.append(drug_code)
items.append({
'drug_code': item_row.DrugCode or '',
'name': item_row.GoodsName or item_row.DrugCode or '',
'drug_code': drug_code,
'name': item_row.GoodsName or drug_code,
'quantity': int(item_row.SL_NM_item or 0),
'price': int(item_row.SL_TOTAL_PRICE or 0),
'category': item_row.PRINT_TYPE or ''
'category': item_row.PRINT_TYPE or '',
'image': None
})
purchases.append({
@ -744,6 +751,34 @@ def get_patient_otc_history(cus_code):
conn.close()
# 제품 이미지 조회 (product_images.db)
image_map = {}
try:
img_db_path = Path(__file__).parent / 'db' / 'product_images.db'
if img_db_path.exists() and all_drug_codes:
img_conn = sqlite3.connect(str(img_db_path))
img_cursor = img_conn.cursor()
placeholders = ','.join(['?' for _ in all_drug_codes])
img_cursor.execute(f'''
SELECT drug_code, thumbnail_base64
FROM product_images
WHERE drug_code IN ({placeholders}) AND thumbnail_base64 IS NOT NULL
''', all_drug_codes)
for row in img_cursor.fetchall():
image_map[row[0]] = row[1]
img_conn.close()
except Exception as img_err:
logging.warning(f"제품 이미지 조회 오류: {img_err}")
# 이미지 매핑
for purchase in purchases:
for item in purchase['items']:
if item['drug_code'] in image_map:
item['image'] = image_map[item['drug_code']]
# 통계 계산
total_amount = sum(p['amount'] for p in purchases)
total_visits = len(purchases)

View File

@ -261,14 +261,40 @@
}
.otc-purchase-item {
display: flex;
justify-content: space-between;
padding: 5px 0;
align-items: center;
gap: 10px;
padding: 8px 0;
font-size: 0.85rem;
border-bottom: 1px solid #f1f5f9;
}
.otc-purchase-item:last-child { border-bottom: none; }
.otc-purchase-item .name { color: #1e293b; }
.otc-purchase-item .qty { color: #64748b; }
.otc-purchase-item .thumb {
width: 40px;
height: 40px;
border-radius: 6px;
object-fit: cover;
background: #f1f5f9;
flex-shrink: 0;
}
.otc-purchase-item .thumb-placeholder {
width: 40px;
height: 40px;
border-radius: 6px;
background: #e2e8f0;
display: flex;
align-items: center;
justify-content: center;
color: #94a3b8;
font-size: 1.2rem;
flex-shrink: 0;
}
.otc-purchase-item .info {
flex: 1;
min-width: 0;
}
.otc-purchase-item .name { color: #1e293b; font-weight: 500; }
.otc-purchase-item .category { font-size: 0.75rem; color: #64748b; }
.otc-purchase-item .qty { color: #64748b; white-space: nowrap; }
/* 약품 목록 */
.medication-list {
@ -1118,7 +1144,14 @@
<div class="otc-purchase-items">
${p.items.map(item => `
<div class="otc-purchase-item">
<span class="name">${item.name}</span>
${item.image
? `<img class="thumb" src="data:image/jpeg;base64,${item.image}" alt="">`
: `<div class="thumb-placeholder">💊</div>`
}
<div class="info">
<div class="name">${item.name}</div>
${item.category ? `<div class="category">${item.category}</div>` : ''}
</div>
<span class="qty">${item.quantity}개 / ${item.price.toLocaleString()}원</span>
</div>
`).join('')}