""" LoRA utilities for Lily LLM API """ import logging logger = logging.getLogger(__name__) def setup_lora_for_model(profile, lora_manager): """모델 프로필에 따른 LoRA 설정 (공통 함수)""" if not lora_manager: logger.warning("⚠️ LoRA가 사용 불가능하여 자동 설정 건너뜀") return False try: logger.info("🔧 LoRA 자동 설정 시작...") # 🔄 모델 프로필에서 경로 및 타입 정보 가져오기 current_model_path = None model_type = "causal_lm" # 기본값 # 🔄 모델 프로필에서 경로 및 타입 정보 가져오기 if hasattr(profile, 'local_path') and profile.local_path: # 로컬 환경: 로컬 경로 사용 current_model_path = profile.local_path # 🔄 local_path 사용 시에도 model_type 설정 필요 if hasattr(profile, 'model_id') and profile.model_id: model_id = profile.model_id if model_id == "kanana-1.5-v-3b-instruct": model_type = "vision2seq" # 🔄 kanana는 vision2seq 타입 else: model_type = "causal_lm" # 기본값 logger.info(f"🔍 모델 프로필에서 로컬 경로 사용: {current_model_path}") logger.info(f"🔍 결정된 모델 타입: {model_type}") elif hasattr(profile, 'model_id') and profile.model_id: # 모델 ID를 기반으로 경로 결정 model_id = profile.model_id logger.info(f"🔍 모델 ID 기반 경로 결정: {model_id}") # 🔄 환경에 따른 경로 결정 if hasattr(profile, 'is_local') and profile.is_local: # 로컬 환경: 로컬 경로 사용 if model_id == "polyglot-ko-1.3b-chat": current_model_path = "./lily_llm_core/models/polyglot_ko_1_3b_chat" model_type = "causal_lm" elif model_id == "kanana-1.5-v-3b-instruct": current_model_path = "./lily_llm_core/models/kanana_1_5_v_3b_instruct" model_type = "vision2seq" # 🔄 kanana는 vision2seq 타입 elif model_id == "polyglot-ko-5.8b-chat": current_model_path = "./lily_llm_core/models/polyglot_ko_5_8b_chat" model_type = "causal_lm" else: # 배포 환경: HF 모델명 사용 (로컬 경로 없음) current_model_path = None logger.info(f"🔍 배포 환경: LoRA 설정 건너뜀 (HF 모델)") return False logger.info(f"🔍 결정된 모델 경로: {current_model_path}") logger.info(f"🔍 결정된 모델 타입: {model_type}") if not current_model_path: logger.warning("⚠️ 현재 모델의 경로를 찾을 수 없어 LoRA 자동 로드 건너뜀") return False logger.info(f"🔍 LoRA 모델 경로: {current_model_path}") logger.info(f"🔍 LoRA 모델 타입: {model_type}") # 🔄 이미 로드된 메인 모델을 LoRA에 직접 적용 (중복 로드 방지) logger.info("🔧 기존 메인 모델에 LoRA 직접 적용 시작...") # 🔄 lora_manager에 기존 메인 모델 설정 if hasattr(lora_manager, 'base_model') and lora_manager.base_model is None: # 전역 변수에서 메인 모델 가져오기 from ..services.model_service import get_current_model current_model = get_current_model() if current_model is not None: lora_manager.base_model = current_model logger.info("✅ 기존 메인 모델을 LoRA 관리자에 설정 완료") else: logger.warning("⚠️ 메인 모델을 찾을 수 없어 LoRA 설정 건너뜀") return False # LoRA 설정 생성 logger.info("🔧 LoRA 설정 생성 시작...") # 🔄 모델별 target modules 설정 if model_type == "vision2seq" and "kanana" in profile.model_id: # Kanana 모델: Llama 기반 language model 사용 (첫 번째 레이어만 사용) target_modules = [ "language_model.model.layers.0.self_attn.q_proj", "language_model.model.layers.0.self_attn.k_proj", "language_model.model.layers.0.self_attn.v_proj", "language_model.model.layers.0.self_attn.o_proj", "language_model.model.layers.0.mlp.gate_proj", "language_model.model.layers.0.mlp.up_proj", "language_model.model.layers.0.mlp.down_proj" ] else: # 기존 모델들: GPTNeoX 기반 target_modules = ["query_key_value", "mlp.dense_h_to_4h", "mlp.dense_4h_to_h"] lora_config = lora_manager.create_lora_config( r=16, lora_alpha=32, lora_dropout=0.1, bias="none", task_type="CAUSAL_LM" if model_type == "causal_lm" else "VISION_2_SEQ", target_modules=target_modules ) logger.info("✅ LoRA 설정 생성 완료") # LoRA 어댑터 적용 (기존 메인 모델에 직접) logger.info("🔧 LoRA 어댑터 적용 시작...") adapter_success = lora_manager.apply_lora_to_model("auto_adapter") if adapter_success: logger.info("✅ LoRA 어댑터 적용 완료: auto_adapter") logger.info("🎉 LoRA 자동 설정 완료!") return True else: logger.error("❌ LoRA 어댑터 적용 실패") return False except Exception as e: logger.error(f"❌ LoRA 자동 설정 중 오류: {e}") return False