ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/Types-Serialiser/Serialiser.pm
Revision: 1.1
Committed: Sun Oct 27 19:49:33 2013 UTC (11 years, 1 month ago) by root
Branch: MAIN
Log Message:
*** empty log message ***

File Contents

# User Rev Content
1 root 1.1 =head1 NAME
2    
3     Types::Serialiser - simple data types for common serialisation formats
4    
5     =encoding utf-8
6    
7     =head1 SYNOPSIS
8    
9     =head1 DESCRIPTION
10    
11     This module provides some extra datatypes that are used by common
12     serialisation formats such as JSON or CBOR. The idea is to have a
13     repository of simple/small constants and containers that can be shared by
14     different implementations so they become interoperable between each other.
15    
16     =cut
17    
18     package Types::Serialiser;
19    
20     use common::sense;
21    
22     our $VERSION = 0.01;
23    
24     =head1 SIMPLE SCALAR CONSTANTS
25    
26     Simple scalar constants are values that are overloaded to act like simple
27     Perl values, but have (class) type to differentiate them from normal Perl
28     scalars. This is necessary because these have different representations in
29     the serialisation formats.
30    
31     =head2 BOOLEANS (Types::Serialiser::Boolean class)
32    
33     This type has only two instances, true and false. A natural representation
34     for these in Perl is C<1> and C<0>, but serialisation formats need to be
35     able to differentiate between them and mere numbers.
36    
37     =over 4
38    
39     =item $Types::Serialiser::true, Types::Serialiser::true
40    
41     This value represents the "true" value. In most contexts is acts like
42     the number C<1>. It is up to you whether you use the variable form
43     (C<$Types::Serialiser::true>) or the constant form (C<Types::Serialiser::true>).
44    
45     The constant is represented as a reference to a scalar containing C<1> -
46     implementations are allowed to directly test for this.
47    
48     =item $Types::Serialiser::false, Types::Serialiser::false
49    
50     This value represents the "false" value. In most contexts is acts like
51     the number C<0>. It is up to you whether you use the variable form
52     (C<$Types::Serialiser::false>) or the constant form (C<Types::Serialiser::false>).
53    
54     The constant is represented as a reference to a scalar containing C<0> -
55     implementations are allowed to directly test for this.
56    
57     =item $is_bool = Types::Serialiser::is_bool $value
58    
59     Returns true iff the C<$value> is either C<$Types::Serialiser::true> or
60     C<$Types::Serialiser::false>.
61    
62     For example, you could differentiate between a perl true value and a
63     C<Types::Serialiser::true> by using this:
64    
65     $value && Types::Serialiser::is_bool $value
66    
67     =item $is_true = Types::Serialiser::is_true $value
68    
69     Returns true iff C<$value> is C<$Types::Serialiser::true>.
70    
71     =item $is_false = Types::Serialiser::is_false $value
72    
73     Returns false iff C<$value> is C<$Types::Serialiser::false>.
74    
75     =back
76    
77     =head2 ERROR (Types::Serialiser::Error class)
78    
79     This class has only a single instance, C<error>. It is used to signal
80     an encoding or decoding error. In CBOR for example, and object that
81     couldn't be encoded will be represented by a CBOR undefined value, which
82     is represented by the error value in Perl.
83    
84     =over 4
85    
86     =item $Types::Serialiser::error, Types::Serialiser::error
87    
88     This value represents the "error" value. Accessing values of this type
89     will throw an exception.
90    
91     The constant is represented as a reference to a scalar containing C<undef>
92     - implementations are allowed to directly test for this.
93    
94     =item $is_error = Types::Serialiser::is_error $value
95    
96     Returns false iff C<$value> is C<$Types::Serialiser::error>.
97    
98     =back
99    
100     =cut
101    
102     our $true = do { bless \(my $dummy = 1), Types::Serialiser::Boolean:: };
103     our $false = do { bless \(my $dummy = 0), Types::Serialiser::Boolean:: };
104     our $error = do { bless \(my $dummy ), Types::Serialiser::Error:: };
105    
106     sub true () { $true }
107     sub false () { $false }
108     sub error () { $error }
109    
110     sub is_bool ($) { UNIVERSAL::isa $_[0], Types::Serialiser::Boolean:: }
111     sub is_true ($) { $_[0] && UNIVERSAL::isa $_[0], Types::Serialiser::Boolean:: }
112     sub is_false ($) { !$_[0] && UNIVERSAL::isa $_[0], Types::Serialiser::Boolean:: }
113     sub is_error ($) { UNIVERSAL::isa $_[0], Types::Serialiser::Error:: }
114    
115     package Types::Serialiser::Boolean;
116    
117     use overload
118     "0+" => sub { ${$_[0]} },
119     "++" => sub { $_[0] = ${$_[0]} + 1 },
120     "--" => sub { $_[0] = ${$_[0]} - 1 },
121     fallback => 1;
122    
123     package Types::Serialiser::Error;
124    
125     sub error {
126     require Carp;
127     Carp::croak ("caught attempt to use Types::Serialiser::error value");
128     };
129    
130     use overload
131     "0+" => \&error,
132     "++" => \&error,
133     "--" => \&error,
134     fallback => 1;
135    
136     =head1 BUGS
137    
138     The use of L<overload> makes this module much heavier than it should be
139     (on my system, this module: 4kB RSS, overload: 260kB RSS).
140    
141     =head1 SEE ALSO
142    
143     Currently, L<JSON::XS> and L<CBOR::XS> use these types.
144    
145     =head1 AUTHOR
146    
147     Marc Lehmann <schmorp@schmorp.de>
148     http://home.schmorp.de/
149    
150     =cut
151    
152     1
153