apple/WWDC

Foundation Models 프레임워크 만나보기(Meet the Foundation Models Framework) - WWDC25

lgvv 2025. 7. 6. 22:57

Foundation Models 프레임워크 만나보기(Meet the Foundation Models Framework) - WWDC25

 

Apple Intelligence에 숨겨진 온디바이스 대규모 언어 모델을 활용하는 방법에 대한 새로운 프레임워크 소개

 

Swift API를 통해 Applle Intelligence를 사용 가능한 LLM 모델에 접근할 수 있음.

 


온디바이스에서 개인 맞춤형 검색을 지원하거나 여행 앱에서 일정을 생성하거나 게임 속 캐릭터의 대화를 실시간으로 생성할 수도 있음.

 

콘텐츠 생성, 텍스트 요약, 사용자 입력에 대한 분석 등 다양한 작업에 최적화되어 있음

 

 

 

모든 작업은 온디바이스에 이뤄지기 때문에 보안적으로도 안전하며, 오프라인 상태에서도 작동함.

또한 해당 기능은 OS 내부에 위치해서 앱 용량도 늘어나지 않음.

 

 

 

프레임워크 전체에 대한 개요를 설명

 

 

  • The model
    • 모델에 대한 세부사항을 설명
    • 이번 세션에서 가장 중요한 부분
  • Guideed generation
    • 가이드 기반으로 생성을 요청하는 방법에 대한 설명
  • Sanpshot straming
    • 생성하는 동안 걸리는 지연 시간동안 보내는 시간을 사용자에게 적절히 대응할 수 있는 강력한 Streaming API를 소개
  • Tool calling
    • 모델이 앱에서 정의한 코드를 자율적으로 실행할 수 있는 Tool을 호출하는 기능에 대한 설명
  • Stateful sessions
    • 상태 기반으로 대화를 제공하는 방법
  • Developer experience
    • 프레임워크를 Apple 개발자 생태계에 원활하게 통합하는 방법 소개

 

 

 

모델에 프롬프트르 보내는 가장 좋은 방법은 Xcode에서 바로 시작하는 것

다양한 프롬프트를 시험해보며 가장 적합한 방식을 찾는 것은 LLM 개발시 가장 중요한 과정.

 

플레이그라운드에서 단순히 몇줄을 추가하는 것만으로도 온디바이스 모델에 프롬프트를 보낼 수 있음.

 

 

 

30억 개의 매개변수를 가진 LLM으로 각 매개변수는 2비트로 양자화되어 있음.

이 모델은 다른 OS에 포함된 어떤 모델들 보다 수십 배 이상 큼.

 

온디바이스 모델은 LLM이어도 결국은 디바이스에서 실행 가능한 규모의 모델임을 염두하는 것이 중요함.

요약, 추출, 분류, 등 다양한 용도에 최적화되어 있음.

 

온디바이스 모델은 서버급 LLM이 수행하는 세계의 모든 지식이나 고급 추론 작업을 위한 것이 아님.

 

 

온디바이스 규모의 모델은 작업 단위를 더 세세히 나눠서 처리해야 함.

해당 모델을 사용하면서 강점과 약점을 자연스럽게 파악할 수 있음.

 

 

컨텐츠 태깅 같은 일반적은 작업은 Foundation Models에서 Adapters로 제공되어 특정 도멩니에서 모델의 역량을 극대화 함.

 

또한 시간이 지남에 따라서 모델을 더 개선해 나감.

 

 

 

 

Guided generation에 대해서 알아볼건데 기본적으로 언어 모델은 구조화되지 않은 자연어 형태로 출력되어 사람은 읽기 쉽지만 앱 UI에 그대로 노출하기엔 어려운 부분이 존재함.

 

 

일반적인 해결책은 json이나 csv 파일처럼 구문 분석하기 쉬운 형태로 모델에 요청하는 것임.

 

 

하지만 이렇게 할 경우 금새 여러 문제들이 지속적으로 발생함.

무엇을 해야 하고 하지 말아야 하는지를 점점 더 구체적으로 추가해야 함.

 

 

결국 이 방법은 크게 효용가치가 없어서 컨텐츠를 추출하고 fetch하기 위해서 별도의 방법을 사용하게 됨.

모델이 확률적이기 때문에 구조적인 오류가 발생 가능하여 신뢰할 수가 없음.

 

 

 

 

가이드 기반 생성은 이에 대한 해결책을 제공함.

Foundation Models을 불러오면 @Generable 및 @Guide를 사용할 수 있음.

 

@Generable은 모델이 생성할 타입을 설명할 수 있게 해줌.

@Guide는 자연어 설명을 제공하고 생성 값을 프로그래밍 방식으로 제어할 수 있게 해줌.

 

 



@Generalble 타입을 설명하면 모델이 프롬프트에 응답해 해당 인스턴스를 생성

이렇게 사용할 경우 프롬프트에 출력 형식을 따로 지정할 필요가 없어지며, 프레임워크가 알아서 처리해 줌.

 

 

@Generable 타입은 문자열, 정수, 실수 등 기본 자료구조형으로 구성할 수 있음.

또한 다른 타입을 조합해서도 사용 가능하며, 재귀적으로 타입을 구성할 수도 있음.

생성형 UI와 같은 도메인에 강력하게 작용함.

 

 

@Generable을 사용하면, 내가 주어준 structure로 데이터가 나오는걸 보장함.

이에 따라 원하는 동작에 집중하고 간단한 프롬프트를 사용할 수 있음.

또한 이를 사용할 경우 모델의 정확도를 향상시키고, 추론 속도를 높이는 최적화도 가능함.

 

 

Foundation Models의 학습을 Apple의 OS에 정교하게 통합함으로써 가능해짐.

 

 

대규모 LLM을 사용해 본 경험이 있다면, 텍스트가 토큰이라는 짧은 문자 단위로 나타남.

일반적으로 스트리밍 형태로 출력시 토큰은 델타라는 타입으로 전달되지만 FoundationModels에서는 다른 방식을 사용함.

 

 

델타가 생성될 때 누적해서 처리하는건 개발자에게 책임이 있음.

델타가 들어오면 개발자가 이를 추가함. 점점 Accumulation은 커짐.

 

하지만 결과에 구조체 형태가 있을 때 문제가 생기는데, 델타가 생성될 때마다 문자열을 보여주려면 누적된 결과에서 구문을 분석해야 하는데, 복잡한 구조일 경우 쉽지 않음.

델타 스트리밍은 구조적 출력을 다룰때는 적절한 방식이 아님.

 

하지만 Foundation Models 프레임워크의 핵심은 구조적으로 출력 된다는 것임.

따라서 애플은 다른 형태로 개발했고, 원시값인 delta 대신 스냅샷을 스트리밍 형태로 내보냄.

 

 

스냅샷은 부분적으로 생성된 응답을 나타냄.

스냅샷은 모든 속성 값은 옵셔널 형태이며, 해당 모델이 응답을 더 생성할수록 속성들이 누적되어 나타남.

스냅샷은 구조적인 부분을 스트리밍할 때 견고하고 편리한 표현 방식임.

 

 

익숙한 @General에 매크로는 부분적으로 생성된 타입의 정의가 나타나는 곳이기도 함.

매크로를 확장해서 보면 `PartiallyGenerated`라는 타입을 생성함.

 

이는 외부 구조를 그대로 반영하되 모든 속성이 옵셔널인 형태임.

`PartiallyGenerated` 타입은 세션의 streamResponse 메서드 호출에서 사용됨.

 

 

스트림의 응답은 미동기 시퀀스를 반환함.

해당 시퀀스의 Elments는 `PartiallyGenerated` 타입의 인스턴스임.

시퀀스의 각 요소는 업데이트 된 스냅샷을 포함함.

 

 

SwiftUI와 같은 선언형 프레임워크랑 잘어울린다고 함.

해당 형태로 작성해 UI가 동적으로 변하는 것을 확인할 수 있음.

 

 

모델이 가장 좋은 형태의 summary를 생성하려면 구조체에서 가장 마지막에 위치하는 것이 좋음

*개인적인 의견인데 프롬프트 엔지니어링 할 때랑 비슷한 거 같음.

 

 

 

Tool을 호출하는 것인 핵심 기능중에 하나임.

이를 통해서 모델이 앱에서 정의한 코드를 제대로 실행할 수 있음.

 

이 기능은 모델의 성능을 최대한 활용하는데 중요한데, Tool calling이 모델에 많은 추가 기능을 제공하기 때문임.

이 기능은 모델에 추가 정보나 조치가 필요할 수 있음을 인식하고, 프로그래밍적으로 결정하기 어려운 상황에서 어떤 도구를 언제 사용할 지 자율적으로 판단할 수 있게 함.

 

모델에 제공하는 정보는 세계 지식, 최근 사건 또는 개인 데이터일 수도 있음.

예를들어서 MapKit을 통해 다양한 위치 정보를 얻을 수 있음.

 

이 기능으로 모델이 신뢰하는 출처를 인용해 할루시네이션(거짓)을 줄이고 모델 출력 결과를 검증할 수 있음.

마지막으로 이 기능은 모델이 앱 내에서든 시스템에서든 실제 환경에서든 다양한 작업을 할 수 있게 도와줌.

앱 내의 다양한 정보 출처와 통합하는 것은 상당히 이점임.

 

 

 

  • 이전까지 기록된 정보가 있음.
  • 세션에 Tool을 제공했다면, 세션은 Tool definition과 함께 모델에 제시함.
  • 다음은 프롬프트로 모델에게 방문하려는 목적지를 알려줌.
  • 이제 모델의 Tool 호출이 응답을 향상한다고 판단하면, 하나 이상의 Tool을 호출함.
    • 이 예시에서 모델은 레스토랑과 호텔 2가지 Tool call을 수행함. (여행앱이라서 특정)
  • 이 단계에서 FoundationModels 프레임워크는 Tool을 위해 작성한 코드를 자동으로 호출함.
  • 그 후 Tool의 출력값을 대화 내역(transcript)에 자동으로 삽입함
  • 마지막으로 모델은 Tool output과 대화 내역(transcript)의 다른 모든 내용을 함께 반영해 최종 응답을 생성함

 

 

  • Tool 프로토콜을 따르는 GetWeatherTool을 정의
    • GetWeatherTool은 Tool calling의 Hello World와 같은 예제
  • 프로토콜은 name과 설명을 지정하도록 요구
  • 프레임워크는 모델이 Tool을 언제 호출할지 이해할 수 있도록 해당 정보를 자동으로 제공
  • 모델에서 Tool 호출시 정의한 `func call(arguments: Arguments)` 메서드가 실행됨
  • `call` 메서드의 arguments는 어떤 @Generable 타입도 될 수 있음

 

 

@Generable이어야 하는 이유는 Tool calling 모델이 잘못된 Tool name 혹은 arguments를 생성하지 않도록 guided generation를 기반으로 하기 때문.

 

 

arguments를 정의한 후에는 메서드에 원하는 내용을 작성할 수 있음

- 해당 코드는 CoreLocation 및 WheatherKit을 사용해 특정 도시의 온도를 찾음.

 

output은 구조적 데이터를 위해 GeneratedContent에서 생성가능한 ToolOuput 타입으로 표현됨.

 

 

만약 출력이 자연어 형태라면 위 처럼 설정할 수도 있음.

 

 

Tool을 정의했으므로 모델이 도구에 접근할 수 있게끔 해야함.

  • 세션을 초기화하는 메서드에 Tool을 전달
    • Tool은 세션이 초기화 될 때 연결되어야 하며 세션이 유지되는 동안 모델이 사용할 수 있음.
  • Tool을 포함한 세션을 생성한 후에는 평소처럼 모델에 프롬프트를 전달하기만 하면 됨.
  • Tool의 호출은 투명하고 자율적으로 이루어지며, 모델은 Tool의 출력을 최종 응답에 반영함.

해당 영상에서의 예제는 컴파일 시 타입 안정성이 보장되는 Tool을 정의하는 방법을 설명하며 대부분 사용 사례에 적절함.

 

 

하지만 Tool은 동적으로도 사용할 수 있음.

예를들어 런타임에 생성 스키마를 사용해 실행시, Tool과 arguments의 동작을 정의할 수 있음.

 

 

FoundationModels Frameworks는 저장 세션을 기반으로 구축

기본적으로 세션을 생성하면 온디바이스 범용 모델에 프롬프트를 전달하게 됨.

그리고 커스텀 Instructions을 제공할 수 있으며, Instructions은 모델에게 역할을 알려주고 응답 방식을 가이드할 수 있는 기회로 스타일이나 구체적인 지시를 할 수 있음.
커스텀 Instructions은 선택사항이라서 지정하지 않을 경우에는 합리적인 기본 Instructions이 사용됨.

 

 


만약 커스텀 Instructions을 사용하기로 결정했다면 prompts와의 차이를 이해하는 것이 중요함.

  • Instructions은 개발자가 제공해야 함.
  • prompts는 사용자가 제공할 수 있음
    • 이는 모델이 프롬프트 지시를 따르도록 훈련되었기 때문

이 방법은 프롬프트 인젝션 공격을 어느정도 방어하는 데 도움은 되지만 완벽한 보호책은 아님.

일반적으로는 Instructions는 대부분 정적이며 신뢰할 수 없는 사용자 입력을 Instructions에서 제외하는게 좋음.

이는 Instructions와 메시지 구성의 기본적인 입문서와 같은 내용임

 

 

 

respondstreamResponse 같은 메서드는 사용자가 모델과 주고받는 **대화(상호작용)**를 내부적으로 계속 저장.

그래서 모델은 이전 대화 내용(이전 질문·답변들)을 기억하고 맥락을 이해한 채로 다음 응답을 생성할 수 있음.

즉, 한 번 질문하고 답한 걸로 끝나는 게 아니라, 여러 차례 오가는 멀티턴 대화에서도 일관된 문맥을 유지할 수 있게 해준다는 의미.

 

세션 객체의 transcript 속성은 이전 대화(상호작용) 확인하고 이를 나타내는 UI 뷰를 그리는데 사용할 수 있음.

또는 이를 표현하기 위해 UI에 뷰를 그림.

 

 

모델이 출력을 생성하는 동안에 session에 isResponding 속성이 true로 되어있음.

속성을 관찰하고 모델이 응답을 완료할 때까지 다른 프롬프트를 다시 제출하지 않도록 해야할 수도 있음.

 

기본 모델 외에도 어댑터가 지원하는 추가적인 built-in 특화된 useCase를 제공하고 있음.

필요에 맞는 내장 사례를 찾으면 SystemLanguageModel의 초기화 메서드에 전달할 수 있음.

 

 

어떤 built-in useCase가 있는지와 최적의 활용법을 이해하려면 개발자 웹사이트의 문서에서 확인할 수 있음.

contentTagging는 태그 생성, 엔티티 추출, 토픽 감지를 함.

 

 

 

기본적으로 어댑터는 학습을 통해 태그를 출력하고 가이드 기반 생성 기능과 즉시 통합됨.

사용자의 입력을 넘겨서 토픽을 추출할 수도 있음.

 

 

또한 아니라 커스텀 Instructions 및 Generable 타입 지정시 행동이나 감정 등을 감지할 수도 있음.

 

 

 

세션을 만들기 전에 모델은 애플 인텔리전스 지원 기기와 지원하는 지역에서만 사용되어서 미리 사용 가능한지 체크해야함.

 

 

마지막으로 모델을 호출할 때 오류가 발생할 수도 있음.

오류로는 가드레인 위반 및 지원하지 않는 언어, 컨텍스트 윈도우 초과 등이 있음.

최상의 사용자 경험을 위해 오류를 적절히 처리해야 하며, 

 

 

 

개발자 경험에 대해서 이야기 할 건데, 플레이그라운드 매크로에서 모델에 요청할 수 있음.

플레이그라운드는 앱을 다시 빌드하고 실행하지 않고도 프롬프트를 빠르게 반복할 수 있어서 유용함.

플레이그라운드에서는 이미 UI를 구동하는 Generable 타입 등 프로젝트 모든 타입에 접근 가능함.

 

 

LLM 기반으로 구동되는 앱 경험을 만들 때는 내부 지연 시간을 이해하는 것이 중요한데 기존 ML 보다 실행 시간이 더 오래 걸림.

지연 시간에 프롬프트는 세밀하게 제어하고 미리 사전에 API를 호출하는 작업을 수행할 수 있음.

 

 

인스트루먼트에서 새로운 기능을 지원함.

모델 요청의 지연시간을 프로파일링하고 최적화 할 부분을 관찰하며 개선 효과를 수치로 확인할 수 있음.

 

 

만약 내가 ML 전문가라면 어탭터 학습 툴킷을 통해 맞춤형 어댑터를 학습시킬 수 있음.

단, 애플이 이 모델을 개선할 때마다 다시 학습 시켜야 하므로 상당한 책임이 따름. 

 

 

 

파운데이션 모델이 제공하는 다양한 기능들 및 넥스트 스텝!

 

 

 

 

(참고)

https://www.youtube.com/watch?v=mJMvFyBvZEk