import json import os from typing import Optional, Tuple class RegionCodeConverter: """위치 정보를 시군구 코드로 변환하는 유틸리티""" def __init__(self): """지역 코드 데이터 로드""" base_path = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) # 전체 지역 코드 로드 with open(os.path.join(base_path, 'data', 'region_codes.json'), 'r', encoding='utf-8') as f: self.full_codes = json.load(f) # 간략 지역 코드 로드 with open(os.path.join(base_path, 'data', 'region_codes_simple.json'), 'r', encoding='utf-8') as f: self.simple_codes = json.load(f) def get_region_code(self, location: str) -> Tuple[Optional[str], Optional[str]]: """ 위치 정보를 시군구 코드로 변환 Args: location: 위치 텍스트 (예: "강남구", "서울 강남", "서울특별시 강남구") Returns: (지역코드, 매칭된 지역명) 튜플 """ if not location: return None, None location = location.strip() # 1. 정확한 매칭 시도 (전체 이름) for full_name, code in self.full_codes.items(): if location in full_name or full_name in location: return code, full_name # 2. 간략 이름으로 매칭 시도 for simple_name, code in self.simple_codes.items(): if simple_name in location: # 전체 이름 찾기 for full_name, full_code in self.full_codes.items(): if full_code == code: return code, full_name return code, simple_name # 3. 부분 매칭 시도 (구, 시, 군 단위) location_parts = location.split() for part in location_parts: # 구/시/군으로 끝나는 부분 찾기 if part.endswith('구') or part.endswith('시') or part.endswith('군'): # 간략 코드에서 찾기 if part in self.simple_codes: code = self.simple_codes[part] # 전체 이름 찾기 for full_name, full_code in self.full_codes.items(): if full_code == code and part in full_name: return code, full_name return code, part # 전체 코드에서 찾기 for full_name, code in self.full_codes.items(): if part in full_name: return code, full_name # 4. 동 이름으로 구 추정 (주요 동 매핑) dong_to_gu = { # 서울 강남구 '역삼': '강남구', '삼성': '강남구', '청담': '강남구', '논현': '강남구', '대치': '강남구', '도곡': '강남구', '개포': '강남구', '일원': '강남구', '수서': '강남구', '세곡': '강남구', # 서울 서초구 '반포': '서초구', '서초': '서초구', '방배': '서초구', '양재': '서초구', '잠원': '서초구', '우면': '서초구', '내곡': '서초구', # 서울 송파구 '잠실': '송파구', '신천': '송파구', '석촌': '송파구', '송파': '송파구', '가락': '송파구', '문정': '송파구', '장지': '송파구', '방이': '송파구', '오금': '송파구', '풍납': '송파구', # 서울 강동구 '천호': '강동구', '성내': '강동구', '길동': '강동구', '둔촌': '강동구', '암사': '강동구', '명일': '강동구', '고덕': '강동구', '상일': '강동구', # 서울 노원구 '상계': '노원구', '중계': '노원구', '하계': '노원구', '월계': '노원구', '공릉': '노원구', # 서울 양천구 '목동': '양천구', '신정': '양천구', '신월': '양천구', # 서울 영등포구 '여의도': '영등포구', '당산': '영등포구', '영등포': '영등포구', '문래': '영등포구', '양평': '영등포구', '신길': '영등포구', '대림': '영등포구', # 서울 마포구 '홍대': '마포구', '합정': '마포구', '상수': '마포구', '망원': '마포구', '연남': '마포구', '서교': '마포구', '공덕': '마포구', '아현': '마포구', '도화': '마포구', '용강': '마포구', # 서울 성동구 '성수': '성동구', '왕십리': '성동구', '행당': '성동구', '금호': '성동구', '옥수': '성동구', # 서울 용산구 '이태원': '용산구', '한남': '용산구', '동빙고': '용산구', '서빙고': '용산구', '이촌': '용산구', '한강로': '용산구', '효창': '용산구', '용문': '용산구', # 서울 종로구 '광화문': '종로구', '종로': '종로구', '인사동': '종로구', '삼청': '종로구', '평창': '종로구', '부암': '종로구', '무악': '종로구', '교남': '종로구', # 서울 중구 '명동': '중구', '충무로': '중구', '을지로': '중구', '남대문': '중구', '회현': '중구', '필동': '중구', '장충': '중구', '신당': '중구', '다산': '중구', # 경기도 성남시 분당구 '판교': '분당구', '정자': '분당구', '서현': '분당구', '수내': '분당구', '야탑': '분당구', '이매': '분당구', '분당': '분당구', '구미': '분당구', '금곡': '분당구', # 경기도 용인시 '동백': '기흥구', '보정': '기흥구', '죽전': '수지구', '수지': '수지구', # 경기도 수원시 '영통': '영통구', '광교': '영통구', '원천': '영통구', '매탄': '영통구', # 경기도 고양시 '일산': '일산동구', '백석': '일산동구', '마두': '일산서구', '주엽': '일산서구' } for dong, gu in dong_to_gu.items(): if dong in location: if gu in self.simple_codes: code = self.simple_codes[gu] # 전체 이름 찾기 for full_name, full_code in self.full_codes.items(): if full_code == code: return code, full_name return code, gu return None, None