From: Michal Fojtik <[email protected]>
Signed-off-by: Michal fojtik <[email protected]> --- server/lib/deltacloud/models/hardware_profile.rb | 194 ++++++++++++++++++++++ server/lib/deltacloud/models/state_machine.rb | 99 +++++++++++ server/lib/deltacloud/state_machine.rb | 115 ------------- 3 files changed, 293 insertions(+), 115 deletions(-) create mode 100644 server/lib/deltacloud/models/hardware_profile.rb create mode 100644 server/lib/deltacloud/models/state_machine.rb delete mode 100644 server/lib/deltacloud/state_machine.rb diff --git a/server/lib/deltacloud/models/hardware_profile.rb b/server/lib/deltacloud/models/hardware_profile.rb new file mode 100644 index 0000000..45e77a1 --- /dev/null +++ b/server/lib/deltacloud/models/hardware_profile.rb @@ -0,0 +1,194 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. The +# ASF licenses this file to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance with the +# License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. + +module Deltacloud + class HardwareProfile + + UNITS = { + :memory => "MB", + :storage => "GB", + :architecture => "label", + :cpu => "count" + } + + def self.unit(name) + UNITS[name] + end + + class Property + attr_reader :name, :kind, :default + # kind == :range + attr_reader :first, :last + # kind == :enum + attr_reader :values + # kind == :fixed + attr_reader :value + + def initialize(name, values, opts = {}) + @name = name + if values.is_a?(Range) + @kind = :range + @first = values.first + @last = values.last + @default = values.first + elsif values.is_a?(Array) + @kind = :enum + @values = values + @default = values.first + else + @kind = :fixed + @value = values + @default = @value + end + @default = opts[:default] if opts[:default] + end + + def unit + HardwareProfile.unit(name) + end + + def param + :"hwp_#{name}" + end + + def fixed? + kind == :fixed + end + + def valid?(v) + v = convert_property_value_type(v) + case kind + # NOTE: + # Currently we cannot validate fixed values because of UI + # limitation. In UI we have multiple hwp_* properties which overide + # each other. + # Then provider have one 'static' hardware profile and one + # 'customizable' when user select the static one the UI also send + # values from the customizable one (which will lead to a validation + # error because validation algorith will think that client want to + # overide fixed values. + # + # when :fixed then (v == @default.to_s) + when :fixed then true + when :range then match_type?(first, v) and (first..last).include?(v) + when :enum then match_type?(values.first, v) and values.include?(v) + else false + end + end + + def to_param + if defined? Sinatra::Rabbit + Sinatra::Rabbit::Param.new([param, :string, :optional, []]) + end + end + + def include?(v) + if kind == :fixed + return v == value + else + return values.include?(v) + end + end + + private + + def match_type?(reference, value) + true if reference.class == value.class + end + + def convert_property_value_type(v) + return v.to_f if v =~ /(\d+)\.(\d+)/ + return v.to_i if v =~ /(\d+)/ + v.to_s + end + end + + class << self + def property(prop) + define_method(prop) do |*args| + values, opts, *ignored = *args + instvar = :"@#{prop}" + unless values.nil? + @properties[prop] = Property.new(prop, values, opts || {}) + end + @properties[prop] + end + end + end + + attr_reader :name + property :cpu + property :architecture + property :memory + property :storage + + def initialize(name,&block) + @properties = {} + @name = name + instance_eval &block if block_given? + end + + def each_property(&block) + @properties.each_value { |prop| yield prop } + end + + def properties + @properties.values + end + + def property(name) + @properties[name.to_sym] + end + + def default?(prop, v) + p = @properties[prop.to_sym] + p && p.default.to_s == v + end + + def to_hash + props = [] + self.each_property do |p| + if p.kind.eql? :fixed + props << { :kind => p.kind, :value => p.value, :name => p.name, :unit => p.unit } + else + param = { :operation => "create", :method => "post", :name => p.name } + if p.kind.eql? :range + param[:range] = { :first => p.first, :last => p.last } + elsif p.kind.eql? :enum + param[:enum] = p.values.collect { |v| { :entry => v } } + end + param + props << { :kind => p.kind, :value => p.default, :name => p.name, :unit => p.unit, :param => param } + end + end + { + :id => self.name, + :properties => props + } + end + + def include?(prop, v) + p = @properties[prop] + p.nil? || p.include?(v) + end + + def params + @properties.values.inject([]) { |m, prop| + m << prop.to_param + }.compact + end + end +end diff --git a/server/lib/deltacloud/models/state_machine.rb b/server/lib/deltacloud/models/state_machine.rb new file mode 100644 index 0000000..19fb9f2 --- /dev/null +++ b/server/lib/deltacloud/models/state_machine.rb @@ -0,0 +1,99 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. The +# ASF licenses this file to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance with the +# License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. + +module Deltacloud + class StateMachine + + attr_reader :states + def initialize(&block) + @states = [] + instance_eval &block if block + end + + def start() + state(:start) + end + + def finish() + state(:finish) + end + + def state(name) + state = @states.find{|e| e.name == name.to_sym} + if ( state.nil? ) + state = State.new( self, name.to_sym ) + @states << state + end + state + end + + def method_missing(sym,*args) + return state( sym ) if ( args.empty? ) + super( sym, *args ) + end + + class State + + attr_reader :name + attr_reader :transitions + + def initialize(machine, name) + @machine = machine + @name = name + @transitions = [] + end + + def to_s + self.name.to_s + end + + def to(destination_name) + destination = @machine.state(destination_name) + transition = Transition.new( @machine, destination ) + @transitions << transition + transition + end + + end + + class Transition + + attr_reader :destination + attr_reader :action + + def initialize(machine, destination) + @machine = machine + @destination = destination + @auto = false + @action = nil + end + + def automatically + @auto = true + end + + def automatically? + @auto + end + + def on(action) + @action = action + end + + end + + end +end diff --git a/server/lib/deltacloud/state_machine.rb b/server/lib/deltacloud/state_machine.rb deleted file mode 100644 index facd4ba..0000000 --- a/server/lib/deltacloud/state_machine.rb +++ /dev/null @@ -1,115 +0,0 @@ -# -# Licensed to the Apache Software Foundation (ASF) under one or more -# contributor license agreements. See the NOTICE file distributed with -# this work for additional information regarding copyright ownership. The -# ASF licenses this file to you under the Apache License, Version 2.0 (the -# "License"); you may not use this file except in compliance with the -# License. You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT -# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the -# License for the specific language governing permissions and limitations -# under the License. - -module Deltacloud - class StateMachine - - attr_reader :states - def initialize(opts = {}, &block) - @all_states = opts[:all_states] - @all_actions = opts[:all_actions] - @states = [] - instance_eval &block if block - end - - def start() - state(:start) - end - - def finish() - state(:finish) - end - - def state(name) - unless valid_state_name?(name) - raise "State '#{name}' not in list of allowed states" - end - state = @states.find{|e| e.name == name.to_sym} - if ( state.nil? ) - state = State.new( self, name.to_sym ) - @states << state - end - state - end - - def valid_state_name?(name) - @all_states.nil? || @all_states.include?(name.to_sym) - end - - def valid_action_name?(name) - @all_actions.nil? || @all_actions.include?(name.to_sym) - end - - def method_missing(sym,*args) - return state( sym ) if ( args.empty? ) - super( sym, *args ) - end - - class State - - attr_reader :name - attr_reader :transitions - - def initialize(machine, name) - @machine = machine - @name = name - @transitions = [] - end - - def to_s - self.name.to_s - end - - def to(destination_name) - destination = @machine.state(destination_name) - transition = Transition.new( @machine, destination ) - @transitions << transition - transition - end - - end - - class Transition - - attr_reader :destination - attr_reader :action - - def initialize(machine, destination) - @machine = machine - @destination = destination - @auto = false - @action = nil - end - - def automatically - @auto = true - end - - def automatically? - @auto - end - - def on(action) - unless @machine.valid_action_name?(action) - raise "Action '#{action}' not in list of allowed actions" - end - @action = action - end - - end - - end -end -- 1.7.10
