class Puppet::Pops::Serialization::AbstractWriter

Abstract class for protocol specific writers such as MsgPack or JSON The abstract write is capable of writing the primitive scalars:

and, by using extensions, also

@api public

Public Class Methods

new(packer, options, extension_packer = nil) click to toggle source

@param [MessagePack::Packer,JSON::Packer] packer the underlying packer stream @param [Hash] options @option options [Boolean] :tabulate `true` if tabulation is enabled (which is the default). @param [DebugPacker,nil] extension_packer Optional specific extension packer. Only used for debug output @api public

   # File lib/puppet/pops/serialization/abstract_writer.rb
33 def initialize(packer, options, extension_packer = nil)
34   @tabulate = options[:tabulate]
35   @tabulate = true if @tabulate.nil?
36   @written = {}
37   @packer = packer
38   @extension_packer = extension_packer.nil? ? packer : extension_packer
39   register_types
40 end

Public Instance Methods

build_payload() click to toggle source

Called from extension callbacks only

@api private

   # File lib/puppet/pops/serialization/abstract_writer.rb
80 def build_payload
81   raise SerializationError, "Internal error: Class #{self.class} does not implement method 'build_payload'"
82 end
extension_packer() click to toggle source

@api private

   # File lib/puppet/pops/serialization/abstract_writer.rb
85 def extension_packer
86   @extension_packer
87 end
finish() click to toggle source

Tell the underlying packer to flush. @api public

   # File lib/puppet/pops/serialization/abstract_writer.rb
44 def finish
45   @packer.flush
46 end
inspect() click to toggle source
    # File lib/puppet/pops/serialization/abstract_writer.rb
217 def inspect
218   to_s
219 end
register_type(extension_number, payload_class, &block) click to toggle source

@api private

    # File lib/puppet/pops/serialization/abstract_writer.rb
116 def register_type(extension_number, payload_class, &block)
117   @packer.register_type(extension_number, payload_class, &block)
118 end
register_types() click to toggle source

@api private

    # File lib/puppet/pops/serialization/abstract_writer.rb
121 def register_types
122   # 0x00 - 0x0F are reserved for low-level serialization / tabulation extensions
123 
124   register_type(Extension::INNER_TABULATION, Extension::InnerTabulation) do |o|
125     build_payload { |ep| ep.write(o.index) }
126   end
127 
128   register_type(Extension::TABULATION, Extension::Tabulation) do |o|
129     build_payload { |ep| ep.write(o.index) }
130   end
131 
132   # 0x10 - 0x1F are reserved for structural extensions
133 
134   register_type(Extension::ARRAY_START, Extension::ArrayStart) do |o|
135     build_payload { |ep| ep.write(o.size) }
136   end
137 
138   register_type(Extension::MAP_START, Extension::MapStart) do |o|
139     build_payload { |ep| ep.write(o.size) }
140   end
141 
142   register_type(Extension::PCORE_OBJECT_START, Extension::PcoreObjectStart) do |o|
143     build_payload { |ep| write_tpl_qname(ep, o.type_name); ep.write(o.attribute_count) }
144   end
145 
146   register_type(Extension::OBJECT_START, Extension::ObjectStart) do |o|
147     build_payload { |ep| ep.write(o.attribute_count) }
148   end
149 
150   # 0x20 - 0x2f reserved for special extension objects
151 
152   register_type(Extension::DEFAULT, Extension::Default) do |o|
153     build_payload { |ep| }
154   end
155 
156   register_type(Extension::COMMENT, Extension::Comment) do |o|
157     build_payload { |ep| ep.write(o.comment) }
158   end
159 
160   register_type(Extension::SENSITIVE_START, Extension::SensitiveStart) do |o|
161     build_payload { |ep| }
162   end
163 
164   # 0x30 - 0x7f reserved for mapping of specific runtime classes
165 
166   register_type(Extension::REGEXP, Regexp) do |o|
167     build_payload { |ep| ep.write(o.source) }
168   end
169 
170   register_type(Extension::TYPE_REFERENCE, Types::PTypeReferenceType) do |o|
171     build_payload { |ep| ep.write(o.type_string) }
172   end
173 
174   register_type(Extension::SYMBOL, Symbol) do |o|
175     build_payload { |ep| ep.write(o.to_s) }
176   end
177 
178   register_type(Extension::TIME, Time::Timestamp) do |o|
179     build_payload { |ep| nsecs = o.nsecs; ep.write(nsecs / 1000000000); ep.write(nsecs % 1000000000) }
180   end
181 
182   register_type(Extension::TIMESPAN, Time::Timespan) do |o|
183     build_payload { |ep| nsecs = o.nsecs; ep.write(nsecs / 1000000000); ep.write(nsecs % 1000000000) }
184   end
185 
186   register_type(Extension::VERSION, SemanticPuppet::Version) do |o|
187     build_payload { |ep| ep.write(o.to_s) }
188   end
189 
190   register_type(Extension::VERSION_RANGE, SemanticPuppet::VersionRange) do |o|
191     build_payload { |ep| ep.write(o.to_s) }
192   end
193 
194   if supports_binary?
195     register_type(Extension::BINARY, Types::PBinaryType::Binary) do |o|
196       # The Ruby MessagePack implementation has special treatment for "ASCII-8BIT" strings. They
197       # are written as binary data.
198       build_payload { |ep| ep.write(o.binary_buffer) }
199     end
200   else
201     register_type(Extension::BASE64, Types::PBinaryType::Binary) do |o|
202       build_payload { |ep| ep.write(o.to_s) }
203     end
204   end
205 
206   URI.scheme_list.values.each do |uri_class|
207     register_type(Extension::URI, uri_class) do |o|
208       build_payload { |ep| ep.write(o.to_s) }
209     end
210   end
211 end
supports_binary?() click to toggle source
   # File lib/puppet/pops/serialization/abstract_writer.rb
48 def supports_binary?
49   false
50 end
to_s() click to toggle source
    # File lib/puppet/pops/serialization/abstract_writer.rb
213 def to_s
214   "#{self.class.name}"
215 end
write(value) click to toggle source

Write a value on the underlying stream @api public

   # File lib/puppet/pops/serialization/abstract_writer.rb
54 def write(value)
55   written = false
56   case value
57   when Integer
58     # not tabulated, but integers larger than 64-bit cannot be allowed.
59     raise SerializationError, _('Integer out of bounds') if value > MAX_INTEGER || value < MIN_INTEGER
60   when Numeric, Symbol, Extension::NotTabulated, true, false, nil
61     # not tabulated
62   else
63     if @tabulate
64       index = @written[value]
65       if index.nil?
66         @packer.write(value)
67         written = true
68         @written[value] = @written.size
69       else
70         value = Extension::InnerTabulation.new(index)
71       end
72     end
73   end
74   @packer.write(value) unless written
75 end
write_tpl(ep, value) click to toggle source

Called from extension callbacks only

@api private

    # File lib/puppet/pops/serialization/abstract_writer.rb
101 def write_tpl(ep, value)
102   #TRANSLATORS 'Integers' is a Ruby class for numbers and should not be translated
103   raise ArgumentError, _('Internal error. Integers cannot be tabulated in extension payload') if value.is_a?(Integer)
104   if @tabulate
105     index = @written[value]
106     if index.nil?
107       @written[value] = @written.size
108     else
109       value = index
110     end
111   end
112   ep.write(value)
113 end
write_tpl_qname(ep, qname) click to toggle source

Called from extension callbacks only

@api private

   # File lib/puppet/pops/serialization/abstract_writer.rb
92 def write_tpl_qname(ep, qname)
93   names = qname.split('::')
94   ep.write(names.size)
95   names.each {|n| write_tpl(ep, n)}
96 end