summaryrefslogtreecommitdiff
path: root/lib/yaml/emitter.rb
blob: a6be4a6733eccac4fb8d0a5d569d42c3d41488ef (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
#
# Output classes and methods
#

require 'yaml/baseemitter'
require 'yaml/encoding'

module YAML

	#
	# Emit a set of values
	#
    
	class Emitter

        include BaseEmitter

		attr_accessor :options

		def initialize( opts )
			opts = {} if opts.class != Hash
			@options = YAML::DEFAULTS.dup.update( opts )
            @headless = 0
            @seq_map = false
            @anchors = {}
            @anchor_extras = {}
            @active_anchors = []
            @level = -1
            self.clear
		end

		def clear
			@buffer = []
		end

        def level
            @level
        end

		#
		# Version string
		#
		def version_s
			" %YAML:#{@options[:Version]}" if @options[:UseVersion]
		end

		#
		# Header
		#
		def header
            if @headless.nonzero?
                ""
            else
                "---#{version_s} "
            end
		end

		#
		# Concatenate to the buffer
		#
		def <<( str )
            #p [ self.id, @level, str ]
			@buffer.last << str
		end

        #
        # Monitor objects and allow references
        #
        def start_object( oid )
		    @level += 1
            @buffer.push( "" )
            #p [ self.id, @level, :OPEN ]
            idx = nil
            if oid
                if @anchors.has_key?( oid )
                    idx = @active_anchors.index( oid )
                    unless idx
                        idx = @active_anchors.length
                        af_str = "&#{@options[:AnchorFormat]} " % [ idx + 1 ]
                        af_str += @anchor_extras[ @anchors[ oid ] ].to_s
                        @buffer[ @anchors[ oid ] ][0,0] = af_str
					    @headless = 0 if @anchors[ oid ].zero?
                    end
                    idx += 1
                    @active_anchors.push( oid )
                else
                    @anchors[ oid ] = @buffer.length - 1
                end
            end
            return idx
        end

		#
		# Output method
		#
		def end_object
		    @level -= 1
            @buffer.push( "" )
            #p [ self.id, @level, :END ]
			if @level < 0
				header + @buffer.to_s[@headless..-1].to_s
			end
		end
	end

end