Polyglot-ko-3.8B + LoRA 기반 라이브커머스 판별 모델 API 서버
입력으로 제목(title), 채팅(chat), 화자의 발화(speech) 를 보내면
→ 이 콘텐츠가 라이브커머스인지 / 일반 영상인지 자동 분류합니다.
이 모델은 다음 데이터로 파인튜닝되었습니다:
라이브커머스 영상은 제목·대화 흐름·판매 관련 패턴이 분명하여
이를 Polyglot-ko-3.8B 기반으로 분류하는 모델입니다.
본 API 서버는:
구조는 학습용 노트북(finetune.ipynb)과 추론 서버(app.py)를 기반으로 구현됩니다.
EleutherAI/polyglot-ko-3.8b이 모델은 “분류 모델”이지만, 내부적으로는
질문(prompt) + “네 / 아니요 / 모름”
을 생성하는 방식으로 학습되어, 생성 결과를 가지고 라이브커머스 여부를 판별합니다.
원본 JSONL 구조 (merged_normalized.jsonl)
title: 영상 제목chat: 채팅 메시지 리스트whisper_transcript: 화자 발화를 Whisper 등으로 받아 적은 자막label: 1(라이브커머스), 0(비라이브커머스), 그 외(모름/애매)레이블 → 자연어 응답으로 변환 (merged_data.jsonl)
label == 1 → response = "네 </s>"label == 0 → response = "아니요 </s>"response = "모름 </s>"</s> 는 EOS 토큰으로, 문장의 끝을 명시하기 위해 추가.프롬프트/응답 구조로 변환 (converted_prompt_response.jsonl)
각 샘플은 아래와 같은 형태의 prompt/response 쌍으로 재구성됩니다.
prompt 템플릿:
📌 제목: {title}
📌 채팅: {chat_1 chat_2 ...}
📌 자막: {whisper_transcript}
이 방송은 제품을 판매하는 라이브커머스인가요?
[답]:
response:
"네 </s>" 또는 "아니요 </s>" 또는 "모름 </s>"최종 JSONL 구조:
{"prompt": "...", "response": "네 </s>"}
Train / Validation / Test 분할
converted_prompt_response.jsonl을 로드한 뒤:
random_state=42Dataset으로 변환 후 Trainer에 전달.하나의 학습 샘플은 결국 다음 문장을 완성하도록 모델을 학습시키는 것입니다:
“📌 제목: …\n📌 채팅: …\n📌 자막: …\n이 방송은 제품을 판매하는 라이브커머스인가요?\n[답]: 네 ”
또는
“…\n[답]: 아니요 ”
즉,
이 구조 덕분에:
학습은 “Causal LM” 방식으로 진행되지만,
손실(loss)은 오직 ‘답변 구간’에만 걸리도록 마스킹을 합니다.
토크나이저 설정
EleutherAI/polyglot-ko-3.8b</s> 를 추가입력/라벨 구성
full_text = prompt + " " + responseprompt_ids = tokenizer(prompt)full_ids = tokenizer(full_text)labels를 만들 때:
-100 (loss 계산에서 무시)-100이렇게 하면 질문 부분은 단지 조건(conditioning) 으로만 사용되고,
“답변 토큰을 얼마나 잘 생성하는지”만 학습하게 됩니다.
모델 전체를 finetune 하는 대신, 아래와 같이 LoRA를 사용하여 일부 Linear 계층만 학습합니다.
Base Model 로딩
BitsAndBytesConfig(load_in_4bit=True, bnb_4bit_compute_dtype=torch.float16))device_map="auto" 로 GPU 자원에 맞게 자동 배치resize_token_embeddings 호출LoRA 설정 주요 하이퍼파라미터
r = 8lora_alpha = 32lora_dropout = 0.05bias = "none"task_type = "CAUSAL_LM"target_modules = ["query_key_value"]효과
학습은 HuggingFace Trainer를 사용해 진행하며, 주요 설정은 다음과 같습니다.
output_dir = "./results_polyglot"per_device_train_batch_size = 2per_device_eval_batch_size = 2gradient_accumulation_steps = 8learning_rate = 2e-4num_train_epochs = 최대 100fp16 = True (반정밀도 학습)eval_strategy = "epoch" (매 epoch마다 validation)save_strategy = "epoch" (매 epoch 체크포인트 저장)load_best_model_at_end = Truemetric_for_best_model = "eval_loss"greater_is_better = False (loss가 낮을수록 좋음)EarlyStoppingCallback(early_stopping_patience=3)이 설정으로:
학습 완료 후에는:
final_model_polyglot/ 또는 체크포인트 디렉토리추론 서버(app.py)에서는:
PeftModel.from_pretrained(fine_tuned_model_path) 로 LoRA 어댑터 적용/generate 엔드포인트를 통해 HTTP로 분류 결과를 제공이로써, 학습 노트북 → 저장된 LoRA 모델 → Flask 서버로 이어지는 전체 파이프라인이 완성됩니다.
서버는 다음 파일을 기반으로 동작합니다:
/generate 엔드포인트 정의주요 기능:
/generate에서 프롬프트를 입력받아 생성 결과 반환POST /generate
Content-Type: application/json
{
"prompt": "📌 제목: 여름 원피스 특가 판매합니다\n📌 채팅: 가격 알려주세요!\n📌 자막: 지금 구매하시면 할인 적용됩니다.\n이 방송은 제품을 판매하는 라이브커머스인가요?\n[답]:",
"max_new_tokens": 10
}
서버는 다음 파일을 기반으로 동작합니다:
주요 기능:
/generate 엔드포인트에서 분류 출력project/
├── app.py
├── finetune.ipynb
├── converted_prompt_response.jsonl
├── checkpoint-2030/ # LoRA 체크포인트
├── final_model_polyglot/ # 최종 저장 모델(선택)
└── readme.yaml
2 commits
Jupyter Notebook
80.4%
Python
19.6%
Polyglot-ko-3.8B + LoRA 기반 라이브커머스 판별 모델 API 서버
입력으로 제목(title), 채팅(chat), 화자의 발화(speech) 를 보내면
→ 이 콘텐츠가 라이브커머스인지 / 일반 영상인지 자동 분류합니다.
이 모델은 다음 데이터로 파인튜닝되었습니다:
라이브커머스 영상은 제목·대화 흐름·판매 관련 패턴이 분명하여
이를 Polyglot-ko-3.8B 기반으로 분류하는 모델입니다.
본 API 서버는:
구조는 학습용 노트북(finetune.ipynb)과 추론 서버(app.py)를 기반으로 구현됩니다.
EleutherAI/polyglot-ko-3.8b이 모델은 “분류 모델”이지만, 내부적으로는
질문(prompt) + “네 / 아니요 / 모름”
을 생성하는 방식으로 학습되어, 생성 결과를 가지고 라이브커머스 여부를 판별합니다.
원본 JSONL 구조 (merged_normalized.jsonl)
title: 영상 제목chat: 채팅 메시지 리스트whisper_transcript: 화자 발화를 Whisper 등으로 받아 적은 자막label: 1(라이브커머스), 0(비라이브커머스), 그 외(모름/애매)레이블 → 자연어 응답으로 변환 (merged_data.jsonl)
label == 1 → response = "네 </s>"label == 0 → response = "아니요 </s>"response = "모름 </s>"</s> 는 EOS 토큰으로, 문장의 끝을 명시하기 위해 추가.프롬프트/응답 구조로 변환 (converted_prompt_response.jsonl)
각 샘플은 아래와 같은 형태의 prompt/response 쌍으로 재구성됩니다.
prompt 템플릿:
📌 제목: {title}
📌 채팅: {chat_1 chat_2 ...}
📌 자막: {whisper_transcript}
이 방송은 제품을 판매하는 라이브커머스인가요?
[답]:
response:
"네 </s>" 또는 "아니요 </s>" 또는 "모름 </s>"최종 JSONL 구조:
{"prompt": "...", "response": "네 </s>"}
Train / Validation / Test 분할
converted_prompt_response.jsonl을 로드한 뒤:
random_state=42Dataset으로 변환 후 Trainer에 전달.하나의 학습 샘플은 결국 다음 문장을 완성하도록 모델을 학습시키는 것입니다:
“📌 제목: …\n📌 채팅: …\n📌 자막: …\n이 방송은 제품을 판매하는 라이브커머스인가요?\n[답]: 네 ”
또는
“…\n[답]: 아니요 ”
즉,
이 구조 덕분에:
학습은 “Causal LM” 방식으로 진행되지만,
손실(loss)은 오직 ‘답변 구간’에만 걸리도록 마스킹을 합니다.
토크나이저 설정
EleutherAI/polyglot-ko-3.8b</s> 를 추가입력/라벨 구성
full_text = prompt + " " + responseprompt_ids = tokenizer(prompt)full_ids = tokenizer(full_text)labels를 만들 때:
-100 (loss 계산에서 무시)-100이렇게 하면 질문 부분은 단지 조건(conditioning) 으로만 사용되고,
“답변 토큰을 얼마나 잘 생성하는지”만 학습하게 됩니다.
모델 전체를 finetune 하는 대신, 아래와 같이 LoRA를 사용하여 일부 Linear 계층만 학습합니다.
Base Model 로딩
BitsAndBytesConfig(load_in_4bit=True, bnb_4bit_compute_dtype=torch.float16))device_map="auto" 로 GPU 자원에 맞게 자동 배치resize_token_embeddings 호출LoRA 설정 주요 하이퍼파라미터
r = 8lora_alpha = 32lora_dropout = 0.05bias = "none"task_type = "CAUSAL_LM"target_modules = ["query_key_value"]효과
학습은 HuggingFace Trainer를 사용해 진행하며, 주요 설정은 다음과 같습니다.
output_dir = "./results_polyglot"per_device_train_batch_size = 2per_device_eval_batch_size = 2gradient_accumulation_steps = 8learning_rate = 2e-4num_train_epochs = 최대 100fp16 = True (반정밀도 학습)eval_strategy = "epoch" (매 epoch마다 validation)save_strategy = "epoch" (매 epoch 체크포인트 저장)load_best_model_at_end = Truemetric_for_best_model = "eval_loss"greater_is_better = False (loss가 낮을수록 좋음)EarlyStoppingCallback(early_stopping_patience=3)이 설정으로:
학습 완료 후에는:
final_model_polyglot/ 또는 체크포인트 디렉토리추론 서버(app.py)에서는:
PeftModel.from_pretrained(fine_tuned_model_path) 로 LoRA 어댑터 적용/generate 엔드포인트를 통해 HTTP로 분류 결과를 제공이로써, 학습 노트북 → 저장된 LoRA 모델 → Flask 서버로 이어지는 전체 파이프라인이 완성됩니다.
서버는 다음 파일을 기반으로 동작합니다:
/generate 엔드포인트 정의주요 기능:
/generate에서 프롬프트를 입력받아 생성 결과 반환POST /generate
Content-Type: application/json
{
"prompt": "📌 제목: 여름 원피스 특가 판매합니다\n📌 채팅: 가격 알려주세요!\n📌 자막: 지금 구매하시면 할인 적용됩니다.\n이 방송은 제품을 판매하는 라이브커머스인가요?\n[답]:",
"max_new_tokens": 10
}
서버는 다음 파일을 기반으로 동작합니다:
주요 기능:
/generate 엔드포인트에서 분류 출력project/
├── app.py
├── finetune.ipynb
├── converted_prompt_response.jsonl
├── checkpoint-2030/ # LoRA 체크포인트
├── final_model_polyglot/ # 최종 저장 모델(선택)
└── readme.yaml
2 commits
Jupyter Notebook
80.4%
Python
19.6%