SFSpeechRecognizer — 개요, API 및 iOS 통합

저자: IT Sectr 게시일: 2026-07-19 읽는 시간: 10 분

SFSpeechRecognizer는 iOS 생태계에서 Apple의 기본 음성 인식 API입니다. 이 프레임워크는 Speech.framework를 통해 기기의 ASR 엔진에 대한 액세스를 제공하며, 실시간 스트리밍 전사 및 일회성 오디오 파일 인식을 지원합니다. SFSpeechRecognizer는 iOS 10+, macOS 10.15+, watchOS 6+ 및 tvOS 17+에서 사용할 수 있습니다. iOS 17에서 Apple은 인터넷 연결 없이 음성 인식을 가능하게 하는 완전한 온디바이스 모드를 추가했습니다. Apple Speech Documentation, 2025에 따르면, SFSpeechRecognizer는 200,000개 이상의 App Store 애플리케이션에서 사용되며 영어에서 7%의 WER로 하루에 수백만 건의 요청을 처리합니다.

핵심 사항

  • SFSpeechRecognizer — iOS용 Apple의 기본 ASR API (iOS 10+)
  • 온디바이스 — iOS 17부터 인터넷 없는 인식, 러시아어 WER 12–14%
  • 스트리밍 — 실시간 부분 결과
  • 60개 이상 언어 — 러시아어, 영어, 중국어, 아랍어 등
  • Swift 네이티브 — AVFoundation, Combine, Swift Concurrency와 완전 통합

SFSpeechRecognizer란: 기능 개요

SFSpeechRecognizer는 특정 언어에 대한 음성 인식기를 나타내는 Speech.framework의 클래스입니다. Locale(ru_RU, en_US, zh_CN)로 초기화됩니다. SFSpeechRecognizer는 인식 요청(SFSpeechRecognitionRequest)을 관리하고 전사 및 메타데이터가 포함된 결과(SFSpeechRecognitionResult)를 반환합니다. 두 가지 유형의 요청을 지원합니다: SFSpeechAudioBufferRecognitionRequest(라이브 오디오 스트림) 및 SFSpeechURLRecognitionRequest(오디오 파일). 둘 다 SFTranscription을 반환합니다 — 대체 인식 가설의 배열입니다.

SFSpeechRecognitionResult에는 다음이 포함됩니다: bestTranscription(최상의 가설, SFTranscription), transcriptions(모든 대안), isFinal(최종/중간). SFTranscription에는 다음이 포함됩니다: formattedString(텍스트), segments(타임스탬프, 신뢰도, substringRange, alternativeSubstrings가 있는 SFTranscriptionSegment 배열). 각 세그먼트의 신뢰도(0..1) — 신뢰할 수 없는 부분을 필터링할 수 있습니다. Segments는 Speech.framework의 핵심 기능입니다: 신뢰도 점수와 함께 단어별 마크업을 제공합니다.

SFSpeechRecognizer 아키텍처: AVFoundation(오디오 캡처) → Audio Buffer → SFSpeechAudioBufferRecognitionRequest → SFSpeechRecognizer(ASR 엔진) → SFSpeechRecognitionResult → SFSpeechRecognitionTask(제어: cancel, finish, pause). Apple의 ASR 엔진은 하이브리드 아키텍처를 사용합니다: 온디바이스용 Conformer(인코더) + RNNT(디코더), 클라우드용 Transducer. 모델은 Apple Neural Engine(ANE)에 최적화되어 있습니다. A17 Pro에서 온디바이스 ASR은 RTF 0.3–0.6(실시간보다 빠름)으로 실행됩니다.

구성 요소목적iOS 버전
SFSpeechRecognizer기본 인식 클래스iOS 10+
SFSpeechAudioBufferRecognitionRequest라이브 오디오 스트림iOS 10+
SFSpeechURLRecognitionRequest오디오 파일(.wav, .m4a)iOS 10+
SFSpeechRecognitionTask요청 관리(cancel, finish)iOS 10+
온디바이스 인식오프라인 ASRiOS 17+
결합 인식하이브리드 온디바이스 + 클라우드iOS 17+

오디오 요구 사항: SFSpeechRecognizer는 LPCM(16kHz, 16bit, 모노) 또는 Opus(iOS 17+)를 허용합니다. AVFoundation은 모든 형식의 버퍼를 캡처할 수 있으며 요청이 자동으로 변환합니다. 최소 길이: 0.5초(무음 감지). 최대: 요청당 1분(클라우드) / 2분(온디바이스). 긴 전사의 경우 2–5초 오버랩으로 30–60초 청크로 오디오를 분할합니다.

SFSpeechRecognizer 설정 및 권한

사용자 권한: SFSpeechRecognizer에는 두 가지 명시적 권한이 필요합니다. NSMicrophoneUsageDescription(Privacy — Microphone Usage Description) — 마이크 액세스용. NSSpeechRecognitionUsageDescription(Privacy — Speech Recognition Usage Description) — 음성 인식 액세스용. 둘 다 사용자에게 이유를 설명하는 문자열입니다. SFSpeechRecognizer.requestAuthorization — 권한 대화상자를 표시합니다. 상태: notDetermined, denied, restricted, authorized. authorized 상태가 없으면 recognizer를 호출하면 오류 216(Speech framework error)이 반환됩니다.

가용성 확인: SFSpeechRecognizer.isAvailable — 현재 언어에 ASR을 사용할 수 있는지 확인합니다. iOS 16-에서는 isAvailable = false(인터넷 없음). iOS 17+에서는 온디바이스 언어의 경우 오프라인에서도 isAvailable = true. SFSpeechRecognizer.supportedLocales — 기기에서 지원하는 언어 목록을 가져오는 정적 메서드. 시작할 때마다 isAvailable을 확인하는 것이 좋습니다(사용자가 설정에서 Siri/받아쓰기를 비활성화할 수 있음). 가용성은 지역에 따라 다릅니다: 중국어 — 중국에서만, 아랍어 — UAE.

swift
// SFSpeechRecognizer 설정
import Speech

SFSpeechRecognizer.requestAuthorization { status in
    guard status == .authorized else { return }
}

let recognizer = SFSpeechRecognizer(locale: Locale(identifier: "ru_RU"))!
guard recognizer.isAvailable else {
    print("ASR을 사용할 수 없습니다. 설정에서 Siri와 받아쓰기를 활성화하세요")
    return
}

let request = SFSpeechAudioBufferRecognitionRequest()
request.requiresOnDeviceRecognition = true

오류 처리: SFSpeechRecognizer는 Error를 반환할 수 있는 completion handler와 함께 호출됩니다. 주요 오류: 203 — 인터넷 없음(클라우드, iOS 16-); 216 — 권한 없음(권한 없음); 301 — 오디오 오류(마이크/형식 문제); 401 — 서비스를 사용할 수 없음(서비스 과부하); 601 — 언어를 사용할 수 없음(기기에서 언어가 지원되지 않음). 온디바이스 iOS 17+의 주요 오류: 301(오디오), 601(언어). 항상 completion handler를 처리하세요 — 녹음 중 언제든지 오류가 발생할 수 있습니다.

마이크에서 라이브 음성 인식

라이브 ASR 파이프라인: AVAudioEngine(마이크 캡처) → installTap(오디오 버퍼) → request.append(buffer) → SFSpeechRecognizer → recognitionTask → delegate/resultHandler. AVAudioEngine은 낮은 지연 시간(마이크에서 버퍼까지 5–10ms)을 제공합니다. SFSpeechRecognitionDelegate: didHypothesizeTranscription(200–500ms마다 — 부분 텍스트), didFinishRecognition(최종 결과). Task.isFinishing — 인식이 완료되면 취소할 수 있습니다. 연속 인식(무한 받아쓰기)의 경우 isFinal 후에 새 작업을 만듭니다.

SFSpeechRecognitionTaskDelegate: 선택적 메서드. speechRecognitionDidDetectSpeech(음성 시작) — UI 표시용. didHypothesizeTranscription(중간 텍스트) — 말하는 동안 표시용. didFinishRecognition(최종 결과) — 텍스트 확정용. didFinishSuccessfully(성공/오류) — 완료용. didProcessAudio(오디오 버퍼 처리됨) — RMS 미터용. didHypothesizeTranscription을 구현하는 것이 좋습니다 — 사용자는 지연 없이 즉시 텍스트를 볼 수 있습니다. 최종 전사는 저장용입니다.

swift
// 라이브 음성 인식
let audioEngine = AVAudioEngine()
let request = SFSpeechAudioBufferRecognitionRequest()
request.shouldReportPartialResults = true

recognitionTask = recognizer.recognitionTask(with: request) { result, error in
    if let result = result {
        textView.text = result.bestTranscription.formattedString
    }
    if error != nil || result?.isFinal == true {
        audioEngine.stop()
        request.endAudio()
    }
}

let inputNode = audioEngine.inputNode
let recordingFormat = inputNode.outputFormat(forBus: 0)
inputNode.installTap(onBus: 0, bufferSize: 1024,
                     format: recordingFormat) { buffer, _ in
    request.append(buffer)
}
audioEngine.prepare()
try audioEngine.start()

연속 인식: “항상 듣기” 모드(음성 입력, 어시스턴트)의 경우 isFinal 후에 작업을 다시 시작해야 합니다. 루프 만들기: finishTask → request = SFSpeechAudioBufferRecognitionRequest() → recognitionTask = recognizer.recognitionTask(with: request). 간격을 피하려면 한 작업의 끝을 다음 시작과 겹치게 합니다(이전 작업이 끝나기 1–2초 전에 새 요청 시작). AVFoundation AVAudioSession — 동시 재생 및 녹음을 위해 .playAndRecord를 구성합니다. iOS 17+에서 온디바이스 연속 ASR은 시간당 2–5%의 배터리를 소비합니다(A15+).

오디오 파일 및 녹음 인식

SFSpeechURLRecognitionRequest — URL로 오디오 파일을 인식하기 위한 요청입니다. 지원 형식: .wav(16kHz, 16bit, 모노), .m4a(AAC), .mp4, .mov. 최대 길이: 클라우드 약 1분, 온디바이스 약 2분. 더 긴 파일의 경우 청크로 분할합니다(AVAssetExportSession + trim). SFSpeechURLRecognitionRequest는 스트리밍을 지원하지 않습니다(부분 결과 없음) — 최종 결과만. 파일로 부분 결과를 얻으려면 Audio Buffer Request로 변환합니다.

오디오 파일 전사 가져오기: SFSpeechRecognizer.recognitionTask(with: request) resultHandler. bestTranscription.formattedString을 추출합니다. 단어 수준 타임스탬프 — bestTranscription.segments의 segments(segment.duration, segment.timestamp, segment.substring). 세그먼트별 신뢰도 — 각 단어의 ASR 신뢰도(필터링에 사용). 대체 가설 — 신뢰도가 낮은 단어의 transcriptionFormatter 대안. 여러 화자가 있는 파일의 경우 SFSpeechRecognitionRequest는 여러 요청을 반환할 수 있습니다(화자당 하나, iOS 17+).

swift
// 오디오 파일 전사
let audioURL = Bundle.main.url(forResource: "recording", withExtension: "m4a")!
let request = SFSpeechURLRecognitionRequest(url: audioURL)
request.requiresOnDeviceRecognition = true

recognizer.recognitionTask(with: request) { result, error in
    guard let result = result, error == nil else {
        print("오류: \(error?.localizedDescription ?? "unknown")")
        return
    }

    let transcription = result.bestTranscription
    let text = transcription.formattedString
    let words = transcription.segments.map { segment in
        Word(text: segment.substring,
              start: segment.timestamp,
              duration: segment.duration,
              confidence: segment.confidence)
    }
}

긴 오디오 파일 분할: 1분 이상 파일의 경우 2–3초 오버랩(스티칭)으로 30–60초 청크로 분할합니다. AVAssetExportSession + CMTimeRange — 청크 내보내기. 대안: UISelectionView(사용자가 세그먼트 선택). 전사 스티칭: 텍스트 연결, 오버랩으로 스티칭(이전 청크의 마지막 2–3단어를 다음 청크의 처음 2–3단어와 비교 — 중복 제거). Vosk와 Whisper는 긴 오디오를 기본적으로 지원하지만 SFSpeechRecognizer는 지원하지 않습니다. 긴 전사의 경우 Whisper(Core ML)를 권장합니다 — 길이 제한이 없습니다.

온디바이스 대 클라우드: 모드 비교

온디바이스 모드(iOS 17+): request.requiresOnDeviceRecognition = true. ASR이 Apple Neural Engine(ANE)에서 로컬로 실행됩니다. 장점: 인터넷 불필요, 개인정보 보호(오디오가 기기를 떠나지 않음), 무료, 낮은 지연 시간(RTF 0.3–0.6). 단점: 낮은 정확도(WER 12–14% vs 7–12%), 요청당 2분 제한, 제한된 언어 세트(60개 언어 모두 온디바이스 사용 가능하지 않음). 온디바이스 모델은 기기에서 약 50–100MB를 차지하며 첫 번째 요청 시 다운로드됩니다.

클라우드(iOS 16-): request.requiresOnDeviceRecognition = false(또는 매개변수 없음). Apple 서버의 ASR — 더 정확함(WER 7% EN, 12% RU), 더 많은 언어, 요청당 최대 1분. 인터넷(WiFi 또는 셀룰러) 필요. Apple은 클라우드 ASR에 대해 개발자에게 요금을 부과하지 않습니다(무료). 제한: 애플리케이션당 분당 1회 요청(지정되지 않음), 하지만 Apple은 프로덕션 규모에서 제한할 수 있습니다. 클라우드 ASR은 SLA 없이 최선의 품질을 제공합니다. 엔터프라이즈 앱의 경우 Google Cloud ASR 또는 Whisper(Core ML)를 사용하세요.

매개변수온디바이스(iOS 17+)클라우드(iOS 10+)
인터넷 필요아니요
WER (EN)10–12%7%
WER (RU)12–14%12%
지연 시간(RTF)0.3–0.60.3–0.8(+네트워크)
최대 길이2분1분
개인정보 보호완전오디오가 기기를 떠남
무료

결합 인식(iOS 17+): request.requiresOnDeviceRecognition = false(인터넷 있음, 클라우드), = true(오프라인, 폴백). Apple이 자동으로 모드를 선택합니다. 정확도가 중요한 앱: NetworkMonitor(NWPathMonitor) 확인 — 인터넷 있으면 클라우드, 없으면 온디바이스. 개인정보가 중요한 앱: 항상 온디바이스. 전사: 클라우드(더 정확). 음성 입력: 온디바이스(더 빠름). 결합 권장: 80% 클라우드, 20% 온디바이스 폴백.

iOS 앱에서 SFSpeechRecognizer 활용

사용자 정의 키보드에서 음성 입력 — SFSpeechRecognizer를 키보드 확장(iOS 10+)에 통합. 사용자가 마이크 버튼을 누르면 ASR이 음성을 텍스트로 변환하여 텍스트 필드에 삽입합니다. 요구 사항: 부분 결과(실시간 텍스트 확인), 온디바이스(키보드는 인터넷 없이 작동해야 함). SFSpeechRecognizer + AVSpeechSynthesizer — 음성 입력 + 음성 출력. iOS 17+에서 사용자 정의 키보드의 경우 온디바이스를 사용합니다. 키보드 확장 제한: AVAudioEngine을 사용할 수 있지만 시간 제한이 있습니다(백그라운드 실행 제한).

회의 및 강의 전사 — 오디오를 녹음하고 전사하는 앱(Otter.ai, Rev, Apple Voice Memos). SFSpeechURLRecognitionRequest가 .m4a 파일을 처리합니다. 긴 녹음(30–60분)의 경우 — Whisper Core ML(길이 제한 없음). 타임스탬프가 있는 SFSpeechRecognizer segments — 오디오와 텍스트 동기화용(재생 중 텍스트 강조). 세그먼트별 신뢰도 — 신뢰할 수 없는 부분 표시용(노란색 강조). 화자 분할(누가 말했는지) — Apple이 API를 제공하지 않으므로 서버에서 pyannote-audio + Whisper를 사용합니다.

iOS 앱에서 음성 명령 — SFSpeechRecognizer + VGS 프레임워크(Voice Grammar Services)로 명령 실행: “설정 열기”, “메시지 보내기”, “불 켜기”. 문법 기반 인식: SFSpeechRecognitionRequest contextualStrings = 명령 배열. 명령 인식 정확도가 95%로 향상됩니다(자유 형식 85% 대비). SFSpeechRecognitionTask.cancel — 명령 실행 후 중단. VGS + SFSpeechRecognizer + Shortcuts — UI를 작성하지 않고 사용자 정의 음성 명령. 접근성: Voice Control(내장) + SFSpeechRecognizer(사용자 정의 명령).

swift
// 컨텍스트 문자열을 사용한 음성 명령
let request = SFSpeechAudioBufferRecognitionRequest()
request.requiresOnDeviceRecognition = true
request.shouldReportPartialResults = true
request.contextualStrings = ["open contacts", "send message",
                             "show notifications", "손전등 켜기"]

recognitionTask = recognizer.recognitionTask(with: request) { result, _ in
    guard let text = result?.bestTranscription.formattedString.lowercased() else { return }
    voiceCommands.first { text.contains($0) }.map { command in
        DispatchQueue.main.async { self.executeCommand(command) }
        recognitionTask?.cancel()
    }
}

의료 및 법률 앱에서 받아쓰기 — SFSpeechRecognizer로 음성으로 구조화된 문서 만들기. 도메인 적응: 의료/법률 용어가 포함된 contextualStrings(500개 이상 구문). SFSpeechRecognitionRequest.customLmProbability — contextualStrings 영향(0.1–1.0). 의료 받아쓰기의 경우 온디바이스 사용(환자 데이터 개인정보 보호). 의료 데이터로 미세 조정된 Whisper — 기본 SFSpeechRecognizer의 12% 대신 WER 5%의 대안. HIPAA 규정 준수: 온디바이스 모드(데이터가 기기를 떠나지 않음). 약속 전사 — SFSpeechURLRecognitionRequest + 화자 타임스탬프가 있는 segments.

자주 묻는 질문

SFSpeechRecognizer는 어떤 iOS 버전부터 지원되나요?

SFSpeechRecognizer는 iOS 10, macOS 10.15, watchOS 6 및 tvOS 17부터 사용할 수 있습니다. 온디바이스 모드는 iOS 17부터(requiresOnDeviceRecognition). iOS 10–16에서는 SFSpeechRecognizer가 Apple의 클라우드 서버를 통해서만 작동합니다(인터넷 필요). 모든 버전에서 명시적 사용자 권한이 필요합니다(NSMicrophoneUsageDescription + NSSpeechRecognitionUsageDescription). SFSpeechRecognizer.supportedLocales — 동적 목록, 지역 및 기기 모델에 따라 다릅니다.

SFSpeechRecognizer를 연속 인식에 사용할 수 있나요?

예, isFinal 후에 새 recognitionTask를 만들어 가능합니다. 연속 인식을 위해 이전 작업이 완료된 후 작업을 다시 시작합니다. iOS 17에서 온디바이스 연속 ASR은 시간당 2–5%의 배터리를 소비합니다(A15+). iOS 16-에서 연속 ASR은 인터넷이 필요합니다(트래픽 ~1MB/분). 진정한 연속 인식(항상 듣기)의 경우 Vosk(오프라인) 또는 Whisper Core ML을 사용하세요. SFSpeechRecognizer는 iOS 16-에서 항상 켜짐 모드를 지원하지 않습니다.

SFSpeechRecognizer에서 각 단어의 신뢰도를 얻는 방법은?

result.bestTranscription.segments를 사용하세요 — 각 SFTranscriptionSegment에는 단어의 confidence(Float 0..1)가 포함됩니다. segments[i].substring — 단어 텍스트. segments[i].confidence — 해당 단어의 ASR 신뢰도. confidence < 0.5인 단어는 신뢰할 수 없습니다 — UI에서 강조 표시하세요. segments[i].timestamp — 시작 시간(TimeInterval). segments[i].duration — 지속 시간. segments[i].alternativeSubstrings — 단어의 대체 인식 가설. 긴 파일의 경우 segments를 반복하면 수동 구문 분석 없이 단어별 신뢰도를 얻을 수 있습니다.

SFSpeechRecognizer가 오류 203을 반환하는 이유는?

203은 SFSpeechError.ErrorCode.opportunistic(클라우드 ASR용 인터넷 없음)입니다. iOS 16-에서 또는 request.requiresOnDeviceRecognition = false일 때 인터넷 없이 발생합니다. 해결책: 오프라인 작동을 위해 requiresOnDeviceRecognition = true(iOS 17+)로 설정합니다. iOS 16-에서는 NWPathMonitor를 사용 — 인터넷이 없을 때 “음성 인식에는 인터넷 연결이 필요합니다”라는 메시지를 표시합니다. 대안: 네트워크를 사용할 수 없을 때 폴백으로 Vosk(오프라인, iOS 12+)를 사용합니다.

SFSpeechRecognizer와 Whisper Core ML의 차이점은?

SFSpeechRecognizer — Apple 내장 API, 무료, 통합 쉬움, 하지만 길이 제한(1–2분), WER 정확도 7–14%, iOS 생태계만 해당. Whisper Core ML — 오픈소스(MIT), 99개 언어 지원, WER 6–10%, 길이 제한 없음, 하지만 수동 통합, Core ML 모델(39M–769M 매개변수), RTF 0.5–6(SFSpeechRecognizer보다 느림) 필요. SFSpeechRecognizer — 표준 음성 입력용. Whisper — 고정확도 긴 오디오 전사용.

요약

  • SFSpeechRecognizer — 내장 Apple ASR API, iOS 10+, 60개 이상 언어
  • 온디바이스 모드 — iOS 17+, 인터넷 불필요, 러시아어 WER 12–14%
  • 라이브 마이크 — AVAudioEngine + request.append(buffer) + 부분 결과
  • 오디오 파일 — SFSpeechURLRecognitionRequest, .m4a/.wav, 최대 1–2분
  • Segments — 단어별 타임스탬프 + 신뢰도(0..1)
  • 무료 — 제한 없음, Apple 요금 없음, 타사 SDK 없음
  • 용도 — 음성 입력, 전사, 명령, 접근성, 받아쓰기

턴키 방식의 모바일 애플리케이션을 개발해 드립니다

IT Sectr는 2017년부터 스타트업과 기업을 위한 iOS 및 Android 애플리케이션을 만듭니다. 저희가 상담해 드리고 최적의 솔루션을 제안하겠습니다.

프로젝트 논의

더 읽어보기