wakame 0.5.0 → 0.5.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (111) hide show
  1. data/History.txt +4 -0
  2. data/LICENSE +202 -0
  3. data/Rakefile +11 -12
  4. data/VERSION +1 -1
  5. data/app_generators/wakame/templates/bin/wakame-agent +1 -1
  6. data/app_generators/wakame/templates/bin/wakame-master +1 -1
  7. data/app_generators/wakame/templates/config/cluster.rb +32 -24
  8. data/app_generators/wakame/templates/config/init.d/centos/wakame-agent +40 -0
  9. data/app_generators/wakame/templates/config/init.d/centos/wakame-master +40 -0
  10. data/app_generators/wakame/templates/config/init.d/wakame-master +1 -1
  11. data/lib/ext/eventmachine.rb +5 -5
  12. data/lib/wakame.rb +12 -0
  13. data/lib/wakame/action.rb +10 -11
  14. data/lib/wakame/actions/deploy_application.rb +61 -0
  15. data/lib/wakame/actions/deploy_config.rb +1 -3
  16. data/lib/wakame/actions/freeze_cluster.rb +15 -0
  17. data/lib/wakame/actions/launch_cluster.rb +1 -3
  18. data/lib/wakame/actions/launch_vm.rb +1 -1
  19. data/lib/wakame/actions/migrate_service.rb +4 -3
  20. data/lib/wakame/actions/notify_child_changed.rb +3 -6
  21. data/lib/wakame/actions/notify_parent_changed.rb +4 -7
  22. data/lib/wakame/actions/propagate_resource.rb +1 -3
  23. data/lib/wakame/actions/propagate_service.rb +1 -3
  24. data/lib/wakame/actions/register_agent.rb +43 -0
  25. data/lib/wakame/actions/reload_service.rb +2 -2
  26. data/lib/wakame/actions/shutdown_cluster.rb +4 -6
  27. data/lib/wakame/actions/shutdown_vm.rb +27 -6
  28. data/lib/wakame/actions/start_service.rb +40 -32
  29. data/lib/wakame/actions/stop_service.rb +8 -10
  30. data/lib/wakame/actions/unfreeze_cluster.rb +15 -0
  31. data/lib/wakame/actor.rb +2 -5
  32. data/lib/wakame/actor/deploy.rb +110 -0
  33. data/lib/wakame/actor/monitor.rb +14 -0
  34. data/lib/wakame/actor/s3fs.rb +45 -0
  35. data/lib/wakame/actor/service_monitor.rb +0 -17
  36. data/lib/wakame/actor/system.rb +5 -1
  37. data/lib/wakame/agent.rb +29 -179
  38. data/lib/wakame/agent_manager.rb +11 -0
  39. data/lib/wakame/agent_managers/actor_manager.rb +101 -0
  40. data/lib/wakame/agent_managers/monitor_manager.rb +48 -0
  41. data/lib/wakame/command.rb +4 -7
  42. data/lib/wakame/command/actor.rb +9 -12
  43. data/lib/wakame/command/agent_status.rb +2 -2
  44. data/lib/wakame/command/control_service.rb +66 -0
  45. data/lib/wakame/command/deploy_application.rb +18 -0
  46. data/lib/wakame/command/deploy_config.rb +16 -0
  47. data/lib/wakame/command/launch_cluster.rb +1 -1
  48. data/lib/wakame/command/launch_vm.rb +1 -1
  49. data/lib/wakame/command/propagate_resource.rb +1 -1
  50. data/lib/wakame/command/propagate_service.rb +5 -3
  51. data/lib/wakame/command/reload_service.rb +1 -1
  52. data/lib/wakame/command/shutdown_cluster.rb +1 -1
  53. data/lib/wakame/command/shutdown_vm.rb +37 -11
  54. data/lib/wakame/command/start_service.rb +1 -1
  55. data/lib/wakame/command/status.rb +6 -4
  56. data/lib/wakame/command/stop_service.rb +1 -1
  57. data/lib/wakame/configuration.rb +5 -0
  58. data/lib/wakame/event.rb +85 -33
  59. data/lib/wakame/event_dispatcher.rb +2 -2
  60. data/lib/wakame/initializer.rb +97 -31
  61. data/lib/wakame/master.rb +23 -346
  62. data/lib/wakame/master_manager.rb +11 -0
  63. data/lib/wakame/master_managers/action_manager.rb +321 -0
  64. data/lib/wakame/master_managers/agent_monitor.rb +166 -0
  65. data/lib/wakame/master_managers/cluster_manager.rb +176 -0
  66. data/lib/wakame/master_managers/command_queue.rb +133 -0
  67. data/lib/wakame/models/agent_pool.rb +113 -0
  68. data/lib/wakame/models/application_repository.rb +34 -0
  69. data/lib/wakame/models/object_store.rb +32 -0
  70. data/lib/wakame/models/service_cluster_pool.rb +36 -0
  71. data/lib/wakame/monitor.rb +3 -6
  72. data/lib/wakame/monitor/agent.rb +9 -6
  73. data/lib/wakame/monitor/service.rb +56 -29
  74. data/lib/wakame/runner/administrator_command.rb +210 -24
  75. data/lib/wakame/runner/agent.rb +2 -0
  76. data/lib/wakame/runner/master.rb +2 -1
  77. data/lib/wakame/service.rb +140 -130
  78. data/lib/wakame/status_db.rb +101 -121
  79. data/lib/wakame/util.rb +26 -15
  80. data/tests/setup_master.rb +1 -0
  81. data/tests/test_master.rb +0 -2
  82. data/tests/test_model_agent_pool.rb +21 -0
  83. data/tests/test_service.rb +14 -8
  84. data/tests/test_status_db.rb +2 -0
  85. data/tests/test_util.rb +12 -1
  86. data/wakame_generators/resource/templates/apache_app/apache_app.rb +20 -11
  87. data/wakame_generators/resource/templates/apache_app/conf/vh/aaa.test.conf +1 -1
  88. data/wakame_generators/resource/templates/apache_lb/apache_lb.rb +7 -7
  89. data/wakame_generators/resource/templates/apache_lb/conf/system-lb.conf +6 -4
  90. data/wakame_generators/resource/templates/apache_www/apache_www.rb +15 -13
  91. data/wakame_generators/resource/templates/ec2_elastic_ip/ec2_elastic_ip.rb +17 -17
  92. data/wakame_generators/resource/templates/ec2_elb/ec2_elb.rb +22 -15
  93. data/wakame_generators/resource/templates/mongodb/conf/mongodb.conf +95 -0
  94. data/wakame_generators/resource/templates/mongodb/init.d/mongodb +244 -0
  95. data/wakame_generators/resource/templates/mongodb/mongodb.rb +64 -0
  96. data/wakame_generators/resource/templates/mysql_master/mysql_master.rb +17 -21
  97. data/wakame_generators/resource/templates/nginx/conf/nginx.conf +4 -0
  98. data/wakame_generators/resource/templates/nginx/conf/vh/ec2_elb_common.conf +19 -0
  99. data/wakame_generators/resource/templates/nginx/init.d/nginx +6 -0
  100. data/wakame_generators/resource/templates/nginx/init.d/spawn-fcgi +46 -0
  101. data/wakame_generators/resource/templates/nginx/nginx.rb +15 -10
  102. data/wakame_generators/resource/templates/nginx_passenger/conf/nginx-passenger.conf +39 -0
  103. data/wakame_generators/resource/templates/nginx_passenger/conf/vh/ec2_elb_common.conf +10 -0
  104. data/wakame_generators/resource/templates/nginx_passenger/init.d/nginx-passenger +70 -0
  105. data/wakame_generators/resource/templates/nginx_passenger/nginx_passenger.rb +71 -0
  106. data/wakame_generators/resource/templates/s3fs/s3fs.rb +24 -0
  107. metadata +195 -74
  108. data/lib/wakame/action_manager.rb +0 -303
  109. data/lib/wakame/command/clone_service.rb +0 -12
  110. data/lib/wakame/command_queue.rb +0 -135
  111. data/lib/wakame/vm_manipulator.rb +0 -187
@@ -66,6 +66,8 @@ module Wakame
66
66
  daemonize(@options[:log_file])
67
67
  end
68
68
 
69
+ Initializer.run(:process_agent)
70
+
69
71
  EM.epoll if Wakame.config.eventmachine_use_epoll
70
72
  EM.run {
71
73
  Wakame::Agent.start(opts)
@@ -66,7 +66,8 @@ module Wakame
66
66
  end
67
67
 
68
68
  change_privilege(@options[:uid]) if @options[:uid]
69
-
69
+
70
+ Initializer.run(:process_master)
70
71
 
71
72
  EM.epoll if Wakame.config.eventmachine_use_epoll
72
73
  EM.run {
@@ -24,6 +24,7 @@ module Wakame
24
24
  STATUS_MIGRATING = 7
25
25
  STATUS_ENTERING = 8
26
26
  STATUS_QUITTING = 9
27
+ STATUS_RUNNING = 10
27
28
 
28
29
  # Data model for agent
29
30
  # Status life cycle:
@@ -35,11 +36,15 @@ module Wakame
35
36
  STATUS_ONLINE = 1
36
37
  STATUS_UNKNOWN = 2
37
38
  STATUS_TIMEOUT = 3
39
+ STATUS_RUNNING = 4
40
+ STATUS_REGISTERRING = 5
41
+ STATUS_TERMINATING = 6
38
42
 
39
43
  property :last_ping_at
40
44
  property :vm_attr
41
45
  property :root_path
42
46
  property :status, {:read_only=>true, :default=>STATUS_INIT}
47
+ property :monitor_status, {:read_only=>true, :default=>STATUS_INIT}
43
48
  property :reported_services, {:read_only=>true, :default=>{}}
44
49
  property :cloud_host_id
45
50
 
@@ -56,11 +61,15 @@ module Wakame
56
61
  end
57
62
 
58
63
  def agent_ip
59
- vm_attr[:local_ipv4]
64
+ vm_attr[:private_dns_name]
60
65
  end
61
66
 
62
67
  def vm_id
63
- vm_attr[:instance_id]
68
+ vm_attr[:aws_instance_id]
69
+ end
70
+
71
+ def cloud_host
72
+ self.cloud_host_id.nil? ? nil : CloudHost.find(self.cloud_host_id)
64
73
  end
65
74
 
66
75
  # Tentative...
@@ -73,6 +82,13 @@ module Wakame
73
82
  if @status != new_status
74
83
  @status = new_status
75
84
  self.save
85
+ end
86
+ end
87
+
88
+ def update_monitor_status(new_status)
89
+ if @monitor_status != new_status
90
+ @monitor_status = new_status
91
+ self.save
76
92
 
77
93
  ED.fire_event(Event::AgentStatusChanged.new(self))
78
94
  # Send status specific event
@@ -83,6 +99,9 @@ module Wakame
83
99
  end
84
100
  end
85
101
 
102
+ def actor_request(path, *args)
103
+ Master.instance.actor_request(self.id, path, *args)
104
+ end
86
105
 
87
106
  def renew_reported_services(svc_id_list)
88
107
  reported_services.clear
@@ -101,120 +120,22 @@ module Wakame
101
120
  end
102
121
 
103
122
  def terminate
104
- end
105
- end
106
-
107
- class AgentPool < StatusDB::Model
108
- property :group_observed, {:default=>{}}
109
- property :group_active, {:default=>{}}
110
-
111
- ID=self.to_s
112
-
113
- def self.instance
114
- a = self.find(ID)
115
- if a.nil?
116
- a = self.new
117
- a.save
118
- end
119
- a
120
- end
121
-
122
- def self.reset
123
- ap = self.instance
124
-
125
- nil_cloud_host_id = lambda { |agent_id|
126
- agent = Agent.find(agent_id)
127
- agent.cloud_host_id = nil
128
- agent.save
129
- }
130
-
131
- ap.group_observed.keys.each &nil_cloud_host_id
132
- ap.group_active.keys.each &nil_cloud_host_id
133
- ap.save
134
- end
135
-
136
-
137
- def id
138
- ID
139
- end
140
-
141
- def create_or_find(agent_id)
142
- agent = Service::Agent.find(agent_id)
143
- if agent.nil?
144
- agent = Service::Agent.new
145
- agent.id = agent_id
146
- Wakame.log.debug("#{self.class}: Created new agent object with Agent ID: #{agent_id}")
147
- end
148
- agent
149
- end
150
-
151
- def register_as_observed(agent)
152
- agent_id = agent.id
153
- if group_observed.has_key?(agent_id)
154
- else
155
- if group_active.has_key?(agent_id)
156
- # Move the reference from unregistered group to the registered group.
157
- group_active.delete(agent_id)
158
- group_observed[agent_id]=1
159
- else
160
- # The agent is going to be registered at first time.
161
- group_observed[agent_id]=1
162
- end
163
-
164
- self.save
165
- Wakame.log.debug("#{self.class}: Register agent to observed group: #{agent_id}")
166
- end
167
- end
168
-
169
- def register(agent)
170
- raise ArgumentError unless agent.is_a?(Agent)
171
- agent_id = agent.id
172
- if group_active.has_key?(agent_id)
173
- else
174
- if group_observed.has_key?(agent_id)
175
- # Move the reference from unregistered group to the registered group.
176
- group_observed.delete(agent_id)
177
- group_active[agent_id]=1
178
- else
179
- # The agent is going to be registered at first time.
180
- group_active[agent_id]=1
181
- end
182
-
183
- self.save
184
-
185
- Wakame.log.debug("#{self.class}: Register agent to active group: #{agent_id}")
186
- ED.fire_event(Event::AgentMonitored.new(agent))
123
+ if mapped?
124
+ raise "#{self.class}[#{self.id}]: CloudHost is assigned live services." if cloud_host.assigned_services.all? {|svc_id| ServiceInstance.find(svc_id).status == Service::STATUS_TERMINATE }
125
+ CloudHost.delete(cloud_host_id)
187
126
  end
127
+ self.delete
188
128
  end
189
129
 
190
- def unregister(agent)
191
- raise ArgumentError unless agent.is_a?(Agent)
192
- agent_id = agent.id
193
-
194
- unregistered = false
195
- if group_active.has_key?(agent_id)
196
- group_active.delete(agent_id)
197
- unregistered = true
198
- end
199
-
200
- if group_observed.has_key?(agent_id)
201
- group_observed.delete(agent_id)
202
- unregistered = true
130
+ def update_vm_attr
131
+ if Wakame.config.environment == :EC2
132
+ require 'right_aws'
133
+ ec2 = RightAws::Ec2.new(Wakame.config.aws_access_key, Wakame.config.aws_secret_key)
134
+ dat = ec2.describe_instances([self.id])
135
+ @vm_attr = dat[0]
203
136
  end
204
-
205
- if unregistered
206
- self.save
207
-
208
- Wakame.log.debug("#{self.class}: Unregister agent: #{agent.id}")
209
- ED.fire_event(Event::AgentUnMonitored.new(agent))
210
- end
211
- end
212
-
213
- def find_agent(agent_id)
214
- raise "The agent ID \"#{agent_id}\" is not registered in the pool" unless group_active.has_key? agent_id
215
- Agent.find(agent_id) || raise("The agent ID #{agent_id} is registered. but not in the database.")
137
+ self.save
216
138
  end
217
-
218
139
  end
219
140
 
220
141
  class CloudHost < StatusDB::Model
@@ -232,14 +153,14 @@ module Wakame
232
153
 
233
154
  def map_agent(agent)
234
155
  raise ArgumentError unless agent.is_a?(Agent)
235
- raise "Ensure to call unmap_agent() prior to mapping new agent" if self.mapped?
236
- raise "The agent \"#{agent.id}\" is already mapped to the cloud host: #{agent.cloud_host_id}" if agent.mapped?
156
+ raise "Ensure to call unmap_agent() prior to mapping new agent: #{self.agent_id}" if self.mapped?
237
157
 
238
158
  self.agent_id = agent.id
239
159
  agent.cloud_host_id = self.id
240
160
 
241
161
  self.save
242
162
  agent.save
163
+ ED.fire_event(Event::AgentMappedCloudHost.new(self.id, agent.id))
243
164
  end
244
165
 
245
166
  def unmap_agent()
@@ -252,6 +173,7 @@ module Wakame
252
173
 
253
174
  self.agent_id = nil
254
175
  self.save
176
+ ED.fire_event(Event::AgentUnmappedCloudHost.new(self.id, agent.id))
255
177
  end
256
178
  end
257
179
 
@@ -266,6 +188,35 @@ module Wakame
266
188
  spec
267
189
  end
268
190
 
191
+ # Combine all the monitorring data from associated Resources.
192
+ # Example of return value:
193
+ # { '/service' => {
194
+ # 'svcid1' => {:type=>:pidfile, :path=>'/var/run/pid1.pid'},
195
+ # 'svcid2' => {:type=>:command, :cmdline=>'ps -ef | grep key'}
196
+ # }
197
+ # }
198
+ def live_monitors(live_stats=[Service::STATUS_ENTERING, Service::STATUS_STARTING, Service::STATUS_RUNNING])
199
+ mon = {}
200
+ c = ServiceCluster.find(cluster_id)
201
+ c.services.keys.each { |svc_id|
202
+ svc = ServiceInstance.find(svc_id)
203
+ next unless svc.cloud_host_id == self.id
204
+ next unless live_stats.member?(svc.status)
205
+
206
+ svc.resource.monitors.each { |path, data|
207
+
208
+ data.dup.each { |k, v|
209
+ if v.is_a? String
210
+ data[k] = instance_eval('"' + v.gsub(/%\{/, '#{') + '"')
211
+ end
212
+ }
213
+
214
+ mon[path] ||= {}
215
+ mon[path][svc_id] = data
216
+ }
217
+ }
218
+ mon
219
+ end
269
220
 
270
221
  # Delegate methods for Agent class
271
222
 
@@ -333,10 +284,13 @@ module Wakame
333
284
  STATUS_OFFLINE = 0
334
285
  STATUS_ONLINE = 1
335
286
  STATUS_PARTIAL_ONLINE = 2
287
+ STATUS_FROZEN = 3
288
+ STATUS_UNFROZEN = 4
336
289
 
337
290
  property :name
338
291
  property :status, {:readonly=>true, :default=>STATUS_OFFLINE}
339
292
  property :status_changed_at, {:readonly=>true, :default=>proc{Time.now} }
293
+ property :freeze_status, {:readonly=>true, :default=>STATUS_UNFROZEN}
340
294
  property :services, {:default=>{}}
341
295
  property :resources, {:default=>{}}
342
296
  property :cloud_hosts, {:default=>{}}
@@ -368,6 +322,7 @@ module Wakame
368
322
  end
369
323
 
370
324
  def reset
325
+ check_freeze
371
326
  services.clear
372
327
  resources.clear
373
328
  cloud_hosts.clear
@@ -407,6 +362,7 @@ module Wakame
407
362
 
408
363
  #
409
364
  def add_resource(resource, &blk)
365
+ check_freeze
410
366
  if resource.is_a?(Class) && resource <= Resource
411
367
  resource = resource.new
412
368
  elsif resource.is_a? Resource
@@ -429,6 +385,7 @@ module Wakame
429
385
 
430
386
  # Set dependency between two resources.
431
387
  def set_dependency(res_name1, res_name2)
388
+ check_freeze
432
389
  validate_arg = proc {|o|
433
390
  o = Util.build_const(o) if o.is_a? String
434
391
  raise ArgumentError unless o.is_a?(Class) && o <= Resource
@@ -470,6 +427,7 @@ module Wakame
470
427
  #thread_immutable_methods :launch
471
428
 
472
429
  def destroy(svc_id)
430
+ check_freeze
473
431
  raise("Unknown service instance : #{svc_id}") unless self.services.has_key?(svc_id)
474
432
  svc = ServiceInstance.find(svc_id)
475
433
  svc.unbind_cluster
@@ -484,12 +442,15 @@ module Wakame
484
442
 
485
443
  svc.delete
486
444
  self.save
445
+
446
+ ED.fire_event(Event::ServiceDestroied.new(svc_id))
487
447
  end
488
448
  thread_immutable_methods :destroy
489
449
 
490
450
 
491
451
  #def propagate(resource, force=false)
492
452
  def propagate_resource(resource, cloud_host_id=nil, force=false)
453
+ check_freeze
493
454
  res_id = Resource.id(resource)
494
455
  res_obj = (self.resources.has_key?(res_id) && Resource.find(res_id)) || raise("Unregistered resource: #{resource.to_s}")
495
456
  raise ArgumentError if res_obj.require_agent && cloud_host_id.nil?
@@ -516,12 +477,14 @@ module Wakame
516
477
  svc.save
517
478
  self.save
518
479
 
480
+ ED.fire_event(Event::ServicePropagated.new(svc.id))
519
481
  svc
520
482
  end
521
483
  thread_immutable_methods :propagate_resource
522
484
  alias :propagate :propagate_resource
523
485
 
524
486
  def propagate_service(svc_id, cloud_host_id=nil, force=false)
487
+ check_freeze
525
488
  src_svc = (self.services.has_key?(svc_id) && ServiceInstance.find(svc_id)) || raise("Unregistered service: #{svc_id.to_s}")
526
489
  res_obj = src_svc.resource
527
490
 
@@ -552,11 +515,13 @@ module Wakame
552
515
  svc.save
553
516
  self.save
554
517
 
518
+ ED.fire_event(Event::ServicePropagated.new(svc.id))
555
519
  svc
556
520
  end
557
521
  thread_immutable_methods :propagate_service
558
522
 
559
523
  def add_cloud_host(&blk)
524
+ check_freeze
560
525
  h = CloudHost.new
561
526
  h.cluster_id = self.id
562
527
  self.cloud_hosts[h.id]=1
@@ -570,13 +535,19 @@ module Wakame
570
535
  end
571
536
 
572
537
  def remove_cloud_host(cloud_host_id)
538
+ check_freeze
573
539
  if self.cloud_hosts.has_key?(cloud_host_id)
574
540
  self.cloud_hosts.delete(cloud_host_id)
575
541
 
576
542
  self.save
577
543
  end
578
544
 
579
- CloudHost.delete(cloud_host_id) rescue nil
545
+ begin
546
+ ch = CloudHost.find(cloud_host_id)
547
+ ch.unmap_agent
548
+ ch.delete
549
+ rescue => e
550
+ end
580
551
  end
581
552
 
582
553
  def find_service(svc_id)
@@ -651,17 +622,15 @@ module Wakame
651
622
 
652
623
  alias :instances :services
653
624
 
654
- #private
655
-
656
625
  def update_cluster_status
657
626
  onlines = []
658
627
  all_offline = false
659
628
 
660
629
  onlines = self.each_instance.select { |i|
661
- i.status == Service::STATUS_ONLINE
630
+ i.monitor_status == Service::STATUS_ONLINE
662
631
  }
663
632
  all_offline = self.each_instance.all? { |i|
664
- i.status == Service::STATUS_OFFLINE
633
+ i.monitor_status == Service::STATUS_OFFLINE
665
634
  }
666
635
  #Wakame.log.debug "online instances: #{onlines.size}, assigned instances: #{self.instances.size}"
667
636
 
@@ -677,6 +646,28 @@ module Wakame
677
646
  end
678
647
  thread_immutable_methods :update_cluster_status
679
648
 
649
+
650
+ def update_freeze_status(new_status)
651
+ raise "Invalid freeze status: #{new_status}" unless [STATUS_FROZEN, STATUS_UNFROZEN].member?(new_status)
652
+ if @freeze_status != new_status
653
+ @freeze_status = new_status
654
+
655
+ self.save
656
+
657
+ case @freeze_status
658
+ when STATUS_FROZEN
659
+ ED.fire_event(Event::ClusterFrozen.new(id))
660
+ when STATUS_UNFROZEN
661
+ ED.fire_event(Event::ClusterUnfrozen.new(id))
662
+ end
663
+ end
664
+ end
665
+
666
+ private
667
+ def check_freeze
668
+ raise "#{self.class}: The cluster #{self.name} is in freeze mode." if freeze_status == STATUS_FROZEN
669
+ end
670
+
680
671
  end
681
672
 
682
673
 
@@ -776,30 +767,47 @@ module Wakame
776
767
  property :resource_id
777
768
  property :cluster_id
778
769
  property :status, {:read_only=>true, :default=>Service::STATUS_INIT}
779
- property :monitor_status, {:default=>Service::STATUS_INIT}
780
- property :status_changed_at, {:read_only=>true, :default=>proc{Time.now}}
770
+ property :monitor_status, {:default=>Service::STATUS_UNKNOWN}
771
+ property :status_changed_at, {:read_only=>true, :default=>Time.at(0)}
772
+ property :monitor_status_changed_at, {:read_only=>true, :default=>Time.at(0)}
781
773
 
782
- def update_status(new_status, changed_at=Time.now, fail_message=nil)
774
+ def update_status(new_status)
783
775
  if @status != new_status
784
776
  prev_status = @status
785
777
  @status = new_status
786
- @status_changed_at = changed_at
778
+ @status_changed_at = Time.now
779
+
780
+ self.save
781
+
782
+ ED.fire_event(Event::ServiceStatusChanged.new(self.id, new_status, prev_status))
783
+ end
784
+ end
785
+
786
+ def update_monitor_status(new_status, changed_at=Time.now, fail_message=nil)
787
+ raise "Invalid status has been assigned: #{new_status}" unless [STATUS_UNKNOWN, STATUS_ONLINE, STATUS_OFFLINE, STATUS_FAIL].member?(new_status)
788
+
789
+ if @monitor_status != new_status
790
+
791
+ Wakame.log.debug("#{self.class}: #{self.id} update_monitor_status #{new_status}, #{@monitor_status}")
792
+ prev_status = @monitor_status
793
+ @monitor_status = new_status
794
+ @monitor_status_changed_at = changed_at
787
795
 
788
796
  self.save
789
797
 
790
- event = Event::ServiceStatusChanged.new(self.id, resource, new_status, prev_status)
791
- event.time = @status_changed_at.dup
798
+ event = Event::ServiceMonitorStatusChanged.new(self.id, new_status, prev_status)
799
+ event.time = changed_at.dup
792
800
  ED.fire_event(event)
793
801
 
794
802
  tmp_event = nil
795
803
  if prev_status != Service::STATUS_ONLINE && new_status == Service::STATUS_ONLINE
796
- tmp_event = Event::ServiceOnline.new(self.id, self.resource)
804
+ tmp_event = Event::ServiceOnline.new(self.id)
797
805
  tmp_event.time = @status_changed_at.dup
798
806
  elsif prev_status != Service::STATUS_OFFLINE && new_status == Service::STATUS_OFFLINE
799
- tmp_event = Event::ServiceOffline.new(self.id, self.resource)
807
+ tmp_event = Event::ServiceOffline.new(self.id)
800
808
  tmp_event.time = @status_changed_at.dup
801
809
  elsif prev_status != Service::STATUS_FAIL && new_status == Service::STATUS_FAIL
802
- tmp_event = Event::ServiceFailed.new(self.id, self.resource, fail_message)
810
+ tmp_event = Event::ServiceFailed.new(self.id, fail_message)
803
811
  tmp_event.time = @status_changed_at.dup
804
812
  end
805
813
  ED.fire_event(tmp_event) if tmp_event
@@ -822,7 +830,7 @@ module Wakame
822
830
  self.cloud_host_id = new_cloud_host.id
823
831
  self.save
824
832
 
825
- ED.fire_event(Event::ServiceBoundHost.new(self, new_cloud_host))
833
+ ED.fire_event(Event::ServiceBoundCloudHost.new(self.id, new_cloud_host.id))
826
834
  end
827
835
  thread_immutable_methods :bind_cloud_host
828
836
 
@@ -834,7 +842,7 @@ module Wakame
834
842
 
835
843
  self.save
836
844
 
837
- ED.fire_event(Event::ServiceUnboundHost.new(self, old_item))
845
+ ED.fire_event(Event::ServiceUnboundCloudHost.new(self.id, old_item.id))
838
846
  old_item
839
847
  end
840
848
  thread_immutable_methods :unbind_cloud_host
@@ -1011,7 +1019,7 @@ module Wakame
1011
1019
 
1012
1020
  def satisfy?(vm_attr, diff)
1013
1021
  # Compare critical variables which will return false if they are not same.
1014
- return false unless [:availability_zone, :instance_type, :image_id].all? { |k| diff[k].nil? ? true : diff[k] == vm_attr[k] }
1022
+ return false unless [:availability_zone, :instance_type, :image_id].all? { |k| diff[k].nil? ? true : diff[k] == vm_attr[self.class.vm_attr_defs[k][:right_aws_key]] }
1015
1023
  true
1016
1024
  end
1017
1025
 
@@ -1048,6 +1056,8 @@ module Wakame
1048
1056
  property :max_instances, {:default=>1}
1049
1057
  property :startup, {:default=>true}
1050
1058
  property :require_agent, {:default=>true}
1059
+ property :tags, {:read_only=>true, :default=>[]}
1060
+ property :monitors, {:default=>{}}
1051
1061
 
1052
1062
  def self.inherited(klass)
1053
1063
  klass.class_eval {