apple/WWDC

SpeechAnalyzer로 앱에 고급 음성 텍스트 변환 기능 가져오기 (Bring advanced speech-to-text capabilities to your app with SpeechAnalyzer) - WWDC25

lgvv 2025. 7. 14. 07:13

SpeechAnalyzer로 앱에 고급 음성 텍스트 변환 기능 가져오기 (Bring advanced speech-to-text capabilities to your app with SpeechAnalyzer) - WWDC25 

 

 

 

더욱 발전된 음성 텍스트 변환 API 및 기술인 SpeechAnalyzer가 올해 도입되었음.

 

  • 이번 세션에서는 SpeechAnalyzer API 및 이와 관련된 핵심 개념을 살펴볼 것
  • API의 기반이 되는 모델에 도입된 새기능에 관해 간단히 설명
  • 마지막으로 API 사용 방법과 데모 앱을 만나 볼 예정.

 

 

다양한 앱에서 이미 해당 기능을 사용하고 있음.

이를 Apple Intelligence와 결합하면 통화 요약과 같은 기능을 구현할 수 있음.

해당 API를 활용해서 실시간으로 음성을 글로 바꾸는 기능을 만들 예정.

 

 

 

자동 음성 인식(ASR)이라고 불리는 음성 텍스트 변환은 실시간으로 말하기 또는 녹음된 음성을 사용해 텍스트 형식으로 변환하여 기계에서 텍스트를 쉽게 표시하고 해석할 수 있는 기술.

 

앱은 실시간으로 텍스트를 저장, 검색 또는 전송하거나 텍스트 기반의 LLM 모델로 전달할 수 있음.

 

 


iOS 10에서 SFSpeechRecognizer가 나왔고 Siri 음성 텍스트 변환 모델에 접근할 수 있게 하고 짧은 형태의 받아쓰기에 잘 작동했으며 리소스가 제한된 기기에서는 Apple의 서버를 사용할 수 있었지만 일부 사례에서는 충분히 대응하지 못해 사용자가 언어를 직접 추가해야 하는 불편함이 존재.

 

 

새로운 API로 더 많은 사용 사례를 지원하며 Swift의 장점을 활용해 음성 텍스트 변환 처리를 실행하고 사용자 기기의 assets도 관리할 수 있음.

 

 

새로운 API와 함께 새로운 음성 텍스트 변환 모델도 출시했는데 이 모델은 이미 Apple 플랫폼에서 여러 앱 기능을 지원하고 있음.

SFSpeechRecognizer보다 더 빠르고 유연하며 강의, 회의, 대화처럼 멀리서 들리는 긴 형태의 오디오에 유용함

 

 

새로운 API는 SpeechAnalyer를 비롯한 여러 클래스로 구성됨.

SpeechAnalyer는 분석 세션을 관리하는데 세션에 모듈 클래스를 추가해 특정 타입의 분석을 수행할 수 있음.

만약 세션에 trasncriber 모듈을 추가하면 음성 텍스트 변환을 처리하는 세션이 됨.

 

오디오 버퍼를 Analyzer 인스턴스에 전달하면 Tanscriber를 통해 음성 텍스트 변환 모델로 전달됨.

모델은 음성 오디오에 해당하는 텍스트를 예측한 후 일부 메타 데이터와 함께 텍스트를 애플리케이션으로 반환함.

이 과정은 비동기적으로 진행되는데, 오디오를 처리하는 것과 별개로 앱에서는 다른 작업을 통해 결과를 표시하거나 추가로 처리할 수 있음.

 

Swift의 AsyncSequence는 입력과 결과를 버퍼링하고 분리함.

 

 

입력과 결과를 연결하기 위해서 API는 대응되는 오디오의 타임 코드를 사용함.

실제로 모든 API 작업은 오디오 타임라인의 타임 코드를 통해 예약되므로 순서를 예측할 수 있고 호출 시기와 무관함.

타임 코드는 개별 오디오 샘플에서도 정확하기 때문.

 

Tanscriber에서 결과를 순서대로 제공한다는 점에 주목.

각 결과는 고유한 오디오 범위를 반영하며 겹치지 않음.

 

 

음성 텍스트 변환은 일반적으로 이 프로세스를 따라 진행되며, 특정 오디오 범위 내에서 반복적인 변환을 수행할 수도 있음.

앱에서 UI에 즉각적으로 반영하고 싶을 때 대략적인 결과를 보여준 후 몇 초 이내에 더 나은 결과를 점진적으로 보여줄 수도 있음.

 

 

즉각적으로 표시되는 결과를 Volatile results(임시 결과)라고 부름.

Volatile results(임시 결과)는 말하자마자 바로 제공되지만 정확도가 떨어짐.

하지만 모델인 맥락과 오디오를 더 확보함에 따라 변환 내용을 개선하고 결국에는 최선의 결과를 얻어 Transcriber에서 마지막으로 최종 결과를 전달하게 됨.

 

Finalized result를 반환한 후에는 해당 범위에 대해서 더 이상 결과를 전달하지 않고 다음 범위로 이동하게 됨.

 

 

나중에 생성된 더 좋은 결과가 이전 결과를 대체하면서 타임 코드도 바뀜.

이는 임시 결과를 활성화 했을때만 나타나면 Tanscriber는 최종 결과만 전달하며 이전 결과를 대체하지 않음.

 

파일만 읽고 변환만 소리를 음성으로 변환만 담당하는 것이라면 하나의 함수만으로 transcription을 구축할 수 있음.

이런 작업에는 임시 결과 처리나 높은 동시성이 필요하지 않기 때문에임.

 

 

transcriber 모듈을 만들고 변환할 언어의 Locale을 알려줌.

이후에 결과를 위해 AsnycSequece를 사용하고 reduce를 이용해 연결.

결과가 끝나면 finish를 호출하고 결과를 반환하면서 종료함.

 

 

SpeechTransciber model이 가진 장점으로는 Apple이 새롭게 설계한 모델로 구동되며 다양한 useCase를 지원함

이 모든것은 on device model로 구현되었음.

 

 

SpeechTransciber는 강력한 텍스트 변환 모델을 제공하므로 이러한 모델을 직접 만들거나 관리하지 않아도 됨.

새로운 AssetInventory API를 통해 관련한 모델 Asset을 설치하면 됨.

 

필요할 때 다운로드 할 수 있고, 모델을 시스템 스토리지에 저장되며 앱의 다운로드 또는 스토리지 용량을 늘리지 않으며, 런타임에 메모리 크기도 늘어나지 않음.

앱이 아닌 메모리 외부 공간에서 작동해서 메모리를 과도하게 사용할까봐 걱정하지 않아도 됨.

 

 

SpeechTranscriber는 현재 이러한 언어를 음성에서 텍스트로 변환할 수 있고 추후에 지원 언어가 추가될 예정.

 

일부 하드웨어 요구사항이 존재하는데 지원되지 않는 언어나 기기가 필요한 경우를 대비해 Apple에서는 DictationTranscriber라는 transcriber 클래스를 제공.

이 클래스는 iOS 10의 온디바이스 SFSpeechRecognizer와 동일한 언어, 음성 텍스트 변환 모델 및 디바이스를 지원하지만 SFSpeechRecognizer보다 더 향상된 클래스로써 사용자에게 설정으로 이동하여 특정 언어에 대해 Siri나 키보드 받아쓰기를 켜도록 안내하지 않아도 됨.

 

 

Transcription은 총 세 단계로 나뉘는데, SpeechTransciber를 구성하고, model이 존재하는지 확인한 다음 결과를 처리하면 됨.

 

 

Locale의 언어 코드는 음성에서 텍스트로 변환 결과를 받고 싶은 언어에 해당함.

임시 결과는 실시간 추측용으로 최종 결과가 가장 정확한 추측임. 

 

audioTimeRange 옵션을 사용하면 오디오와 동기화할 수 있으며, 다른 옵션들도 존재함

 

음성에서 텍스트 변환 모델을 준비할 수 있음.

 


이후에 레퍼런스를 AsyncStream 입력에 저장하고 analyzer를 시작하여 SpeechTranscriber 설정을 마무리함.

 

 

이제는 모델을 얻는 방법에 대해서 알아볼 것임.

ensureModel 메서드에서 우리가 원하는 언어의 변환을 SpeechTranscriber가 지원하는지 검사하고, 해당 언어가 다운로드 및 설치되었는지도 함께 체크함.

 

해당 예제에서는 언어가 다운로드 되지 않았다면 AssetInventory에 요청을 전송해 다운로드함.

음성에서 텍스트를 변환하는건 완전히 온디바이스로 진행되지만 모델은 가져와야 함.

다운로드 요청의 progress 객체를 사용하면 진행중인 작업을 사용자에게 알릴 수 있음.

 

 

앱에서 지원할 수 있는 언어는 제한되어 있음. 제한을 초과한 경우 AssetInventory에 요청하여 하나 이상의 언어를 할당 해제해 공간을 확보할 수 있음.

 

 

위 형태로 Task를 옵저빙할 수 있음. 임시 결과와 최종 결과를 받기 위해 AttributedString 변수도 생성

 

 

result 객체에는 여러가지 객체들이 존재함

우선 text로 AttributedString이며 오디오 세그먼트에 대한 음성에 대한 텍스트 변환 결과임

또한 isFinal로 온전하게 변환이 되었는지 확인할 수 있음

또한 text의 시간에 대한 정보도 포함되어 있음.

 

 

오디오를 설정하는 방법에 대해서 알아볼 예정인데, 사용자가 `record`를 누를 때 호출되는 해당 메서드에서 오디오 권한을 요청한 다음에 시작함.

 

오디오 소스마다 출력 형식과 샘플링 속도가 달라서 SpeechTranscriber는 사용 가능한 bestAvailableAudioFormat을 제공해줌.

오디오 버퍼를 전환 단계로 전달하여 형식이 bestAvailableAudioFormat과 일치하도록 설정

그런 다음에 inputBuilder로 전달 

 

 

녹음을 중지할 때는 몇 가지 작업을 수행해야 하는데 audioEngine과 transcriber를 중지시킴

작업을 취소하고 analyzer 스트림에서 finalize를 호출해야하는데, 이 코드를 호출하면 임시 결과가 모두 최종 결과로 바뀜.

 

 

단순히 텍스트만 변환하는게 아니라 Apple Intelligence의 Foundation Models를 활용해 이야기가 끝나면 제목을 생성할 수도 있음.

파운데이션 모델 덕분에 제목도 쉽게 생성할 수 있음.

 

 

 

 

(참고)

https://www.youtube.com/watch?v=0m6dimDDj8M