Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save TheFlyingFiddle/7e5d0ce8bc4850a90214 to your computer and use it in GitHub Desktop.
Save TheFlyingFiddle/7e5d0ce8bc4850a90214 to your computer and use it in GitHub Desktop.
local encoding = require "encoding"
--This gist contains some simple usage of the
--encoding library. Specificaly this gist
--focuses on typed encoding.
--We start by defining a simple type
local types = encoding.types
local itemType = types.tuple{
{ field = "id", types.varint },
{ field = "label", types.string },
{ field = "expDate", types.date } }
--This corresponds to something like this
-- Tuple 03 VARINT STRING DATE (assuming a DATE primitive type)
-- And some data of that type
local milk =
{
id = 3125
label = "Best milk you ever tasted!"
expDate = "22/12/2017"
}
local cabbage =
{
id = 1425
label = "Fresh from your local farm"
expDate = "16/12/2017"
}
local knife =
{
id = 13551
label = "Never gets dull"
}
--- Encoding and Decoding without typing specification.
--We begin the conversion process by encoding the data.
local encodedMilk = encoding.encode(milk)
local encodedCabbage = encoding.encode(cabbage)
local encodedKnife = encoding.encode(knife)
-- Since we did not specify type information for
-- the encoding it falls back to using a standard
-- generic type for all three items. This type
-- could be DYNAMIC or a UNION based type using maps.
-- In any case the data would not be packed in the most
-- efficient form since you will need some addition typing
-- information contained within the message. Inclding the names
-- of the fields.
-- Decoding
local decodedMilk = encoding.decode(encodedMilk)
local decodedCabbage = encoding.decode(encodedCabbage)
local decodedKnife = encoding.decode(encodedKnife)
--Decoding is as simmple as calling encoding.decode.
--The decoded objects should deeply equal to the
--encoded objects.
assertDeepEquals(milk, decodedMilk);
assertDeepEquals(cabbage, decodedCabbage);
assertDeepEquals(knife, decodedKnife);
--- Encoding and Decoding with typing specifications.
local encodedMilk2 = encoding.encode(milk, itemType)
local encodedCabbage2 = encoding.encode(cabbage, itemType)
-- Fails due to the absence of expData.
-- local encodedKnife = encoding.encode(knife, itemType)
-- The encoded values that where encoding with type specifications
-- Get a more specific binary layout then the onces that
-- where encoded without. This will mean that they take
-- less space in the data section since it won't have to be cluttered
-- with additional typing information.
-- Note specifically that knife can no longer be encoded since it does
-- not have all the required information.
-- Decoding
local decodedMilk2 = encoding.decode(encodedMilk2, itemType)
local decodedCabbage2 = encoding.decode(encodedCabbage2, itemType)
-- As with untyped decoding decoded(Milk/Cabbage)2 should
-- be deeply equal to milk/cabbage
assertDeepEquals(milk, decodedMilk2)
assertDeepEquals(cabbage, decodedCabbage2)
-- Take note of the fact that to get identical tables
-- both the encode and decode functions need to have
-- the type specification present in their invocation.
-- Consider what would happen if decode was called without
-- typing specifications.
local decodedMilk3 = encoding.decode(encodedMilk2)
-- What will decodedMilk3 contain?
-- Will encoding.decode even work?
-- The answer can be found if we consider what itemType
-- represents. This: TUPLE 03 VARINT STRING DATE
-- The binary encoding holds no information about our named
-- fields so this information is lost. But the raw value
-- stored is stil present. And this is the information
-- that decodedMilk3 will contain. A tuple.
-- Here is one possible interpretation
-- The implementation simply flattens the tuple.
assertEquals(decodedMilk3[1], milk.id)
assertEquals(decodedMilk3[2], milk.label)
assertEquals(decodedMilk3[3], milk.expDate)
-- Here is another
-- The implementation does not flatten the tuple
-- and keeps it as the first item in an array.
assertEquals(decodedMilk3[1][1], milk.id)
assertEquals(decodedMilk3[1][2], milk.label)
assertEquals(decodedMilk3[1][3], milk.expDate)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment