모바일 개발에서의 데이터 직렬화 — 정의, 포메이트, 작동 원리

저자: IT Sectr 게시일: 2026-03-08 읽는 시간: 8 분

직렬화는 객체 또는 데이터 구조를 네트워크 전송이나 파일 저장에 적합한 순차적 형식으로 변환하는 과정입니다. 역 과정인 역직렬화는 데이터를 원래 상태로 복원합니다. MDN Web Docs에 따르면, 직렬화는 모든 프로세스간 통신에 필수적입니다. 직렬화는 REST API, 캐시딩 그리고 애플리케이션 컴포넌트 간의 데이터 교환의 기초를 이룩니다.

주요 포인트

  • 직렬화 — 전송 또는 저장을 위해 객체를 데이터 스트림으로 변환
  • JSON — REST API와 웹 통신에서 주로 사용되는 텍스트 포메이트
  • Protobuf — 최대 성능과 압축을 제공하는 바이너리 포메이트
  • XML — 기업 및 Android 개발을 위한 검증 기능이 있는 엄격한 포메이트
  • 포메이트 선택은 성능 및 호환성 요구사항에 따라 달라짐

직렬화란?

직렬화는 RAM에 있는 객체를 네트워크로 전송하거나, 파일에 저장하거나, 다른 프로세스에 전달할 수 있는 일련의 바이트 또는 문자 시퀀으로 변환하는 과정입니다. 직렬화 없이는 네트워크 통신, 상태 지속성 및 프로세스간 상호작용이 불가능합니다.

직렬화에는 두 가지 반대된 과정이 있습니다. 정방향 과정(직렬화)은 데이터를 전송 형식으로 패키징합니다. 역방향 과정(역직렬화)은 데이터를 객체로 복원합니다. 역직렬화는 보안에 광저하게 중요합니다: 잘못된 입력 데이터는 애플리케이션에 취약성을 초래할 수 있습니다.

모바일 애플리케이션 개발에서 직렬화는 모든 곳에서 사용됩니다: 서버에 요청 전송 및 응답 처리, 화면 회전 시 애플리케이션 상태 저장, 디스크에 데이터 캐시, Intent(Android) 또는 Segue(iOS)를 통한 화면 간 데이터 전달 등에서입니다.

직렬화의 주요 작업

  • 네트워크 통신 — 클라이언트와 서버 간의 데이터 전송
  • 상태 지속성 — 애플리케이션 데이터 저장 및 복구
  • 캐시딩 — 오프라인 액세스를 위한 요청 결과 저장
  • 크로스 플랫폼 — 다른 언어의 시스템 간 데이터 교환
  • 로깅 — 로그 기록을 위한 객체 직렬화

주요 직렬화 포메이트

직렬화 포메이트는 텍스트형과 바이너리형으로 나뉕니다. 텍스트 포메이트(JSON, XML)는 사람이 읽을 수 있으며 보기 위한 도구가 필요 없습니다. 바이너리 포메이트(Protobuf, FlatBuffers, MessagePack)는 더 압축되고 빠르지만 역직렬화 없이는 읽을 수 없습니다. 포메이트 선택은 성능과 디버깅 편의성 간의 타협입니다.

JSON, XML, Protobuf 외에도 전문 포메이트가 있습니다: Google의 FlatBuffers(게임 및 AR 용), MessagePack — JSON의 압축된 바이너리 대체, Apache의 Avro(Kafka에서 빅 데이터 용), YAML — 주석을 지원하는 설정 포메이트.

포메이트 유형 스키메 크기 속도
JSON 텍스트 선택 사항 중간 중간
XML 텍스트 XSD 크림 낮음
Protobuf 바이너리 필수 작음 높음
FlatBuffers 바이너리 필수 작음 최고
MessagePack 바이너리 없음 작음 높음
Avro 바이너리 JSON Schema 작음 높음

모바일 개발에서의 직렬화

모바일 플랫폼에서 직렬화는 고유한 특이가 있습니다: 제한된 대역폭, 덕 단 프로세서, 화면 회전 시 상태 유지 필요성이 그것입니다. Android에서는 Gson, Moshi, Kotlinx Serialization이 사용됩니다. iOS에서는 Codable, JSONSerialization, PropertyListEncoder가 사용됩니다. 올바른 라이브러리 선택은 애플리케이션 성능에 중대한 영향을 미칭니다.

Kotlinx Serialization은 JetBrains의 Kotlin Multiplatform Mobile을 위한 최신 라이브러리입니다. JSON, Protobuf, CBOR 및 사용자 정의 포메이트를 지원합니다. Kotlin Serialization 플러그인을 통해 컴파일 시점에 코드 생성이 일어나며, 리플렉션을 사용하지 않고 높은 성능을 제공합니다.

Kotlinx Serialization (Kotlin Multiplatform)

Kotlinx Serialization 라이브러리는 클래스에 @Serializable 어노테이션을 사용하고 컴파일러 플러그인으로 직렬화기를 생성합니다. 이를 통해 높은 성능과 타입 안전성이 보장됩니다. 기본 포메이트는 JSON이지만, 추가 모듈을 통해 다른 포메이트도 지원됩니다.

kotlin
import kotlinx.serialization.Serializable
import kotlinx.serialization.json.Json
import kotlinx.serialization.encodeToString
import kotlinx.serialization.decodeFromString

@Serializable
data class Project(
    val id: Int,
    val name: String,
    val platforms: List<String>,
    val active: Boolean
)

val json = Json {
    prettyPrint = true
    ignoreUnknownKeys = true
    encodeDefaults = true
}

fun main() {
    val project = Project(1, "MobileApp",
        listOf("Android", "iOS"), true)

    // 직렬화
    val jsonString = json.encodeToString(project)

    // 역직렬화
    val restored = json.decodeFromString<Project>(jsonString)
}

iOS의 Codable (Swift)

Codable 프로토콜은 Swift의 내장 직렬화 메커니즘입니다. Encodable(직렬화)과 Decodable(역직렬화) 프로토콜을 결합합니다. JSONEncoder와 JSONDecoder는 중첩 구조, 배열, 옵션널 값, 그리고 CodingKeys를 통한 사용자 정의 키를 자동으로 처리합니다.

swift
import Foundation

struct AppConfig: Codable {
    let appName: String
    let version: String
    let features: [String]
    let isProduction: Bool
}

let config = AppConfig(
    appName: "MyApp",
    version: "2.1.0",
    features: ["push", "analytics", "offline"],
    isProduction: true
)

let encoder = JSONEncoder()
encoder.outputFormatting = [.prettyPrinted, .sortedKeys]

guard let data = try? encoder.encode(config) else { return }
let jsonString = String(data: data, encoding: .utf8)

성능 및 포메이트 비교

직렬화 포메이트의 성능은 세 가지 메트릭으로 평가됩니다: 메시지 크기, 직렬화 속도, 역직렬화 속도. 모바일 애플리케이션에서는 세 가지 모두 중요합니다. 크기는 데이터 사용량과 로드 시간에 영향을 미치고, 속도는 인터페이스 반응성과 애플리케이션 시작 시간에 영향을 미칩니다.

Protobuf와 FlatBuffers는 바이너리 표현으로 최고의 결과를 보여줍니다. FlatBuffers는 별도의 역직렬화 단계가 필요 없다는 점에서 두드랩니다 — 데이터가 변환 없이 바이너리 버퍼에서 바로 읽힌미로, 최소 지연 요구사항이 있는 게임 및 AR 애플리케이션에 이상적입니다. JSON은 더 나쁜 성능에도 불구하고, 그 단순성과 보편성 때문에 REST API에서 가장 인기있는 포메이트로 남아 있습니다.

시나리오 추천 포메이트 이유
REST API JSON 보편성, 가독성, 지원
마이크로서비스 Protobuf 압축성, 속도, gRPC
게임 / AR FlatBuffers Zero-copy, 최소 지연
빅 데이터 Avro Kafka 및 Hadoop과의 호환성
설정 YAML 주석, 가독성
Android 레이아웃 XML 플랫폼 표준

벤치마크 테스트

1000개의 사용자 객체 데이터셋에 대한 실용 테스트 결과: Protobuf는 12KB 메시지를 생성합니다(JSON은 85KB, XML은 120KB). 직렬화 시간: Protobuf 2ms, JSON 8ms, XML 25ms. 이 수치는 바이너리 포메이트가 고부하 시스템과 제한된 데이터를 사용하는 모바일 애플리케이션에서 선호됨을 보여줍니다.

데이터 직렬화 예제

예제는 동일한 객체를 다양한 포메이트로 직렬화하는 것을 보여줍니다. 이를 통해 크기와 가독성을 시각적으로 비교할 수 있습니다. 동일한 User 객체가 JSON, XML, Protobuf로 직렬화됩니다 — JSON이 XML보다 더 압축되었고, Protobuf가 가장 압축되었으며 읽을 수 없다는 것이 붅니다.

세 가지 포메이트의 단일 객체

JSON — 미니멀 구문, 따옴표로 감싸인 키, 다양한 유형의 값. 80자 차지. 가독성이 높고 시각적 구조가 명확합니다. 개발 및 디버깅 속도가 중요한 API에 적합합니다.

XML — 각 요소가 열린 태그와 닫힌 태그로 감싸지며 150자를 차지합니다. 가독성은 중간이며 구조가 엄격합니다. 문서 워크플로와 XSD 검증이 필요한 시스템에 적합합니다.

Protobuf — 바이너리, 이 데이터에 32바이트. 읽을 수 없음 — 보려면 역직렬화가 필요. 작은 크기로 고부하 시스템과 모바일 애플리케이션에 이상적입니다.

json
{
  "id": 42,
  "name": "IT Sectr",
  "email": "team@itsectr.com",
  "role": "admin",
  "active": true
}
xml
<user>
    <id>42</id>
    <name>IT Sectr</name>
    <email>team@itsectr.com</email>
    <role>admin</role>
    <active>true</active>
</user>

직렬화 최선 실무

최선 실무는 일반적인 실수를 피하고 프로젝트에 맞는 직렬화 전략을 선택하는 데 도움이 됩니다. 이러한 권고사항을 따르면 성능, 보안 및 코드 유지보수성이 향상됩니다.

모바일 개발을 위한 권고사항

  1. 시나리오에 따라 포메이트를 선택하세요 — REST API에는 JSON, gRPC와 마이크로서비스에는 Protobuf
  2. Java Serializable을 피하세요 — 늘리고 불안전한 메커니즘, Kotlinx Serialization이나 Moshi를 사용하세요
  3. 알 수 없는 키를 무시하세요 — 모델에 없는 필드를 스킵하도록 파서를 설정하세요
  4. 역직렬화된 데이터를 캐시하세요 — 동일한 데이터를 반복해서 파싱하는 것을 피하세요
  5. 입력 데이터를 검증하세요 — 역직렬화 시 경계와 유형을 확인하세요

보안 및 직렬화

직렬화 보안은 매우 중요한 요소이며, 특히 신뢰할 수 없는 출처의 데이터를 역직렬화할 때 그렇습니다. 역직렬화 공격은 원격 코드 실행(RCE)으로 이어질 수 있으며, 이는 웹 및 모바일 애플리케이션에서 가장 위험한 취약성 중 하나입니다. 가장 잘 알려진 사례는 Java Serializable과 Python pickle과 관련되어 있습니다.

Protobuf와 JSON은 이러한 공격에 대한 내장 보호 기능이 있습니다. 이는 이들이 데이터로만 작동하고, 임의의 객체로는 작동하지 않기 때문입니다. 반면, Java Serializable은 classpath에 있는 모든 클래스를 복구할 수 있으므로 외부 출처에서 데이터를 수신할 때 위험합니다. Android에서는 표준 Java Serialization 대신 Kotlinx Serialization이나 Moshi를 사용할 것을 권장합니다.

추가 보안 조치: 입력 데이터 크기에 제한을 설정하고, 역직렬화 전에 스키마를 검증하고, HTTP 헤더의 Content-Type을 신뢰하지 말고, 허용된 클래스의 앨로우리스트를 사용하세요. 취약성이 정기적으로 발견되고 수정되므로 직렬화 라이브러리를 정기적으로 업데이하세요.

자주 묻는 질문

직렬화와 마셜링의 차이점은 무엇인가요?

직렬화는 객체를 바이트 시퀀으로 변환하는 반면, 마셜링은 유형과 구조를 유지하면서 다른 주소 공간 간에 데이터를 전달합니다. 마셜링은 프로세스의 일부로 직렬화를 포함하지만, 참조 인코딩과 메모리 관리도 포함할 수 있습니다.

어떤 직렬화 포메이트가 가장 빠른가요?

Google의 FlatBuffers는 zero-copy 역직렬화 덕분에 최고의 속도를 제공합니다 — 데이터가 변환 없이 바이너리 버퍼에서 바로 읽힙니다. Protobuf가 둘째, JSON이 셼째입니다. XML은 일반적인 포메이트 중 가장 늜융니다.

Android에서 Gson, Moshi, Kotlinx Serialization 중 뭘 선택해야 하나요?

Kotlinx Serialization은 Kotlin 새 프로젝트에 최고의 선택입니다: 컴파일러 생성, Kotlin Multiplatform 지원, null safety. Moshi는 Java 프로젝트에 좋은 선택으로 Gson보다 성능이 능륩합니다. Gson은 시작하기 가장 쉽지만, 늘리고 리플렉션을 사용합니다.

순환 참조가 있는 객체를 직렬화하는 방법은?

순환 참조는 직렬화 중 무한 재귀를 초래합니다. 해결 방법: 직접 객체 참조 대신 ID 참조를 사용하고, 전문 직렬화 어댑터를 적용하고(예: Jackson의 @JsonIgnore), 또는 순환을 제거하기 위해 데이터 모델을 재설계하세요.

직렬화가 애플리케이션 보안에 영향을 미치나요?

그러합니다, 특히 신뢰하지 못한 데이터의 역직렬화에서 그렇습니다. 역직렬화 취약성은 원격 코드 실행으로 이어질 수 있습니다. 권고사항: 신뢰하지 못한 출처의 데이터를 역직렬화하지 말고, 역직렬화 시 클래스의 앨로우리스트를 사용하고, 처리 전에 데이터 스키마를 검증하세요.

요약

  • 직렬화는 객체를 전송 및 저장을 위한 데이터 스트림으로 변환하고, 역직렬화는 복원합니다
  • JSON은 REST API 표준, XML은 문서 워크플로, Protobuf는 마이크로서비스와 고부하용
  • 바이너리 포메이트(Protobuf, FlatBuffers)는 텍스트 포메이트보다 3–10배 압축되고 빠릅니다
  • Android에서는 Kotlinx Serialization, iOS에서는 내장 Codable 추천
  • 역직렬화된 데이터 캐시는 CPU 부하를 줄이고 애플리케이션을 가속합니다
  • 역직렬화 보안은 중요합니다 — 입력 데이터를 검증하고 앨로우리스트를 사용하세요
  • 포메이트 선택은 가독성, 성능, 호환성 간의 타협입니다

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

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

프로젝트 논의

더 읽어보기