1 module styx2000.extrautil.msgranges; 2 3 private { 4 import std.algorithm : map; 5 import std.conv : to; 6 import std..string : replace; 7 8 import styx2000.lowlevel.endianness : fromLEBytes; 9 import styx2000.protobj.styxobject : StyxObject; 10 import styx2000.protomsg : decode; 11 } 12 13 private { 14 // raw byte range 15 struct ByteMessageRange 16 { 17 private { 18 ubyte[] _bytes; 19 ubyte[] _message; 20 uint _size; 21 } 22 23 this(ubyte[] bytes...) 24 { 25 _bytes = bytes; 26 } 27 28 bool empty() @property { 29 bool isEmpty; 30 // if range contains valid message size marker 31 if (_bytes.length > 4) 32 { 33 // message marker 34 _size = fromLEBytes!uint(_bytes[0..4]); 35 // if rest's length greather than real length 36 if (_size > _bytes.length) 37 { 38 isEmpty = true; 39 } 40 } 41 else 42 { 43 isEmpty = true; 44 } 45 return isEmpty; 46 } 47 48 ubyte[] front() { 49 _message = _bytes[0.._size]; 50 return _message; 51 } 52 53 void popFront() 54 { 55 _bytes = _bytes[_size..$]; 56 } 57 } 58 } 59 60 // create message range (in byte form) from bytes 61 auto byRawMessage(ubyte[] bytes...) 62 { 63 return ByteMessageRange(bytes); 64 } 65 66 // create StyxObject range from bytes 67 auto byStyxMessage(ubyte[] bytes...) 68 { 69 return bytes.byRawMessage.map!decode; 70 } 71 72 // create string representation for entire StyxObject array 73 auto toTextObject(StyxObject[] msg) 74 { 75 return msg 76 .to!string 77 .replace(`[`, `{`) 78 .replace(`]`, `}`); 79 } 80 81 // create string representation range from bytes 82 auto byTextMessage(ubyte[] bytes...) 83 { 84 return bytes.byStyxMessage.map!toTextObject; 85 }