wakame-dolphin 0.0.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +9 -0
- data/.rspec +4 -0
- data/.travis.yml +25 -0
- data/Gemfile +18 -0
- data/Makefile +56 -0
- data/README.md +77 -0
- data/Rakefile +67 -0
- data/bin/dolphin_server +98 -0
- data/config/db/cassandra_clear.txt +1 -0
- data/config/db/cassandra_schema.txt +14 -0
- data/config/db/sequel/migrations/0001_add_notification.rb +15 -0
- data/config/db/sequel/migrations/0002_add_event.rb +15 -0
- data/config/dolphin-mysql.conf.travis +26 -0
- data/config/dolphin.conf.example +26 -0
- data/lib/dolphin.rb +148 -0
- data/lib/dolphin/data_store.rb +55 -0
- data/lib/dolphin/data_stores/base_rdb.rb +57 -0
- data/lib/dolphin/data_stores/cassandra.rb +98 -0
- data/lib/dolphin/data_stores/mysql.rb +31 -0
- data/lib/dolphin/helpers/message/zabbix_helper.rb +16 -0
- data/lib/dolphin/helpers/request_helper.rb +72 -0
- data/lib/dolphin/mailer.rb +83 -0
- data/lib/dolphin/manager.rb +35 -0
- data/lib/dolphin/message_builder.rb +98 -0
- data/lib/dolphin/models/base.rb +8 -0
- data/lib/dolphin/models/cassandra/base.rb +11 -0
- data/lib/dolphin/models/cassandra/event.rb +42 -0
- data/lib/dolphin/models/cassandra/notification.rb +28 -0
- data/lib/dolphin/models/rdb/base.rb +12 -0
- data/lib/dolphin/models/rdb/event.rb +47 -0
- data/lib/dolphin/models/rdb/notification.rb +27 -0
- data/lib/dolphin/models/rdb/orm/base.rb +10 -0
- data/lib/dolphin/models/rdb/orm/event.rb +8 -0
- data/lib/dolphin/models/rdb/orm/notification.rb +8 -0
- data/lib/dolphin/query_processor.rb +50 -0
- data/lib/dolphin/request_handler.rb +150 -0
- data/lib/dolphin/sender.rb +47 -0
- data/lib/dolphin/util.rb +18 -0
- data/lib/dolphin/version.rb +3 -0
- data/lib/dolphin/worker.rb +149 -0
- data/script/console +13 -0
- data/spec/files/cassandra_models_spec.rb +127 -0
- data/spec/files/dolphin_spec.rb +110 -0
- data/spec/files/endpoint/event_spec.rb +123 -0
- data/spec/files/endpoint/notification_spec.rb +54 -0
- data/spec/files/message_builder_spec.rb +15 -0
- data/spec/helpers/test_helper.rb +21 -0
- data/spec/helpers/web_request_helper.rb +40 -0
- data/spec/spec_helper.rb +18 -0
- data/templates/email/alert_port.erb +24 -0
- data/templates/email/default.erb +3 -0
- data/tests/test_dolphin +10 -0
- data/tests/test_get_event +31 -0
- data/tests/test_get_notification +27 -0
- data/tests/test_post_event +37 -0
- data/tests/test_post_notification +43 -0
- data/wakame-dolphin.gemspec +40 -0
- metadata +311 -0
@@ -0,0 +1,83 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
require 'action_mailer'
|
4
|
+
require 'mail-iso-2022-jp'
|
5
|
+
|
6
|
+
module Dolphin
|
7
|
+
class Mailer < ActionMailer::Base
|
8
|
+
ActionMailer::Base.raise_delivery_errors = true
|
9
|
+
case Dolphin.settings['mail']['type']
|
10
|
+
when 'file'
|
11
|
+
ActionMailer::Base.delivery_method = :file
|
12
|
+
ActionMailer::Base.file_settings = {
|
13
|
+
:location => '/var/tmp'
|
14
|
+
}
|
15
|
+
when 'tls-mail'
|
16
|
+
ActionMailer::Base.delivery_method = :smtp
|
17
|
+
ActionMailer::Base.smtp_settings = {
|
18
|
+
:address => Dolphin.settings['mail']['host'],
|
19
|
+
:port => Dolphin.settings['mail']['port'],
|
20
|
+
:user_name => Dolphin.settings['mail']['user_name'],
|
21
|
+
:password => Dolphin.settings['mail']['password'],
|
22
|
+
:authentication => :plain,
|
23
|
+
:enable_starttls_auto => true
|
24
|
+
}
|
25
|
+
when 'mail'
|
26
|
+
ActionMailer::Base.delivery_method = :smtp
|
27
|
+
ActionMailer::Base.smtp_settings = {
|
28
|
+
:address => Dolphin.settings['mail']['host'],
|
29
|
+
:port => Dolphin.settings['mail']['port'],
|
30
|
+
}
|
31
|
+
end
|
32
|
+
|
33
|
+
default :charset => 'ISO-2022-JP'
|
34
|
+
|
35
|
+
|
36
|
+
#
|
37
|
+
# ==== Examples
|
38
|
+
#
|
39
|
+
# read_iso2022_jp_mail('/var/tmp/test@example.com')
|
40
|
+
#
|
41
|
+
def self.read_iso2022_jp_mail(path, encoding_type='UTF-8')
|
42
|
+
data = File.open(path, 'rb').read
|
43
|
+
ec = Encoding::Converter.new("ISO-2022-JP", encoding_type)
|
44
|
+
converted_data = ec.convert(data)
|
45
|
+
data = converted_data.split("\r\n\r\n")
|
46
|
+
header = data[0].split("\r\n")
|
47
|
+
body = data[1]
|
48
|
+
|
49
|
+
h = Hash.new
|
50
|
+
h[:date] = header[0]
|
51
|
+
h[:from] = header[1]
|
52
|
+
h[:to] = header[2]
|
53
|
+
h[:message_id] = header[3]
|
54
|
+
h[:subject] = header[4]
|
55
|
+
h[:mime_version] = header[5]
|
56
|
+
h[:event_id] = header[9]
|
57
|
+
h.map{|k,v| h[k] = v.split(':')[1].strip}
|
58
|
+
|
59
|
+
h[:body] = body
|
60
|
+
h
|
61
|
+
end
|
62
|
+
|
63
|
+
def notify(send_params)
|
64
|
+
if send_params[:from].blank?
|
65
|
+
raise 'Not found from field.'
|
66
|
+
end
|
67
|
+
|
68
|
+
fqdn = send_params[:from].split('@')[1]
|
69
|
+
|
70
|
+
m = mail(send_params)
|
71
|
+
m.message_id(generate_message_id(send_params[:event_id], fqdn))
|
72
|
+
m.deliver
|
73
|
+
end
|
74
|
+
|
75
|
+
private
|
76
|
+
|
77
|
+
# Refernced function from https://github.com/mikel/mail/blob/master/lib/mail/fields/message_id_field.rb#L77-L79
|
78
|
+
def generate_message_id(event_id, fqdn)
|
79
|
+
"<#{event_id}@#{fqdn}>"
|
80
|
+
end
|
81
|
+
|
82
|
+
end
|
83
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
require 'celluloid'
|
4
|
+
|
5
|
+
module Dolphin
|
6
|
+
class Manager < Celluloid::SupervisionGroup
|
7
|
+
include Dolphin::Util
|
8
|
+
|
9
|
+
trap_exit :actor_died
|
10
|
+
|
11
|
+
def actor_died(actor, reason)
|
12
|
+
logger :info, "Actor died"
|
13
|
+
restart_actor(actor, "Breaked actor")
|
14
|
+
logger :info, "Actor restarted"
|
15
|
+
end
|
16
|
+
|
17
|
+
def start
|
18
|
+
end
|
19
|
+
|
20
|
+
def shutdown
|
21
|
+
end
|
22
|
+
|
23
|
+
def run_workers
|
24
|
+
end
|
25
|
+
|
26
|
+
def terminate_workers
|
27
|
+
end
|
28
|
+
|
29
|
+
def run_request_handlers
|
30
|
+
end
|
31
|
+
|
32
|
+
def terminate_request_handlers
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,98 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
require 'erubis'
|
3
|
+
require 'extlib/blank'
|
4
|
+
|
5
|
+
module Dolphin
|
6
|
+
|
7
|
+
class TemplateBuilder
|
8
|
+
|
9
|
+
include Dolphin::Helpers::Message::ZabbixHelper
|
10
|
+
|
11
|
+
def build(template_str, params)
|
12
|
+
template = Erubis::Eruby.new(template_str)
|
13
|
+
if params.is_a? Hash
|
14
|
+
params.each {|key, val|
|
15
|
+
instance_variable_set("@#{key}", val)
|
16
|
+
}
|
17
|
+
end
|
18
|
+
template.result(binding)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
module MessageBuilder
|
23
|
+
|
24
|
+
EXT = '.erb'.freeze
|
25
|
+
|
26
|
+
class Base
|
27
|
+
|
28
|
+
include Dolphin::Util
|
29
|
+
|
30
|
+
def initialize
|
31
|
+
end
|
32
|
+
|
33
|
+
def build
|
34
|
+
raise NotImplementedError
|
35
|
+
end
|
36
|
+
|
37
|
+
def build_message(str, params)
|
38
|
+
begin
|
39
|
+
template = TemplateBuilder.new
|
40
|
+
template.build(str, params).encode("UTF-8")
|
41
|
+
rescue SyntaxError => e
|
42
|
+
logger :error, e
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
class Mail < Base
|
48
|
+
|
49
|
+
MESSAGE_BOUNDARY="----------------------------------------".freeze
|
50
|
+
|
51
|
+
def build(template_id, params)
|
52
|
+
message = ''
|
53
|
+
|
54
|
+
if template_id.blank?
|
55
|
+
template_id = 'default'
|
56
|
+
end
|
57
|
+
|
58
|
+
body_template = template(template_id)
|
59
|
+
if body_template.nil?
|
60
|
+
return nil
|
61
|
+
end
|
62
|
+
|
63
|
+
message = build_message(body_template, params['messages'])
|
64
|
+
subject, body = message.split(MESSAGE_BOUNDARY)
|
65
|
+
subject.strip! unless subject.nil?
|
66
|
+
body.strip! unless body.nil?
|
67
|
+
|
68
|
+
notification = NotificationObject.new
|
69
|
+
notification.subject = subject
|
70
|
+
notification.from = Dolphin.settings['mail']['from']
|
71
|
+
notification.to = params["to"]
|
72
|
+
notification.cc ||= params["cc"]
|
73
|
+
notification.bcc ||= params["bcc"]
|
74
|
+
notification.body = body
|
75
|
+
notification
|
76
|
+
end
|
77
|
+
|
78
|
+
private
|
79
|
+
def template(template_id)
|
80
|
+
file_path = File.join(template_path, template_file(template_id))
|
81
|
+
if File.exists? file_path
|
82
|
+
File.read(file_path, :encoding => Encoding::UTF_8)
|
83
|
+
else
|
84
|
+
logger :warn, "File not found #{file_path}"
|
85
|
+
nil
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
def template_file(template_id)
|
90
|
+
template_id + EXT
|
91
|
+
end
|
92
|
+
|
93
|
+
def template_path
|
94
|
+
File.join(Dolphin.templates_path, '/email')
|
95
|
+
end
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
require 'multi_json'
|
4
|
+
require 'simple_uuid'
|
5
|
+
|
6
|
+
module Dolphin
|
7
|
+
module Models
|
8
|
+
module Cassandra
|
9
|
+
class Event < Base
|
10
|
+
COLUMN_FAMILY = 'events'.freeze
|
11
|
+
ROW_KEY = 'history'.freeze
|
12
|
+
|
13
|
+
def get(params)
|
14
|
+
|
15
|
+
options = {
|
16
|
+
:count => params[:count]
|
17
|
+
}
|
18
|
+
|
19
|
+
if params[:start_id]
|
20
|
+
options[:start] = params[:start_id]
|
21
|
+
elsif params[:start_time]
|
22
|
+
options[:start] = params[:start_time]
|
23
|
+
end
|
24
|
+
|
25
|
+
db.get(COLUMN_FAMILY, ROW_KEY, options).collect do |event| {
|
26
|
+
'id' => event[0].to_guid,
|
27
|
+
'event' => MultiJson.load(event[1]),
|
28
|
+
'created_at' => SimpleUUID::UUID.new(event[0].to_guid).to_time.iso8601
|
29
|
+
}
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def put(event)
|
34
|
+
column_name = SimpleUUID::UUID.new(Time.now).to_guid
|
35
|
+
value = MultiJson.dump(event[:messages])
|
36
|
+
db.insert(COLUMN_FAMILY, ROW_KEY, {column_name => value})
|
37
|
+
column_name
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
require 'multi_json'
|
4
|
+
|
5
|
+
module Dolphin
|
6
|
+
module Models
|
7
|
+
module Cassandra
|
8
|
+
class Notification < Base
|
9
|
+
def get(id)
|
10
|
+
res = db.get('notifications', id.to_s)
|
11
|
+
MultiJson.load(res['methods'])
|
12
|
+
end
|
13
|
+
|
14
|
+
def put(id, methods)
|
15
|
+
column_name = 'methods'
|
16
|
+
row_key = id.to_s
|
17
|
+
value = MultiJson.dump(methods)
|
18
|
+
|
19
|
+
db.insert('notifications', row_key, {column_name => value})
|
20
|
+
end
|
21
|
+
|
22
|
+
def delete(id)
|
23
|
+
db.remove('notifications', id)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
require 'multi_json'
|
4
|
+
require 'simple_uuid'
|
5
|
+
|
6
|
+
module Dolphin::Models
|
7
|
+
module Rdb
|
8
|
+
class Event < Base
|
9
|
+
def get(params)
|
10
|
+
options = {
|
11
|
+
:count => params[:count]
|
12
|
+
}
|
13
|
+
|
14
|
+
if params[:start_id]
|
15
|
+
options[:start] = params[:start_id]
|
16
|
+
elsif params[:start_time]
|
17
|
+
options[:start] = params[:start_time]
|
18
|
+
end
|
19
|
+
|
20
|
+
if options[:start]
|
21
|
+
event = db.find(:uuid => params[:start_id])
|
22
|
+
h = {}
|
23
|
+
h['id'] = event.uuid
|
24
|
+
h['event'] = MultiJson.load(event.value)
|
25
|
+
h['created_at'] = SimpleUUID::UUID.new(event.uuid).to_time.iso8601
|
26
|
+
[h]
|
27
|
+
else
|
28
|
+
db.order(Sequel.desc(:id)).find_all.collect do |event| {
|
29
|
+
'id' => event.uuid,
|
30
|
+
'event' => MultiJson.load(event.value),
|
31
|
+
'created_at' => SimpleUUID::UUID.new(event.uuid).to_time.iso8601
|
32
|
+
}
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
def put(event)
|
38
|
+
d = db.new
|
39
|
+
d.uuid = SimpleUUID::UUID.new(Time.now).to_guid
|
40
|
+
d.value = MultiJson.dump(event[:messages])
|
41
|
+
d.timestamp = DateTime.now
|
42
|
+
d.save
|
43
|
+
d.uuid
|
44
|
+
end
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
require 'multi_json'
|
4
|
+
|
5
|
+
module Dolphin::Models
|
6
|
+
module Rdb
|
7
|
+
class Notification < Base
|
8
|
+
def get(id)
|
9
|
+
res = db.find(:uuid => id)
|
10
|
+
MultiJson.load(res.value)
|
11
|
+
end
|
12
|
+
|
13
|
+
def put(id, methods)
|
14
|
+
d = db.find(:uuid => id)
|
15
|
+
d = db.new if d.nil?
|
16
|
+
d.uuid = id.to_s
|
17
|
+
d.value = MultiJson.dump(methods)
|
18
|
+
d.save
|
19
|
+
end
|
20
|
+
|
21
|
+
def delete(id)
|
22
|
+
res = db.find(:uuid => id)
|
23
|
+
res.destroy
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
require 'celluloid'
|
4
|
+
|
5
|
+
module Dolphin
|
6
|
+
class QueryProcessor
|
7
|
+
include Celluloid
|
8
|
+
include Dolphin::Util
|
9
|
+
|
10
|
+
def get_notification(id)
|
11
|
+
logger :info, "Get notification #{id}"
|
12
|
+
send('get_notification', id)
|
13
|
+
end
|
14
|
+
|
15
|
+
def put_event(event)
|
16
|
+
logger :info, "Put event #{event}"
|
17
|
+
send('put_event', event)
|
18
|
+
end
|
19
|
+
|
20
|
+
def get_event(params)
|
21
|
+
send('get_event', params)
|
22
|
+
end
|
23
|
+
|
24
|
+
def put_notification(notification)
|
25
|
+
logger :info, notification
|
26
|
+
notification_id = notification[:id]
|
27
|
+
methods = notification[:methods]
|
28
|
+
send('put_notification', notification_id, methods)
|
29
|
+
end
|
30
|
+
|
31
|
+
def delete_notification(notification)
|
32
|
+
logger :info, notification
|
33
|
+
notification_id = notification[:id]
|
34
|
+
send('delete_notification', notification_id)
|
35
|
+
end
|
36
|
+
|
37
|
+
private
|
38
|
+
def send(action, *args)
|
39
|
+
begin
|
40
|
+
ds = DataStore.current_store
|
41
|
+
ds.connect
|
42
|
+
ds.__send__(action, *args)
|
43
|
+
rescue => e
|
44
|
+
logger :error, e.backtrace
|
45
|
+
logger :error, e
|
46
|
+
false
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|