Ktor는 멀티플랫폼 개발을 지원하는 Kotlin용 비동기 HTTP 클라이언트 및 서버 프레임워크입니다. 라이브러리는 Kotlin 코루틴을 기반으로 구축되었으며 JVM, iOS, Android, JS 및 Native에서 실행됩니다. GitHub의 Ktor 저장소에 따르면 이 프로젝트는 JetBrains 팀에 의해 적극적으로 개발되고 있습니다. Ktor는 HTTP 연결의 유연한 구성을 위한 플러그인 시스템을 갖춘 모듈식 아키텍처를 제공합니다.
주요 포인트
Ktor는 JetBrains에서 개발한 Kotlin으로 HTTP 클라이언트와 서버를 만들기 위한 프레임워크입니다. 기존 라이브러리와 달리 Ktor는 처음부터 멀티플랫폼 개발을 위해 설계되었으며 Kotlin이 지원하는 모든 플랫폼에서 작동합니다.
Ktor는 Kodein과 Express.js의 아키텍처에서 영감을 받은 미들웨어 핸들러 접근 방식을 사용합니다. 각 요청은 요청과 응답을 수정할 수 있는 핸들러 함수의 파이프라인을 통과합니다. 이는 어노테이션 기반의 엄격한 아키텍처를 가진 라이브러리에서는 제공되지 않는 유연성을 제공합니다.
현재 버전 Ktor 3.0은 Kotlin 2.0, K2 컴파일러 및 성능이 향상된 새로운 CIO(Coroutine I/O) 엔진에 대한 지원을 포함합니다. 라이브러리는 Apache 2.0 라이선스에 따라 배포되며 제한 없이 상업적으로 사용할 수 있습니다.
Ktor의 클라이언트 측은 완전히 Kotlin 코루틴을 기반으로 구축되어 스레드 차단 없이 효율적인 비동기 요청 실행을 제공합니다. 서버 측에서는 라우팅, 요청 처리 및 WebSocket 연결을 갖춘 HTTP 서버를 만들 수 있습니다.
Ktor는 플러그인 아키텍처를 사용합니다. 로깅, 직렬화, 인증 등 모든 추가 기능은 플러그인을 통해 연결됩니다. 이렇게 하면 라이브러리가 모듈화되어 필요한 구성 요소만 연결할 수 있어 최종 애플리케이션 크기가 줄어듭니다.
모든 플랫폼에서 통합된 API 덕분에 개발자는 iOS와 Android용으로 다른 HTTP 클라이언트를 배울 필요가 없습니다. 멀티플랫폼 프로젝트에서 네트워크 계층 코드는 완전히 공유되며 플랫폼별 구현은 HttpClient 엔진 뒤에 숨겨집니다. 이는 개발 시간을 단축하고 플랫폼 차이와 관련된 오류 수를 줄입니다.
Ktor는 최신 Kotlin 프로젝트, 특히 멀티플랫폼 프로젝트에 매력적인 선택이 되는 다양한 기능을 제공합니다.
Ktor는 JVM, Android, iOS, macOS, Windows, Linux, JavaScript 및 Wasm에서 작동합니다. 동일한 HTTP 클라이언트 코드가 변경 없이 모든 플랫폼에서 실행됩니다. 이는 OkHttp나 URLSession에 종속된 라이브러리에 비해 핵심적인 이점입니다.
Kotlin의 코루틴은 콜백 없이 자연스러운 비동기 처리를 제공합니다. 각 요청은 모든 코루틴에서 호출할 수 있는 suspend 함수입니다. Ktor는 Flow를 통한 응답 스트리밍을 지원하므로 긴 연결 및 WebSocket에 편리합니다.
Ktor 플러그인은 install 블록을 통해 연결되며 개별적으로 구성됩니다. 주요 플러그인: 직렬화용 ContentNegotiation, 로깅용 Logging, 인증용 Auth, 양방향 통신용 WebSockets. 각 플러그인은 독립적으로 활성화 또는 비활성화할 수 있습니다.
Ktor의 오류 처리는 예외를 기반으로 합니다. ClientRequestException 클래스는 4xx 코드, ServerResponseException은 5xx, IOException은 네트워크 오류에 대해 발생합니다. 타임아웃은 HttpTimeout 플러그인을 통해 구성되며 연결, 읽기 및 쓰기에 대한 대기 시간을 설정합니다. 재시도에는 시도 횟수 및 지연 설정이 있는 Retry 플러그인이 사용됩니다.
Ktor는 각 요청이 핸들러 체인을 통과하는 파이프라인 아키텍처를 사용합니다. 클라이언트는 설치된 플러그인으로 HttpClient 구성을 생성하며 get 또는 post에 대한 각 호출은 연결된 순서대로 플러그인을 통과합니다.
HttpClient 객체는 플랫폼별 엔진으로 생성됩니다. JVM 및 Android용 CIO, iOS 및 macOS용 Darwin, Android 호환용 OkHttp, 브라우저용 Js. 엔진을 명시적으로 선택하거나 자동 선택에 맡길 수 있습니다. 각 요청은 응답 본문, 헤더 및 상태를 포함하는 HttpResponse를 반환합니다.
val client = HttpClient(CIO) {
install(ContentNegotiation) {
json(Json {
ignoreUnknownKeys = true
})
}
}
suspend fun fetchUsers(): List<User> {
return client.get("https://api.example.com/users").body()
}
Ktor 설치는 Gradle 또는 Maven을 통해 수행됩니다. 멀티플랫폼 프로젝트의 경우 각 대상에 대한 sourceSets에 종속성이 지정됩니다. Ktor는 Maven Central을 통해 배포됩니다.
build.gradle.kts에 공통 코드용 ktor-client-core 종속성과 특정 플랫폼용 엔진을 추가합니다. Ktor 버전은 gradle.properties의 변수를 통해 설정됩니다. Ktor 3.x에는 Kotlin 2.0+가 필요하며 K2 컴파일러를 지원합니다.
val ktorVersion = "3.0.3"
dependencies {
implementation("io.ktor:ktor-client-core:$ktorVersion")
implementation("io.ktor:ktor-client-cio:$ktorVersion")
implementation("io.ktor:ktor-client-content-negotiation:$ktorVersion")
implementation("io.ktor:ktor-serialization-kotlinx-json:$ktorVersion")
implementation("io.ktor:ktor-client-logging:$ktorVersion")
}
iOS의 경우 네이티브 URLSession을 래핑하는 Darwin 엔진이 사용됩니다. Kotlin Multiplatform에서 이는 최대 성능과 iOS 시스템 캐싱 메커니즘과의 통합을 제공합니다. 엔진은 iOS sourceSet에 별도의 종속성으로 추가됩니다.
Ktor의 중요한 기능은 ContentNegotiation을 통한 다양한 직렬화 형식 지원입니다. JSON 외에도 플러그인은 Protobuf, CBOR, XML 및 사용자 정의 형식을 지원합니다. 직렬화에는 kotlinx.serialization 또는 Jackson 라이브러리가 사용되며 개발자는 요청 코드를 변경하지 않고도 전환할 수 있습니다.
아래 예제는 Ktor 클라이언트 작업의 일반적인 시나리오(기본 GET 요청, 데이터 전송 및 멀티플랫폼 코드 작업)를 보여줍니다.
응답을 데이터 클래스로 자동 역직렬화하는 간단한 GET 요청입니다. Ktor는 kotlinx.serialization과 함께 ContentNegotiation 플러그인을 사용하여 JSON을 객체로 변환합니다. 코드는 간결하고 타입 안전합니다.
@Serializable
data class Post(
val id: Int,
val title: String,
val body: String
)
suspend fun getPosts(): List<Post> {
val response = client.get("https://jsonplaceholder.typicode.com/posts")
return response.body()
}
Ktor의 POST 요청은 contentType 및 setBody와 함께 post 메서드를 통해 데이터 클래스를 JSON 본문으로 전송합니다. ContentNegotiation 플러그인은 자동으로 객체를 JSON 문자열로 직렬화합니다. 응답은 동기식 또는 비동기식으로 처리할 수 있습니다.
suspend fun createPost(): Post {
val newPost = Post(
id = 0,
title = "새 게시물",
body = "게시물 내용"
)
val response = client.post("https://jsonplaceholder.typicode.com/posts") {
contentType(ContentType.Application.Json)
setBody(newPost)
}
return response.body()
}
Ktor의 submitFormWithBinaryData 메서드는 multipart 형식으로 파일과 양식을 보낼 수 있습니다. Ktor는 자동으로 데이터를 부분으로 분할하고 헤더를 추가합니다. 진행 상황을 추적하려면 onUpload를 사용하여 전송된 데이터의 바이트를 받습니다.
suspend fun uploadFile(fileBytes: ByteArray) {
client.submitFormWithBinaryData(
url = "https://api.example.com/upload",
formData = formData {
append("file", fileBytes, Headers.build {
append(HttpHeaders.ContentType, "image/png")
append(HttpHeaders.ContentDisposition, "filename=\"photo.png\"")
})
}
)
}
선택은 프로젝트 아키텍처와 멀티플랫폼 요구사항에 따라 달라집니다. Retrofit은 Android 전용 프로젝트의 표준으로 남아 있으며 Ktor는 Kotlin Multiplatform에 가장 적합한 선택입니다.
Ktor는 WebSocket 및 SSE(Server-Sent Events)에 대한 내장 지원도 제공하므로 실시간 애플리케이션에 편리합니다. Retrofit은 WebSocket을 직접 지원하지 않으며 별도의 OkHttp WebSocket 라이브러리가 필요합니다. Ktor는 각 플러그인이 하나의 기능을 담당하는 플러그인 시스템 덕분에 다양한 환경에 맞게 구성하기도 쉽습니다.
Ktor의 Auth 플러그인은 기본 인증, Bearer 토큰, Digest 및 OAuth2를 지원합니다. 인증 구성은 선언적으로 수행됩니다. 개발자가 제공자, 토큰 소스 및 범위를 지정합니다. Ktor는 자동으로 요청에 인증 헤더를 추가하고 토큰이 만료되면 갱신할 수 있습니다.
프로젝트가 iOS와 Android에서 공유 코드를 사용하는 Kotlin Multiplatform을 사용하는 경우 Ktor는 추가 계층 없이 두 플랫폼에서 모두 작동하는 유일한 옵션입니다. Retrofit은 OkHttp 및 JVM에 밀접하게 연결되어 iOS에 적합하지 않습니다.
Android 전용 프로젝트의 경우 Retrofit은 더 성숙한 API, 더 많은 수의 변환기 및 OkHttp 인터셉터를 제공합니다. Ktor도 이 시나리오에서 작동하지만 플러그인 생태계가 덜 광범위합니다. 두 라이브러리 모두 코루틴을 지원하고 비슷한 성능을 제공합니다.
| 기준 | Ktor | Retrofit |
|---|---|---|
| 멀티플랫폼 | iOS, Android, JVM, JS, Native | JVM 및 Android만 |
| HTTP 엔진 | CIO, Darwin, OkHttp, Js | OkHttp |
| 변환기 | kotlinx.serialization, Jackson | Gson, Moshi, Jackson, Protobuf |
| 아키텍처 | 플러그인이 있는 파이프라인 | 코드 생성이 있는 어노테이션 |
| 개발사 | JetBrains | Square |
자주 묻는 질문
Ktor는 JetBrains의 코루틴 기반 멀티플랫폼 HTTP 클라이언트입니다. Retrofit은 OkHttp 기반 Square의 Android 라이브러리입니다. Ktor는 iOS, Android, JS 및 Native에서 작동하지만 Retrofit은 JVM에서만 작동합니다.
네, Ktor는 네이티브 URLSession을 사용하는 Darwin 엔진을 통해 iOS를 지원합니다. 이는 최대 성능과 iOS 시스템 캐시와의 올바른 작동을 보장합니다. 클라이언트 코드는 플랫폼 간에 공유됩니다.
Ktor는 다음 엔진을 지원합니다: CIO(JVM/Android), Darwin(iOS/macOS), OkHttp(Android), Js(브라우저), Jetty, Netty, Tomcat(서버). 엔진을 명시적으로 선택하거나 기본 자동 선택에 맡길 수 있습니다.
네, Ktor는 클라이언트와 서버 모두에서 WebSocket에 대한 내장 지원을 제공합니다. 클라이언트의 경우 WebSockets 플러그인이 사용되어 양방향 연결을 설정하고 실시간으로 메시지를 교환할 수 있습니다.
오류는 suspend 호출 주변의 try-catch를 통해 처리됩니다. Ktor는 4xx에 ClientRequestException, 5xx에 ServerResponseException, 네트워크 오류에 IOException을 발생시킵니다. 통일을 위해 Result 유형 사용이 권장됩니다.
요약
턴키 방식의 모바일 애플리케이션을 개발해 드립니다
IT Sectr는 2017년부터 스타트업과 기업을 위한 iOS 및 Android 애플리케이션을 만듭니다. 저희가 상담해 드리고 최적의 솔루션을 제안하겠습니다.