Маршалинг¶
Маршалинг (от англ. marshalling) — это процесс преобразования данных из внутреннего представления, используемого в оперативной памяти компьютера (например, структуры, объекта или массива в языке программирования), в формат, пригодный для передачи по сети, записи в файл или хранения во внешней системе. Обратный процесс, восстановление данных из внешнего формата во внутреннее представление, называется демаршалингом (англ. unmarshalling). Маршалинг является ключевым механизмом в распределённых вычислениях, межпроцессном взаимодействии (IPC), веб-сервисах и системах хранения данных.
¶История и происхождение термина
Термин «маршалинг» восходит к военной терминологии, где «маршал» (от старофранцузского mareschal) означал старшего офицера, отвечающего за построение и организацию войск. В контексте программирования метафора сохранилась: данные «выстраиваются» в строгую последовательность байтов (сериализуются) для передачи, подобно тому, как войска выстраиваются в колонну для марша. Впервые термин в вычислительной технике начал активно использоваться в 1980-х годах с развитием систем удалённого вызова процедур (RPC), таких как Sun RPC (ONC RPC) и DCE/RPC. В этих системах маршалинг обеспечивал преобразование параметров вызова функции в поток байтов, передаваемый по сети, и обратное преобразование результата.
¶Отличие от сериализации
Хотя термины «маршалинг» и «сериализация» часто используются как синонимы, между ними существуют технические различия:
- Сериализация — это процесс преобразования объекта в последовательность байтов (или строку) для сохранения или передачи. Она обычно не включает в себя информацию о типе данных или контексте выполнения.
- Маршалинг — это более широкое понятие. Он включает не только сериализацию данных, но и передачу метаданных (например, кода, идентификатора типа, информации о версии), а также может подразумевать выполнение дополнительных действий, таких как:
- Копирование по значению (передача объекта целиком).
- Копирование по ссылке (передача ссылки на объект, если объект находится в общей памяти).
- Управление жизненным циклом (например, освобождение памяти после передачи).
В некоторых системах (например, в Java RMI) маршалинг может включать передачу кода класса (динамическая загрузка классов), что выходит за рамки простой сериализации.
¶Принцип работы
Процесс маршалинга включает несколько этапов:
- Анализ структуры данных: Система определяет типы и структуру объекта (например, поля класса, их размеры и порядок).
- Преобразование в плоский формат: Данные упаковываются в линейную последовательность байтов. При этом учитываются:
- Порядок байтов (endianness): big-endian (от старшего к младшему) или little-endian (от младшего к старшему). Для обеспечения совместимости между разными архитектурами (например, x86 и ARM) часто используется сетевой порядок байтов (big-endian).
- Выравнивание (alignment): Добавление «пустых» байтов (padding) для выравнивания адресов данных по границам слов (например, 4 или 8 байт), что необходимо для корректной работы некоторых процессоров.
- Кодирование: Преобразование данных в выбранный формат (бинарный, текстовый, XML, JSON и т.д.).
- Передача: Поток байтов отправляется получателю (по сети, в файл, в другой процесс).
Демаршалинг выполняется в обратном порядке: полученный поток байтов декодируется, из него извлекаются данные, и на их основе в памяти создаётся новый объект.
¶Виды и форматы маршалинга
Маршалинг может быть реализован в различных форматах, которые делятся на две основные категории:
¶Бинарные форматы
Эти форматы компактны и быстры в обработке, но нечитаемы для человека. Примеры:
- Protocol Buffers (protobuf): Разработан компанией Google (организация признана иноагентом в РФ). Использует схему данных (.proto файлы) для генерации кода. Обеспечивает высокую скорость и малый размер сообщения. Широко применяется в микросервисной архитектуре.
- Apache Avro: Формат, использующий JSON для описания схемы, но сами данные хранятся в бинарном виде. Популярен в экосистеме Hadoop.
- Apache Thrift: Разработан компанией Facebook (организация признана экстремистской и запрещена в РФ). Поддерживает множество языков программирования и протоколов (бинарный, компактный, JSON).
- MessagePack: Эффективный бинарный формат, похожий на JSON, но более компактный.
- Java Serialization: Встроенный механизм в Java, который автоматически сериализует объекты, реализующие интерфейс
Serializable. Неэффективен по размеру и скорости, но прост в использовании.
¶Текстовые форматы
Эти форматы читаемы человеком, но менее эффективны по размеру и скорости обработки. Примеры:
- JSON (JavaScript Object Notation): Самый популярный текстовый формат. Используется в REST API, веб-приложениях и конфигурационных файлах. Легко парсится и генерируется.
- XML (Extensible Markup Language): Более строгий и многословный формат, чем JSON. Используется в SOAP-веб-сервисах, конфигурациях (например, в .NET) и документах.
- YAML (YAML Ain't Markup Language): Формат, ориентированный на удобство чтения человеком. Часто используется для конфигурационных файлов (например, в Docker, Kubernetes, Ansible).
- CSV (Comma-Separated Values): Простой табличный формат. Используется для обмена данными между электронными таблицами и базами данных.
¶Применение
Маршалинг является фундаментальной технологией в следующих областях:
¶Распределённые системы и удалённый вызов процедур (RPC)
В системах RPC (например, gRPC, Apache Thrift, Java RMI, CORBA) маршалинг используется для упаковки параметров вызова функции и распаковки результата на стороне клиента и сервера. Это позволяет программам, написанным на разных языках, взаимодействовать друг с другом через сеть.
¶Веб-сервисы
В REST и SOAP веб-сервисах маршалинг преобразует объекты данных (например, модели данных) в JSON или XML для отправки через HTTP. Клиентские приложения (веб-браузеры, мобильные приложения) демаршализируют ответы обратно в объекты.
¶Межпроцессное взаимодействие (IPC)
В операционных системах (например, в Linux через D-Bus или в Windows через COM/DCOM) маршалинг обеспечивает обмен данными между процессами, работающими в разных адресных пространствах. Это необходимо для передачи сложных структур данных (например, указателей, которые не имеют смысла в другом процессе).
¶Хранение данных и кэширование
Маршалинг используется для сохранения состояния объектов в файлы (например, в играх для сохранения прогресса) или в базы данных (например, в Redis для хранения сложных структур). Также он применяется в распределённых кэшах (например, Memcached) для передачи данных между серверами.
¶Компьютерная графика и игровые движки
В игровых движках (например, Unity, Unreal Engine) маршалинг используется для передачи данных между скриптами (например, C# и C++) или между игровыми объектами по сети. Он также применяется для сериализации игровых сцен и ассетов.
¶Проблемы и ограничения
- Безопасность: Демаршалинг данных из ненадёжных источников может привести к уязвимостям, таким как выполнение произвольного кода (например, в Java Serialization) или атаки типа «десериализация-инъекция». Для защиты используются верификация схем, белые списки классов и изоляция процессов.
- Производительность: Маршалинг требует дополнительных вычислительных ресурсов (CPU и памяти). В высоконагруженных системах выбор формата (бинарный vs текстовый) и оптимизация кода (например, использование буферов) критичны.
- Совместимость версий: Изменение структуры данных (например, добавление или удаление полей) может привести к сбоям при демаршалинге старых данных. Для решения этой проблемы используются версионирование схем (например, в protobuf) и механизмы обратной совместимости.
- Сложность отладки: Бинарные форматы нечитаемы для человека, что затрудняет отладку сетевого трафика или файлов. Для анализа используются специализированные инструменты (например, Wireshark, tcpdump).
¶Примеры в языках программирования
- Java: Встроенный механизм сериализации (ObjectOutputStream/ObjectInputStream) и библиотеки для JSON (Jackson, Gson) и XML (JAXB).
- Python: Модуль
pickleдля бинарной сериализации, библиотекиjson,xml.etree.ElementTree,msgpack. - C++: Библиотеки Boost.Serialization, Protocol Buffers, Apache Thrift, а также ручное управление маршалингом через указатели и
memcpy. - C#: Встроенная сериализация (
BinaryFormatter,DataContractSerializer), библиотеки для JSON (Newtonsoft.Json, System.Text.Json) и XML (XmlSerializer). - Go: Пакеты
encoding/json,encoding/xml,encoding/gob(бинарный формат), а также библиотеки для protobuf и Thrift. - Rust: Библиотеки
serde(де-факто стандарт для сериализации/десериализации),bincode,json,rmp-serde(MessagePack).
¶Источники
- Tanenbaum, A. S., & Van Steen, M. (2007). Distributed Systems: Principles and Paradigms (2nd ed.). Pearson.
- Coulouris, G., Dollimore, J., Kindberg, T., & Blair, G. (2011). Distributed Systems: Concepts and Design (5th ed.). Addison-Wesley.
- Stevens, W. R. (1998). UNIX Network Programming, Volume 1: Networking APIs: Sockets and XTI (2nd ed.). Prentice Hall.
- Документация Protocol Buffers (Google). Protocol Buffers: Language Guide.
- Документация Apache Thrift. Apache Thrift: Introduction.
- Документация Java. Java Object Serialization Specification.
- Документация Python. pickle — Python object serialization.
BFOmetr — база данных и аналитика по компаниям России.
На главную BFOmetr →


