Как получить бинарное представление MD5-хеша и конвертировать его в Base64 в 1С 8.2

Программист 1С v8.3 (Обычные формы) IT и автоматизация бизнеса
← На главную

В современных версиях платформы 1С (8.3.11 и выше) работа с криптографией и хешированием стала тривиальной задачей благодаря встроенным функциям. Однако на платформе 1С 8.2 или в конфигурациях, работающих в режиме совместимости со старыми версиями, разработчики часто сталкиваются с отсутствием метода ХешированиеДанных. Стандартная задача — получить MD5-хеш от строки (например, пароля) и представить его не в виде привычной 32-символьной строки (Hex), а в кодировке Base64. Разберем по шагам, как решить эту задачу, используя COM-объекты и системные библиотеки Windows.

Постановка задачи и анализ ограничений

Обычно функции хеширования возвращают результат в шестнадцатеричном виде (например, "d41d8cd98f00b204e9800998ecf8427e"). Это строковое представление 16 байт, из которых состоит MD5. Для формирования Base64 нам нужно именно исходное бинарное представление (массив из 16 чисел), а не его текстовый "слепок". Проблема в 1С 8.2 заключается в том, что стандартные средства работы с бинарными данными крайне ограничены: нет объекта ПотокВПамяти, а объект ДвоичныеДанные не позволяет напрямую манипулировать байтами.

Шаг 1. Вычисление MD5-хеша с помощью .NET

Для начала воспользуемся системным объектом System.Security.Cryptography.MD5CryptoServiceProvider. Он доступен на любой Windows-машине с установленным .NET Framework. Основная задача здесь — правильно передать строку в кодировке UTF-8 и получить обратно массив байтов.

Рассмотрим код функции, которая подготавливает данные:


Функция ПолучитьБинарныйХешMD5(ИсходнаяСтрока)
    // Создаем необходимые COM-объекты .NET
    ЛокальныйMD5 = Новый COMОбъект("System.Security.Cryptography.MD5CryptoServiceProvider");
    // Используем UTF8 без BOM для совместимости с большинством внешних сервисов
    ЛокальныйEnc = Новый COMОбъект("System.Text.UTF8Encoding");
    
    // Преобразуем строку 1С в массив байтов (SafeArray)
    МассивБайтов = ЛокальныйEnc.GetBytes_4(ИсходнаяСтрока);
    
    // Вычисляем хеш. Метод возвращает также SafeArray (16 байт)
    БинарныйХеш = ЛокальныйMD5.ComputeHash_2(МассивБайтов);
    
    Возврат БинарныйХеш;
КонецФункции

В данном примере крайне важно использовать метод GetBytes_4 и ComputeHash_2. Суффиксы с подчеркиванием и числом в именах методов COM-объектов .NET связаны с перегрузкой методов в исходном коде библиотек. В 1С невозможно вызвать перегруженные методы напрямую, поэтому обращение идет через их порядковые номера в таблице экспорта типов.

Шаг 2. Конвертация бинарного хеша в Base64

После получения БинарныйХеш (который в 1С представлен как COMSafeArray), нам нужно перевести его в Base64. В 1С 8.2 нет встроенной функции Base64Строка() для массивов, поэтому мы воспользуемся еще одним системным объектом — MSXML2.DOMDocument. Этот объект умеет эффективно работать с бинарными данными и их преобразованием в текст.

Проанализируем алгоритм конвертации:


Функция ПреобразоватьВBase64(БинарныеДанные)
    // Используем DOMDocument для работы с типами bin.base64
    Документ = Новый COMОбъект("MSXML2.DOMDocument");
    Элемент = Документ.createElement("base64");
    
    // Устанавливаем тип данных для узла
    Элемент.dataType = "bin.base64";
    
    // Записываем наш COMSafeArray в значение узла
    Элемент.nodeTypedValue = БинарныеДанные;
    
    // Получаем строковое представление
    РезультатBase64 = Элемент.text;
    
    // Очищаем переносы строк, которые DOMDocument может добавлять автоматически
    Возврат СтрЗаменить(РезультатBase64, Символы.ПС, "");
КонецФункции

Преимущество этого метода в том, что MSXML2 напрямую принимает SafeArray, который вернул нам .NET объект. Нам не нужно перебирать массив в цикле 1С, что значительно ускоряет работу при массовой обработке данных.

Шаг 3. Объединение в итоговое решение

Теперь соберем все части в единую процедуру, которую можно использовать в конфигурации. Проанализируем итоговый код, учитывая нюансы кодировок и очистку объектов.


Функция MD5_Base64(СтрокаПароля) Экспорт
    
    Попытка
        // 1. Получаем хеш
        КриптоПровайдер = Новый COMОбъект("System.Security.Cryptography.MD5CryptoServiceProvider");
        Кодировщик = Новый COMОбъект("System.Text.UTF8Encoding");
        
        БайтыСтроки = Кодировщик.GetBytes_4(СтрокаПароля);
        ХешМассив = КриптоПровайдер.ComputeHash_2(БайтыСтроки);
        
        // 2. Конвертируем в Base64 через MSXML
        XMLДок = Новый COMОбъект("MSXML2.DOMDocument");
        Узел = XMLДок.createElement("temp");
        Узел.dataType = "bin.base64";
        Узел.nodeTypedValue = ХешМассив;
        
        Результат = СтрЗаменить(Узел.text, Символы.ПС, "");
        
        // 3. Освобождаем COM-объекты
        КриптоПровайдер = Неопределено;
        Кодировщик = Неопределено;
        XMLДок = Неопределено;
        
        Возврат Результат;
    Исключение
        ЗаписьЖурналаРегистрации("Ошибка хеширования", УровеньЖурналаРегистрации.Ошибка, , , ОписаниеОшибки());
        Возврат "";
    КонецПопытки;
    
КонецФункции

Важные нюансы и рекомендации

  1. Кодировка UTF-8 и BOM: Некоторые веб-сервисы ожидают, что MD5 будет вычислен от строки без метки BOM (Byte Order Mark). Объект System.Text.UTF8Encoding в .NET по умолчанию может добавлять или учитывать BOM. Если вы получаете несовпадающие хеши с внешними системами (например, с PHP-функцией md5()), попробуйте инициализировать кодировщик с параметром Ложь, чтобы принудительно отключить BOM.
  2. Производительность: Создание COM-объектов — ресурсоемкая операция. Если вам нужно обрабатывать тысячи строк в цикле, создавайте объекты MD5CryptoServiceProvider и DOMDocument один раз вне цикла и передавайте их в функцию как параметры или используйте переменные модуля.
  3. Альтернатива через БСП: Если ваша конфигурация (даже на платформе 8.2) содержит библиотеку стандартных подсистем (БСП) последних версий для этой платформы, проверьте наличие модуля ОбщегоНазначения или специализированных криптографических модулей. В некоторых версиях УПП 1.3 уже реализованы функции математического вычисления MD5 на чистом коде 1С, что избавляет от зависимости от COM-объектов.
  4. Безопасность: Помните, что алгоритм MD5 на сегодняшний день считается криптографически небезопасным против атак поиска коллизий. Однако он все еще широко используется для проверки целостности данных и в качестве простого хеша для некритичных паролей в legacy-системах.

Используя предложенный подход, мы успешно обходим ограничения старой платформы 1С 8.2, эффективно взаимодействуя с системными компонентами Windows для получения точного бинарного представления данных.

← На главную