안녕하세요, 코린이의 코딩 학습기 채니 입니다.
개인 포스팅용으로 내용에 오류 및 잘못된 정보가 있을 수 있습니다.
STT (Speech-To-Text) 기술을 사용해야하는 프로젝트가 생겨서 Google, Naver, Azure가 제공하는 STT 서비스를 기술 검토해보았다.
검토사항은 아래와 같다.
- 스트리밍 처리가 가능한가
- 한국어를 가장 잘 인식할 수 있는가
- 가격은 저렴한가
Google Cloud
- 125개 언어 지원
- 스트리밍의 경우, 기본적으로 최대 5분까지 스트림을 열어둘 수 있음
- 무한 스트리밍 처리도 가능
- Google Cloud 공식 홈페이지
가격
표준 동적 일괄 인식은 낮은 긴급도로 오디오를 처리하는 기능으로 현재는 굳이 필요 없다고 판단하였다.
따라서 표준 인식 모델 & 인식(로깅) 서비스를 이용한다고 가정했을 때 (한 달에 0~500,000분까지 사용했을 경우) 가격은 아래와 같다.
- 1분: $0.016 (약 22.14원)
- 1시간: $0.96 (약 1,328원)
리소스 한도
서비스 이용해보기 (v2)
나는 Python과 친하지 않아서.. 가상환경 생성하는 것부터 예제코드 적용까지를 정리해보도록 하겠다.
Anaconda 설치 및 설정 (이미 설치되어 있는 경우 생략 가능)
$ brew install --cask anaconda
$ /opt/homebrew/anaconda3/bin/conda init zsh
$ source ~/.zshrc
가상환경 생성
$ conda create -n googleCloudSttSample python=3.11
⭐️ 반드시 python 버전을 3.11
로 설치 ⭐️
Google Cloud STT 서비스는 ADC (ADC란) 로만 인증 처리가 가능하다.
따라서 gcloud (gcloud 설치 가이드) 라는 것을 설치하고 gcloud를 통해 인증 처리를 해주는데, 이 때 지원되는 Python 버전이 3.8~3.12이기 때문에 반드시 Python 버전을 3.11로 설치해준다.
(3.12도 가능하겠지만 "기본 설치 스크립트는 CPython의 Python 3.11을 설치하도록 제공" 한다는 구글 가이드에 따라 3.11로 설치)
패키지 설치
$ brew install portaudio
requirements.txt 파일 생성
cachetools==5.5.0
certifi==2024.8.30
charset-normalizer==3.4.0
google-api-core==2.22.0
google-auth==2.35.0
google-cloud-speech==2.28.0
googleapis-common-protos==1.65.0
grpcio==1.67.1
grpcio-status==1.67.1
idna==3.10
proto-plus==1.25.0
protobuf==5.28.3
pyasn1==0.6.1
pyasn1_modules==0.4.1
PyAudio==0.2.14
requests==2.32.3
rsa==4.9
urllib3==2.2.3
$ pip install -r requirements.txt
gcloud CLI 설치 (Mac)
(Google Cloud 프로젝트를 모두 생성했다고 가정 - 프로젝트 생성부터 해야한다면 stt 서비스 가이드 를 참조하자)
- 명령줄에서 다음 명령어 실행
$ curl https://sdk.cloud.google.com | bash
- 메시지가 표시되면 파일 시스템에서 위치(일반적으로 홈 디렉터리)를 선택하여
google-cloud-sdk
하위 디렉터리 생성 - gcloud CLI 개선을 위해 익명 사용 통계를 보내려면 메시지가 표시될 때
Y
로 응답 - PATH에 glcoud CLI 명령줄 도구 추가하고, 명령어 완성을 사용 설정하려면 메시지가 표시될 때
Y
로 응답- 업데이트할 rc 파일 경로를 묻는 경우 →
Enter
- 업데이트할 rc 파일 경로를 묻는 경우 →
- 셸 재실행
$ exec -l $SHELL
- Google Cloud CLI 환경 초기화
$ gcloud init
- 구글 계정 로그인
- default로 사용할 프로젝트 선택 (없는 경우 새로 생성)
- 로컬 셸 사용 시, 사용자 계정에 대한 로컬 인증 자격 증명 생성
$ gcloud auth application-default login
예제코드
from google.cloud.speech_v2 import SpeechClient
from google.cloud.speech_v2.types import cloud_speech as cloud_speech_types
import pyaudio
import time
import threading
PROJECT_ID = "PROJECT_ID"
RATE = 16000
CHUNK_SIZE = 12800
def print_every_second():
current_time = time.strftime("%H:%M:%S", time.localtime())
print(f"1초마다 출력됩니다. 현재 시간: {current_time}")
threading.Timer(1, print_every_second).start()
def get_microphone_stream():
audio = pyaudio.PyAudio()
try:
return audio.open(
format=pyaudio.paInt16,
channels=1,
rate=RATE,
input=True,
frames_per_buffer=CHUNK_SIZE
)
except OSError as error:
print(f"[WARNING]: Unable to access microphone. {error}")
def save_text_to_file(text):
if text.strip():
with open("transcription_output.txt", "a", encoding="utf-8") as file:
file.write(f"{text}\n")
def transcribe_streaming_v2() -> cloud_speech_types.StreamingRecognizeResponse:
# Instantiates a client
client = SpeechClient()
stream = get_microphone_stream()
# 인식 요청 처리에 대한 정보를 저장해준다.
recognition_config = cloud_speech_types.RecognitionConfig(
explicit_decoding_config=cloud_speech_types.ExplicitDecodingConfig(
sample_rate_hertz=RATE,
encoding=cloud_speech_types.ExplicitDecodingConfig.AudioEncoding.LINEAR16,
audio_channel_count=1
),
language_codes=["ko-KR"],
model="long",
features=cloud_speech_types.RecognitionFeatures(
# 구두점 추가
enable_automatic_punctuation=True,
# 욕설 걸러내기 (fuck -> f***)
profanity_filter=True,
),
# 모델을 chirp or chirp_2 이용해야하는데 해당 모델은 비스트리밍에서만 지원
# translation_config=cloud_speech_types.TranslationConfig(
# target_language="en-US"
# )
)
# 스트리밍 요청에 대한 구성 정보를 제공해준다.
streaming_config = cloud_speech_types.StreamingRecognitionConfig(
config=recognition_config,
streaming_features=cloud_speech_types.StreamingRecognitionFeatures(
# 중간 결과가 클라이언트에 스트리밍 되지 않도록 함
# "여러분 안녕하세요"를 말했다고 가정했을 때 클라이언트에 아래와 같이 전달됨
# True -> 여러분. 안녕하세요. 여러분 안녕하세요.
# False -> 여러분 안녕하세요.
interim_results=True,
enable_voice_activity_events=True,
# voice_activity_timeout=cloud_speech_types.StreamingRecognitionFeatures.VoiceActivityTimeout(
# # 스피치가 시작하고 5초 동안 아무 말이 없으면 스트림을 닫음
# speech_start_timeout=duration_pb2.Duration(seconds=5),
# # 스피치를 감지하고 10초 동안 아무 말이 없으면 스트림을 닫음
# speech_end_timeout=duration_pb2.Duration(seconds=10)
# )
)
)
# 인식기와 스트리밍 유형을 지정해준다. (음성을 실시간으로 인식하기 위한 준비 단계)
config_request = cloud_speech_types.StreamingRecognizeRequest(
recognizer=f"projects/{PROJECT_ID}/locations/global/recognizers/_",
streaming_config=streaming_config,
)
def requests():
yield config_request
print_every_second()
while True:
try:
audio_chunk = stream.read(CHUNK_SIZE)
yield cloud_speech_types.StreamingRecognizeRequest(audio=audio_chunk)
except Exception:
pass
# Transcribes the audio into text
responses_iterator = client.streaming_recognize(requests=requests())
for response in responses_iterator:
if not response.results:
continue
result = response.results[0]
if not result.alternatives:
continue
if hasattr(result, "is_final") and result.is_final:
transcript = result.alternatives[0].transcript
print(f"Transcript: {transcript}")
save_text_to_file(transcript)
try:
transcribe_streaming_v2()
except Exception as error:
print(f"[ERROR]: {error}")
공식 홈페이지의 오디오 스트리밍 예제 코드를 참고하여 마이크로 말하는 음성에 대해 텍스트로 변환하는 python 코드를 짜보았다.
pyaudio로 마이크 스트림을 만들고 예제코드와 Cloud STT V2 documentiation를 참고하여 필요한 설정을 하였다.
위 코드는 5분 이상 스트림을 열어두는 경우
10 ABORTED: Max duration of 5 minutes reached for stream.
오류가 발생한다.
만일 무한 스트리밍을 구현하고 싶다면, Python 무한 스트리밍 예제 코드를 참고해보자.
(구글에서 제공하는 예제 코드인데.. 오류 발생하긴 함..;)
성능 테스트
샘플동영상을 10분 정도 틀어놓고 얼마나 잘 인식하는지 테스트 해보았다.
결과 값은 아래 파일을 참고하자!
구글이 가장.. 성능이 별로였다. (내가 코드를 잘못 짰나? 싶을 정도로 별로였는데 똑같은 음성으로 구글 테스트 페이지에서 테스트해봤는데 똑같았음)
음성 인식을 잘 못하고 소음이 조금이라도 섞이면 정신을 못차리더라..ㅠ (한국어 기준)
'AI' 카테고리의 다른 글
STT) Azure STT 기술 검토 (0) | 2024.12.10 |
---|---|
STT) Naver Cloud(Clova) STT 기술 검토 (1) | 2024.12.10 |