off_the_grid 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 07155e2121e33460113166ae7876130af5698fff
4
+ data.tar.gz: ef80d7252bedc9328729276b1a2e0c8cd78b760a
5
+ SHA512:
6
+ metadata.gz: cfd6d1f0c1b1ef367c6b1fdcee8aa5a09ff6cdeaee40245ed719138ec91edd62f9c7bdaafee36a7c5b909cae9974bc12b8d09200e378ccb3e519f79e6cb5da4d
7
+ data.tar.gz: a9e08a7cc9ace51e28536cd0b272edbe481b7c5bf1df299ab3f77437716e6df9b7a04ea2115118f82c06124df09d84c1d84b1c6ca6c5654cebcd132aa891e5fe
data/LICENSE ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2016 KnuEdge Corporation
2
+
3
+ Permission is hereby granted, free of charge, to any person
4
+ obtaining a copy of this software and associated documentation
5
+ files (the "Software"), to deal in the Software without
6
+ restriction, including without limitation the rights to use,
7
+ copy, modify, merge, publish, distribute, sublicense, and/or sell
8
+ copies of the Software, and to permit persons to whom the
9
+ Software is furnished to do so, subject to the following
10
+ conditions:
11
+
12
+ The above copyright notice and this permission notice shall be
13
+ included in all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
17
+ OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
19
+ HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
20
+ WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21
+ FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
22
+ OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,19 @@
1
+ # Standard Library
2
+ require 'erb'
3
+ require 'tempfile'
4
+
5
+ # Internal Requirements
6
+ require 'off_the_grid/version'
7
+ require 'off_the_grid/erb_helpers'
8
+ require 'off_the_grid/templates/execute_host'
9
+ require 'off_the_grid/templates/project'
10
+ require 'off_the_grid/templates/user'
11
+ require 'off_the_grid/grid_resource'
12
+ require 'off_the_grid/host'
13
+ require 'off_the_grid/host_group'
14
+ require 'off_the_grid/access_list'
15
+ require 'off_the_grid/admin_host'
16
+ require 'off_the_grid/execute_host'
17
+ require 'off_the_grid/submit_host'
18
+ require 'off_the_grid/project'
19
+ require 'off_the_grid/user'
@@ -0,0 +1,50 @@
1
+ module OffTheGrid
2
+ class AccessList
3
+ attr_reader :name
4
+ include GridResource
5
+
6
+ # Get the list of SGE access lists
7
+ def self.list
8
+ `qconf -sul`.chomp.split("\n").sort.collect {|name| self.new(name) }
9
+ end
10
+
11
+ def details
12
+ `qconf -su #{name}`.chomp
13
+ end
14
+
15
+ def users
16
+ if new?
17
+ @unsaved_users ||= []
18
+ else
19
+ # Only returns users
20
+ extract_detail(:entries).select {|e| !e.match /^@/ }.collect {|user| User.new(user) }
21
+ end
22
+ end
23
+
24
+ def add_user(user)
25
+ if new?
26
+ @unsaved_users ||= []
27
+ @unsaved_users << user
28
+ else
29
+ users.include?(user) ? true : system("qconf -au #{user.name} #{name}")
30
+ end
31
+ end
32
+
33
+ def remove_user(user)
34
+ users.include?(user) ? system("qconf -du #{user.name} #{name}") : true
35
+ end
36
+
37
+ private
38
+
39
+ # Add an SGE access list
40
+ def add
41
+ fail "Creating ACL Requires One or More Users" if users.empty?
42
+ system("qconf -au #{users.map(&:name).join(',')} #{name}")
43
+ end
44
+
45
+ # Remove an SGE access list
46
+ def remove
47
+ system("qconf -dul #{name}")
48
+ end
49
+ end
50
+ end
@@ -0,0 +1,20 @@
1
+ module OffTheGrid
2
+ class AdminHost < Host
3
+ # Get the list of SGE adminstrative hosts
4
+ def self.list
5
+ `qconf -sh`.chomp.split("\n").sort.collect {|name| self.new(name) }
6
+ end
7
+
8
+ private
9
+
10
+ # Add an SGE administrative host
11
+ def add
12
+ system("qconf -ah #{hostname}")
13
+ end
14
+
15
+ # Remove an SGE administrative host
16
+ def remove
17
+ system("qconf -dh #{hostname}")
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,7 @@
1
+ module OffTheGrid
2
+ module ErbHelpers
3
+ def render(template_data)
4
+ ERB.new(template_data.gsub(/^(\t|\s)+<%/, '<%'), 0, "<>").result(binding)
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,48 @@
1
+ module OffTheGrid
2
+ class ExecuteHost < Host
3
+ # Get the list of SGE execute hosts
4
+ def self.list
5
+ `qconf -sel`.chomp.split("\n").sort.collect {|name| self.new(name) }
6
+ end
7
+
8
+ def details
9
+ `qconf -se #{name}`.chomp
10
+ end
11
+
12
+ def load_scaling
13
+ extract_detail(:load_scaling).last
14
+ end
15
+
16
+ def load_values
17
+ extract_detail(:load_values)
18
+ end
19
+
20
+ def processors
21
+ value = extract_detail(:processors).last
22
+ value.match(/[0-9]+/) ? Integer(value) : value
23
+ end
24
+
25
+ # very slow method for now
26
+ def host_groups
27
+ HostGroup.list.select {|group| group.hosts.include?(self) }
28
+ end
29
+
30
+ private
31
+
32
+ # Add an SGE execution host
33
+ def add
34
+ # TODO construct a template
35
+ Tempfile.open do |tmpfile|
36
+ tmpfile.puts render(Templates::ExecuteHost::ERB)
37
+ tmpfile.flush
38
+ system("qconf -Ae #{tmpfile.path}")
39
+ sleep 5
40
+ end
41
+ end
42
+
43
+ # Remove an SGE execution host
44
+ def remove
45
+ system("qconf -de #{hostname}")
46
+ end
47
+ end
48
+ end
@@ -0,0 +1,65 @@
1
+ module OffTheGrid
2
+ module GridResource
3
+ include Comparable
4
+
5
+ def initalize(name)
6
+ @name = name
7
+ end
8
+
9
+ def self.list
10
+ []
11
+ end
12
+
13
+ def new?
14
+ !self.class.list.map(&:name).include?(name)
15
+ end
16
+
17
+ def save(safe = true)
18
+ if safe
19
+ raise "Validation Failed" unless validate_before_save
20
+ add
21
+ else
22
+ add # don't bother checking if the resource exists
23
+ end
24
+ end
25
+
26
+ def delete(safe = true)
27
+ if safe
28
+ raise "Validation Failed" unless validate_before_delete
29
+ remove
30
+ else
31
+ remove # don't bother checking if the resource exists
32
+ end
33
+ end
34
+
35
+ def extract_detail(detail, options = {})
36
+ options[:split_on] ||= /,|\s/
37
+ return [] unless respond_to?(:details)
38
+
39
+ values = []
40
+ details.split("\n").each do |line|
41
+ if values.size > 0
42
+ # Add follow-up lines from the weird word-wrapped output
43
+ line.match(/^( ){8}/) ? values << line : break
44
+ end
45
+ values << line if line.match /^#{detail.to_s} /
46
+ end
47
+ values.join
48
+ .gsub(/(#{detail.to_s} |\\|\s{2,})/, '')
49
+ .split(options[:split_on])
50
+ .uniq - ['']
51
+ end
52
+
53
+ def validate_before_save
54
+ new?
55
+ end
56
+
57
+ def validate_before_delete
58
+ !new?
59
+ end
60
+
61
+ def <=>(other)
62
+ name <=> other.name
63
+ end
64
+ end
65
+ end
@@ -0,0 +1,18 @@
1
+ module OffTheGrid
2
+ class Host
3
+ attr_reader :hostname
4
+ include GridResource
5
+
6
+ def initialize(hostname)
7
+ @hostname = hostname
8
+ end
9
+
10
+ def name
11
+ hostname
12
+ end
13
+
14
+ def name=(hname)
15
+ hostname = hname
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,37 @@
1
+ module OffTheGrid
2
+ class HostGroup
3
+ attr_reader :name
4
+ include GridResource
5
+
6
+ # Get the list of SGE host groups
7
+ def self.list
8
+ `qconf -shgrpl`.chomp.split("\n").sort.collect {|name| self.new(name)}
9
+ end
10
+
11
+ def details
12
+ `qconf -shgrp #{name}`.chomp
13
+ end
14
+
15
+ def as_tree
16
+ `qconf -shgrp_tree #{name}`.chomp
17
+ end
18
+
19
+ def hosts
20
+ extract_detail(:hostlist).map {|host| ExecuteHost.new(host) }
21
+ end
22
+
23
+ # TODO Adding a Host to a HostGroup...
24
+
25
+ private
26
+
27
+ # Add an SGE host group
28
+ def add
29
+ system("qconf -ahgrp #{name}")
30
+ end
31
+
32
+ # Remove an SGE host group
33
+ def remove
34
+ system("qconf -dhgrp #{name}")
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,51 @@
1
+ module OffTheGrid
2
+ class Project
3
+ attr_reader :name
4
+ include GridResource
5
+
6
+ # Get the list of SGE projects
7
+ def self.list
8
+ `qconf -sprjl`.chomp.split("\n").sort.collect {|name| self.new(name) }
9
+ end
10
+
11
+ def details
12
+ `qconf -sprj #{name}`.chomp
13
+ end
14
+
15
+ def acls
16
+ extract_detail(:acl).each do |acl|
17
+ AccessList.new(acl)
18
+ end
19
+ end
20
+
21
+ def xacls
22
+ extract_detail(:xacl).each do |acl|
23
+ AccessList.new(acl)
24
+ end
25
+ end
26
+
27
+ # A Read-only list of users that can use this project
28
+ # Uses ACL association
29
+ def users
30
+ acls.map(&:users).flatten.uniq
31
+ end
32
+
33
+ private
34
+
35
+ # Add an SGE project
36
+ def add
37
+ # TODO construct a template
38
+ Tempfile.open do |tmpfile|
39
+ tmpfile.puts render(Templates::Project::ERB)
40
+ tmpfile.flush
41
+ system("qconf -Aprj #{tmpfile.path}")
42
+ sleep 5
43
+ end
44
+ end
45
+
46
+ # Remove an SGE project
47
+ def remove
48
+ system("qconf -dprj #{name}")
49
+ end
50
+ end
51
+ end
@@ -0,0 +1,20 @@
1
+ module OffTheGrid
2
+ class SubmitHost < Host
3
+ # Get the list of SGE submit hosts
4
+ def self.list
5
+ `qconf -ss`.chomp.split("\n").sort.collect {|name| self.new(name)}
6
+ end
7
+
8
+ private
9
+
10
+ # Add an SGE submit host
11
+ def add
12
+ system("qconf -as #{hostname}")
13
+ end
14
+
15
+ # Remove an SGE submit host
16
+ def remove
17
+ system("qconf -ds #{hostname}")
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,17 @@
1
+ module OffTheGrid
2
+ module Templates
3
+ module ExecuteHost
4
+ ERB = <<EOF
5
+ hostname <%= @hostname %>
6
+ load_scaling NONE
7
+ complex_values NONE
8
+ user_lists NONE
9
+ xuser_lists NONE
10
+ projects NONE
11
+ xprojects NONE
12
+ usage_scaling NONE
13
+ report_variables NONE
14
+ EOF
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,13 @@
1
+ module OffTheGrid
2
+ module Templates
3
+ module Project
4
+ ERB = <<EOF
5
+ name <%= @name %>
6
+ oticket 0
7
+ fshare 0
8
+ acl NONE
9
+ xacl NONE
10
+ EOF
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,13 @@
1
+ module OffTheGrid
2
+ module Templates
3
+ module User
4
+ ERB = <<EOF
5
+ name <%= @name %>
6
+ oticket 0
7
+ fshare 0
8
+ delete_time 0
9
+ default_project <%= @project %>
10
+ EOF
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,77 @@
1
+ module OffTheGrid
2
+ class User
3
+ attr_reader :name
4
+
5
+ include GridResource
6
+
7
+ # Get the list of all SGE users
8
+ def self.list
9
+ `qconf -suserl`.chomp.split("\n").sort.collect {|name| self.new(name)}
10
+ end
11
+
12
+ # Get the list of admin users
13
+ def self.admins
14
+ `qconf -sm`.chomp.split("\n").sort.collect {|name| self.new(name)}
15
+ end
16
+
17
+ # An alias for admins
18
+ def self.managers
19
+ admins
20
+ end
21
+
22
+ # Get the list of operator users
23
+ def self.operators
24
+ `qconf -so`.chomp.split("\n").sort.collect {|name| self.new(name)}
25
+ end
26
+
27
+ def details
28
+ `qconf -suser #{name}`.chomp
29
+ end
30
+
31
+ def default_project=(project)
32
+ @default_project = project
33
+ end
34
+
35
+ def default_project
36
+ @default_project
37
+ end
38
+
39
+ def admin?
40
+ admins.include?(self)
41
+ end
42
+
43
+ alias_method :manager?, :admin?
44
+
45
+ def operator?
46
+ # TODO learn more about the difference between "operator" and "manager"
47
+ # Maybe admins are always operators?
48
+ operators.include?(self)
49
+ end
50
+
51
+ private
52
+
53
+ # Add an SGE user
54
+ def add
55
+ Tempfile.open do |tmpfile|
56
+ tmpfile.puts render(Templates::User::ERB)
57
+ tmpfile.flush
58
+ system("qconf -Auser #{tmpfile.path}")
59
+ sleep 5
60
+ end
61
+ end
62
+
63
+ # Remove an SGE user
64
+ def remove
65
+ system("qconf -duser #{name}")
66
+ end
67
+
68
+ # Validations go here
69
+ def validate_before_save
70
+ if super
71
+ (@default_project && @default_project.is_a?(Project))
72
+ else
73
+ false
74
+ end
75
+ end
76
+ end
77
+ end
@@ -0,0 +1,5 @@
1
+ module OffTheGrid
2
+ def self.version
3
+ '0.0.1'
4
+ end
5
+ end
metadata ADDED
@@ -0,0 +1,102 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: off_the_grid
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Jonathan Gnagy
8
+ - Daniel Schaaff
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2016-10-30 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: rspec
16
+ requirement: !ruby/object:Gem::Requirement
17
+ requirements:
18
+ - - "~>"
19
+ - !ruby/object:Gem::Version
20
+ version: '3.1'
21
+ type: :development
22
+ prerelease: false
23
+ version_requirements: !ruby/object:Gem::Requirement
24
+ requirements:
25
+ - - "~>"
26
+ - !ruby/object:Gem::Version
27
+ version: '3.1'
28
+ - !ruby/object:Gem::Dependency
29
+ name: rubocop
30
+ requirement: !ruby/object:Gem::Requirement
31
+ requirements:
32
+ - - "~>"
33
+ - !ruby/object:Gem::Version
34
+ version: '0.35'
35
+ type: :development
36
+ prerelease: false
37
+ version_requirements: !ruby/object:Gem::Requirement
38
+ requirements:
39
+ - - "~>"
40
+ - !ruby/object:Gem::Version
41
+ version: '0.35'
42
+ - !ruby/object:Gem::Dependency
43
+ name: yard
44
+ requirement: !ruby/object:Gem::Requirement
45
+ requirements:
46
+ - - "~>"
47
+ - !ruby/object:Gem::Version
48
+ version: '0.8'
49
+ type: :development
50
+ prerelease: false
51
+ version_requirements: !ruby/object:Gem::Requirement
52
+ requirements:
53
+ - - "~>"
54
+ - !ruby/object:Gem::Version
55
+ version: '0.8'
56
+ description: The Ruby library for interacting with Son of Grid Engine
57
+ email: jgnagy@knuedge.com
58
+ executables: []
59
+ extensions: []
60
+ extra_rdoc_files: []
61
+ files:
62
+ - LICENSE
63
+ - lib/off_the_grid.rb
64
+ - lib/off_the_grid/access_list.rb
65
+ - lib/off_the_grid/admin_host.rb
66
+ - lib/off_the_grid/erb_helpers.rb
67
+ - lib/off_the_grid/execute_host.rb
68
+ - lib/off_the_grid/grid_resource.rb
69
+ - lib/off_the_grid/host.rb
70
+ - lib/off_the_grid/host_group.rb
71
+ - lib/off_the_grid/project.rb
72
+ - lib/off_the_grid/submit_host.rb
73
+ - lib/off_the_grid/templates/execute_host.rb
74
+ - lib/off_the_grid/templates/project.rb
75
+ - lib/off_the_grid/templates/user.rb
76
+ - lib/off_the_grid/user.rb
77
+ - lib/off_the_grid/version.rb
78
+ homepage: https://github.com/knuedge/off_the_grid
79
+ licenses:
80
+ - MIT
81
+ metadata: {}
82
+ post_install_message: Thanks for installing Off The Grid!
83
+ rdoc_options: []
84
+ require_paths:
85
+ - lib
86
+ required_ruby_version: !ruby/object:Gem::Requirement
87
+ requirements:
88
+ - - "~>"
89
+ - !ruby/object:Gem::Version
90
+ version: '2.2'
91
+ required_rubygems_version: !ruby/object:Gem::Requirement
92
+ requirements:
93
+ - - ">="
94
+ - !ruby/object:Gem::Version
95
+ version: '0'
96
+ requirements: []
97
+ rubyforge_project:
98
+ rubygems_version: 2.5.1
99
+ signing_key:
100
+ specification_version: 4
101
+ summary: Off The Grid can perform basic management tasks for SGE.
102
+ test_files: []