본문 바로가기

Project/MovieClip

🔥 배우의 영어로된 소개글을 한글로 번역하기

 

📌 Google Translate API를 사용하여 배우 소개글(Biography)을 번역하는 과정

 

https://cloud.google.com/translate?hl=ko

 

https://cloud.google.com/translate?hl=ko

 

cloud.google.com

 

🎯 목표

  • TMDB API에서 배우의 정보를 가져오면 영어로 된 biography(소개글)가 기본 제공
  • Google Translate API를 활용해 자동으로 한글 번역된 내용을 UI에 표시
  • 번역된 내용을 UITableViewCell (PeopleOverviewTableViewCell) 에 적용

 

🛠 1. 프로젝트에서 Google Translate API 사용하기

Google Translate API를 사용하려면 Google Cloud Console에서 API 키를 받아야 함

🔹 API 키 발급 절차

  1. Google Cloud Console에 접속:
    👉 Google Cloud Console
  2. 새 프로젝트 생성 또는 기존 프로젝트 선택
  3. "번역 API (Cloud Translation API)" 사용 설정
    • "API 및 서비스" > "API 및 서비스 사용 설정"
    • "Cloud Translation API" 검색 후 활성화
  4. API 키 생성
    • "API 및 서비스" > "사용자 인증 정보"
    • "사용자 인증 정보 만들기" 클릭
    • "API 키" 생성 후 키 복사 (해당 키를 사용하여 API 요청)

 

🚀 2. Swift에서 Google Translate API 호출하기

https://cloud.google.com/translate/docs/reference/rest/v2/translate

 

Method: translate  |  Cloud Translation  |  Google Cloud

Send feedback Method: translate Stay organized with collections Save and categorize content based on your preferences. Translates input text, returning translated text. HTTP request POST https://translation.googleapis.com/language/translate/v2The URL uses

cloud.google.com

 

NetworkManager 클래스에서 생성

// 구글 클라우드 번역 API를 통해 번역하는 메서드
    func translateText(_ text: String) async -> String {
        let targetLanguage = "ko" // 한국어(Korean)로 번역
        let sourceLanguage = "en" // 영어(English)로부터 번역
        
        // ✅ API 요청 URL 생성
        let urlString = "https://translation.googleapis.com/language/translate/v2?key=\(Constants.googleAPI_KEY)"
        guard let url = URL(string: urlString) else {
            return text         // ✅ 번역 실패 시 원본 반환
        }
        
        // ✅ 요청 데이터 설정 (JSON Body)
        let parameters: [String: Any] = [
            "q": text, // 번역할 텍스트
            "source": sourceLanguage, // 원본 언어
            "target": targetLanguage, // 번역할 언어
            "format": "text"
        ]

        guard let jsonData = try? JSONSerialization.data(withJSONObject: parameters) else {
            return text
        }
        
        // ✅ URLRequest 설정
        var request = URLRequest(url: url)
        request.httpMethod = "POST"
        request.setValue("application/json", forHTTPHeaderField: "Content-Type")
        request.httpBody = jsonData
    
        do {
            let (data, _) = try await URLSession.shared.data(for: request)
            let json = try JSONSerialization.jsonObject(with: data, options: []) as? [String: Any]

            if let data = json?["data"] as? [String: Any],
               let translations = data["translations"] as? [[String: Any]],
               let translatedText = translations.first?["translatedText"] as? String {
                return translatedText // ✅ 번역 결과 반환
            } else {
                return text // ✅ 번역 실패 시 원본 반환
            }
        } catch {
            return text
        }
    }

 

 

🚀 3. PeopleDetatilViewController에서 번역 실행 

배우의 biography를 먼저 번역하여 한글로 번환된 데이터를 koreanBio에 저장

class PeopleDetatilViewController: UIViewController {
    
    ...
    // ✅ 번역된 소개글 저장 
    private var koreanBio: String = ""
    
    ... 
    
    // MARK: - Function
    private func fetchedPeopleDetailInfo() {
        Task {
            do {
                let peopleInfo = try await NetworkManager.shared.getPeopleDetailInfo(peopleID: peopleID)
                let socialLinks = try await NetworkManager.shared.getPeopleExternalIDs(peopleID: peopleID)
                
                // ✅ biography 번역
                let translatedBio = await NetworkManager.shared.translateText(peopleInfo.biography ?? "정보 없음 😅")
                
                DispatchQueue.main.async { [self] in
                    
                    self.peopleDetail = peopleInfo
                    self.socialLinks = socialLinks
                    
                    // ✅ 번역 할당
                    self.koreanBio = translatedBio
                    
                    guard let peopleDetail = self.peopleDetail else {
                        print("❌ no peopleDetail")
                        return
                    }
                   
                    self.configureDetailHeaderView()
                    self.peopleDetailHeaderView?.configure(with: peopleDetail, socialLinks: socialLinks)
                    
                    self.peopleTableView.reloadData()
                }
            } catch {
                print("❌ 데이터 로드 실패: \(error)")
            }
        }
    }
/ MARK: - Extension
extension PeopleDetatilViewController: UITableViewDelegate, UITableViewDataSource {
	...
    
    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        
        let sectionType = PeopleDetailSection.allCases[indexPath.section]
        
        switch sectionType {
            
        case .overview:
            
            guard let cell = tableView.dequeueReusableCell(withIdentifier: PeopleOverviewTableViewCell.reuseIdentifier, for: indexPath) as? PeopleOverviewTableViewCell else { return UITableViewCell() }
        
            let isExpanded = expandedCells.contains(indexPath.row)    
            
            // ✅ 번역된 소개글 유무에 조건에 맞춰 소개글 전달 (없는 경우도 있기 때문)
            if koreanBio.count != 0 {
                cell.configure(with: koreanBio, isExpanded: isExpanded)
            } else {
                cell.configure(with: "정보 없음 😅", isExpanded: isExpanded)
            }
        
            cell.delegate = self
            
            return cell
            
        case .filmography:
            break
        }
        
        let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath)
        cell.textLabel?.text = "Test"
        
        return cell
        
    }
    ...

 

 

🚀 4. PeopleOverviewTableViewCell 에서 configure 메서드 구현 

PeopleDetatilViewController로 부터 전달 받은 content을 overviewLabel에 할당

class PeopleOverviewTableViewCell: UITableViewCell {
    
    ...
    // MARK: - Function
    func configure(with content: String, isExpanded: Bool) {
        
        overviewLabel.text = content
        self.isExpanded = isExpanded
        
        overviewLabel.numberOfLines = isExpanded ? 0 : 5   // // ✅ 확장 여부에 따라 줄 수 변경
        expandButton.setTitle(isExpanded ? "접기" : "더보기", for: .normal)
    }