baleen 0.1.1 → 0.1.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (116) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +1 -0
  3. data/.gitmodules +3 -0
  4. data/Dockerfile +1 -0
  5. data/Gemfile +1 -0
  6. data/README.md +1 -0
  7. data/baleen.gemspec +2 -0
  8. data/baleen.yml.sample +46 -0
  9. data/bin/baleen +91 -22
  10. data/bin/baleen-server +47 -16
  11. data/lib/baleen/builder.rb +46 -0
  12. data/lib/baleen/ci_server.rb +63 -0
  13. data/lib/baleen/client.rb +19 -9
  14. data/lib/baleen/configuration.rb +24 -0
  15. data/lib/baleen/connection.rb +47 -0
  16. data/lib/baleen/default.rb +57 -0
  17. data/lib/baleen/error.rb +9 -0
  18. data/lib/baleen/job.rb +7 -5
  19. data/lib/baleen/message/base.rb +9 -40
  20. data/lib/baleen/message/exception.rb +21 -0
  21. data/lib/baleen/message/message.rb +3 -2
  22. data/lib/baleen/message/to_client.rb +32 -0
  23. data/lib/baleen/project.rb +122 -0
  24. data/lib/baleen/result_display.rb +24 -16
  25. data/lib/baleen/runner.rb +41 -92
  26. data/lib/baleen/serializable.rb +61 -0
  27. data/lib/baleen/server.rb +40 -18
  28. data/lib/baleen/task/base.rb +55 -0
  29. data/lib/baleen/task/cucumber.rb +44 -0
  30. data/lib/baleen/task/generic.rb +17 -0
  31. data/lib/baleen/task/image_update.rb +22 -0
  32. data/lib/baleen/task/run_project.rb +14 -0
  33. data/lib/baleen/task/task.rb +5 -0
  34. data/lib/baleen/utils/{colored_puts.rb → highlighter.rb} +3 -3
  35. data/lib/baleen/utils/logger.rb +74 -0
  36. data/lib/baleen/validator.rb +115 -0
  37. data/lib/baleen/version.rb +1 -1
  38. data/lib/baleen.rb +11 -3
  39. data/spec/lib/baleen/spec_result_display.rb +47 -0
  40. data/spec/lib/baleen/spec_serializable.rb +45 -0
  41. data/spec/lib/baleen/spec_task.rb +62 -0
  42. data/spec/lib/baleen/spec_validator.rb +53 -0
  43. data/spec/spec_helper.rb +31 -0
  44. metadata +62 -76
  45. data/lib/baleen/container.rb +0 -32
  46. data/lib/baleen/message/request.rb +0 -29
  47. data/lib/baleen/message/response.rb +0 -34
  48. data/poc/.gitignore +0 -15
  49. data/poc/Gemfile +0 -49
  50. data/poc/README.rdoc +0 -261
  51. data/poc/Rakefile +0 -7
  52. data/poc/app/assets/images/rails.png +0 -0
  53. data/poc/app/assets/javascripts/application.js +0 -15
  54. data/poc/app/assets/stylesheets/application.css +0 -13
  55. data/poc/app/controllers/application_controller.rb +0 -3
  56. data/poc/app/helpers/application_helper.rb +0 -2
  57. data/poc/app/mailers/.gitkeep +0 -0
  58. data/poc/app/models/.gitkeep +0 -0
  59. data/poc/app/models/ar_profile.rb +0 -3
  60. data/poc/app/views/layouts/application.html.erb +0 -14
  61. data/poc/config/application.rb +0 -62
  62. data/poc/config/boot.rb +0 -6
  63. data/poc/config/cucumber.yml +0 -8
  64. data/poc/config/database.yml +0 -28
  65. data/poc/config/environment.rb +0 -5
  66. data/poc/config/environments/development.rb +0 -37
  67. data/poc/config/environments/production.rb +0 -67
  68. data/poc/config/environments/test.rb +0 -37
  69. data/poc/config/initializers/backtrace_silencers.rb +0 -7
  70. data/poc/config/initializers/inflections.rb +0 -15
  71. data/poc/config/initializers/mime_types.rb +0 -5
  72. data/poc/config/initializers/secret_token.rb +0 -7
  73. data/poc/config/initializers/session_store.rb +0 -8
  74. data/poc/config/initializers/wrap_parameters.rb +0 -14
  75. data/poc/config/locales/en.yml +0 -5
  76. data/poc/config/routes.rb +0 -58
  77. data/poc/config.ru +0 -4
  78. data/poc/db/.gitkeep +0 -0
  79. data/poc/db/migrate/20130914144710_create_ar_profiles.rb +0 -11
  80. data/poc/db/schema.rb +0 -24
  81. data/poc/db/seeds.rb +0 -7
  82. data/poc/features/step_definitions/fake_test_steps.rb +0 -25
  83. data/poc/features/support/env.rb +0 -60
  84. data/poc/features/support/ruby_prof_cucumber.rb +0 -15
  85. data/poc/features/t1.feature +0 -12
  86. data/poc/features/t10.feature +0 -12
  87. data/poc/features/t2.feature +0 -12
  88. data/poc/features/t3.feature +0 -12
  89. data/poc/features/t4.feature +0 -12
  90. data/poc/features/t5.feature +0 -12
  91. data/poc/features/t6.feature +0 -12
  92. data/poc/features/t7.feature +0 -12
  93. data/poc/features/t8.feature +0 -12
  94. data/poc/features/t9.feature +0 -12
  95. data/poc/lib/assets/.gitkeep +0 -0
  96. data/poc/lib/tasks/.gitkeep +0 -0
  97. data/poc/lib/tasks/cucumber.rake +0 -65
  98. data/poc/public/404.html +0 -26
  99. data/poc/public/422.html +0 -26
  100. data/poc/public/500.html +0 -25
  101. data/poc/public/favicon.ico +0 -0
  102. data/poc/public/index.html +0 -241
  103. data/poc/public/robots.txt +0 -5
  104. data/poc/script/cucumber +0 -10
  105. data/poc/script/rails +0 -6
  106. data/poc/test/fixtures/.gitkeep +0 -0
  107. data/poc/test/fixtures/ar_profiles.yml +0 -11
  108. data/poc/test/functional/.gitkeep +0 -0
  109. data/poc/test/integration/.gitkeep +0 -0
  110. data/poc/test/performance/browsing_test.rb +0 -12
  111. data/poc/test/test_helper.rb +0 -13
  112. data/poc/test/unit/.gitkeep +0 -0
  113. data/poc/test/unit/ar_profile_test.rb +0 -7
  114. data/poc/vendor/assets/javascripts/.gitkeep +0 -0
  115. data/poc/vendor/assets/stylesheets/.gitkeep +0 -0
  116. data/poc/vendor/plugins/.gitkeep +0 -0
@@ -1,55 +1,24 @@
1
- require "json"
1
+ require 'baleen/utils/highlighter'
2
2
 
3
3
  module Baleen
4
4
  module Message
5
-
6
- def symbolize_keys(hash)
7
- hash.inject({}){|new_hash, key_value|
8
- key, value = key_value
9
- value = symbolize_keys(value) if value.is_a?(Hash)
10
- new_hash[key.to_sym] = value
11
- new_hash
12
- }
13
- end
14
-
15
- class Decoder
16
- include Baleen::Message
17
-
18
- def initialize(json_string)
19
- @params = JSON.parse(json_string)
20
- end
21
-
22
- def decode
23
- klass = @params.delete "klass"
24
- Object.const_get(klass).new(symbolize_keys(@params))
25
- end
26
- end
27
-
28
5
  class Base
29
6
 
30
- def initialize
7
+ include Serializable
8
+
9
+ def initialize()
31
10
  @params = {}
32
11
  @params[:klass] = self.class.to_s
33
12
  end
34
13
 
35
- def method_missing(name, *args)
36
- Base.class_eval{
37
- define_method "#{name}" do
38
- @params[name.to_sym]
39
- end
40
- }
41
- send(name)
14
+ def results
15
+ nil
42
16
  end
43
17
 
44
- def params
45
- @params
18
+ def terminate?
19
+ false
46
20
  end
47
21
 
48
- def to_json
49
- @params.to_json
50
- end
51
22
  end
52
-
53
23
  end
54
-
55
- end
24
+ end
@@ -0,0 +1,21 @@
1
+ require 'baleen/utils/highlighter'
2
+
3
+ module Baleen
4
+ module Message
5
+ class Exception < Baleen::Message::Base
6
+
7
+ def initialize(opt)
8
+ super()
9
+ @params[:message] = opt[:message]
10
+ end
11
+
12
+ def terminate?
13
+ true
14
+ end
15
+
16
+ def print_message
17
+ hl_error message
18
+ end
19
+ end
20
+ end
21
+ end
@@ -1,2 +1,3 @@
1
- require "baleen/message/request"
2
- require "baleen/message/response"
1
+ require "baleen/message/base"
2
+ require "baleen/message/to_client"
3
+ require "baleen/message/exception"
@@ -0,0 +1,32 @@
1
+ require 'baleen/utils/highlighter'
2
+
3
+ module Baleen
4
+ module Message
5
+ class ToClient < Baleen::Message::Base
6
+
7
+ def initialize(opt)
8
+ super()
9
+ @params[:message] = opt[:message]
10
+ @params[:level] = opt[:level]
11
+ end
12
+
13
+ def terminate?
14
+ false
15
+ end
16
+
17
+ def print_message
18
+ case level
19
+ when "info"
20
+ hl_info message
21
+ when "warn"
22
+ hl_warn message
23
+ when "error"
24
+ hl_error message
25
+ else
26
+ hl_error "Unknown message level"
27
+ hl_error inspect
28
+ end
29
+ end
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,122 @@
1
+ module Baleen
2
+ class Project
3
+
4
+ include Default
5
+
6
+ @@projects = {}
7
+
8
+ attr_reader :name, :config
9
+
10
+ def self.projects(name=nil)
11
+ if name
12
+ @@projects[name.to_sym]
13
+ else
14
+ @@projects
15
+ end
16
+ end
17
+
18
+ def self.load_project(config)
19
+ if File.exists?(config)
20
+ yaml = Baleen::Serializable.symbolize_keys(YAML.load_file(config))
21
+ else
22
+ hl_error "Config file not found"
23
+ raise Baleen::Error::ConfigMissing
24
+ end
25
+
26
+ yaml.each do |project, cfg|
27
+ if Baleen::Validation::Validator.check(cfg)
28
+ @@projects[project] = self.new(project, cfg)
29
+ end
30
+ end
31
+ end
32
+
33
+ def self.find_project(name, attribute, params={})
34
+ projects = Baleen::Project.projects
35
+
36
+ if name && attribute
37
+ raise "You cannot specify name and attribute at the same time"
38
+ elsif name
39
+ return projects[name.to_sym]
40
+ elsif attribute
41
+ projects.each do |project, attributes|
42
+ attributes.config.each do |attr, values|
43
+ if attr == attribute
44
+ params.each do |_k, _v|
45
+ return nil unless values[_k] == _v
46
+ end
47
+ return projects[project]
48
+ end
49
+ end
50
+ end
51
+ end
52
+ end
53
+
54
+ def self.find_project_by_name(name)
55
+ find_project(name.to_sym, nil)
56
+ end
57
+
58
+ def self.find_project_by_ci(params)
59
+ find_project(nil, :ci, params)
60
+ end
61
+
62
+ def self.find_project_by_runner(params)
63
+ find_project(nil, :runner, params)
64
+ end
65
+
66
+ def self.find_project_by_framework(params)
67
+ find_project(nil, :framework, params)
68
+ end
69
+
70
+ def initialize(name, cfg)
71
+ @name = name
72
+ load_config(cfg)
73
+ end
74
+
75
+ def load_config(cfg)
76
+ if Baleen::Validation::Validator.check(cfg)
77
+ cfg[:runner][:before_command] ||= default_before_command
78
+ cfg[:runner][:concurrency] ||= default_concurrency
79
+ cfg[:runner][:work_dir] ||= default_work_dir
80
+ cfg[:runner][:image]
81
+
82
+ case cfg[:framework][:type]
83
+ when "cucumber"
84
+ cfg[:framework][:files] = cfg[:framework][:features] || default_features
85
+ else
86
+ raise "Passed unknown framework from config yml: #{cfg[:framework][:type]}"
87
+ end
88
+ end
89
+ @config = cfg
90
+ end
91
+
92
+ def ci
93
+ @config[:ci]
94
+ end
95
+
96
+ def image
97
+ @config[:runner][:image]
98
+ end
99
+
100
+ def branch
101
+ ci[:branch]
102
+ end
103
+
104
+ def repo
105
+ ci[:repo]
106
+ end
107
+
108
+ def url
109
+ ci[:url]
110
+ end
111
+
112
+ def task
113
+ Baleen::Task::Cucumber.new(
114
+ image: @config[:runner][:image],
115
+ work_dir: @config[:runner][:work_dir],
116
+ files: @config[:framework][:files],
117
+ before_command: @config[:runner][:before_command],
118
+ concurrency: @config[:runner][:concurrency].to_i,
119
+ )
120
+ end
121
+ end
122
+ end
@@ -2,39 +2,47 @@ require "colorize"
2
2
 
3
3
  module Baleen
4
4
  class ResultDisplay
5
- def initialize(result, start_time: nil, end_time: nil)
6
- @result = result.result
5
+ def initialize(result, start_time, end_time, output)
6
+ @result = result
7
7
  @start_time = start_time
8
8
  @end_time = end_time
9
+ @output = output
10
+ end
11
+
12
+ def report_result
13
+ if @result
14
+ summary
15
+ detail
16
+ end
9
17
  end
10
18
 
11
19
  def summary
12
- tests_result = pass_all? ? "Pass".green : "Fail".red
20
+ tests_result = pass_all? ? "Pass".blue : "Fail".red
13
21
  time = run_time
14
22
 
15
- puts ""
16
- notice "[Summary]"
17
- puts "Result: ".yellow + tests_result
18
- puts "Time: ".yellow + time.green
19
- puts ""
23
+ @output.puts ""
24
+ @output.puts "[Summary]".yellow
25
+ @output.puts "Result: ".yellow + tests_result
26
+ @output.puts "Time: ".yellow + time.green
27
+ @output.puts ""
20
28
  end
21
29
 
22
30
  def detail
23
- notice "[Details]"
31
+ @output.puts "[Details]".yellow
24
32
  @result.each do |r|
25
- puts "Id: ".yellow + "#{r[:container_id]}".green
26
- puts "status code: ".yellow + "#{r[:status_code]}".green
27
- puts "feature file: ".yellow + "#{r[:file]}".green
28
- puts "logs:".yellow
29
- puts "------------------------------------".yellow
30
- puts "#{r[:log]}".green
33
+ @output.puts "Id: ".yellow + "#{r['container_id']}".green
34
+ @output.puts "status code: ".yellow + "#{r['status_code']}".green
35
+ @output.puts "feature file: ".yellow + "#{r['file']}".green
36
+ @output.puts "logs:".yellow
37
+ @output.puts "------------------------------------".yellow
38
+ @output.puts "#{r['log']}".green
31
39
  end
32
40
  end
33
41
 
34
42
  private
35
43
 
36
44
  def pass_all?
37
- @result.all? {|r| r[:status_code] == 0}
45
+ @result.all? {|r| r['status_code'] == 0}
38
46
  end
39
47
 
40
48
  def run_time
data/lib/baleen/runner.rb CHANGED
@@ -1,124 +1,67 @@
1
1
  require "baleen/error"
2
+ require 'forwardable'
2
3
 
3
4
  module Baleen
4
5
 
5
- class DockerParam
6
- def initialize(params)
7
- @params = params
8
- end
9
-
10
- def method_missing(name, *args)
11
- DockerParam.class_eval{
12
- define_method "#{name}" do
13
- @params[name.to_sym]
14
- end
15
-
16
- define_method "#{name}=" do |*args|
17
- @params[name.to_sym] = args.first
18
- end
19
- }
20
- send(name)
21
- end
22
-
23
- def commands
24
- %{
25
- #{@params[:before_command]}
26
- cd #{@params[:work_dir]}
27
- #{command}
28
- }
29
- end
30
-
31
- def command
32
- @params[:command] ||= %{#{@params[:exe]} #{@params[:files]}}
33
- end
34
-
35
- def command=(c)
36
- @params[:command] = c
37
- end
38
-
39
- def dup
40
- copy_params = @params.dup
41
- Object.const_get(self.class.to_s).new(copy_params)
42
- end
43
- end
44
-
45
6
  class RunnerManager
46
- include Celluloid::IO
47
-
48
- CONCURRENCY=2
49
-
50
- def initialize(socket, msg)
51
- @socket = socket
52
- @queue = []
53
- @results = []
54
- @params = DockerParam.new(msg.params)
7
+ def initialize(connection, task)
8
+ @task = task
9
+ @connection = connection
55
10
  end
56
11
 
57
12
  def run
13
+ results = []
14
+ prepare_task
58
15
  create_runners.each do |runners|
59
- @queue = runners
60
- @queue.each do |runner|
61
- runner.async.run
16
+ runners.map{|runner| runner.future.run}.each do |actor|
17
+ results << actor.value
62
18
  end
63
- loop {break if monitor_runners}
64
- @results += @queue.map {|runner| runner.status.params}
65
19
  end
66
- msg = Message::Response::JobComplete.new(status: "done", results: @results.to_json)
67
- @socket.puts(msg.to_json)
20
+ @task.results = results
21
+ yield @task
68
22
  end
69
23
 
70
24
  private
71
25
 
72
- def create_runners
73
- target_files.map {|file|
74
- params = @params.dup
75
- params.files = file
76
- Runner.new(params)
77
- }.each_slice(@params.concurrency).map {|r| r}
26
+ def prepare_task
27
+ @task.prepare
78
28
  end
79
29
 
80
- def target_files
81
- params = @params.dup
82
- params.command = %{find #{params.files} | grep "\\.feature"}
83
- runner = Runner.new(params)
84
- runner.run
85
- runner.status.log.split("\n")
30
+ def create_runners
31
+ @task.target_files.map {|file|
32
+ task = @task.dup
33
+ task.files = file
34
+ Runner.new(task, @connection)
35
+ }.each_slice(@task.concurrency).map {|r| r}
86
36
  end
87
37
 
88
- def monitor_runners
89
- @queue.all?{ |r| r.status }
90
- end
91
38
  end
92
39
 
93
40
  class Runner
94
- include Celluloid::IO
41
+ include Celluloid
42
+ extend Forwardable
95
43
 
96
- attr_reader :status
44
+ def_delegator :@connection, :notify_info
97
45
 
98
- def initialize(params)
99
- @docker_client = Container::DockerClient.new
100
- @status = nil
101
- @params = params
46
+ def initialize(task, connection=nil)
47
+ @container = Docker::Container.create('Cmd' => [task.shell, task.opt, task.commands], 'Image' => task.image)
48
+ @connection = connection ? connection : Connection.new
49
+ @task = task
102
50
  end
103
51
 
104
52
  def run
105
- start_runner do |result|
106
- @status = Message::Response::RunnerFinish.new(
107
- status_code: result.status_code,
108
- container_id: result.container_id,
109
- log: result.log,
110
- file: @params.files,
111
- )
112
- end
113
- sleep 0.1 # Stop a moment until RunnerManager checks the status
114
- end
115
-
116
- def start_runner
117
53
  max_retry = 3; count = 0
118
54
 
119
55
  begin
120
- @docker_client.create_container(@params)
121
- @docker_client.start_container
56
+ notify_info("Start container #{@container.id}")
57
+ @container.start
58
+ @container.wait(600) #TODO move to configuration
59
+ notify_info("Finish container #{@container.id}")
60
+
61
+ if @task.commit
62
+ notify_info("Committing the change of container #{@container.id}")
63
+ @container.commit({repo: @task.image}) if @task.commit
64
+ end
122
65
  rescue Excon::Errors::NotFound => e
123
66
  count += 1
124
67
  if count > max_retry
@@ -127,7 +70,13 @@ module Baleen
127
70
  retry
128
71
  end
129
72
  end
130
- yield( @docker_client.result )
73
+
74
+ return {
75
+ status_code: @container.json["State"]["ExitCode"],
76
+ container_id: @container.id,
77
+ log: @container.attach(:stream => false, :stdout => true, :stderr => true, :logs => true),
78
+ file: @task.files,
79
+ }
131
80
  end
132
81
 
133
82
  end
@@ -0,0 +1,61 @@
1
+ require "json"
2
+
3
+ module Baleen
4
+ module Serializable
5
+
6
+ def self.deserialize(json_string)
7
+ params = JSON.parse(json_string)
8
+ klass = params.delete "klass"
9
+ Object.const_get(klass).new(symbolize_keys(params))
10
+ end
11
+
12
+ def self.symbolize_keys(hash)
13
+ hash.inject({}){|new_hash, key_value|
14
+ key, value = key_value
15
+ value = symbolize_keys(value) if value.is_a?(Hash)
16
+ new_hash[key.to_sym] = value
17
+ new_hash
18
+ }
19
+ end
20
+
21
+ # Dynamically define getter and setter for keys of @params
22
+ def method_missing(name, *args)
23
+ _name = name.to_s.sub("=", "")
24
+
25
+ if @params.has_key?(_name.to_sym)
26
+ self.class.class_eval{
27
+ define_method "#{_name}" do
28
+ @params[_name.to_sym]
29
+ end
30
+ }
31
+ self.class.class_eval{
32
+ define_method "#{_name}=" do |*args|
33
+ @params[_name.to_sym] = args.first
34
+ end
35
+ }
36
+ if name.to_s[-1, 1] == "="
37
+ send(name, args.first)
38
+ else
39
+ send(name)
40
+ end
41
+ else
42
+ raise NoMethodError.new("undefined method: #{name}", name, args)
43
+ end
44
+ end
45
+
46
+ def params
47
+ @params
48
+ end
49
+
50
+ def to_json
51
+ @params.to_json
52
+ end
53
+
54
+ def dup
55
+ copy_params = @params.dup
56
+ Object.const_get(self.class.to_s).new(copy_params)
57
+ end
58
+
59
+ end
60
+
61
+ end
data/lib/baleen/server.rb CHANGED
@@ -8,10 +8,13 @@ module Baleen
8
8
 
9
9
  class Server
10
10
  include Celluloid::IO
11
+ include Default
12
+
11
13
  finalizer :shutdown
12
14
 
13
- def initialize(docker_host: "127.0.0.1", docker_port: 4243, port: 5533)
15
+ def initialize(docker_host, docker_port, port, project_file)
14
16
  Docker.url = "http://#{docker_host}:#{docker_port}"
17
+ Baleen::Project.load_project(project_file)
15
18
  @server = TCPServer.new("0.0.0.0", port)
16
19
  async.run
17
20
  end
@@ -21,7 +24,11 @@ module Baleen
21
24
  end
22
25
 
23
26
  def shutdown
24
- @server.close if @server
27
+ begin
28
+ @server.close
29
+ rescue IOError
30
+ BL.info "Shutting down baleen-server..."
31
+ end
25
32
  end
26
33
 
27
34
  def handle_connection(socket)
@@ -31,36 +38,51 @@ module Baleen
31
38
  case ex
32
39
  when IOError; nil # when trying to close already closed socket
33
40
  else
34
- warn "Unknown exception occured"
35
41
  puts ex.inspect
36
42
  raise ex
37
43
  end
38
44
  end
39
45
 
40
46
  def handle_request(socket)
41
- message = socket.gets
47
+ json_request = socket.gets
42
48
 
43
- if message.nil?
49
+ if json_request.nil?
44
50
  socket.close
45
51
  return
46
52
  end
47
- msg = parse_request(message)
48
-
49
- case msg
50
- when Message::Request::ClientDisconnect
51
- socket.close
52
- when Message::Request::Cucumber
53
- manager = RunnerManager.new(socket, msg)
54
- manager.run
53
+
54
+ conn = Connection.new(socket)
55
+ request = parse_request(json_request)
56
+
57
+ begin
58
+ if request.is_a? Baleen::Task::RunProject
59
+ task = find_project(request.project, conn).task
55
60
  else
56
- warn "Received unknown request"
57
- puts msg.inspect
61
+ task = request # request itself is a task
62
+ end
63
+ rescue Baleen::Error::ProjectNotFound
64
+ return
65
+ end
66
+
67
+ RunnerManager.new(conn, task).run do |response|
68
+ conn.respond(response)
58
69
  end
59
70
  end
60
71
 
61
- def parse_request(message)
62
- Baleen::Message::Decoder.new(message).decode
72
+ def parse_request(request)
73
+ Serializable.deserialize(request)
74
+ end
75
+
76
+ def find_project(name, conn)
77
+ project = Baleen::Project.find_project_by_name(name.to_sym)
78
+
79
+ unless project
80
+ conn.notify_exception("No project found: #{name}")
81
+ raise Baleen::Error::ProjectNotFound
82
+ end
83
+
84
+ project
63
85
  end
64
86
  end
87
+ end
65
88
 
66
- end
@@ -0,0 +1,55 @@
1
+ module Baleen
2
+ module Task
3
+ class Base
4
+ include Serializable
5
+
6
+ def initialize
7
+ @params = {}
8
+ @params[:klass] = self.class.to_s
9
+ @params[:shell] = nil
10
+ @params[:opt] = nil
11
+ @params[:work_dir] = nil
12
+ @params[:files] = nil
13
+ @params[:exe] = nil
14
+ @params[:concurrency] = nil
15
+ @params[:image] = nil
16
+ @params[:before_command] = nil
17
+ @params[:command] = nil
18
+ @params[:results] = nil
19
+ @params[:status] = nil
20
+ @params[:commit] = nil
21
+ end
22
+
23
+ def commands
24
+ %{
25
+ #{@params[:before_command]}
26
+ cd #{@params[:work_dir]}
27
+ #{command}
28
+ }
29
+ end
30
+
31
+ def command
32
+ @params[:command] ||= %{#{@params[:exe]} #{@params[:files]}}
33
+ end
34
+
35
+ def command=(c)
36
+ @params[:command] = c
37
+ end
38
+
39
+ def result
40
+ @params[:results]
41
+ end
42
+
43
+ def respond
44
+ nil
45
+ end
46
+
47
+ def terminate?
48
+ true
49
+ end
50
+
51
+ end
52
+ end
53
+ end
54
+
55
+