[Pharo-users] [squeak-dev] encoding challenge
Robert Withers
robert.w.withers at gmail.com
Mon Dec 21 21:03:03 UTC 2015
Thank you, this is good. I was modeling DateAndTime as UTCTime, which is
a specified format for two digit years:
http://www.obj-sys.com/asn1tutorial/node15.html. I noticed this other
time representation while lookin... GeneralizedTime:
http://www.obj-sys.com/asn1tutorial/node14.html. To meet that format
with padding, I decided to convert to strings. Not pretty but there is a
test! :)
Unfortunately the ASN.1 DER endoding for time is specific format. I
coudl just throws milliseconds in an integer slot, but I wanted to meet
the spec as well for a full ASN.1 tool. I am undecided whether to use
ASN.1 for header encoding in SecureSession, or custom binary
specification - I use the second option at this time. Yet I am in the
middle of redefining that message protocol, so now would be the time to
decide.
Fuel and I have a date coming up, for sure.
thank you,
Robert
On 12/21/2015 03:34 PM, Sven Van Caekenberghe wrote:
> Robert,
>
>> On 19 Dec 2015, at 07:09, Robert Withers <robert.w.withers at gmail.com> wrote:
>>
>> A core part of communications, whether online or to persistence, is encoding, or marshalling. Let's do an example! Thank you for your thoughtful, earnest participation, as God wills it.
>>
>> Here are 2 methods that encode and decode a DateAndTime object, but rather poorly. I've been going without much sleep for a bit and I can't figure it out. Here is the code in hopes that some will find this an interesting exercise in team and community building. For that intention, as a beginning. What's the best solution?
>>
>> Let's show them how to code when given the space in the environment. Tnks! :)
>>
>> In class ASN1UTCTimeType..
>>
>> encodeValue: anObject withDERStream: derStream
>>
>> | yy mo dd hh mm ss utcDateTime |
>> yy := anObject year asString copyFrom: 3 to: 4.
>> mo := anObject month asString padded: #left to: 2 with: $0.
>> dd := anObject dayOfMonth asString padded: #left to: 2 with: $0.
>> hh := anObject hour asString padded: #left to: 2 with: $0.
>> mm := anObject minute asString padded: #left to: 2 with: $0.
>> ss := anObject seconds asString padded: #left to: 2 with: $0.
>> utcDateTime := (yy, mo, dd, hh, mm, ss, 'Z') asByteArray.
>> derStream nextPutAll: utcDateTime.
>>
>>
>>
>> decodeValueWithDERStream: derStream length: length
>>
>> | aUTCDateTime |
>> aUTCDateTime := (derStream next: length) asByteArray asString.
>> ^ (DateAndTime readFromString: (
>> ((aUTCDateTime copyFrom: 1 to: 2) asInteger > 50 ifTrue: ['19'] ifFalse: ['20']),
>> (aUTCDateTime copyFrom: 1 to: 2), '-',
>> (aUTCDateTime copyFrom: 3 to: 4), '-',
>> (aUTCDateTime copyFrom: 5 to: 6), 'T',
>> (aUTCDateTime copyFrom: 7 to: 8), ':',
>> (aUTCDateTime copyFrom: 9 to: 10), ':',
>> (aUTCDateTime copyFrom: 11 to: 12)))
>> offset: 0
>>
>>
>> --
>> . .. .. ^,^ robert
> Like you say, this is *not* good, because it is pretty inefficient. You want to encode binary, yet you create a string representation. But even that is done badly ;-) Any you are introducing 2YK all over again.
>
> Anyway, the solution is to encode the timestamp using one or more numbers, directly. From your code I assume you are only interested in second precision and the UTC/GMT/Z timezone. In that case either one rather large number (seconds since X, like unix time) or two smaller numbers (julian day number and seconds since midnight) are way more efficient.
>
> For inspiration, have a look at Fuel's DateAndTime>>#serializeOn: (that also encodes nanoseconds and the timezone).
>
> HTH,
>
> Sven
>
>
>
--
. .. ... ^,^ robert
Go Panthers!
More information about the Squeak-dev
mailing list
|