Сжатие/Распаковка данных по алгоритму Deflate встроенными (!) средствами платформы 1С

0. Серега (SerVer1C) 49 05.05.17 02:16 Сейчас в теме
Сжатие/Распаковка данных по алгоритму Deflate встроенными (и только!) средствами платформы 1С. Теперь работать напрямую с данными в СУБД стало проще ))

Перейти к публикации

Лучшие комментарии
1. Александр Шпагин (alexandersh) 180 09.05.17 16:13 Сейчас в теме
хм, а по мне так все уже придумано)
решается конструкцией:
	
	ХЗ = Новый ХранилищеЗначения(НашеЗначениеКотороеНадоСжать, СжатиеДанных(9));
	СтрокаBase64 = СериализаторXDTO.XMLСтрока(ХЗ);
	СжатыеДвоичныеДанные = Base64Значение(СтрокаBase64);
...Показать Скрыть

и обратно:
	СтрокаBase64 = Base64Строка(СжатыеДвоичныеДанные);
	ХЗ = СериализаторXDTO.XMLЗначение(Тип("ХранилищеЗначения"), СтрокаBase64);
	НашеЗначение = ХЗ.Получить();
...Показать Скрыть

может на несколько байт и будет больше, за счет описания Хранилища значения, зато без костылей)
Alien_job; config; SerVer1C; Caliban; Aleskey_K; SvoyakMartin; philya; ZLENKO; +8 Ответить 1
Остальные комментарии
1. Александр Шпагин (alexandersh) 180 09.05.17 16:13 Сейчас в теме
хм, а по мне так все уже придумано)
решается конструкцией:
	
	ХЗ = Новый ХранилищеЗначения(НашеЗначениеКотороеНадоСжать, СжатиеДанных(9));
	СтрокаBase64 = СериализаторXDTO.XMLСтрока(ХЗ);
	СжатыеДвоичныеДанные = Base64Значение(СтрокаBase64);
...Показать Скрыть

и обратно:
	СтрокаBase64 = Base64Строка(СжатыеДвоичныеДанные);
	ХЗ = СериализаторXDTO.XMLЗначение(Тип("ХранилищеЗначения"), СтрокаBase64);
	НашеЗначение = ХЗ.Получить();
...Показать Скрыть

может на несколько байт и будет больше, за счет описания Хранилища значения, зато без костылей)
Alien_job; config; SerVer1C; Caliban; Aleskey_K; SvoyakMartin; philya; ZLENKO; +8 Ответить 1
2. Серега (SerVer1C) 49 10.05.17 10:10 Сейчас в теме
(1) Да, действительно, таким образом можно распаковать значение из бинарника, полученного из скульного значения 1с-ного ХЗ. Значит, приведенный в статье алгоритм останется для каких-то специфических задач при распаковке данных, сжатых алгоритмом Deflate каким-либо альтернативным ПО.
3. lucas ___ (lucas_) 10 10.05.17 11:51 Сейчас в теме
В развитие темы - а нельзя ли распаковать BinaryData, используя DECOMPRESS (функцию sql 2016)? Не подскажите, нет ли где описания формата запакованного бинарника 1С?
4. Серега (SerVer1C) 49 10.05.17 13:56 Сейчас в теме
(3) Судя по описанию функции DECOMPRESS, она как раз может извлечь данные из сжатого 1С-кой хранилища значений. Только придется отбросить первые 18 байт - это описание для ХЗ. Точное описание формата данного заголовка не встречал.
5. lucas ___ (lucas_) 10 10.05.17 14:20 Сейчас в теме
Нет, не получается.
Declare @b varbinary(max) =
(SELECT BinaryData FROM     Params WHERE  (FileName = N'DBNames'))
Set @b =  SUBSTRING(@b, 19, LEN(@b)-18)
Select  DECOMPRESS(@b) 
...Показать Скрыть


Выдает: Сообщение 9826, уровень 16, состояние 1, строка 4
В качестве аргумента во встроенную инструкцию DECOMPRESS переданы несжатые или поврежденные данные.
6. Александр (AlkB) 21 11.05.17 12:59 Сейчас в теме
Данный метод действительно работает. А метод с СериализаторXDTO у меня не заработал.
7. Серега (SerVer1C) 49 18.05.17 08:44 Сейчас в теме
(5) Дело вот в чем: когда мы сжимаем данные функцией COMPRESS, то получается на выходе бинарник следующей структуры: 10 байт описание GZIP формата (здесь всегда 0x1F8B0800000000000400), далее идет Deflate-поток, затем 4 байта CRC несжатых данных и в конце 4 байта - размер несжатых данных. При выполнении DECOMPRESS функция сверяет CRC и размер исходных данных из сжатого бинарника с рассчитанным CRC и размером распакованных данных. В случае их расхождения получается та самая ошибка. Из поля скуля, содержащего эсовское ХЗ, мы можем получить все, кроме CRC исходных данных. Поэтому чисто средствами скуля распаковать эсовское хранилище не получится.
Deflate-поток легко распаковывается приведенной в статье обработкой.
Также если собрать вручную GZIP на основе Deflate-потока из эсовского ХЗ и подставить корректный CRC и размер исходных данных, то DECOMPRESS распакует исходные данные.
Если кто знает, как в ф. DECOMPRESS игнорить CRC, то напишите :-)
8. lucas ___ (lucas_) 10 18.05.17 13:31 Сейчас в теме
Ну, далее - просто мысли вслух. Я не совсем уловил. 1С-бинарник где-то внутри себя содержит CRC? Это CRC такое же, как и у аналогичных данных, сжатых COMPRESS или же другое?
9. Серега (SerVer1C) 49 18.05.17 16:35 Сейчас в теме
(8) В том-то и печаль, что 1С-бинарник НЕ содержит внутри себя CRC. А ф. DECOMPRESS обязательно требует CRC исходных данных для распаковки.
10. lucas ___ (lucas_) 10 18.05.17 17:34 Сейчас в теме
Жаль. Есть еще некая функция DECOMPRESSSCALAR. Но не найти ее описания, не заставить ее работать мне пока не удалось.
11. Серега (SerVer1C) 49 19.05.17 01:18 Сейчас в теме
(10) Как я понял, это такой баг, когда IntelliSence отображает внутренние функции. И исправлять этот баг пока не собираются. Пруф: https [] connect.microsoft.com/SQLServer/feedback/details/688606/denali-ctp3-internal-system-fuctions-are-exposed-in-intellisence-hints
12. lucas ___ (lucas_) 10 19.05.17 09:11 Сейчас в теме
То есть работать на решение поставленной задачи данная функция точно не будет?
13. Серега (SerVer1C) 49 19.05.17 10:23 Сейчас в теме
(12) DECOMPRESSSCALAR - не будет. DECOMPRESS будет, если в нее передавать правильный GZIP. DECOMPRESS даже распакует архив, созданный в 7-zip с форматом GZIP и методом сжатия Deflate.
14. lucas ___ (lucas_) 10 19.05.17 12:08 Сейчас в теме
Опять же мысли вслух - CRC есть функция сжатого бинарника? Возможно, ее имеет смысл просто вычислить средствами скуля? Вот здесь http://www.zlib.org/rfc-gzip.html#crc-code, на мой первый непросвещенный взгляд, все выглядит не очень страшно.
15. Серега (SerVer1C) 49 19.05.17 13:00 Сейчас в теме
(14) CRC считается 25-ю строками кода - это не проблема. НО только CRC надо рассчитывать не от сжатых данных, а от исходных! А пока мы сжатые данные не распакуем, то не посчитаем CRC исходных данных. Вот такая вот рекурсия ))
16. Олег (Alligator84) 24.06.17 17:45 Сейчас в теме
Есть ли возможность DECOMPRESS DT?
17. Серега (SerVer1C) 49 26.06.17 11:08 Сейчас в теме
(16) Нет. Файл DT имеет сложную структуру. Вдоль и поперек данный формат исследовал пользователь awa. Почитайте его статьи.
Alligator84; +1 Ответить
Оставьте свое сообщение