Skip to main content

XML Canonicalization для Python

Project description

xmlcanon - XML Canonicalization для Python

Python Version License Tests

Реализация трансформации Exclusive XML Canonicalization согласно спецификации W3C для использования в XML подписях по стандарту ГОСТ.

Описание

Этот модуль реализует алгоритм Exclusive XML Canonicalization (ExcC14N), который является критически важным компонентом для создания XML цифровых подписей. Модуль создан на основе анализа библиотеки GostCryptography для обеспечения совместимости с российскими стандартами цифровой подписи.

Структура модуля

xmlcanon/
├── xmlcanon/                    # Основной пакет
│   ├── __init__.py             # Публичный API
│   ├── transform.py            # Основная логика ExcC14N
│   └── exceptions.py           # Пользовательские исключения
├── tests/                      # Тесты
│   ├── __init__.py
│   └── test_transform.py       # 14 unit тестов
├── examples/                   # Примеры использования
│   ├── __init__.py
│   ├── basic_usage.py          # Базовые примеры
│   ├── gost_integration.py     # Интеграция с ГОСТ
│   └── performance_test.py     # Тесты производительности
├── docs/                       # Документация
│   ├── CHANGELOG.md            # История изменений
│   └── CONTRIBUTING.md         # Руководство разработчика
├── setup.py                    # Установочный скрипт
├── requirements.txt            # Зависимости
├── MANIFEST.in                 # Файлы для включения в пакет
├── LICENSE                     # MIT лицензия
└── README.md                   # Основная документация

Основные особенности

  • Полная совместимость с W3C спецификацией Exclusive XML Canonicalization
  • Исключение неиспользуемых пространств имен - ключевая особенность ExcC14N
  • Принудительное включение определенных пространств имен
  • Корректная сортировка атрибутов согласно канонизации
  • Правильное экранирование текста и значений атрибутов
  • Поддержка вложенных структур любой сложности
  • Обработка ошибок и валидация входных данных
  • Совместимость с lxml и стандартной библиотекой
  • 14 unit тестов покрывают все сценарии

Установка

Установка из PyPI

pip install xmlcanon

Установка с опциональными зависимостями

# С поддержкой lxml (рекомендуется для лучшей производительности)
pip install xmlcanon[lxml]

# Для разработки
pip install xmlcanon[dev]

Установка из исходного кода

git clone https://github.com/imdeniil/xmlcanon.git
cd xmlcanon
pip install -e .

Зависимости

  • Python 3.6+
  • lxml >= 4.0.0 (опционально, рекомендуется для лучшей производительности)

Быстрый старт

Простое использование

from xmlcanon import canonicalize_xml

xml_input = '''<root xmlns:ns="http://example.com/ns">
    <ns:element attr="value">Содержимое</ns:element>
</root>'''

canonicalized = canonicalize_xml(xml_input)
print(canonicalized)

Расширенное использование

from xmlcanon import XmlCanonicalizer

# Создание канонизатора с принудительным включением пространств имен
canonicalizer = XmlCanonicalizer(
    inclusive_ns_prefixes=['force', 'include']
)

canonicalized = canonicalizer.transform(xml_input)

API Reference

canonicalize_xml(xml_input, inclusive_ns_prefixes=None)

Удобная функция для быстрого применения XML канонизации.

Параметры:

  • xml_input (str): Исходный XML документ
  • inclusive_ns_prefixes (List[str], optional): Префиксы пространств имен для принудительного включения

Возвращает:

  • str: Канонизированный XML

Исключения:

  • InvalidXMLError: При некорректном входном XML
  • TransformationError: При ошибке трансформации

class XmlCanonicalizer

Основной класс для выполнения XML канонизации.

__init__(inclusive_ns_prefixes=None)

Параметры:

  • inclusive_ns_prefixes (List[str], optional): Список префиксов пространств имен для принудительного включения

transform(xml_input)

Применяет канонизацию к XML документу.

Возвращает:

  • str: Канонизированный XML

Исключения

from xmlcanon.exceptions import InvalidXMLError, TransformationError

try:
    result = canonicalize_xml(xml_input)
except InvalidXMLError as e:
    print(f"Некорректный XML: {e}")
except TransformationError as e:
    print(f"Ошибка трансформации: {e}")

Примеры использования

Пример 1: Исключение неиспользуемых пространств имен

from xmlcanon import canonicalize_xml

xml_input = '''<root xmlns:used="http://used.com"
                    xmlns:unused="http://unused.com">
    <used:element>Только used используется</used:element>
</root>'''

result = canonicalize_xml(xml_input)
# Результат НЕ будет содержать xmlns:unused

Пример 2: SOAP структура (как в ГИИС ДМДК)

soap_xml = '''<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
                                xmlns:ns="urn://xsd.dmdk.goznak.ru/exchange/1.0">
    <soapenv:Header/>
    <soapenv:Body>
        <ns:SendDealRequest>
            <ns:RequestData id="body">
                <content>Данные для подписи</content>
            </ns:RequestData>
        </ns:SendDealRequest>
    </soapenv:Body>
</soapenv:Envelope>'''

canonicalized = canonicalize_xml(soap_xml)
# Готово для применения следующих трансформаций (например, СМЭВ)

Пример 3: Принудительное включение пространств имен

from xmlcanon import XmlCanonicalizer

xml_input = '''<root xmlns:force="http://force.com"
                    xmlns:used="http://used.com">
    <used:element>Только used используется в содержимом</used:element>
</root>'''

canonicalizer = XmlCanonicalizer(inclusive_ns_prefixes=['force'])
result = canonicalizer.transform(xml_input)
# Результат БУДЕТ содержать xmlns:force несмотря на неиспользование

Тестирование

# Запуск всех тестов
python -m pytest tests/

# Запуск с покрытием
python -m pytest tests/ --cov=xmlcanon --cov-report=html

# Запуск конкретного теста
python -m pytest tests/test_transform.py::TestXmlCanonicalizer::test_simple_element

Покрытие тестами

  • ✅ Базовые операции с элементами и атрибутами
  • ✅ Обработка пространств имен (объявления, исключения, включения)
  • ✅ Сортировка атрибутов и пространств имен
  • ✅ Экранирование текста и значений атрибутов
  • ✅ Реальные SOAP структуры (ГИИС ДМДК)
  • ✅ Обработка ошибок

Интеграция с XML подписями

Этот модуль предназначен для использования в качестве первой трансформации при создании XML подписей по ГОСТ:

def create_gost_xml_signature(xml_data, certificate):
    # 1. Применяем XML канонизацию
    canonicalized = canonicalize_xml(xml_data)

    # 2. Применяем СМЭВ трансформацию (отдельный модуль)
    smev_transformed = apply_smev_transform(canonicalized)

    # 3. Вычисляем хеш ГОСТ
    digest = compute_gost_digest(smev_transformed)

    # 4. Создаем подпись
    signature = create_gost_signature(digest, certificate)

    return signature

Соответствие спецификациям

  • W3C Exclusive XML Canonicalization Version 1.0 - полное соответствие
  • XML-DSig спецификация - поддержка трансформаций для подписей
  • ГОСТ стандарты - совместимость с российскими криптографическими стандартами

Производительность

Характеристики

  • Обработка XML документов до 1MB
  • Оптимизация для типичных SOAP структур
  • Минимальное потребление памяти
  • Поддержка больших документов через потоковую обработку (планируется)

Бенчмарки

  • Малый XML (< 1KB): ~0.001 сек
  • Средний XML (10-50KB): ~0.005 сек
  • Большой XML (100KB+): ~0.020 сек

Разработка

Настройка среды разработки

# Клонирование репозитория
git clone https://github.com/imdeniil/xmlcanon.git
cd xmlcanon

# Создание виртуального окружения
python -m venv venv
source venv/bin/activate  # Linux/Mac
# или
venv\Scripts\activate  # Windows

# Установка в режиме разработки
pip install -e ".[dev]"

Код стиль

# Форматирование кода
black xmlcanon/ tests/ examples/

# Проверка стиля
flake8 xmlcanon/ tests/ examples/

# Проверка типов
mypy xmlcanon/

Документация

Вклад в развитие

Модуль открыт для доработок и улучшений:

  • Issues: GitHub Issues
  • Pull Requests: приветствуются улучшения
  • Документация: в docs/CONTRIBUTING.md
  • Стиль кода: Black + PEP 8

Лицензия

Этот проект распространяется под лицензией MIT. См. файл LICENSE для подробностей.

Контакты и поддержка

История изменений

v1.0.0

  • Первый релиз
  • Полная реализация ExcC14N согласно W3C спецификации
  • Поддержка lxml и стандартной библиотеки
  • Полное покрытие тестами (14 тестов)
  • Совместимость с ГОСТ стандартами

Создано на основе анализа библиотеки GostCryptography

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

xmlcanon-1.0.0.tar.gz (29.2 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

xmlcanon-1.0.0-py3-none-any.whl (12.9 kB view details)

Uploaded Python 3

File details

Details for the file xmlcanon-1.0.0.tar.gz.

File metadata

  • Download URL: xmlcanon-1.0.0.tar.gz
  • Upload date:
  • Size: 29.2 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.7

File hashes

Hashes for xmlcanon-1.0.0.tar.gz
Algorithm Hash digest
SHA256 2c3ceae83ce394e213eedc95b6778af24ec960e409294042b6f60be373f6de90
MD5 215eb28040a35bfaf8b29e6985506223
BLAKE2b-256 c1e0595aed29749347280f4e6c1f6dd93f90c0ba0571ee9aec76efb60a8491d9

See more details on using hashes here.

File details

Details for the file xmlcanon-1.0.0-py3-none-any.whl.

File metadata

  • Download URL: xmlcanon-1.0.0-py3-none-any.whl
  • Upload date:
  • Size: 12.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.7

File hashes

Hashes for xmlcanon-1.0.0-py3-none-any.whl
Algorithm Hash digest
SHA256 68c1d80b32b8b370ce01ca4cf04ae98dec9f1a30ebdc29787e7f216a24a6bdbb
MD5 4203b264b20c06f50e0f3c281d4b2f13
BLAKE2b-256 22dec6adf3682c1381769e5549902db8e06699b52886748e440e54a92ea5365e

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page