Class: SWS::DefinitionParser

Inherits:
Object
  • Object
show all
Includes:
Singleton
Defined in:
lib/sws/parsers.rb

Overview

Class that retrieves definition of the component from .sws and/or .api files. Parsed definitions are cached to avoid unnecessary overhead.

Instance Method Summary collapse

Constructor Details

#initializeDefinitionParser

Returns a new instance of DefinitionParser.



12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
# File 'lib/sws/parsers.rb', line 12

def initialize ()
	
	# .sws file cache
	@sws_cache = Hash.new do |hash,filename|
		$log_sws_parser.debug( "Parsing .sws #{filename}" )
		hash[filename] = YAML::load( File.open( filename ) ) #sws_parse( filename )
	end

	# .api file cache
	@api_cache = Hash.new do |hash,filename|
		$log_sws_parser.debug( "Parsing .api #{filename}" )
		hash[filename] = YAML::load( File.open( filename ) )
	end

end

Instance Method Details

#component_for_token_with_parent(token, parent) ⇒ Object

Most important method of the class - returns Component object for given token in given parent component. Does it by parsing parent definition file and looking for definition of Component with given token name. When the definition is found, new Component object with proper slots and definition (again retrieved from file and parsed) is created.



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
# File 'lib/sws/parsers.rb', line 34

def component_for_token_with_parent ( token, parent )

	
	# Element to find - component definition
	component_definition = nil
	
	# Definition is looked for in parent component recursively - up to the
	# topmost component
	next_parent = parent

	name = token.sws_name
	
	loop do 
	
		$log_sws_parser.debug( "Looking for #{name} in #{next_parent}" )
		
		# Because this is the parent (so it has children) we don't have to check
		# if the .sws file is present
		parent_definition = @sws_cache[ next_parent.definition_filename ]
		
		# Definition of component looked for in parent definition - if not
		# found, the parent's parent will be searched
		# FIXME: this will surely work incorrectly when 2 nested components have
		# subcomponents of the same name!
		component_definition = parent_definition[name]
		
		if ( component_definition != nil ) 
			break
		elsif ( next_parent.parent != nil )	
			next_parent = next_parent.parent
		else
			raise( "Definiton for component #{name} not found!" )
		end
		
	end	

	$log_sws_parser.debug( "Definition found" )
	
	# Create Component object using component_definition hash
	class_name = component_definition[ "_class" ]
	unless( class_name )
		raise( "Cannot find _class attribute for component #{token.sws_name}" )
	end
	component = Component.create( class_name, parent.request, name.dup(), parent )
	component.definition_component = next_parent
	component.html_attrs = token.attributes
	
	slots = Hash.new
	
	if ( component.api_filename != nil )
		@api_cache[ component.api_filename ].each_pair do |slot_name, slot_attrs|

			slot = Slot.new( component, slot_name )
			slot.bind( component_definition[slot_name] )

			if ( slot_attrs )
				slot.default = slot_attrs["default"]
				slot.required = slot_attrs["required"]
				slot.settable = slot_attrs["settable"]
			end

			slots[slot_name] = slot
		end
	end
	
	component.slots = slots
	component.synchronize_slots()
	return component
	
end