factor/extra/bson/reader/reader.factor

198 lines
5.3 KiB
Factor
Raw Normal View History

USING: accessors assocs bson.constants byte-arrays byte-vectors fry io
io.binary io.encodings.string io.encodings.utf8 kernel math namespaces
2009-03-27 11:33:49 -04:00
sequences serialize arrays calendar io.encodings ;
2009-01-03 06:48:11 -05:00
IN: bson.reader
<PRIVATE
2008-12-19 08:57:01 -05:00
TUPLE: element { type integer } name ;
2009-01-23 00:53:08 -05:00
TUPLE: state
{ size initial: -1 } { read initial: 0 } exemplar
result scope element ;
: <state> ( exemplar -- state )
[ state new ] dip
[ clone >>exemplar ] keep
clone [ >>result ] [ V{ } clone [ push ] keep >>scope ] bi
2009-04-25 04:03:09 -04:00
V{ } clone [ T_Object "" element boa swap push ] keep >>element ;
2008-12-19 08:57:01 -05:00
PREDICATE: bson-eoo < integer T_EOO = ;
PREDICATE: bson-not-eoo < integer T_EOO > ;
2008-12-19 08:57:01 -05:00
PREDICATE: bson-double < integer T_Double = ;
PREDICATE: bson-integer < integer T_Integer = ;
2008-12-19 08:57:01 -05:00
PREDICATE: bson-string < integer T_String = ;
PREDICATE: bson-object < integer T_Object = ;
PREDICATE: bson-array < integer T_Array = ;
PREDICATE: bson-binary < integer T_Binary = ;
2009-03-17 12:50:46 -04:00
PREDICATE: bson-regexp < integer T_Regexp = ;
2008-12-19 08:57:01 -05:00
PREDICATE: bson-binary-bytes < integer T_Binary_Bytes = ;
PREDICATE: bson-binary-function < integer T_Binary_Function = ;
PREDICATE: bson-binary-uuid < integer T_Binary_UUID = ;
PREDICATE: bson-binary-custom < integer T_Binary_Custom = ;
2008-12-19 08:57:01 -05:00
PREDICATE: bson-oid < integer T_OID = ;
PREDICATE: bson-boolean < integer T_Boolean = ;
2008-12-19 08:57:01 -05:00
PREDICATE: bson-date < integer T_Date = ;
PREDICATE: bson-null < integer T_NULL = ;
PREDICATE: bson-ref < integer T_DBRef = ;
GENERIC: element-read ( type -- cont? )
GENERIC: element-data-read ( type -- object )
2008-12-19 08:57:01 -05:00
GENERIC: element-binary-read ( length type -- object )
2009-03-27 11:38:29 -04:00
: byte-array>number ( seq -- number )
2009-03-27 11:33:49 -04:00
byte-array>bignum >integer ; inline
: get-state ( -- state )
2008-12-19 08:57:01 -05:00
state get ; inline
: count-bytes ( count -- )
2008-12-19 08:57:01 -05:00
[ get-state ] dip '[ _ + ] change-read drop ; inline
: read-int32 ( -- int32 )
2009-03-27 11:33:49 -04:00
4 [ read byte-array>number ] [ count-bytes ] bi ; inline
2008-12-19 08:57:01 -05:00
: read-longlong ( -- longlong )
2009-03-27 11:33:49 -04:00
8 [ read byte-array>number ] [ count-bytes ] bi ; inline
2008-12-19 08:57:01 -05:00
: read-double ( -- double )
2009-03-27 11:33:49 -04:00
8 [ read byte-array>number bits>double ] [ count-bytes ] bi ; inline
: read-byte-raw ( -- byte-raw )
2008-12-19 08:57:01 -05:00
1 [ read ] [ count-bytes ] bi ; inline
: read-byte ( -- byte )
read-byte-raw first ; inline
: read-cstring ( -- string )
2009-03-27 11:33:49 -04:00
input-stream get utf8 <decoder>
"\0" swap stream-read-until drop ; inline
2008-12-19 08:57:01 -05:00
: read-sized-string ( length -- string )
2009-03-27 11:33:49 -04:00
drop read-cstring ; inline
: read-element-type ( -- type )
2009-01-03 06:48:11 -05:00
read-byte ; inline
2008-12-19 08:57:01 -05:00
: push-element ( type name -- element )
element boa
2009-01-03 06:48:11 -05:00
[ get-state element>> push ] keep ; inline
2008-12-19 08:57:01 -05:00
: pop-element ( -- element )
2009-01-03 06:48:11 -05:00
get-state element>> pop ; inline
2008-12-19 08:57:01 -05:00
: peek-scope ( -- ht )
2009-01-03 06:48:11 -05:00
get-state scope>> peek ; inline
: read-elements ( -- )
read-element-type
element-read
2009-01-03 06:48:11 -05:00
[ read-elements ] when ; inline recursive
2008-12-19 08:57:01 -05:00
GENERIC: fix-result ( assoc type -- result )
M: bson-object fix-result ( assoc type -- result )
2009-01-03 06:48:11 -05:00
drop ;
2008-12-19 08:57:01 -05:00
M: bson-array fix-result ( assoc type -- result )
drop
values ;
2009-01-23 00:53:08 -05:00
GENERIC: end-element ( type -- )
M: bson-object end-element ( type -- )
drop ;
M: bson-array end-element ( type -- )
drop ;
M: object end-element ( type -- )
drop
pop-element drop ;
M: bson-eoo element-read ( type -- cont? )
drop
2009-01-03 06:48:11 -05:00
get-state scope>> [ pop ] keep swap ! vec assoc
pop-element [ type>> ] keep ! vec assoc element
[ fix-result ] dip
rot length 0 > ! assoc element
2008-12-19 08:57:01 -05:00
[ name>> peek-scope set-at t ]
[ drop [ get-state ] dip >>result drop f ] if ;
M: bson-not-eoo element-read ( type -- cont? )
2008-12-19 08:57:01 -05:00
[ peek-scope ] dip ! scope type
2009-03-27 11:33:49 -04:00
'[ _ read-cstring push-element [ name>> ] [ type>> ] bi
2009-01-23 00:53:08 -05:00
[ element-data-read ] keep
end-element
swap
2009-03-27 11:33:49 -04:00
] dip set-at t ;
2009-01-03 06:48:11 -05:00
: [scope-changer] ( state -- state quot )
dup exemplar>> '[ [ [ _ clone ] dip push ] keep ] ; inline
2009-01-03 06:48:11 -05:00
: (object-data-read) ( type -- object )
2008-12-19 08:57:01 -05:00
drop
read-int32 drop
get-state
2009-01-03 06:48:11 -05:00
[scope-changer] change-scope
scope>> peek ; inline
M: bson-object element-data-read ( type -- object )
(object-data-read) ;
M: bson-array element-data-read ( type -- object )
(object-data-read) ;
2008-12-19 08:57:01 -05:00
M: bson-string element-data-read ( type -- object )
drop
2009-01-23 00:53:08 -05:00
read-int32 read-sized-string ;
M: bson-integer element-data-read ( type -- object )
drop
2009-01-23 00:53:08 -05:00
read-int32 ;
2008-12-19 08:57:01 -05:00
M: bson-double element-data-read ( type -- double )
drop
2009-01-23 00:53:08 -05:00
read-double ;
2008-12-19 08:57:01 -05:00
M: bson-boolean element-data-read ( type -- boolean )
2009-03-17 12:50:46 -04:00
drop
2009-05-01 08:03:29 -04:00
read-byte 1 = ;
2009-01-23 00:53:08 -05:00
M: bson-date element-data-read ( type -- timestamp )
2009-03-17 12:50:46 -04:00
drop
read-longlong millis>timestamp ;
2008-12-19 08:57:01 -05:00
M: bson-binary element-data-read ( type -- binary )
2009-03-17 12:50:46 -04:00
drop
read-int32 read-byte element-binary-read ;
2009-01-23 00:53:08 -05:00
2009-03-17 12:50:46 -04:00
M: bson-regexp element-data-read ( type -- mdbregexp )
drop mdbregexp new
read-cstring >>regexp read-cstring >>options ;
2009-01-23 00:53:08 -05:00
M: bson-null element-data-read ( type -- bf )
drop
f ;
2008-12-19 08:57:01 -05:00
M: bson-oid element-data-read ( type -- oid )
drop
read-longlong
read-int32 oid boa ;
2008-12-19 08:57:01 -05:00
M: bson-binary-bytes element-binary-read ( size type -- bytes )
drop read ;
M: bson-binary-custom element-binary-read ( size type -- quot )
2008-12-19 08:57:01 -05:00
drop read bytes>object ;
PRIVATE>
2009-01-03 06:48:11 -05:00
USE: tools.continuations
: stream>assoc ( exemplar -- assoc bytes-read )
2009-01-03 06:48:11 -05:00
<state> dup state
[ read-int32 >>size read-elements ] with-variable
2009-03-27 11:38:29 -04:00
[ result>> ] [ read>> ] bi ;