small edit to article

This commit is contained in:
Tony Hannan 2011-07-13 15:56:16 -04:00
parent 5cc5ec477f
commit bba1c7f141

View file

@ -5,7 +5,7 @@ The [Haskell driver](http://hackage.haskell.org/package/mongoDB) is a production
### BSON ### BSON
BSON is a binary format for documents used by MongoDB but defined independently at [bsonspec.org](http://bsonspec.org). Each language has its own representation for documents but they all serialize to this format. In the Haskell [bson package](http://hackage.haskell.org/package/bson), I chose to represent a *Document* as a list of *Field*s, where each Field has a *Label* and a *Value*. This is isomorphic to an association list, but I chose a custom pair (Field) over the standard pair to make printing of documents nicer. BSON is a binary format for documents used by MongoDB but defined independently at [bsonspec.org](http://bsonspec.org). Each language has its own representation for documents but they all serialize to this format. In the Haskell [bson package](http://hackage.haskell.org/package/bson), I chose to represent a *Document* as a list of *Fields*, where each Field has a *Label* and a *Value*. This is isomorphic to an association list, but I chose a custom pair (Field) over the standard pair to make printing of documents nicer.
A *Value* is one of several basic types, which includes primitive types like Bool, Int32, Double, and UString (UTF-8 string); a handful of special BSON types like Javascript and ObjectId; and two compound types: list of Values (BSON array) and Document itself (embedded documents). To easily wrap/unwrap basic types to/from the Value sum type, I defined a type class called *Val* with *val* (wrap) and *cast* (unwrap) methods. Every basic value type is an instance of this class, so you can simply say `val "hello"` or `val 42` to get a Value, and `cast aValue :: Maybe Bool` to extract the Bool, or Nothing if it is not a Bool. The function *(=:)* constructs a Field but converts the second arg using *val* so you can construct fields directly from basic values, as in `["name" =: "Tony", "score" =: 42]`. Types that are not technically a BSON basic type but compatible with one of them are also instance of Val so they can be used as if they were. Integer, Float, and String are examples of this, their Val instance converts to/from their compatible BSON basic type. A *Value* is one of several basic types, which includes primitive types like Bool, Int32, Double, and UString (UTF-8 string); a handful of special BSON types like Javascript and ObjectId; and two compound types: list of Values (BSON array) and Document itself (embedded documents). To easily wrap/unwrap basic types to/from the Value sum type, I defined a type class called *Val* with *val* (wrap) and *cast* (unwrap) methods. Every basic value type is an instance of this class, so you can simply say `val "hello"` or `val 42` to get a Value, and `cast aValue :: Maybe Bool` to extract the Bool, or Nothing if it is not a Bool. The function *(=:)* constructs a Field but converts the second arg using *val* so you can construct fields directly from basic values, as in `["name" =: "Tony", "score" =: 42]`. Types that are not technically a BSON basic type but compatible with one of them are also instance of Val so they can be used as if they were. Integer, Float, and String are examples of this, their Val instance converts to/from their compatible BSON basic type.