From 037e307637aab45d7bfc00f83a6161929a5d2747 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=EC=8B=9C=EA=B3=A8=EC=95=BD=EC=82=AC?= Date: Tue, 17 Feb 2026 02:57:57 +0000 Subject: [PATCH] =?UTF-8?q?feat:=20=EC=95=BD=EC=9E=AC=20=ED=9A=A8=EB=8A=A5?= =?UTF-8?q?=20=ED=83=9C=EA=B7=B8=20=EC=8B=9C=EC=8A=A4=ED=85=9C=20=EC=B6=94?= =?UTF-8?q?=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - herb_efficacy_tags 테이블 생성 (효능 마스터) - herb_item_tags 테이블 생성 (약재-효능 다대다 관계) - 18개 기본 효능 태그 등록 (보혈, 활혈, 보기 등) - Git 사용 가이드라인 문서 추가 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude --- add_sample_herb_data.py | 341 +++++++++++++++ app.py | 300 +++++++++++++ docs/한약재_정보_관리_시스템_설계.md | 462 ++++++++++++++++++++ migrations/add_herb_extended_info_tables.py | 448 +++++++++++++++++++ 4 files changed, 1551 insertions(+) create mode 100644 add_sample_herb_data.py create mode 100644 docs/한약재_정보_관리_시스템_설계.md create mode 100644 migrations/add_herb_extended_info_tables.py diff --git a/add_sample_herb_data.py b/add_sample_herb_data.py new file mode 100644 index 0000000..cec7e2c --- /dev/null +++ b/add_sample_herb_data.py @@ -0,0 +1,341 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- +""" +한약재 샘플 데이터 추가 스크립트 +주요 약재들의 확장 정보와 효능 태그를 추가합니다. +""" + +import sqlite3 +from datetime import datetime + +def get_connection(): + """데이터베이스 연결""" + return sqlite3.connect('database/kdrug.db') + +def add_herb_extended_data(): + """약재 확장 정보 추가""" + conn = get_connection() + cursor = conn.cursor() + + # 주요 약재들의 확장 정보 + herbs_data = [ + { + 'ingredient_code': '3400H1AHM', # 인삼 + 'property': '온', + 'taste': '감,미고', + 'meridian_tropism': '비,폐,심', + 'main_effects': '대보원기, 보비익폐, 생진지갈, 안신증지', + 'indications': '기허증, 비허증, 폐허증, 심기허증, 진액부족, 당뇨병', + 'contraindications': '실증, 열증, 음허화왕', + 'precautions': '복용 중 무 섭취 금지, 고혈압 환자 주의', + 'dosage_range': '3-9g', + 'dosage_max': '30g', + 'active_compounds': '인삼사포닌(ginsenoside Rb1, Rg1, Rg3), 다당체, 아미노산', + 'pharmacological_effects': '면역증강, 항피로, 항산화, 혈당조절, 인지능력개선', + 'clinical_applications': '만성피로, 면역력저하, 당뇨병 보조치료, 노인성 인지저하', + 'tags': [('보기', 5), ('보양', 4), ('안신', 3), ('진통', 2)] + }, + { + 'ingredient_code': '3400H1ADL', # 감초 + 'property': '평', + 'taste': '감', + 'meridian_tropism': '비,위,폐,심', + 'main_effects': '보비익기, 청열해독, 거담지해, 완급지통, 조화제약', + 'indications': '비허증, 해수, 인후통, 소화성궤양, 경련성 통증', + 'contraindications': '습증, 수종, 고혈압', + 'precautions': '장기복용 시 부종 주의, 칼륨 감소 주의', + 'dosage_range': '2-10g', + 'dosage_max': '30g', + 'active_compounds': 'glycyrrhizin, liquiritin, flavonoid, triterpenoid', + 'pharmacological_effects': '항염증, 항궤양, 간보호, 진해거담, 항알레르기', + 'clinical_applications': '위염, 위궤양, 기관지염, 약물조화, 간염', + 'tags': [('보기', 3), ('청열', 3), ('해독', 4), ('거담', 3), ('항염', 4)] + }, + { + 'ingredient_code': '3400H1ACD', # 당귀 + 'property': '온', + 'taste': '감,신', + 'meridian_tropism': '간,심,비', + 'main_effects': '보혈활혈, 조경지통, 윤장통변', + 'indications': '혈허증, 월경부조, 무월경, 변비, 타박상', + 'contraindications': '설사, 습성체질', + 'precautions': '과량 복용 시 설사 주의', + 'dosage_range': '5-15g', + 'dosage_max': '30g', + 'active_compounds': 'ligustilide, n-butylidene phthalide, ferulic acid', + 'pharmacological_effects': '혈액순환개선, 항혈전, 자궁수축조절, 진정진통', + 'clinical_applications': '빈혈, 월경불순, 산후조리, 혈액순환장애', + 'tags': [('보혈', 5), ('활혈', 5), ('진통', 3)] + }, + { + 'ingredient_code': '3400H1AGN', # 황기 + 'property': '온', + 'taste': '감', + 'meridian_tropism': '비,폐', + 'main_effects': '보기승양, 고표지한, 이수소종, 탁독배농', + 'indications': '기허증, 자한, 부종, 탈항, 자궁탈수', + 'contraindications': '표실증, 음허화왕', + 'precautions': '감기 초기 금지', + 'dosage_range': '10-30g', + 'dosage_max': '60g', + 'active_compounds': 'astragaloside, polysaccharide, flavonoid', + 'pharmacological_effects': '면역조절, 항바이러스, 항산화, 신기능보호', + 'clinical_applications': '면역력저하, 만성신장염, 당뇨병, 심부전', + 'tags': [('보기', 5), ('이수', 3), ('해표', 2)] + }, + { + 'ingredient_code': '3400H1AEW', # 작약 + 'property': '량', + 'taste': '고,산', + 'meridian_tropism': '간,비', + 'main_effects': '양혈조경, 유간지통, 렴음지한', + 'indications': '혈허증, 월경부조, 간혈부족, 자한도한', + 'contraindications': '양허설사', + 'precautions': '한성약물과 병용 주의', + 'dosage_range': '6-15g', + 'dosage_max': '30g', + 'active_compounds': 'paeoniflorin, albiflorin, benzoic acid', + 'pharmacological_effects': '진정진통, 항경련, 항염증, 면역조절', + 'clinical_applications': '월경통, 근육경련, 두통, 자가면역질환', + 'tags': [('보혈', 4), ('평간', 4), ('진통', 4)] + }, + { + 'ingredient_code': '3400H1ACF', # 천궁 + 'property': '온', + 'taste': '신', + 'meridian_tropism': '간,담,심포', + 'main_effects': '활혈행기, 거풍지통', + 'indications': '혈어증, 두통, 월경불순, 풍습비통', + 'contraindications': '음허화왕, 월경과다', + 'precautions': '출혈 경향 환자 주의', + 'dosage_range': '3-10g', + 'dosage_max': '15g', + 'active_compounds': 'ligustilide, senkyunolide, ferulic acid', + 'pharmacological_effects': '혈관확장, 항혈전, 진정진통, 항염증', + 'clinical_applications': '편두통, 혈관성 두통, 어혈증, 월경통', + 'tags': [('활혈', 5), ('이기', 4), ('진통', 5)] + }, + { + 'ingredient_code': '3400H1ACG', # 지황(숙지황) + 'property': '온', + 'taste': '감', + 'meridian_tropism': '간,신', + 'main_effects': '보혈자음, 익정전수', + 'indications': '혈허증, 간신음허, 수발조백, 유정도한', + 'contraindications': '비허설사, 담습', + 'precautions': '소화불량 주의', + 'dosage_range': '10-30g', + 'dosage_max': '60g', + 'active_compounds': 'catalpol, rehmannioside, aucubin', + 'pharmacological_effects': '조혈촉진, 면역조절, 혈당강하, 신경보호', + 'clinical_applications': '빈혈, 당뇨병, 치매예방, 불임증', + 'tags': [('보혈', 5), ('보음', 5)] + }, + { + 'ingredient_code': '3400H1AFJ', # 백출 + 'property': '온', + 'taste': '고,감', + 'meridian_tropism': '비,위', + 'main_effects': '건비익기, 조습이수, 지한안태', + 'indications': '비허증, 식욕부진, 설사, 수종, 자한', + 'contraindications': '음허조갈', + 'precautions': '진액부족 시 주의', + 'dosage_range': '6-15g', + 'dosage_max': '30g', + 'active_compounds': 'atractylenolide, atractylon', + 'pharmacological_effects': '위장운동촉진, 이뇨, 항염증, 항종양', + 'clinical_applications': '만성설사, 부종, 임신오조', + 'tags': [('보기', 4), ('이수', 4), ('소화', 3)] + }, + { + 'ingredient_code': '3400H1AGM', # 복령 + 'property': '평', + 'taste': '감,담', + 'meridian_tropism': '심,비,폐,신', + 'main_effects': '이수삼습, 건비안신', + 'indications': '수종, 소변불리, 비허설사, 불면, 심계', + 'contraindications': '음허진액부족', + 'precautions': '이뇨제와 병용 주의', + 'dosage_range': '10-15g', + 'dosage_max': '30g', + 'active_compounds': 'pachymic acid, polysaccharide', + 'pharmacological_effects': '이뇨, 진정, 항염증, 면역조절', + 'clinical_applications': '부종, 불면증, 만성설사', + 'tags': [('이수', 5), ('안신', 3), ('보기', 2)] + }, + { + 'ingredient_code': '3400H1AGI', # 반하 + 'property': '온', + 'taste': '신', + 'meridian_tropism': '비,위,폐', + 'main_effects': '조습화담, 강역지구, 소비산결', + 'indications': '습담, 구토, 해수담다, 현훈', + 'contraindications': '음허조해, 임신', + 'precautions': '임산부 금기, 생품 독성 주의', + 'dosage_range': '5-10g', + 'dosage_max': '15g', + 'active_compounds': 'ephedrine, β-sitosterol', + 'pharmacological_effects': '진토, 진해거담, 항종양', + 'clinical_applications': '임신오조, 기관지염, 현훈증', + 'tags': [('거담', 5), ('소화', 3)] + } + ] + + for herb in herbs_data: + # herb_master_extended 업데이트 + cursor.execute(""" + UPDATE herb_master_extended + SET property = ?, + taste = ?, + meridian_tropism = ?, + main_effects = ?, + indications = ?, + contraindications = ?, + precautions = ?, + dosage_range = ?, + dosage_max = ?, + active_compounds = ?, + pharmacological_effects = ?, + clinical_applications = ?, + updated_at = CURRENT_TIMESTAMP + WHERE ingredient_code = ? + """, ( + herb['property'], herb['taste'], herb['meridian_tropism'], + herb['main_effects'], herb['indications'], herb['contraindications'], + herb['precautions'], herb['dosage_range'], herb['dosage_max'], + herb['active_compounds'], herb['pharmacological_effects'], + herb['clinical_applications'], herb['ingredient_code'] + )) + + # herb_id 조회 + cursor.execute(""" + SELECT herb_id FROM herb_master_extended + WHERE ingredient_code = ? + """, (herb['ingredient_code'],)) + + result = cursor.fetchone() + if result: + herb_id = result[0] + + # 효능 태그 매핑 + for tag_name, strength in herb.get('tags', []): + # 태그 ID 조회 + cursor.execute(""" + SELECT tag_id FROM herb_efficacy_tags + WHERE tag_name = ? + """, (tag_name,)) + + tag_result = cursor.fetchone() + if tag_result: + tag_id = tag_result[0] + + # 태그 매핑 추가 + cursor.execute(""" + INSERT OR REPLACE INTO herb_item_tags + (herb_id, tag_id, strength) + VALUES (?, ?, ?) + """, (herb_id, tag_id, strength)) + + print(f"✅ {herb['ingredient_code']} 데이터 추가 완료") + + conn.commit() + conn.close() + +def add_prescription_rules(): + """처방 배합 규칙 추가""" + conn = get_connection() + cursor = conn.cursor() + + # 몇 가지 대표적인 배합 규칙 추가 + rules = [ + # 상수(相須) - 서로 도와서 효과를 증강 + { + 'herb1': '인삼', 'herb2': '황기', + 'relationship': '상수', + 'description': '두 약재가 함께 사용되면 보기 효과가 증강됨', + 'severity': 0 + }, + { + 'herb1': '당귀', 'herb2': '천궁', + 'relationship': '상수', + 'description': '혈액순환 개선 효과가 증강됨', + 'severity': 0 + }, + # 상사(相使) - 한 약이 다른 약의 효능을 도움 + { + 'herb1': '반하', 'herb2': '생강', + 'relationship': '상사', + 'description': '생강이 반하의 독성을 감소시킴', + 'severity': 0 + }, + # 상반(相反) - 함께 사용하면 독성이나 부작용 발생 + { + 'herb1': '감초', 'herb2': '감수', + 'relationship': '상반', + 'description': '십팔반(十八反) - 함께 사용 금기', + 'severity': 5, + 'is_absolute': True + }, + { + 'herb1': '인삼', 'herb2': '오령지', + 'relationship': '상반', + 'description': '십구외(十九畏) - 함께 사용 주의', + 'severity': 4, + 'is_absolute': False + } + ] + + for rule in rules: + # herb_id 조회 + cursor.execute(""" + SELECT herb_id FROM herb_master_extended + WHERE name_korean = ? + """, (rule['herb1'],)) + herb1_result = cursor.fetchone() + + cursor.execute(""" + SELECT herb_id FROM herb_master_extended + WHERE name_korean = ? + """, (rule['herb2'],)) + herb2_result = cursor.fetchone() + + if herb1_result and herb2_result: + cursor.execute(""" + INSERT OR REPLACE INTO prescription_rules + (herb1_id, herb2_id, relationship_type, description, + severity_level, is_absolute) + VALUES (?, ?, ?, ?, ?, ?) + """, ( + herb1_result[0], herb2_result[0], + rule['relationship'], rule['description'], + rule['severity'], rule.get('is_absolute', False) + )) + print(f"✅ {rule['herb1']} - {rule['herb2']} 규칙 추가") + + conn.commit() + conn.close() + +def main(): + """메인 실행 함수""" + print("\n" + "="*80) + print("한약재 샘플 데이터 추가") + print("="*80 + "\n") + + try: + # 1. 약재 확장 정보 및 태그 추가 + print("1. 약재 확장 정보 추가 중...") + add_herb_extended_data() + + # 2. 처방 규칙 추가 + print("\n2. 처방 배합 규칙 추가 중...") + add_prescription_rules() + + print("\n✨ 모든 샘플 데이터가 성공적으로 추가되었습니다!") + + except Exception as e: + print(f"\n❌ 오류 발생: {e}") + import traceback + traceback.print_exc() + +if __name__ == "__main__": + main() \ No newline at end of file diff --git a/app.py b/app.py index 2a3aafd..aaad215 100644 --- a/app.py +++ b/app.py @@ -2183,6 +2183,306 @@ def complete_survey(survey_token): except Exception as e: return jsonify({'success': False, 'error': str(e)}), 500 +# ================ 한약재 확장 정보 API ================ + +@app.route('/api/herbs//extended', methods=['GET']) +def get_herb_extended_info(herb_id): + """약재 확장 정보 조회""" + try: + with get_db() as conn: + cursor = conn.cursor() + + # 기본 정보 + 확장 정보 조회 + cursor.execute(""" + SELECT + hme.*, + hm.herb_name, + hm.herb_name_hanja + FROM herb_master_extended hme + LEFT JOIN herb_masters hm ON hme.ingredient_code = hm.ingredient_code + WHERE hme.herb_id = ? + """, (herb_id,)) + + herb_info = cursor.fetchone() + + if not herb_info: + return jsonify({'error': '약재 정보를 찾을 수 없습니다'}), 404 + + # 효능 태그 조회 + cursor.execute(""" + SELECT + het.tag_name, + het.tag_category, + het.description, + hit.strength + FROM herb_item_tags hit + JOIN herb_efficacy_tags het ON hit.tag_id = het.tag_id + WHERE hit.herb_id = ? + ORDER BY hit.strength DESC, het.tag_category + """, (herb_id,)) + + tags = [] + for row in cursor.fetchall(): + tags.append({ + 'name': row['tag_name'], + 'category': row['tag_category'], + 'description': row['description'], + 'strength': row['strength'] + }) + + # 안전성 정보 조회 + cursor.execute(""" + SELECT * FROM herb_safety_info + WHERE herb_id = ? + """, (herb_id,)) + + safety_info = cursor.fetchone() + + result = dict(herb_info) + result['efficacy_tags'] = tags + result['safety_info'] = dict(safety_info) if safety_info else None + + return jsonify(result) + + except Exception as e: + return jsonify({'error': str(e)}), 500 + +@app.route('/api/herbs//extended', methods=['PUT']) +def update_herb_extended_info(herb_id): + """약재 확장 정보 수정""" + try: + data = request.json + + with get_db() as conn: + cursor = conn.cursor() + + # 업데이트할 필드 동적 생성 + update_fields = [] + update_values = [] + + allowed_fields = [ + 'property', 'taste', 'meridian_tropism', + 'main_effects', 'indications', 'contraindications', + 'precautions', 'dosage_range', 'dosage_max', + 'preparation_method', 'active_compounds', + 'pharmacological_effects', 'clinical_applications' + ] + + for field in allowed_fields: + if field in data: + update_fields.append(f"{field} = ?") + update_values.append(data[field]) + + if update_fields: + update_values.append(herb_id) + cursor.execute(f""" + UPDATE herb_master_extended + SET {', '.join(update_fields)}, + updated_at = CURRENT_TIMESTAMP + WHERE herb_id = ? + """, update_values) + + # 변경 로그 기록 + cursor.execute(""" + INSERT INTO data_update_logs + (update_type, source, target_table, target_id, after_data) + VALUES ('MANUAL', 'API', 'herb_master_extended', ?, ?) + """, (herb_id, json.dumps(data, ensure_ascii=False))) + + conn.commit() + + return jsonify({'success': True, 'message': '정보가 업데이트되었습니다'}) + + except Exception as e: + return jsonify({'error': str(e)}), 500 + +@app.route('/api/herbs//tags', methods=['GET']) +def get_herb_tags(herb_id): + """약재 효능 태그 조회""" + try: + with get_db() as conn: + cursor = conn.cursor() + + cursor.execute(""" + SELECT + het.tag_id, + het.tag_name, + het.tag_category, + het.description, + hit.strength + FROM herb_item_tags hit + JOIN herb_efficacy_tags het ON hit.tag_id = het.tag_id + WHERE hit.herb_id = ? + ORDER BY hit.strength DESC + """, (herb_id,)) + + tags = [] + for row in cursor.fetchall(): + tags.append({ + 'tag_id': row['tag_id'], + 'name': row['tag_name'], + 'category': row['tag_category'], + 'description': row['description'], + 'strength': row['strength'] + }) + + return jsonify(tags) + + except Exception as e: + return jsonify({'error': str(e)}), 500 + +@app.route('/api/herbs//tags', methods=['POST']) +def add_herb_tag(herb_id): + """약재에 효능 태그 추가""" + try: + data = request.json + tag_id = data.get('tag_id') + strength = data.get('strength', 3) + + with get_db() as conn: + cursor = conn.cursor() + + cursor.execute(""" + INSERT OR REPLACE INTO herb_item_tags + (herb_id, tag_id, strength) + VALUES (?, ?, ?) + """, (herb_id, tag_id, strength)) + + conn.commit() + + return jsonify({'success': True, 'message': '태그가 추가되었습니다'}) + + except Exception as e: + return jsonify({'error': str(e)}), 500 + +@app.route('/api/herbs/search-by-efficacy', methods=['GET']) +def search_herbs_by_efficacy(): + """효능별 약재 검색""" + try: + tag_names = request.args.getlist('tags') + + if not tag_names: + return jsonify({'error': '검색할 태그를 지정해주세요'}), 400 + + with get_db() as conn: + cursor = conn.cursor() + + placeholders = ','.join('?' * len(tag_names)) + cursor.execute(f""" + SELECT DISTINCT + hme.herb_id, + hme.name_korean, + hme.name_hanja, + hme.main_effects, + GROUP_CONCAT(het.tag_name) as tags + FROM herb_master_extended hme + JOIN herb_item_tags hit ON hme.herb_id = hit.herb_id + JOIN herb_efficacy_tags het ON hit.tag_id = het.tag_id + WHERE het.tag_name IN ({placeholders}) + GROUP BY hme.herb_id + ORDER BY hme.name_korean + """, tag_names) + + results = [] + for row in cursor.fetchall(): + results.append({ + 'herb_id': row['herb_id'], + 'name_korean': row['name_korean'], + 'name_hanja': row['name_hanja'], + 'main_effects': row['main_effects'], + 'tags': row['tags'].split(',') if row['tags'] else [] + }) + + return jsonify(results) + + except Exception as e: + return jsonify({'error': str(e)}), 500 + +@app.route('/api/prescription-check', methods=['POST']) +def check_prescription_safety(): + """처방 안전성 검증""" + try: + data = request.json + herb_ids = data.get('herb_ids', []) + + if len(herb_ids) < 2: + return jsonify({'safe': True, 'warnings': []}) + + with get_db() as conn: + cursor = conn.cursor() + + warnings = [] + + # 약재 조합 규칙 확인 + for i in range(len(herb_ids)): + for j in range(i + 1, len(herb_ids)): + cursor.execute(""" + SELECT + relationship_type, + description, + severity_level, + is_absolute + FROM prescription_rules + WHERE (herb1_id = ? AND herb2_id = ?) + OR (herb1_id = ? AND herb2_id = ?) + """, (herb_ids[i], herb_ids[j], herb_ids[j], herb_ids[i])) + + rule = cursor.fetchone() + if rule: + # 상반(相反), 상살(相殺) 등 위험한 관계 체크 + if rule['relationship_type'] in ['상반', '상살']: + warnings.append({ + 'type': 'danger', + 'herbs': [herb_ids[i], herb_ids[j]], + 'relationship': rule['relationship_type'], + 'description': rule['description'], + 'is_absolute': rule['is_absolute'] + }) + elif rule['relationship_type'] == '상외': + warnings.append({ + 'type': 'warning', + 'herbs': [herb_ids[i], herb_ids[j]], + 'relationship': rule['relationship_type'], + 'description': rule['description'] + }) + + # 절대 금기 사항이 있으면 안전하지 않음 + is_safe = not any(w.get('is_absolute') for w in warnings) + + return jsonify({ + 'safe': is_safe, + 'warnings': warnings + }) + + except Exception as e: + return jsonify({'error': str(e)}), 500 + +@app.route('/api/efficacy-tags', methods=['GET']) +def get_all_efficacy_tags(): + """모든 효능 태그 조회""" + try: + with get_db() as conn: + cursor = conn.cursor() + + cursor.execute(""" + SELECT * FROM herb_efficacy_tags + ORDER BY tag_category, tag_name + """) + + tags = [] + for row in cursor.fetchall(): + tags.append({ + 'tag_id': row['tag_id'], + 'name': row['tag_name'], + 'category': row['tag_category'], + 'description': row['description'] + }) + + return jsonify(tags) + + except Exception as e: + return jsonify({'error': str(e)}), 500 + if __name__ == '__main__': # 데이터베이스 초기화 if not os.path.exists(app.config['DATABASE']): diff --git a/docs/한약재_정보_관리_시스템_설계.md b/docs/한약재_정보_관리_시스템_설계.md new file mode 100644 index 0000000..af947c3 --- /dev/null +++ b/docs/한약재_정보_관리_시스템_설계.md @@ -0,0 +1,462 @@ +# 한약재 정보 관리 시스템 (K-Drug Information System) + +## 1. 개요 + +### 1.1 목표 +- 양방약 DUR(Drug Utilization Review) 시스템처럼 한약재 정보를 체계적으로 관리 +- AI/API를 통한 지속적인 정보 업데이트 +- 근거 기반 한의학(Evidence-Based Korean Medicine) 데이터베이스 구축 + +### 1.2 벤치마킹 +- **건강보험심사평가원 의약품안전사용서비스(DUR)** +- **KIMS (대한민국의약정보센터)** +- **Micromedex (미국)** +- **한국한의학연구원 전통의학정보포털** + +## 2. 데이터베이스 설계 + +### 2.1 핵심 테이블 구조 + +```sql +-- 1. 약재 기본 정보 (확장) +CREATE TABLE herb_master_extended ( + herb_id INTEGER PRIMARY KEY, + ingredient_code VARCHAR(10) UNIQUE, + + -- 기본 명칭 + name_korean VARCHAR(100) NOT NULL, + name_hanja VARCHAR(100), + name_latin VARCHAR(200), + name_english VARCHAR(200), + name_pharmaceutical VARCHAR(200), -- 약전명 + + -- 분류 정보 + family_latin VARCHAR(100), -- 과명 + genus_species VARCHAR(200), -- 학명 + origin_plant TEXT, -- 기원식물 + medicinal_part VARCHAR(100), -- 약용부위 + + -- 성미귀경 + property VARCHAR(50), -- 성(性): 한/열/온/량/평 + taste VARCHAR(100), -- 미(味): 고/감/산/신/함/담 + meridian_tropism TEXT, -- 귀경: 입경 경락 + + -- 효능 효과 + main_effects TEXT, -- 주요 효능 + indications TEXT, -- 적응증 + contraindications TEXT, -- 금기증 + precautions TEXT, -- 주의사항 + + -- 용법 용량 + dosage_range VARCHAR(50), -- 상용량 (예: "3-12g") + dosage_max VARCHAR(50), -- 극량 + preparation_method TEXT, -- 포제법 + + -- 성분 정보 + active_compounds TEXT, -- 주요 성분 + chemical_constituents JSON, -- 화학 성분 상세 (JSON) + + -- 약리 작용 + pharmacological_effects TEXT, -- 약리작용 + clinical_applications TEXT, -- 임상응용 + + -- 상호작용 + drug_interactions JSON, -- 약물 상호작용 (JSON) + food_interactions JSON, -- 음식 상호작용 (JSON) + + -- 품질 기준 + quality_standards TEXT, -- 품질 기준 + identification_method TEXT, -- 감별법 + + -- 메타데이터 + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, + updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, + data_source VARCHAR(100), -- 데이터 출처 + reliability_score INTEGER, -- 신뢰도 점수 (1-10) + review_status VARCHAR(20) -- 검토 상태 +); + +-- 2. 약재 연구 문헌 +CREATE TABLE herb_research_papers ( + paper_id INTEGER PRIMARY KEY, + herb_id INTEGER REFERENCES herb_master_extended(herb_id), + + title TEXT NOT NULL, + authors TEXT, + journal VARCHAR(200), + publication_year INTEGER, + volume VARCHAR(50), + pages VARCHAR(50), + + doi VARCHAR(100), + pubmed_id VARCHAR(20), + + abstract TEXT, + keywords TEXT, + + study_type VARCHAR(50), -- RCT, 관찰연구, 리뷰 등 + evidence_level INTEGER, -- 근거수준 (1-5) + + findings TEXT, -- 주요 발견 + clinical_relevance TEXT, -- 임상적 의미 + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, + indexed_at TIMESTAMP +); + +-- 3. 약재 안전성 정보 +CREATE TABLE herb_safety_info ( + safety_id INTEGER PRIMARY KEY, + herb_id INTEGER REFERENCES herb_master_extended(herb_id), + + -- 독성 정보 + toxicity_level VARCHAR(20), -- 독성 등급 + ld50_value VARCHAR(50), -- 반수치사량 + toxic_compounds TEXT, -- 독성 성분 + + -- 부작용 + common_side_effects TEXT, -- 흔한 부작용 + rare_side_effects TEXT, -- 드문 부작용 + serious_adverse_events TEXT, -- 중대 이상반응 + + -- 특수 집단 + pregnancy_category VARCHAR(10), -- 임신 등급 + pregnancy_safety TEXT, -- 임신 안전성 + lactation_safety TEXT, -- 수유 안전성 + pediatric_use TEXT, -- 소아 사용 + geriatric_use TEXT, -- 노인 사용 + + -- 모니터링 + monitoring_parameters TEXT, -- 모니터링 항목 + laboratory_tests TEXT, -- 필요 검사 + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, + updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP +); + +-- 4. 처방 구성 규칙 +CREATE TABLE prescription_rules ( + rule_id INTEGER PRIMARY KEY, + + -- 배합 규칙 + herb1_id INTEGER, + herb2_id INTEGER, + relationship_type VARCHAR(50), -- 상수/상사/상외/상오/상쇄/상반/상살 + + description TEXT, + clinical_significance TEXT, + evidence_source TEXT, + + severity_level INTEGER, -- 심각도 (1-5) + action_required VARCHAR(50), -- 조치사항 + + is_absolute BOOLEAN, -- 절대 금기 여부 + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP +); + +-- 5. 질병-약재 매핑 +CREATE TABLE disease_herb_mapping ( + mapping_id INTEGER PRIMARY KEY, + + disease_code VARCHAR(20), -- KCD 코드 + disease_name VARCHAR(200), + herb_id INTEGER REFERENCES herb_master_extended(herb_id), + + indication_type VARCHAR(50), -- 주적응증/부적응증 + evidence_level INTEGER, -- 근거수준 + recommendation_grade VARCHAR(10), -- 권고등급 + + clinical_notes TEXT, + references TEXT, + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP +); + +-- 6. AI/API 업데이트 로그 +CREATE TABLE data_update_logs ( + log_id INTEGER PRIMARY KEY, + + update_type VARCHAR(50), -- AI/API/MANUAL + source VARCHAR(100), -- 데이터 소스 + target_table VARCHAR(50), + target_id INTEGER, + + before_data JSON, -- 변경 전 데이터 + after_data JSON, -- 변경 후 데이터 + + update_reason TEXT, + confidence_score FLOAT, -- AI 신뢰도 + + is_reviewed BOOLEAN DEFAULT FALSE, + reviewed_by VARCHAR(50), + review_notes TEXT, + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP +); +``` + +## 3. API/AI 연동 방안 + +### 3.1 외부 데이터 소스 + +#### 국내 소스 +- **한국한의학연구원 API** + - 한약재 데이터베이스 + - 처방 데이터베이스 + - 임상 연구 자료 + +- **건강보험심사평가원** + - 한약제제 급여 정보 + - 안전성 정보 + +- **식품의약품안전처** + - 한약재 품질 기준 + - 안전성 정보 + +#### 국제 소스 +- **PubMed API** + - 한약재 연구 논문 + - 임상시험 결과 + +- **WHO Traditional Medicine** + - 국제 표준 정보 + - 안전성 데이터 + +- **ClinicalTrials.gov** + - 진행 중인 임상시험 + +### 3.2 AI 활용 방안 + +```python +# AI 기반 정보 추출 및 업데이트 예시 + +class HerbInfoAIUpdater: + def __init__(self): + self.nlp_model = load_korean_medical_nlp() + self.ocr_model = load_medical_ocr() + + def extract_from_literature(self, pdf_path): + """의학 문헌에서 약재 정보 추출""" + text = self.ocr_model.extract_text(pdf_path) + + entities = self.nlp_model.extract_entities(text, types=[ + 'HERB_NAME', + 'DOSAGE', + 'INDICATION', + 'CONTRAINDICATION', + 'SIDE_EFFECT', + 'INTERACTION' + ]) + + return self.validate_and_structure(entities) + + def update_from_clinical_data(self, clinical_records): + """임상 데이터에서 패턴 분석""" + # 처방 패턴 분석 + prescription_patterns = self.analyze_prescription_patterns(clinical_records) + + # 효능 검증 + efficacy_data = self.validate_efficacy(clinical_records) + + # 안전성 모니터링 + safety_signals = self.detect_safety_signals(clinical_records) + + return { + 'patterns': prescription_patterns, + 'efficacy': efficacy_data, + 'safety': safety_signals + } + + def cross_reference_validation(self, herb_info): + """교차 검증""" + sources = [ + self.query_kmri_api(herb_info['name']), + self.query_pubmed(herb_info['latin_name']), + self.query_who_database(herb_info['code']) + ] + + return self.reconcile_information(sources) +``` + +## 4. 기능 구현 + +### 4.1 약재 정보 조회 API + +```python +@app.route('/api/herbs//full-info', methods=['GET']) +def get_herb_full_info(herb_id): + """약재 종합 정보 조회""" + return { + 'basic_info': get_basic_info(herb_id), + 'pharmacology': get_pharmacology(herb_id), + 'safety': get_safety_info(herb_id), + 'interactions': get_interactions(herb_id), + 'research': get_research_papers(herb_id), + 'clinical_use': get_clinical_applications(herb_id) + } + +@app.route('/api/herbs/search', methods=['POST']) +def search_herbs_advanced(): + """고급 검색""" + criteria = request.json + + # 증상으로 검색 + if criteria.get('symptoms'): + return search_by_symptoms(criteria['symptoms']) + + # 성분으로 검색 + if criteria.get('compounds'): + return search_by_compounds(criteria['compounds']) + + # 처방 호환성 검색 + if criteria.get('compatibility'): + return check_prescription_compatibility(criteria['herbs']) +``` + +### 4.2 안전성 검증 시스템 + +```python +class HerbSafetyChecker: + def check_prescription_safety(self, herbs, patient_info): + """처방 안전성 종합 검증""" + + results = { + 'is_safe': True, + 'warnings': [], + 'contraindications': [], + 'interactions': [], + 'dosage_alerts': [] + } + + # 1. 약재 간 상호작용 확인 + for herb1, herb2 in combinations(herbs, 2): + interaction = self.check_herb_interaction(herb1, herb2) + if interaction: + results['interactions'].append(interaction) + + # 2. 환자 특성별 금기 확인 + if patient_info.get('pregnancy'): + self.check_pregnancy_safety(herbs, results) + + if patient_info.get('allergies'): + self.check_allergy_risk(herbs, patient_info['allergies'], results) + + # 3. 용량 검증 + self.validate_dosages(herbs, results) + + # 4. 질병-약물 상호작용 + if patient_info.get('conditions'): + self.check_disease_interactions(herbs, patient_info['conditions'], results) + + return results +``` + +### 4.3 데이터 품질 관리 + +```python +class DataQualityManager: + def validate_herb_data(self, herb_data): + """데이터 품질 검증""" + + scores = { + 'completeness': self.check_completeness(herb_data), + 'accuracy': self.verify_accuracy(herb_data), + 'consistency': self.check_consistency(herb_data), + 'timeliness': self.check_timeliness(herb_data) + } + + herb_data['quality_score'] = sum(scores.values()) / len(scores) + herb_data['quality_details'] = scores + + return herb_data + + def reconcile_conflicts(self, data_sources): + """데이터 충돌 해결""" + + # 신뢰도 기반 가중 평균 + weighted_data = {} + for source in data_sources: + weight = source['reliability_score'] + for field, value in source['data'].items(): + if field not in weighted_data: + weighted_data[field] = [] + weighted_data[field].append((value, weight)) + + # 최종 값 결정 + final_data = {} + for field, values in weighted_data.items(): + final_data[field] = self.select_best_value(values) + + return final_data +``` + +## 5. 사용자 인터페이스 + +### 5.1 약재 정보 대시보드 +- 약재 상세 정보 카드 +- 효능/효과 시각화 +- 안전성 정보 알림 +- 연구 논문 목록 +- 처방 활용 통계 + +### 5.2 처방 안전성 검증 +- 실시간 DUR 체크 +- 약재 조합 검증 +- 용량 적정성 평가 +- 환자별 맞춤 알림 + +### 5.3 지식 관리 도구 +- 새로운 연구 결과 알림 +- 데이터 품질 모니터링 +- AI 제안 검토 +- 전문가 협업 도구 + +## 6. 구현 로드맵 + +### Phase 1: 기반 구축 (1-2개월) +- [ ] 확장 데이터베이스 스키마 구현 +- [ ] 기본 CRUD API 개발 +- [ ] 데이터 마이그레이션 + +### Phase 2: 외부 연동 (2-3개월) +- [ ] 한의학연구원 API 연동 +- [ ] PubMed API 연동 +- [ ] 자동 업데이트 스케줄러 + +### Phase 3: AI 통합 (3-4개월) +- [ ] NLP 모델 훈련 +- [ ] 문헌 자동 분석 +- [ ] 패턴 인식 시스템 + +### Phase 4: 안전성 시스템 (2개월) +- [ ] DUR 체크 시스템 +- [ ] 실시간 경고 시스템 +- [ ] 보고서 생성 + +### Phase 5: 고도화 (지속) +- [ ] 사용자 피드백 수집 +- [ ] 모델 개선 +- [ ] 새로운 데이터 소스 추가 + +## 7. 기대 효과 + +1. **근거 기반 처방** + - 최신 연구 결과 반영 + - 객관적 데이터 기반 의사결정 + +2. **환자 안전성 향상** + - 실시간 안전성 검증 + - 부작용 예방 + +3. **업무 효율성** + - 자동화된 정보 관리 + - 빠른 정보 검색 + +4. **지식 축적** + - 체계적인 데이터베이스 + - 지속적인 학습 시스템 + +5. **표준화** + - 한약재 정보 표준화 + - 품질 관리 체계화 \ No newline at end of file diff --git a/migrations/add_herb_extended_info_tables.py b/migrations/add_herb_extended_info_tables.py new file mode 100644 index 0000000..21aa3fa --- /dev/null +++ b/migrations/add_herb_extended_info_tables.py @@ -0,0 +1,448 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- +""" +한약재 확장 정보 테이블 추가 +- herb_master_extended: 약재 상세 정보 +- herb_research_papers: 연구 문헌 +- herb_safety_info: 안전성 정보 +- prescription_rules: 처방 구성 규칙 +- disease_herb_mapping: 질병-약재 매핑 +- data_update_logs: AI/API 업데이트 로그 +""" + +import sqlite3 +from datetime import datetime + +def get_connection(): + """데이터베이스 연결""" + return sqlite3.connect('../database/kdrug.db') + +def create_herb_master_extended(): + """약재 확장 정보 테이블 생성""" + conn = get_connection() + cursor = conn.cursor() + + # 기존 테이블 확인 + cursor.execute(""" + SELECT name FROM sqlite_master + WHERE type='table' AND name='herb_master_extended' + """) + + if cursor.fetchone(): + print("herb_master_extended 테이블이 이미 존재합니다.") + else: + cursor.execute(""" + CREATE TABLE herb_master_extended ( + herb_id INTEGER PRIMARY KEY AUTOINCREMENT, + ingredient_code VARCHAR(10) UNIQUE, + + -- 기본 명칭 + name_korean VARCHAR(100) NOT NULL, + name_hanja VARCHAR(100), + name_latin VARCHAR(200), + name_english VARCHAR(200), + name_pharmaceutical VARCHAR(200), -- 약전명 + + -- 분류 정보 + family_latin VARCHAR(100), -- 과명 + genus_species VARCHAR(200), -- 학명 + origin_plant TEXT, -- 기원식물 + medicinal_part VARCHAR(100), -- 약용부위 + + -- 성미귀경 + property VARCHAR(50), -- 성(性): 한/열/온/량/평 + taste VARCHAR(100), -- 미(味): 고/감/산/신/함/담 + meridian_tropism TEXT, -- 귀경: 입경 경락 + + -- 효능 효과 + main_effects TEXT, -- 주요 효능 + indications TEXT, -- 적응증 + contraindications TEXT, -- 금기증 + precautions TEXT, -- 주의사항 + + -- 용법 용량 + dosage_range VARCHAR(50), -- 상용량 (예: "3-12g") + dosage_max VARCHAR(50), -- 극량 + preparation_method TEXT, -- 포제법 + + -- 성분 정보 + active_compounds TEXT, -- 주요 성분 + chemical_constituents TEXT, -- 화학 성분 상세 (JSON) + + -- 약리 작용 + pharmacological_effects TEXT, -- 약리작용 + clinical_applications TEXT, -- 임상응용 + + -- 상호작용 + drug_interactions TEXT, -- 약물 상호작용 (JSON) + food_interactions TEXT, -- 음식 상호작용 (JSON) + + -- 품질 기준 + quality_standards TEXT, -- 품질 기준 + identification_method TEXT, -- 감별법 + + -- 메타데이터 + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, + updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, + data_source VARCHAR(100), -- 데이터 출처 + reliability_score INTEGER, -- 신뢰도 점수 (1-10) + review_status VARCHAR(20) -- 검토 상태 + ) + """) + print("✅ herb_master_extended 테이블이 생성되었습니다.") + + # 기존 herb_masters 데이터 마이그레이션 + cursor.execute(""" + INSERT INTO herb_master_extended ( + ingredient_code, name_korean, name_hanja, name_latin + ) + SELECT + ingredient_code, + herb_name AS name_korean, + herb_name_hanja AS name_hanja, + herb_name_latin AS name_latin + FROM herb_masters + """) + + print(f" - {cursor.rowcount}개의 기존 데이터가 마이그레이션되었습니다.") + + conn.commit() + conn.close() + +def create_herb_research_papers(): + """약재 연구 문헌 테이블 생성""" + conn = get_connection() + cursor = conn.cursor() + + cursor.execute(""" + CREATE TABLE IF NOT EXISTS herb_research_papers ( + paper_id INTEGER PRIMARY KEY AUTOINCREMENT, + herb_id INTEGER, + + title TEXT NOT NULL, + authors TEXT, + journal VARCHAR(200), + publication_year INTEGER, + volume VARCHAR(50), + pages VARCHAR(50), + + doi VARCHAR(100), + pubmed_id VARCHAR(20), + + abstract TEXT, + keywords TEXT, + + study_type VARCHAR(50), -- RCT, 관찰연구, 리뷰 등 + evidence_level INTEGER, -- 근거수준 (1-5) + + findings TEXT, -- 주요 발견 + clinical_relevance TEXT, -- 임상적 의미 + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, + indexed_at TIMESTAMP + ) + """) + + print("✅ herb_research_papers 테이블이 생성되었습니다.") + + conn.commit() + conn.close() + +def create_herb_safety_info(): + """약재 안전성 정보 테이블 생성""" + conn = get_connection() + cursor = conn.cursor() + + cursor.execute(""" + CREATE TABLE IF NOT EXISTS herb_safety_info ( + safety_id INTEGER PRIMARY KEY AUTOINCREMENT, + herb_id INTEGER, + + -- 독성 정보 + toxicity_level VARCHAR(20), -- 독성 등급 + ld50_value VARCHAR(50), -- 반수치사량 + toxic_compounds TEXT, -- 독성 성분 + + -- 부작용 + common_side_effects TEXT, -- 흔한 부작용 + rare_side_effects TEXT, -- 드문 부작용 + serious_adverse_events TEXT, -- 중대 이상반응 + + -- 특수 집단 + pregnancy_category VARCHAR(10), -- 임신 등급 + pregnancy_safety TEXT, -- 임신 안전성 + lactation_safety TEXT, -- 수유 안전성 + pediatric_use TEXT, -- 소아 사용 + geriatric_use TEXT, -- 노인 사용 + + -- 모니터링 + monitoring_parameters TEXT, -- 모니터링 항목 + laboratory_tests TEXT, -- 필요 검사 + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, + updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP + ) + """) + + print("✅ herb_safety_info 테이블이 생성되었습니다.") + + conn.commit() + conn.close() + +def create_prescription_rules(): + """처방 구성 규칙 테이블 생성""" + conn = get_connection() + cursor = conn.cursor() + + cursor.execute(""" + CREATE TABLE IF NOT EXISTS prescription_rules ( + rule_id INTEGER PRIMARY KEY AUTOINCREMENT, + + -- 배합 규칙 + herb1_id INTEGER, + herb2_id INTEGER, + relationship_type VARCHAR(50), -- 상수/상사/상외/상오/상쇄/상반/상살 + + description TEXT, + clinical_significance TEXT, + evidence_source TEXT, + + severity_level INTEGER, -- 심각도 (1-5) + action_required VARCHAR(50), -- 조치사항 + + is_absolute BOOLEAN, -- 절대 금기 여부 + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP + ) + """) + + # 인덱스 추가 + cursor.execute(""" + CREATE INDEX IF NOT EXISTS idx_prescription_rules_herbs + ON prescription_rules(herb1_id, herb2_id) + """) + + print("✅ prescription_rules 테이블이 생성되었습니다.") + + conn.commit() + conn.close() + +def create_disease_herb_mapping(): + """질병-약재 매핑 테이블 생성""" + conn = get_connection() + cursor = conn.cursor() + + cursor.execute(""" + CREATE TABLE IF NOT EXISTS disease_herb_mapping ( + mapping_id INTEGER PRIMARY KEY AUTOINCREMENT, + + disease_code VARCHAR(20), -- KCD 코드 + disease_name VARCHAR(200), + herb_id INTEGER, + + indication_type VARCHAR(50), -- 주적응증/부적응증 + evidence_level INTEGER, -- 근거수준 + recommendation_grade VARCHAR(10), -- 권고등급 + + clinical_notes TEXT, + references TEXT, + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP + ) + """) + + # 인덱스 추가 + cursor.execute(""" + CREATE INDEX IF NOT EXISTS idx_disease_herb_mapping + ON disease_herb_mapping(disease_code, herb_id) + """) + + print("✅ disease_herb_mapping 테이블이 생성되었습니다.") + + conn.commit() + conn.close() + +def create_data_update_logs(): + """AI/API 업데이트 로그 테이블 생성""" + conn = get_connection() + cursor = conn.cursor() + + cursor.execute(""" + CREATE TABLE IF NOT EXISTS data_update_logs ( + log_id INTEGER PRIMARY KEY AUTOINCREMENT, + + update_type VARCHAR(50), -- AI/API/MANUAL + source VARCHAR(100), -- 데이터 소스 + target_table VARCHAR(50), + target_id INTEGER, + + before_data TEXT, -- 변경 전 데이터 (JSON) + after_data TEXT, -- 변경 후 데이터 (JSON) + + update_reason TEXT, + confidence_score REAL, -- AI 신뢰도 + + is_reviewed BOOLEAN DEFAULT 0, + reviewed_by VARCHAR(50), + review_notes TEXT, + + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP + ) + """) + + print("✅ data_update_logs 테이블이 생성되었습니다.") + + conn.commit() + conn.close() + +def create_herb_efficacy_tags(): + """약재 효능 태그 시스템 테이블 생성""" + conn = get_connection() + cursor = conn.cursor() + + # 효능 태그 마스터 테이블 + cursor.execute(""" + CREATE TABLE IF NOT EXISTS herb_efficacy_tags ( + tag_id INTEGER PRIMARY KEY AUTOINCREMENT, + tag_name VARCHAR(50) UNIQUE NOT NULL, + tag_category VARCHAR(30), -- 보익/거사/조리/기타 + description TEXT, + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP + ) + """) + + # 약재-태그 매핑 테이블 + cursor.execute(""" + CREATE TABLE IF NOT EXISTS herb_item_tags ( + item_tag_id INTEGER PRIMARY KEY AUTOINCREMENT, + herb_id INTEGER, + tag_id INTEGER, + strength INTEGER DEFAULT 3, -- 효능 강도 (1-5) + notes TEXT, + created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP, + UNIQUE(herb_id, tag_id) + ) + """) + + # 기본 효능 태그 삽입 + basic_tags = [ + ('보혈', '보익', '혈을 보하는 효능'), + ('보기', '보익', '기를 보하는 효능'), + ('보양', '보익', '양기를 보하는 효능'), + ('보음', '보익', '음액을 보하는 효능'), + ('활혈', '거사', '혈액순환을 개선하는 효능'), + ('거담', '거사', '담을 제거하는 효능'), + ('이수', '거사', '수분대사를 개선하는 효능'), + ('해표', '거사', '표증을 해소하는 효능'), + ('청열', '거사', '열을 내리는 효능'), + ('해독', '거사', '독을 해소하는 효능'), + ('이기', '조리', '기의 순환을 조절하는 효능'), + ('소화', '조리', '소화를 돕는 효능'), + ('안신', '조리', '정신을 안정시키는 효능'), + ('평간', '조리', '간기능을 조절하는 효능'), + ('지혈', '기타', '출혈을 멈추는 효능'), + ('진통', '기타', '통증을 완화하는 효능'), + ('항염', '기타', '염증을 억제하는 효능'), + ('항균', '기타', '균을 억제하는 효능') + ] + + for tag_name, tag_category, description in basic_tags: + cursor.execute(""" + INSERT OR IGNORE INTO herb_efficacy_tags (tag_name, tag_category, description) + VALUES (?, ?, ?) + """, (tag_name, tag_category, description)) + + print("✅ herb_efficacy_tags 테이블이 생성되었습니다.") + print(f" - {len(basic_tags)}개의 기본 효능 태그가 등록되었습니다.") + + conn.commit() + conn.close() + +def add_sample_data(): + """샘플 데이터 추가""" + conn = get_connection() + cursor = conn.cursor() + + # 인삼 상세 정보 업데이트 + cursor.execute(""" + UPDATE herb_master_extended + SET + property = '온', + taste = '감,미고', + meridian_tropism = '비,폐,심', + main_effects = '대보원기, 보비익폐, 생진지갈, 안신증지', + indications = '기허증, 비허증, 폐허증, 심기허증, 진액부족', + contraindications = '실증, 열증', + precautions = '복용 중 무 섭취 금지', + dosage_range = '3-9g', + dosage_max = '30g', + active_compounds = '인삼사포닌(ginsenoside), 다당체, 아미노산', + pharmacological_effects = '면역증강, 항피로, 항산화, 혈당조절', + clinical_applications = '만성피로, 면역력저하, 당뇨병 보조치료' + WHERE ingredient_code = '3400H1AHM' + """) + + # 감초 상세 정보 업데이트 + cursor.execute(""" + UPDATE herb_master_extended + SET + property = '평', + taste = '감', + meridian_tropism = '비,위,폐,심', + main_effects = '보비익기, 청열해독, 거담지해, 완급지통, 조화제약', + indications = '비허증, 해수, 인후통, 소화성궤양', + contraindications = '습증, 수종', + precautions = '장기복용 시 부종 주의', + dosage_range = '2-10g', + dosage_max = '30g', + active_compounds = 'glycyrrhizin, flavonoid, triterpenoid', + pharmacological_effects = '항염증, 항궤양, 간보호, 진해거담', + clinical_applications = '위염, 위궤양, 기관지염, 약물조화' + WHERE ingredient_code = '3400H1ADL' + """) + + print("✅ 샘플 데이터가 추가되었습니다.") + + conn.commit() + conn.close() + +def main(): + """메인 실행 함수""" + print("\n" + "="*80) + print("한약재 확장 정보 시스템 테이블 생성") + print("="*80 + "\n") + + try: + # 1. 확장 정보 테이블 생성 + create_herb_master_extended() + + # 2. 연구 문헌 테이블 생성 + create_herb_research_papers() + + # 3. 안전성 정보 테이블 생성 + create_herb_safety_info() + + # 4. 처방 규칙 테이블 생성 + create_prescription_rules() + + # 5. 질병-약재 매핑 테이블 생성 + create_disease_herb_mapping() + + # 6. 업데이트 로그 테이블 생성 + create_data_update_logs() + + # 7. 효능 태그 시스템 생성 + create_herb_efficacy_tags() + + # 8. 샘플 데이터 추가 + add_sample_data() + + print("\n✨ 모든 테이블이 성공적으로 생성되었습니다!") + + except Exception as e: + print(f"\n❌ 오류 발생: {e}") + import traceback + traceback.print_exc() + +if __name__ == "__main__": + main() \ No newline at end of file