Skip to content

Latest commit

Β 

History

83 Commits

Folders and files

NameName
Last commit message
Last commit date
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 

Repository files navigation

Job Finder

λ§žμΆ€ν˜• μ·¨μ—… 곡고 μΆ”μ²œ 및 이메일 λ°œμ†‘ μžλ™ν™” μ‹œμŠ€ν…œ

Google μ„€λ¬Έμ§€λ₯Ό 톡해 μˆ˜μ§‘ν•œ ꡬ직자 데이터λ₯Ό λΆ„μ„ν•˜μ—¬, 각 μ§€μ›μžμ˜ μ„ ν˜Έλ„μ— λ§žλŠ” μ±„μš© 곡고λ₯Ό λ§€μΉ­ν•˜κ³  κ°œμΈν™”λœ HTML 이메일을 μžλ™μœΌλ‘œ λ°œμ†‘ν•˜λŠ” μ‹œμŠ€ν…œμž…λ‹ˆλ‹€.

μ£Όμš” κΈ°λŠ₯

  • 곡고 λ§€μΉ­: 4단계 필터링 μ‹œμŠ€ν…œμœΌλ‘œ ꡬ직자 μ„ ν˜Έλ„μ— μ΅œμ ν™”λœ 곡고 μΆ”μ²œ
  • κ°œμΈν™”λœ 이메일: νšŒμ‚¬ 둜고, D-day 정보, μ±„μš© ν˜•νƒœ νƒœκ·Έκ°€ ν¬ν•¨λœ λ§žμΆ€ν˜• HTML 이메일
  • Google Sheets 연동: μ„€λ¬Έ 응닡 데이터 μžλ™ μˆ˜μ§‘ 및 λ°œμ†‘ κ²°κ³Ό 기둝
  • Gmail API 톡합: OAuth 2.0 기반 μ•ˆμ „ν•œ 이메일 λ°œμ†‘
  • μ„ ν˜Έ κΈ°μ—… μš°μ„ μˆœμœ„: μ§€μ›μžκ°€ μ„ νƒν•œ λŒ€κΈ°μ—… κ·Έλ£Ή 곡고에 λ³„ν‘œ ν‘œμ‹œ

ν”„λ‘œμ νŠΈ ꡬ쑰

job-finder/test/
β”œβ”€β”€ main.py                          # 메인 μ‹€ν–‰ 파일
β”œβ”€β”€ requirements.txt                 # νŒ¨ν‚€μ§€ μ˜μ‘΄μ„±
β”œβ”€β”€ .env                            # ν™˜κ²½ λ³€μˆ˜ μ„€μ • (λ³΄μ•ˆ)
β”œβ”€β”€ .env_sample                     # ν™˜κ²½ λ³€μˆ˜ ν…œν”Œλ¦Ώ
β”œβ”€β”€ credentials.json                # Google OAuth 인증 정보
β”‚
β”œβ”€β”€ data/                           # μ±„μš© 곡고 데이터 (JSON)
β”‚   β”œβ”€β”€ 쿠팑_5923444_250917_crawling.json
β”‚   β”œβ”€β”€ 쿠팑_6753367_250917_crawling.json
β”‚   └── ...
β”‚
β”œβ”€β”€ template/                       # 이메일 ν…œν”Œλ¦Ώ
β”‚   └── test_email.html            # HTML 이메일 κΈ°λ³Έ ν…œν”Œλ¦Ώ
β”‚
└── services/                       # 핡심 λΉ„μ¦ˆλ‹ˆμŠ€ 둜직
    β”œβ”€β”€ matching/
    β”‚   └── job_matcher.py         # 곡고 λ§€μΉ­ μ•Œκ³ λ¦¬μ¦˜
    β”œβ”€β”€ email/
    β”‚   β”œβ”€β”€ email_service.py       # 이메일 λ°œμ†‘ μΈν„°νŽ˜μ΄μŠ€
    β”‚   └── gmail_service.py       # Gmail API 톡합
    β”œβ”€β”€ sheets/
    β”‚   β”œβ”€β”€ sheets_auth.py         # Google Sheets OAuth 인증
    β”‚   └── sheets_service.py      # Sheets 데이터 읽기/μ“°κΈ°
    └── template/
        └── template_generator.py  # κ°œμΈν™” 이메일 생성

μ‹œμž‘ν•˜κΈ°

사전 μš”κ΅¬μ‚¬ν•­

  • Python 3.7 이상
  • Google Cloud Platform 계정
  • Gmail API 및 Google Sheets API ν™œμ„±ν™”λœ ν”„λ‘œμ νŠΈ

1. Google Cloud μ„€μ •

  1. Google Cloud Consoleμ—μ„œ μƒˆ ν”„λ‘œμ νŠΈ 생성
  2. Gmail API와 Google Sheets API ν™œμ„±ν™”
  3. OAuth 2.0 ν΄λΌμ΄μ–ΈνŠΈ ID 생성 (λ°μŠ€ν¬ν†± μ•± μœ ν˜•)
  4. 인증 정보λ₯Ό credentials.json으둜 λ‹€μš΄λ‘œλ“œν•˜μ—¬ ν”„λ‘œμ νŠΈ λ£¨νŠΈμ— μ €μž₯

2. ν™˜κ²½ μ„€μ •

# 1. μ €μž₯μ†Œ 클둠
git clone https://github.com/your-username/job-finder.git
cd job-finder/test

# 2. κ°€μƒν™˜κ²½ 생성 (ꢌμž₯)
python -m venv venv
source venv/bin/activate  # Windows: venv\Scripts\activate

# 3. νŒ¨ν‚€μ§€ μ„€μΉ˜
pip install -r requirements.txt

# 4. ν™˜κ²½ λ³€μˆ˜ μ„€μ •
cp .env_sample .env

3. .env 파일 μˆ˜μ •

SPREADSHEET_ID=your-google-sheet-id-here
WORKSHEET_NAME=μ„€λ¬Έμ§€ 응닡 μ‹œνŠΈ1

Google Sheet ID μ°ΎλŠ” 방법:

  • Sheets URL: https://docs.google.com/spreadsheets/d/[SPREADSHEET_ID]/edit
  • μ€‘κ°„μ˜ κΈ΄ λ¬Έμžμ—΄μ΄ SPREADSHEET_IDμž…λ‹ˆλ‹€.

4. μ‹€ν–‰

python main.py

첫 μ‹€ν–‰ μ‹œ:

  • λΈŒλΌμš°μ €κ°€ μžλ™μœΌλ‘œ 열리며 Google 계정 둜그인 μš”μ²­
  • Gmail 및 Google Sheets κΆŒν•œ 승인
  • gmail_token.pickleκ³Ό sheets_token.pickle μžλ™ 생성
  • 이후 μ‹€ν–‰λΆ€ν„°λŠ” 토큰 μž¬μ‚¬μš©μœΌλ‘œ 별도 인증 λΆˆν•„μš”

μž‘λ™ 원리

전체 ν”„λ‘œμ„ΈμŠ€

1. Google Sheetsμ—μ„œ μ„€λ¬Έ 응닡 데이터 λ‘œλ“œ
        ↓
2. μ‹ μž… 곡고λ₯Ό μ°ΎλŠ” μ§€μ›μž 필터링
        ↓
3. 각 μ§€μ›μžμ— λŒ€ν•΄:
   β”œβ”€ data/ ν΄λ”μ˜ μ±„μš© 곡고와 λ§€μΉ­
   β”œβ”€ κ°œμΈν™”λœ HTML 이메일 생성
   β”œβ”€ Gmail API둜 이메일 λ°œμ†‘
   └─ λ°œμ†‘ κ²°κ³Ό 기둝
        ↓
4. Google Sheets에 λ°œμ†‘ μƒνƒœ μ—…λ°μ΄νŠΈ
        ↓
5. μ΅œμ’… 톡계 좜λ ₯ (성곡/μ‹€νŒ¨ 건수)

λ§€μΉ­ μ•Œκ³ λ¦¬μ¦˜ (4단계 필터링)

JobMatcher ν΄λž˜μŠ€κ°€ λ‹΄λ‹Ή:

  1. κ²½λ ₯ 필터링: "μ‹ μž…" 쑰건에 λ§žλŠ” 곡고만 선택
  2. 고용 ν˜•νƒœ 필터링: 희망 고용 ν˜•νƒœ(μ •κ·œμ§, 인턴 λ“±)에 맞좰 필터링
  3. 직무 λ§€μΉ­: 1μˆœμœ„ β†’ 2μˆœμœ„ β†’ 3μˆœμœ„ 희망 직무와 곡고 비ꡐ
  4. ν•™λ ₯ 쑰건 필터링: μ§€μ›μž ν•™λ ₯ 쑰건 μΆ©μ‘± μ—¬λΆ€ 확인

μ •λ ¬ μš°μ„ μˆœμœ„:

  • NULL ν•„λ“œ 개수 (완성도 높은 곡고 μš°μ„ )
  • 직무 μš°μ„ μˆœμœ„ (1μˆœμœ„ λ§€μΉ­ > 2μˆœμœ„ > 3μˆœμœ„)
  • ν•™λ ₯ 쑰건 정확도
  • 고용 ν˜•νƒœ λ§€μΉ­ 점수
  • νšŒμ‚¬λͺ… (동점 μ‹œ)

지원 직무:

  • 데이터 뢄석가
  • 데이터 μ‚¬μ΄μ–Έν‹°μŠ€νŠΈ
  • 데이터 μ—”μ§€λ‹ˆμ–΄
  • AI μ—”μ§€λ‹ˆμ–΄
  • AI 기획자
  • AI 연ꡬ원

이메일 생성

EmailTemplateGeneratorκ°€ λ‹΄λ‹Ή:

  • ν…œν”Œλ¦Ώ 기반 생성: test_email.html κΈ°λ³Έ ꡬ쑰 μ‚¬μš©
  • 동적 컨텐츠 μ‚½μž…: 맀칭된 곡고 μΉ΄λ“œλ₯Ό HTML둜 λ³€ν™˜ν•˜μ—¬ μ‚½μž…
  • νšŒμ‚¬ 둜고 ν‘œμ‹œ: 20개 이상 ν•œκ΅­ μ£Όμš” κΈ°μ—… 둜고 URL λ§€ν•‘
  • D-day 계산: λ§ˆκ°μΌκΉŒμ§€ 남은 일수 μžλ™ 계산
  • 고용 ν˜•νƒœ νƒœκ·Έ: 색상별 뱃지 생성
    • μ‹ μž…: ν•˜λŠ˜μƒ‰
    • κ²½λ ₯: λ³΅μˆ­μ•„μƒ‰
    • μ •κ·œμ§: 녹색
    • 인턴: λ…Έλž€μƒ‰
    • 계약직/μ „ν™˜ν˜•: 보라색
  • μ„ ν˜Έ κΈ°μ—… ν‘œμ‹œ: μ§€μ›μžκ°€ μ„ νƒν•œ λŒ€κΈ°μ—… 곡고에 ⭐ λ³„ν‘œ μΆ”κ°€

Google Sheets 데이터 ν˜•μ‹

μ„€λ¬Έ 응닡 μ‹œνŠΈμ— ν•„μš”ν•œ 컬럼:

컬럼λͺ… μ„€λͺ… μ˜ˆμ‹œ
성함 μ§€μ›μž 이름 홍길동
이메일 μ£Όμ†Œ μˆ˜μ‹  이메일 example@gmail.com
μ°Ύκ³  계신 곡고의 κ²½λ ₯ 쑰건을 μ„ νƒν•΄μ£Όμ„Έμš”. κ²½λ ₯ 쑰건 μ‹ μž…
희망 직무 1μˆœμœ„ (ν•„μˆ˜μ‘λ‹΅) 1μˆœμœ„ 직무 데이터 뢄석가
희망 직무 2μˆœμœ„ 2μˆœμœ„ 직무 데이터 μ‚¬μ΄μ–Έν‹°μŠ€νŠΈ
희망 직무 3μˆœμœ„ 3μˆœμœ„ 직무 AI μ—”μ§€λ‹ˆμ–΄
희망 고용 ν˜•νƒœ (λ³΅μˆ˜μ„ νƒ) 고용 ν˜•νƒœ μ •κ·œμ§, 인턴
μ°Ύκ³  계신 곡고의 ν•™λ ₯ 쑰건을 μ„ νƒν•΄μ£Όμ„Έμš”. ν•™λ ₯ 쑰건 학사 4λ…„μ œ
λŒ€κΈ°μ—… κ·Έλ£Ή 선택 μ»¬λŸΌλ“€ μ„ ν˜Έ κΈ°μ—…κ΅° μ‚Όμ„±, SK, LG...

μ£Όμš” 파일 μ„€λͺ…

전체 μ›Œν¬ν”Œλ‘œμš°λ₯Ό μ‘°μœ¨ν•˜λŠ” 메인 μ‹€ν–‰ νŒŒμΌμž…λ‹ˆλ‹€.

  • ν™˜κ²½ λ³€μˆ˜ 검증
  • 데이터 λ‘œλ“œ 및 필터링
  • 이메일 λ°œμ†‘ 및 κ²°κ³Ό 기둝
  • 톡계 좜λ ₯

곡고 λ§€μΉ­ λ‘œμ§μž…λ‹ˆλ‹€.

  • match_jobs_for_user(): μ‚¬μš©μžλ‹Ή μƒμœ„ 10개 곡고 μΆ”μ²œ
  • 4단계 필터링 μ‹œμŠ€ν…œ
  • ν‚€μ›Œλ“œ 기반 직무λͺ… λ§€μΉ­
  • μ„ ν˜Έ κΈ°μ—… μš°μ„ μˆœμœ„ 처리

κ°œμΈν™”λœ HTML 이메일을 μƒμ„±ν•©λ‹ˆλ‹€.

  • ν…œν”Œλ¦Ώ μΉ˜ν™˜ (이름, 곡고 리슀트)
  • νšŒμ‚¬ 둜고 μ‚½μž…
  • D-day 계산
  • λ°˜μ‘ν˜• λͺ¨λ°”일 λ””μžμΈ

Gmail API μ €μˆ˜μ€€ μž‘μ—…μ„ μ²˜λ¦¬ν•©λ‹ˆλ‹€.

  • OAuth 2.0 인증 흐름
  • 토큰 캐싱 및 κ°±μ‹ 
  • MIME λ©”μ‹œμ§€ 생성
  • 이메일 λ°œμ†‘

Google Sheets 데이터 μž‘μ—…μ„ λ‹΄λ‹Ήν•©λ‹ˆλ‹€.

  • load_recipients_from_sheet(): μ„€λ¬Έ 응닡 데이터 λ‘œλ“œ
  • write_status_to_sheet(): λ°œμ†‘ μƒνƒœ 및 νƒ€μž„μŠ€νƒ¬ν”„ 기둝

μ±„μš© 곡고 데이터 ν˜•μ‹

data/ ν΄λ”μ˜ JSON 파일 ꡬ쑰:

{
  "group_name": "쿠팑",
  "company_name": "쿠팑",
  "job_title": "[μΏ νŒ‘λ‘œμ§€μŠ€ν‹±μŠ€μ„œλΉ„μŠ€] λ‘œμΌ“μ„€μΉ˜ A/S 운영 λ‹΄λ‹Ήμž",
  "position_name": "λ‘œμΌ“μ„€μΉ˜ A/S 운영 λ‹΄λ‹Ήμž",
  "processed_position_name": "데이터 뢄석가",
  "min_experience_level": "μ‹ μž…",
  "employment_type": "μ •κ·œμ§",
  "min_education_level": "학사 4λ…„μ œ",
  "application_start_date": "2025-09-12",
  "application_deadline_date": "2025-10-15",
  "team_introduction": "νŒ€ μ†Œκ°œ...",
  "job_duties": "λ‹΄λ‹Ή 업무...",
  "qualifications": "자격 μš”κ±΄...",
  "preferred_qualifications": "μš°λŒ€ 사항...",
  "work_location": "μ„œμšΈ",
  "recruitment_process": "μ„œλ₯˜μ „ν˜• - μ „ν™”λ©΄μ ‘ - λŒ€λ©΄λ©΄μ ‘",
  "application_link": "https://..."
}

μ£Όμš” κΈ°λŠ₯ 상세

속도 μ œν•œ (Rate Limiting)

  • 10개 이메일 λ°œμ†‘λ§ˆλ‹€ 2초 λŒ€κΈ°
  • Gmail API ν• λ‹ΉλŸ‰ 초과 λ°©μ§€

였λ₯˜ 처리

  • 각 이메일 λ°œμ†‘ μ‹€νŒ¨ μ‹œ 계속 μ§„ν–‰
  • 였λ₯˜ λ©”μ‹œμ§€ Google Sheets에 기둝 (μ΅œλŒ€ 50자)
  • μ΅œμ’… 성곡/μ‹€νŒ¨ 톡계 좜λ ₯

μˆ˜μ • ν•„μš”μ‹œ

  • λ‹€μŒκ³Ό 같이 ν™•μž₯ κ°€λŠ₯ν•©λ‹ˆλ‹€:
  1. λ‹€λ₯Έ κΈ°μ—… 곡고 μΆ”κ°€: data/ 폴더에 동일 ν˜•μ‹μ˜ JSON 파일 μΆ”κ°€
  2. μƒˆλ‘œμš΄ 직무 μΆ”κ°€: job_matcher.py:37-42의 JOB_ROLE_KEYWORDS λ”•μ…”λ„ˆλ¦¬ μˆ˜μ •
  3. νšŒμ‚¬ 둜고 μΆ”κ°€: template_generator.py:158-181의 _load_company_logos() λ©”μ„œλ“œμ— URL μΆ”κ°€
  4. 이메일 λ””μžμΈ λ³€κ²½: test_email.html ν…œν”Œλ¦Ώ μˆ˜μ •

문제 ν•΄κ²°

credentials.json 였λ₯˜

FileNotFoundError: credentials.json not found

β†’ Google Cloud Consoleμ—μ„œ OAuth 인증 정보λ₯Ό λ‹€μš΄λ‘œλ“œν•˜μ—¬ ν”„λ‘œμ νŠΈ λ£¨νŠΈμ— μ €μž₯ν•˜μ„Έμš”.

Gmail API ν• λ‹ΉλŸ‰ 초과

HttpError 429: Quota exceeded

β†’ main.pyμ—μ„œ λŒ€κΈ° μ‹œκ°„ 늘리기 (time.sleep(2) β†’ time.sleep(5))

About

No description, website, or topics provided.

Resources

Stars

3 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages