Extensible Serialization class with type classes

I've been trying to put together a type-class based serialization (XML) for types in GHC. Essentially the serializer class takes the form class Seriliazer a where serialize :: a -> XmlFilter This works very well, but I then wanted to make this system extensible, so that for example for types which are also typed by equivalent XSD Types (i.e. types with constraint XSDType a => a) could have their type-data encoded into the tree. The problem is, it seems to me there is no viable method of adding an extra parameter function to the serialiaze function, which will enforce extra constraints on a and allow recursive serialization. Obviously simply passing a function (C a => a -> XmlFilter) doesn't work, since the type a becomes unified to the top-level type and so can't be passed down. The second attempt was to add another type class called Hook, with two type variables; the first being a dummy type and the second the variable to represent the type being serialized; class Hook a t where hookAttr :: t -> a -> [(String, String)] hookElem :: t -> a -> [XmlFilter] and rewriting serialize as class Hook a t => Serializer a t where serialize :: t -> a -> XmlFilter Then, passing the dummy type to the serialized function as the t value would force the extra constraints from its Hook instance on a. This method though doesn't really work that well; first of all it requires undecidable-instances and second each new instance on serialize requires a humongous context since each type used directly and indirectly needs inferring as an instance of Hook. The idea was that this code could be generated automatically, and that really makes it too difficult to do. The Third attempt was to use existential types to encapsulate a constrained polymorphic type and use Typeable + Generics to choose between a number of functions. This though doesn't work either, since each value down the type tree needs to be of the appropriate monomorphic existentially quantified type since polymorphic types aren't Typeable. I seem to have pretty much exhausted every option for building this extensible Serializer, and so my question is this; is there anyway of passing a hook function to the serializer class instances, such that it will remain polymorphic down the serialization tree but will also enforce the constraints on the input parameter on the type being serialized. For example is it every likely to be possible to reify polymorphic types? -Si.

Simon David Foster wrote:
I've been trying to put together a type-class based serialization (XML) for types in GHC. Essentially the serializer class takes the form
...
The Third attempt was to use existential types to encapsulate a constrained polymorphic type and use Typeable + Generics to choose between a number of functions. This though doesn't work either, since each value down the type tree needs to be of the appropriate monomorphic existentially quantified type since polymorphic types aren't Typeable.
Hi Simon, I think you should be able to succeed with Scrap your boilerplate. (I am not sure that you need existentials.) For the overall XmlIsh style of type erasue and type validation see the XmlIsh example at: http://www.cs.vu.nl/boilerplate/ Regarding Typeable and polymorphism, see the 2nd boilerplate paper: in particular Section 7. Same web site. For paper, you need to a recent GHC build (April 2004 or later). Regards, Ralf

On Thu, 2004-08-26 at 20:52, Ralf Laemmel wrote:
Hi Simon,
I think you should be able to succeed with Scrap your boilerplate. (I am not sure that you need existentials.)
For the overall XmlIsh style of type erasue and type validation see the XmlIsh example at: http://www.cs.vu.nl/boilerplate/
The main requirements for the XML serializer are; 1) It should be scalable; so users should be able to import a compile module with the basic XML infrastructure and add serializers for new Complex and Simple (i.e. leaf node) types. 2) It should be optionally typeable; there exists several systems for typing an XML document, the most prominent of which is XSD. The main requirement is that if the XML tree is to be typed, clearly each node in the tree must be associated with mapping to an XSD name and name-space (2 Strings) or some other data items if typing by another system. The way I was planning on doing this was using a class; XSDType a with functions xsdType :: a -> String and xsdNS :: a -> String. Then at serialisation if a particular type and all it's constituent types were XSD Typeable, extra data (i.e. an extra attribute type="nsp:name") can (again optionally) be inserted into the tree. The XmlIsh example uses a number of functions for serialising different data-types down the tree. I'm not sure how scalable doing it this way would be; can you integrate a type-class system with it? The other problem is dealing with Schematic extensions, such as SOAP Arrays which have the requirement that the elements are always typeable but should not be part of the core serialiser. My other question is, section 7 only mentions polymorphic types which hold constraints Data, Typeable and Typeable1; can the new Generics deal with other polymorphic constraints? This is the main problem; the type-class system can deal fine with just serialisation of data-type content, it just doesn't seem to be able to handle an optional type-system. Ideally I need to produce a system where one XML namespace maps to one module and that module provides data-types, serialisers and typers for the given XML types, such that other modules which use those data-types themselves should be able to import that module and its serialisers to (heuristically) build serialisers for itself. -Si.
participants (2)
-
Ralf Laemmel
-
Simon David Foster