Add support for custom shapes

These changes simplify the handling of Shapes, clean up the relationship between Shapes and hard-coded functionality in Node and EncodeRef, and (at last) enable custom Shapes. A new test case shows how to write a Shape for a simple HList implementation and uses it for table definitions (* projection), intermediate expressions in queries, and values returned from a query, including nested HLists.

Review by @cvogt