Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions src/OneScript.StandardLibrary/Binary/GenericStream.cs
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ This Source Code Form is subject to the terms of the
using System;
using System.IO;
using OneScript.Contexts;
using OneScript.Exceptions;
using ScriptEngine.Machine;
using ScriptEngine.Machine.Contexts;

Expand Down Expand Up @@ -135,6 +136,8 @@ public void Close()
[ContextMethod("Записать", "Write")]
public void Write(BinaryDataBuffer buffer, int positionInBuffer, int number)
{
if (!CanWrite)
throw new RuntimeException("Попытка записи в поток не поддерживающий запись", "Cannot write to a stream that does not support writing");
_commonImpl.Write(buffer, positionInBuffer, number);
}

Expand Down Expand Up @@ -271,6 +274,8 @@ public long CurrentPosition()
[ContextMethod("УстановитьРазмер", "SetSize")]
public void SetSize(long size)
{
if (!CanWrite)
throw new RuntimeException("Попытка записи в поток не поддерживающий запись", "Cannot write to a stream that does not support writing");
_commonImpl.SetSize(size);
}

Expand Down
108 changes: 108 additions & 0 deletions tests/binary-objects.os
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,8 @@
ВсеТесты.Добавить("ТестДолжен_ПроверитьЧтоПриЗаписиВБуферСНевернымИндексомВыбрасываетсяИсключение");
ВсеТесты.Добавить("ТестДолжен_ПроверитьЧтоКорректноРаботаютПобитовыеОперацииЗаписиВБуферДвоичныхДанных");
ВсеТесты.Добавить("ТестДолжен_ПроверитьЧтоМетодОткрытьПотокДляЧтенияВозвращаетПотокТолькоДляЧтения");
ВсеТесты.Добавить("ТестДолжен_ПроверитьЧтоПолучитьПотокТолькоДляЧтенияЗапрещаетЗапись");
ВсеТесты.Добавить("ТестДолжен_ПроверитьЧтоПолучитьПотокТолькоДляЧтенияРазделяетДанныеИПозицию");
ВсеТесты.Добавить("ТестДолжен_ПроверитьЧтоХешированиеРаботаетСПотоком");
ВсеТесты.Добавить("ТестДолжен_ПроверитьЧтоХешированиеРаботаетСДвоичнымиДанными");
ВсеТесты.Добавить("ТестДолжен_ПроверитьЧтоПрочитатьБайтНеВыбрасываетИсключениеВКонцеПотока");
Expand Down Expand Up @@ -325,6 +327,112 @@

КонецПроцедуры

Процедура ТестДолжен_ПроверитьЧтоПолучитьПотокТолькоДляЧтенияЗапрещаетЗапись() Экспорт

Поток = Новый ПотокВПамяти();
Буфер = Новый БуферДвоичныхДанных(10);
Поток.Записать(Буфер, 0, 10); // Запишем какие-то данные

// Получим поток только для чтения
ПотокДляЧтения = Поток.ПолучитьПотокТолькоДляЧтения();

// Проверим, что поток помечен как read-only
юТест.ПроверитьЛожь(ПотокДляЧтения.ДоступнаЗапись);

// Попытаемся записать в поток только для чтения - должно выбросить исключение
Попытка
ПотокДляЧтения.Записать(Новый БуферДвоичныхДанных(10), 0, 10);
ВызватьИсключение "Ожидали исключение при записи в поток только для чтения, но его не было";
Исключение
ОписаниеОшибки = ИнформацияОбОшибке().Описание;
юТест.ПроверитьВхождение(ОписаниеОшибки, "Попытка записи в поток не поддерживающий запись");
КонецПопытки;

// Также проверим, что изменение размера тоже запрещено
Попытка
ПотокДляЧтения.УстановитьРазмер(20);
ВызватьИсключение "Ожидали исключение при изменении размера потока только для чтения, но его не было";
Исключение
ОписаниеОшибки = ИнформацияОбОшибке().Описание;
юТест.ПроверитьВхождение(ОписаниеОшибки, "Попытка записи в поток не поддерживающий запись");
КонецПопытки;

КонецПроцедуры

Процедура ТестДолжен_ПроверитьЧтоПолучитьПотокТолькоДляЧтенияРазделяетДанныеИПозицию() Экспорт

// Создаем поток с данными
Поток = Новый ПотокВПамяти();
Буфер = Новый БуферДвоичныхДанных(20);

// Заполним буфер данными
Для Индекс = 0 По 19 Цикл
Буфер.Установить(Индекс, Индекс + 1);
КонецЦикла;

Поток.Записать(Буфер, 0, 20);
юТест.ПроверитьРавенство(20, Поток.Размер());
юТест.ПроверитьРавенство(20, Поток.ТекущаяПозиция());

// Сбросим позицию на начало
Поток.Перейти(0, ПозицияВПотоке.Начало);
юТест.ПроверитьРавенство(0, Поток.ТекущаяПозиция());

// Получим поток только для чтения
ПотокДляЧтения = Поток.ПолучитьПотокТолькоДляЧтения();

// Проверим, что начальная позиция общая
юТест.ПроверитьРавенство(0, ПотокДляЧтения.ТекущаяПозиция());

// Прочитаем из основного потока 5 байт - позиция должна сдвинуться в обоих потоках
БуферЧтения = Новый БуферДвоичныхДанных(5);
Поток.Прочитать(БуферЧтения, 0, 5);

// Проверим, что позиция изменилась в обоих потоках
юТест.ПроверитьРавенство(5, Поток.ТекущаяПозиция());
юТест.ПроверитьРавенство(5, ПотокДляЧтения.ТекущаяПозиция());

// Прочитаем из потока только для чтения еще 3 байта
БуферЧтения2 = Новый БуферДвоичныхДанных(3);
ПотокДляЧтения.Прочитать(БуферЧтения2, 0, 3);

// Проверим, что позиция изменилась в обоих потоках
юТест.ПроверитьРавенство(8, Поток.ТекущаяПозиция());
юТест.ПроверитьРавенство(8, ПотокДляЧтения.ТекущаяПозиция());

// Проверим, что данные одинаковые - прочитали байты с 6-го по 8-й (значения 6, 7, 8)
юТест.ПроверитьРавенство(6, БуферЧтения2.Получить(0));
юТест.ПроверитьРавенство(7, БуферЧтения2.Получить(1));
юТест.ПроверитьРавенство(8, БуферЧтения2.Получить(2));

// Изменим позицию в потоке только для чтения
ПотокДляЧтения.Перейти(15, ПозицияВПотоке.Начало);

// Проверим, что позиция изменилась в обоих потоках
юТест.ПроверитьРавенство(15, Поток.ТекущаяПозиция());
юТест.ПроверитьРавенство(15, ПотокДляЧтения.ТекущаяПозиция());

// Запишем данные в основной поток (в позицию 15)
БуферЗаписи = Новый БуферДвоичныхДанных(2);
БуферЗаписи.Установить(0, 100);
БуферЗаписи.Установить(1, 200);
Поток.Записать(БуферЗаписи, 0, 2);

// Позиция должна сдвинуться в обоих потоках
юТест.ПроверитьРавенство(17, Поток.ТекущаяПозиция());
юТест.ПроверитьРавенство(17, ПотокДляЧтения.ТекущаяПозиция());

// Вернемся к позиции 15 и прочитаем из потока только для чтения
ПотокДляЧтения.Перейти(15, ПозицияВПотоке.Начало);
БуферЧтения3 = Новый БуферДвоичныхДанных(2);
ПотокДляЧтения.Прочитать(БуферЧтения3, 0, 2);

// Проверим, что мы прочитали измененные данные - данные общие между потоками
юТест.ПроверитьРавенство(100, БуферЧтения3.Получить(0));
юТест.ПроверитьРавенство(200, БуферЧтения3.Получить(1));

КонецПроцедуры

Процедура ТестДолжен_ПроверитьЧтоХешированиеРаботаетСПотоком() Экспорт

ДвоичныеДанные = ПолучитьДвоичныеДанныеИзHexСтроки("1b1e c416 6a11 c03b 3afe faea 442e 7709");
Expand Down