Открыть сервис

Маршалинг

Маршалинг (от англ. marshalling) — это процесс преобразования данных из внутреннего представления, используемого в оперативной памяти компьютера (например, структуры, объекта или массива в языке программирования), в формат, пригодный для передачи по сети, записи в файл или хранения во внешней системе. Обратный процесс, восстановление данных из внешнего формата во внутреннее представление, называется демаршалингом (англ. unmarshalling). Маршалинг является ключевым механизмом в распределённых вычислениях, межпроцессном взаимодействии (IPC), веб-сервисах и системах хранения данных.

История и происхождение термина

Термин «маршалинг» восходит к военной терминологии, где «маршал» (от старофранцузского mareschal) означал старшего офицера, отвечающего за построение и организацию войск. В контексте программирования метафора сохранилась: данные «выстраиваются» в строгую последовательность байтов (сериализуются) для передачи, подобно тому, как войска выстраиваются в колонну для марша. Впервые термин в вычислительной технике начал активно использоваться в 1980-х годах с развитием систем удалённого вызова процедур (RPC), таких как Sun RPC (ONC RPC) и DCE/RPC. В этих системах маршалинг обеспечивал преобразование параметров вызова функции в поток байтов, передаваемый по сети, и обратное преобразование результата.

Отличие от сериализации

Хотя термины «маршалинг» и «сериализация» часто используются как синонимы, между ними существуют технические различия:

  • Сериализация — это процесс преобразования объекта в последовательность байтов (или строку) для сохранения или передачи. Она обычно не включает в себя информацию о типе данных или контексте выполнения.
  • Маршалинг — это более широкое понятие. Он включает не только сериализацию данных, но и передачу метаданных (например, кода, идентификатора типа, информации о версии), а также может подразумевать выполнение дополнительных действий, таких как:
  • Копирование по значению (передача объекта целиком).
  • Копирование по ссылке (передача ссылки на объект, если объект находится в общей памяти).
  • Управление жизненным циклом (например, освобождение памяти после передачи).

В некоторых системах (например, в Java RMI) маршалинг может включать передачу кода класса (динамическая загрузка классов), что выходит за рамки простой сериализации.

Принцип работы

Процесс маршалинга включает несколько этапов:

  1. Анализ структуры данных: Система определяет типы и структуру объекта (например, поля класса, их размеры и порядок).
  2. Преобразование в плоский формат: Данные упаковываются в линейную последовательность байтов. При этом учитываются:
  • Порядок байтов (endianness): big-endian (от старшего к младшему) или little-endian (от младшего к старшему). Для обеспечения совместимости между разными архитектурами (например, x86 и ARM) часто используется сетевой порядок байтов (big-endian).
  • Выравнивание (alignment): Добавление «пустых» байтов (padding) для выравнивания адресов данных по границам слов (например, 4 или 8 байт), что необходимо для корректной работы некоторых процессоров.
  1. Кодирование: Преобразование данных в выбранный формат (бинарный, текстовый, XML, JSON и т.д.).
  2. Передача: Поток байтов отправляется получателю (по сети, в файл, в другой процесс).

Демаршалинг выполняется в обратном порядке: полученный поток байтов декодируется, из него извлекаются данные, и на их основе в памяти создаётся новый объект.

Виды и форматы маршалинга

Маршалинг может быть реализован в различных форматах, которые делятся на две основные категории:

Бинарные форматы

Эти форматы компактны и быстры в обработке, но нечитаемы для человека. Примеры:

  • 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).

Источники

  1. Tanenbaum, A. S., & Van Steen, M. (2007). Distributed Systems: Principles and Paradigms (2nd ed.). Pearson.
  2. Coulouris, G., Dollimore, J., Kindberg, T., & Blair, G. (2011). Distributed Systems: Concepts and Design (5th ed.). Addison-Wesley.
  3. Stevens, W. R. (1998). UNIX Network Programming, Volume 1: Networking APIs: Sockets and XTI (2nd ed.). Prentice Hall.
  4. Документация Protocol Buffers (Google). Protocol Buffers: Language Guide.
  5. Документация Apache Thrift. Apache Thrift: Introduction.
  6. Документация Java. Java Object Serialization Specification.
  7. Документация Python. pickle — Python object serialization.

BFOmetr — база данных и аналитика по компаниям России.

На главную BFOmetr →